schon/vibes_auth/models.py
Egor fureunoir Gorbunov 3590dbbe2b Features: 1) Add caching mechanism for 'recently_viewed' functionality.
Fixes: 1) Remove 'recently_viewed' ManyToManyField from User model and related migration; 2) Correct handling of product addition in 'recently_viewed' logic.

Extra: Refactor 'recently_viewed' to use cache instead of database field; cleanup unused imports and model attributes.
2025-05-19 15:09:45 +03:00

122 lines
3.7 KiB
Python

from uuid import uuid4
from django.contrib.auth.models import AbstractUser
from django.contrib.auth.models import Group as BaseGroup
from django.core.cache import cache
from django.db.models import (
BooleanField,
CharField,
EmailField,
ImageField,
JSONField,
UUIDField,
)
from django.utils.translation import gettext_lazy as _
from rest_framework_simplejwt.token_blacklist.models import (
BlacklistedToken as BaseBlacklistedToken,
)
from rest_framework_simplejwt.token_blacklist.models import (
OutstandingToken as BaseOutstandingToken,
)
from core.abstract import NiceModel
from evibes.settings import LANGUAGE_CODE, LANGUAGES
from vibes_auth.managers import UserManager
from vibes_auth.validators import validate_phone_number
class User(AbstractUser, NiceModel):
def get_uuid_as_path(self, *args):
return str(self.uuid) + "/" + args[0]
email = EmailField(_("email"), unique=True, help_text=_("user email address"))
phone_number = CharField(
_("phone_number"),
max_length=20,
unique=True,
blank=True,
null=True,
help_text=_("user phone number"),
validators=[
validate_phone_number,
],
)
username = None
first_name = CharField(_("first_name"), max_length=150, blank=True, null=True) # noqa: DJ001
last_name = CharField(_("last_name"), max_length=150, blank=True, null=True) # noqa: DJ001
avatar = ImageField(
null=True,
verbose_name=_("avatar"),
upload_to=get_uuid_as_path,
blank=True,
help_text=_("user profile image"),
)
is_verified = BooleanField(
default=False,
verbose_name=_("is verified"),
help_text=_("user verification status"),
)
is_active = BooleanField(
_("is_active"),
default=False,
help_text=_("unselect this instead of deleting accounts"),
)
is_subscribed = BooleanField(
verbose_name=_("is_subscribed"), help_text=_("user's newsletter subscription status"), default=False
)
activation_token = UUIDField(default=uuid4, verbose_name=_("activation token"))
language = CharField(choices=LANGUAGES, default=LANGUAGE_CODE, null=False, blank=False, max_length=7)
attributes = JSONField(verbose_name=_("attributes"), default=dict, blank=True, null=True)
USERNAME_FIELD = "email"
REQUIRED_FIELDS = []
objects = UserManager()
def add_to_recently_viewed(self, product_uuid):
recently_viewed = self.recently_viewed
if not product_uuid in recently_viewed:
if not len(recently_viewed) >= 48:
recently_viewed.append(product_uuid)
cache.set(f"user_{self.uuid}_rv", recently_viewed)
else:
recently_viewed.pop(0)
recently_viewed.append(product_uuid)
cache.set(f"user_{self.uuid}_rv", recently_viewed)
@property
def recently_viewed(self):
return [] or cache.get(f"user_{self.uuid}_rv")
def check_token(self, token):
return str(token) == str(self.activation_token)
def __str__(self):
return self.email
class Meta:
swappable = "AUTH_USER_MODEL"
verbose_name = _("user")
verbose_name_plural = _("users")
class Group(BaseGroup):
class Meta:
proxy = True
verbose_name = _("group")
verbose_name_plural = _("groups")
class OutstandingToken(BaseOutstandingToken):
class Meta:
proxy = True
verbose_name = _("outstanding token")
verbose_name_plural = _("outstanding tokens")
class BlacklistedToken(BaseBlacklistedToken):
class Meta:
proxy = True
verbose_name = _("blacklisted token")
verbose_name_plural = _("blacklisted tokens")