<commit_before>from django.contrib.auth.models import User
from django.db import models
from django.template.defaultfilters import slugify

from twobuntu.categories.models import Category
from twobuntu.cmarkdown import cmarkdown

class Article(models.Model):
    """A post written in Markdown by an author."""

    # Article status constants
    DRAFT      = 0
    UNAPPROVED = 1
    PUBLISHED  = 2

    STATUS = (
        (DRAFT,      'Draft',),
        (UNAPPROVED, 'Unapproved',),
        (PUBLISHED,  'Published',),
    )

    author = models.ForeignKey(User,
                               help_text="The user writing the article.")
    category = models.ForeignKey(Category,
                                 help_text="The category of the article.")

    title = models.CharField(max_length=200,
                             help_text="The title of the article.")
    body = models.TextField(help_text="The body of the article [in Markdown].")

    status = models.PositiveSmallIntegerField(choices=STATUS,
                                              default=DRAFT,
                                              help_text="The current status of the article.")
    cc_license = models.BooleanField(default=True,
                                     help_text="Whether the article is released under the CC-BY-SA 4.0 license or not.")

    date = models.DateTimeField(auto_now=True)

    def __unicode__(self):
        """Return a string representation of the article."""
        return '%s%s' % (
            self.title,
            ' [%s]' % self.get_status_display() if not self.status == self.PUBLISHED else '',
        )
    
    def can_edit(self, request):
        """Determine if the article may be edited by the current user."""
        # The user must either be staff or have written the article and not published it yet
        return request.user.is_staff or request.user == self.author and self.status == self.DRAFT
    
    def can_view(self, request):
        """Determine if the article may be viewed by the current user."""
        # The user must either be staff or have written the article or it must be published
        return request.user.is_staff or request.user == self.author or self.status == self.PUBLISHED

    @models.permalink
    def get_absolute_url(self):
        """Return the absolute URL of the article."""
        return ('articles:view', (), {
            'id':   self.id,
            'slug': slugify(self.title),
        })

    def render(self):
        """Render the Markdown body."""
        return cmarkdown(self.body)

    class Meta:
        ordering = ('-date',)
<commit_msg>Added apply_filter() class method to Article to abstract request-based filtering away from the views.<commit_after>from django.contrib.auth.models import User
from django.db import models
from django.template.defaultfilters import slugify

from twobuntu.categories.models import Category
from twobuntu.cmarkdown import cmarkdown

class Article(models.Model):
    """A post written in Markdown by an author."""

    # Article status constants
    DRAFT      = 0
    UNAPPROVED = 1
    PUBLISHED  = 2

    STATUS = (
        (DRAFT,      'Draft',),
        (UNAPPROVED, 'Unapproved',),
        (PUBLISHED,  'Published',),
    )

    author = models.ForeignKey(User,
                               help_text="The user writing the article.")
    category = models.ForeignKey(Category,
                                 help_text="The category of the article.")

    title = models.CharField(max_length=200,
                             help_text="The title of the article.")
    body = models.TextField(help_text="The body of the article [in Markdown].")

    status = models.PositiveSmallIntegerField(choices=STATUS,
                                              default=DRAFT,
                                              help_text="The current status of the article.")
    cc_license = models.BooleanField(default=True,
                                     help_text="Whether the article is released under the CC-BY-SA 4.0 license or not.")

    date = models.DateTimeField(auto_now=True)

    def __unicode__(self):
        """Return a string representation of the article."""
        return '%s%s' % (
            self.title,
            ' [%s]' % self.get_status_display() if not self.status == self.PUBLISHED else '',
        )
    
    def can_edit(self, request):
        """Determine if the article may be edited by the current user."""
        # The user must either be staff or have written the article and not published it yet
        return request.user.is_staff or request.user == self.author and self.status == self.DRAFT
    
    def can_view(self, request):
        """Determine if the article may be viewed by the current user."""
        # The user must either be staff or have written the article or it must be published
        return request.user.is_staff or request.user == self.author or self.status == self.PUBLISHED
    
    @classmethod
    def apply_filter(cls, request, *args):
        """Return a QuerySet with the correct filter applied based on the request."""
        args = list(args)
        if not request.user.is_staff:
            args.append(models.Q(author=request.user.id) | models.Q(status=cls.PUBLISHED))
        return cls.objects.filter(*args)

    @models.permalink
    def get_absolute_url(self):
        """Return the absolute URL of the article."""
        return ('articles:view', (), {
            'id':   self.id,
            'slug': slugify(self.title),
        })

    def render(self):
        """Render the Markdown body."""
        return cmarkdown(self.body)

    class Meta:
        ordering = ('-date',)

{'fraction_non_alphanumeric': 0.09463397908451912, 'fraction_numerical': 0.0027430138865078006, 'mean_word_length': 2.007216494845361, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 12, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '214079', 'n_tokens_mistral': 1639, 'n_tokens_neox': 1461, 'n_words': 485}