<commit_before>from django import forms
from django.contrib import admin
from django.contrib.admin.util import unquote
from django.conf.urls.defaults import patterns, url
from django.contrib.contenttypes import generic
from django.core import mail
from django.core.context_processors import csrf
from django.core.urlresolvers import reverse
from django.db import models
from django.http import HttpResponseRedirect
from django.shortcuts import render_to_response
from django.utils import translation
from django.utils.translation import ugettext_lazy as _

from pennyblack import settings

import datetime

try:
    from django.utils import timezone
except ImportError:
    now = datetime.datetime.now
else:
    now = timezone.now


#-----------------------------------------------------------------------------
# Job
#-----------------------------------------------------------------------------
class Job(models.Model):
    """A bunch of participants which receive a newsletter"""
    newsletter = models.ForeignKey('pennyblack.Newsletter', related_name="jobs", null=True)
    status = models.IntegerField(choices=settings.JOB_STATUS, default=1)
    date_created = models.DateTimeField(verbose_name=_("created"), default=now)
    date_deliver_start = models.DateTimeField(blank=True, null=True, verbose_name=_("started delivering"), default=None)
    date_deliver_finished = models.DateTimeField(blank=True, null=True, verbose_name=_("finished delivering"), default=None)

    content_type = models.ForeignKey('contenttypes.ContentType', null=True, blank=True)
    object_id = models.PositiveIntegerField(null=True, blank=True)
    group_object = generic.GenericForeignKey('content_type', 'object_id')
    collection = models.TextField(blank=True)

    #ga tracking
    utm_campaign = models.SlugField(verbose_name=_("utm campaign"), blank=True)

    public_slug = models.SlugField(verbose_name=_("slug"), unique=True, 
            help_text=_("Unique slug to allow public access to the newsletter"),
            blank=True, null=True)

    class Meta:
        ordering = ('-date_created',)
        verbose_name = _("newsletter delivery task")
        verbose_name_plural = _("newsletter delivery tasks")
        app_label = 'pennyblack'

    def __unicode__(self):
        return (self.newsletter.subject if self.newsletter is not None else "unasigned delivery task")

    def delete(self, *args, **kwargs):
        """
        If the job refers to a inactive Newsletter delete it.
        """
        if not self.newsletter.active:
            self.newsletter.delete()
        super(Job, self).delete(*args, **kwargs)

    @property
    def public_url(self):
        return self.newsletter.get_base_url() + reverse('pennyblack.views.view_public', args=(self.public_slug,))


    @property
    def count_mails_total(self):
        return self.mails.count()

    @property
    def count_mails_sent(self):
        return self.mails.filter(sent=True).count()

    @property<commit_msg>Fix blank `Job.public_slug`<commit_after>from django import forms
from django.contrib import admin
from django.contrib.admin.util import unquote
from django.conf.urls.defaults import patterns, url
from django.contrib.contenttypes import generic
from django.core import mail
from django.core.context_processors import csrf
from django.core.urlresolvers import reverse, NoReverseMatch
from django.db import models
from django.http import HttpResponseRedirect
from django.shortcuts import render_to_response
from django.utils import translation
from django.utils.translation import ugettext_lazy as _

from pennyblack import settings

import datetime

try:
    from django.utils import timezone
except ImportError:
    now = datetime.datetime.now
else:
    now = timezone.now


#-----------------------------------------------------------------------------
# Job
#-----------------------------------------------------------------------------
class Job(models.Model):
    """A bunch of participants which receive a newsletter"""
    newsletter = models.ForeignKey('pennyblack.Newsletter', related_name="jobs", null=True)
    status = models.IntegerField(choices=settings.JOB_STATUS, default=1)
    date_created = models.DateTimeField(verbose_name=_("created"), default=now)
    date_deliver_start = models.DateTimeField(blank=True, null=True, verbose_name=_("started delivering"), default=None)
    date_deliver_finished = models.DateTimeField(blank=True, null=True, verbose_name=_("finished delivering"), default=None)

    content_type = models.ForeignKey('contenttypes.ContentType', null=True, blank=True)
    object_id = models.PositiveIntegerField(null=True, blank=True)
    group_object = generic.GenericForeignKey('content_type', 'object_id')
    collection = models.TextField(blank=True)

    #ga tracking
    utm_campaign = models.SlugField(verbose_name=_("utm campaign"), blank=True)

    public_slug = models.SlugField(verbose_name=_("slug"), unique=True, 
            help_text=_("Unique slug to allow public access to the newsletter"),
            blank=True, null=True)

    class Meta:
        ordering = ('-date_created',)
        verbose_name = _("newsletter delivery task")
        verbose_name_plural = _("newsletter delivery tasks")
        app_label = 'pennyblack'

    def __unicode__(self):
        return (self.newsletter.subject if self.newsletter is not None else "unasigned delivery task")


    def clean(self, *args, **kwargs):
        self.public_slug = self.public_slug.strip() 
        if self.public_slug == "":
            self.public_slug = None
        super(Job, self).clean(*args, **kwargs)

    def delete(self, *args, **kwargs):
        """
        If the job refers to a inactive Newsletter delete it.
        """
        if not self.newsletter.active:
            self.newsletter.delete()
        super(Job, self).delete(*args, **kwargs)

    @property
    def public_url(self):
        try:
            if self.public_slug:
                return self.newsletter.get_base_url() + reverse('pennyblack.views.view_public', args=(self.public_slug,))
        except (NoReverseMatch,):
            pass
        return None


    @property
    def count_mails_total(self):
        return self.mails.count()

    @property
    def count_mails_sent(self):
        return self.mails.filter(sent=True).count()

    @property
{'fraction_non_alphanumeric': 0.14312766293198675, 'fraction_numerical': 0.00031560675398453525, 'mean_word_length': 3.1263020833333335, 'pattern_counts': {'":': 1, '<': 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': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2453462', 'n_tokens_mistral': 1738, 'n_tokens_neox': 1695, 'n_words': 429}