gault-millau/apps/notification/models.py
2019-12-31 01:22:45 +03:00

149 lines
5.3 KiB
Python
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

"""Notification app models."""
from django.conf import settings
from django.db import models
from django.utils.timezone import now
from django.utils.translation import ugettext_lazy as _
from account.models import User
from utils.methods import generate_string_code
from utils.models import ProjectBaseMixin, TJSONField, TranslatedFieldsMixin
class SubscriptionType(ProjectBaseMixin, TranslatedFieldsMixin):
index_name = models.CharField(max_length=255, verbose_name=_('Index name'), unique=True)
name = TJSONField(blank=True, null=True, default=None,
verbose_name=_('name'),
help_text='{"en-GB":"some text"}')
# TODO: не хватает связи со страной. ForeignKey
# todo: associate user & subscriber after users registration
class SubscriberManager(models.Manager):
"""Extended manager for Subscriber model."""
def make_subscriber(self, email=None, user=None, ip_address=None, country_code=None,
locale=None, subscription_types=None, *args, **kwargs):
"""Make subscriber and update info."""
# search existing object
if not user:
user = User.objects.filter(email=email).first()
if user:
obj = self.model.objects.filter(models.Q(user=user) | models.Q(
email=user.email)).first()
else:
obj = self.model.objects.filter(email=email).first()
# update or create
if obj:
if user:
obj.user = user
obj.email = None
else:
obj.email = email
obj.ip_address = ip_address
obj.country_code = country_code
obj.locale = locale
obj.update_code = generate_string_code()
obj.save()
obj.subscription_types.set(subscription_types)
obj.subscribe_set.update(unsubscribe_date=None)
else:
obj = self.model.objects.create(user=user, email=email, ip_address=ip_address,
country_code=country_code, locale=locale)
obj.subscription_types.set(subscription_types)
obj.subscribe_set.update(unsubscribe_date=None)
return obj
def associate_user(self, user):
"""Associate user."""
obj = self.model.objects.filter(user=user).first()
if obj is None:
obj = self.model.objects.filter(email=user.email_confirmed, user__isnull=True).first()
if obj:
obj.user = user
obj.email = None
obj.save()
return obj
class Subscriber(ProjectBaseMixin):
"""Subscriber model."""
user = models.ForeignKey(
User,
blank=True,
null=True,
default=None,
on_delete=models.SET_NULL,
related_name='subscriber',
verbose_name=_('User'),
)
email = models.EmailField(blank=True, null=True, default=None, unique=True, verbose_name=_('Email'))
ip_address = models.GenericIPAddressField(blank=True, null=True, default=None, verbose_name=_('IP address'))
country_code = models.CharField(max_length=10, blank=True, null=True, default=None, verbose_name=_('Country code'))
locale = models.CharField(blank=True, null=True, default=None, max_length=10, verbose_name=_('Locale identifier'))
update_code = models.CharField(
max_length=254,
blank=True,
null=True,
default=None,
db_index=True,
verbose_name=_('Token'),
)
old_id = models.PositiveIntegerField(_('old id'), blank=True, null=True, default=None)
subscription_types = models.ManyToManyField(SubscriptionType, through='Subscribe')
objects = SubscriberManager()
class Meta:
"""Meta class."""
verbose_name = _('Subscriber')
verbose_name_plural = _('Subscribers')
def save(self, *args, **kwargs):
"""Overrided save method."""
if self.update_code is None:
self.update_code = generate_string_code()
return super(Subscriber, self).save(*args, **kwargs)
def unsubscribe(self, query: dict):
"""Unsubscribe user."""
self.subscribe_set.update(unsubscribe_date=now())
@property
def send_to(self):
"""Actual email."""
return self.user.email if self.user else self.email
@property
def link_to_unsubscribe(self):
"""Link to unsubscribe."""
schema = settings.SCHEMA_URI
site_domain = settings.SITE_DOMAIN_URI
url = settings.SITE_REDIRECT_URL_UNSUBSCRIBE
query = f'?code={self.update_code}'
return f'{schema}://{site_domain}{url}{query}'
@property
def subscribe_objects(self):
return Subscribe.objects.filter(subscriber=self)
class Subscribe(ProjectBaseMixin):
"""Subscribe model."""
subscribe_date = models.DateTimeField(_('Last subscribe date'), blank=True, null=True, default=now)
unsubscribe_date = models.DateTimeField(_('Last unsubscribe date'), blank=True, null=True, default=None)
subscriber = models.ForeignKey(Subscriber, on_delete=models.CASCADE)
subscription_type = models.ForeignKey(SubscriptionType, on_delete=models.CASCADE)
class Meta:
"""Meta class."""
verbose_name = _('Subscribe')
verbose_name_plural = _('Subscribes')