Skip to content

Commit

Permalink
Split VerifyEmailMixin and BasicUserFieldsMixin into more mixins.
Browse files Browse the repository at this point in the history
  • Loading branch information
Kevin Etienne committed Nov 27, 2014
1 parent cf607ed commit 179bf9e
Show file tree
Hide file tree
Showing 3 changed files with 152 additions and 31 deletions.
103 changes: 73 additions & 30 deletions user_management/models/mixins.py
Original file line number Diff line number Diff line change
Expand Up @@ -35,45 +35,76 @@ def create_superuser(self, email, password, **extra_fields):
return user


@python_2_unicode_compatible
class BasicUserFieldsMixin(models.Model):
name = models.CharField(
verbose_name=_('Name'),
max_length=255,
class DateJoinedUserMixin(models.Model):
date_joined = models.DateTimeField(
verbose_name=_('date joined'),
default=timezone.now,
editable=False,
)

class Meta:
abstract = True


class EmailUserMixin(models.Model):
email = models.EmailField(
verbose_name=_('Email address'),
unique=True,
max_length=511,
)
date_joined = models.DateTimeField(
verbose_name=_('date joined'),
default=timezone.now,
editable=False,
)
is_staff = models.BooleanField(_('staff status'), default=False)
email_verification_required = False

objects = UserManager()
email_verification_required = False

USERNAME_FIELD = 'email'
REQUIRED_FIELDS = ['name']

class Meta:
abstract = True
ordering = ['name']

def __str__(self):
return self.name

class IsStaffUserMixin(models.Model):
is_staff = models.BooleanField(_('staff status'), default=False)

class Meta:
abstract = True


class NameUserMethodsMixin:
def get_full_name(self):
return self.name

def get_short_name(self):
return self.name


class ActiveUserMixin(BasicUserFieldsMixin):
class NameUserMixin(NameUserMethodsMixin, models.Model):
name = models.CharField(
verbose_name=_('Name'),
max_length=255,
)
REQUIRED_FIELDS = ['name']

class Meta:
abstract = True
ordering = ['name']


@python_2_unicode_compatible
class BasicUserFieldsMixin(
DateJoinedUserMixin,
EmailUserMixin,
IsStaffUserMixin,
NameUserMixin,
):
objects = UserManager()

class Meta:
abstract = True

def __str__(self):
return self.name


class ActiveUserMixin(models.Model):
is_active = models.BooleanField(_('active'), default=True)

class Meta:
Expand All @@ -93,22 +124,11 @@ def create_superuser(self, email, password, **extra_fields):
return user


class VerifyEmailMixin(BasicUserFieldsMixin):
is_active = models.BooleanField(_('active'), default=False)
email_verification_required = models.BooleanField(
_('Email verification required?'),
default=True,
help_text=_('Indicates if the email address needs to be verified.'))

objects = VerifyEmailManager()

class EmailVerifyUserMethodsMixin:
EMAIL_SUBJECT = '{domain} account validate'
TEXT_EMAIL_TEMPLATE = 'user_management/account_validation_email.txt'
HTML_EMAIL_TEMPLATE = 'user_management/account_validation_email.html'

class Meta:
abstract = True

def email_context(self, site):
return {
'uid': urlsafe_base64_encode(force_bytes(self.pk)),
Expand Down Expand Up @@ -156,6 +176,29 @@ def send_validation_email(self):
context = self.email_context(site)
send(**self.email_kwargs(context, site.domain))


class VerifyEmailManagerMixin:
class Meta:
abstract = True


class EmailVerifyUserMixin(EmailVerifyUserMethodsMixin, models.Model):
is_active = models.BooleanField(_('active'), default=False)
email_verification_required = models.BooleanField(
_('Email verification required?'),
default=True,
help_text=_('Indicates if the email address needs to be verified.'))

class Meta:
abstract = True


class VerifyEmailMixin(EmailVerifyUserMixin, BasicUserFieldsMixin):
objects = VerifyEmailManager()

class Meta:
abstract = True

@classmethod
def check(cls, **kwargs):
errors = super(VerifyEmailMixin, cls).check(**kwargs)
Expand Down
41 changes: 40 additions & 1 deletion user_management/models/tests/models.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,17 @@
from django.contrib.auth.models import AbstractBaseUser, PermissionsMixin
from django.db import models

from ..mixins import AvatarMixin, BasicUserFieldsMixin, VerifyEmailMixin

from ..mixins import (
AvatarMixin,
BasicUserFieldsMixin,
DateJoinedUserMixin,
EmailUserMixin,
EmailVerifyUserMixin,
IsStaffUserMixin,
NameUserMethodsMixin,
VerifyEmailMixin,
)


class User(AvatarMixin, VerifyEmailMixin, PermissionsMixin, AbstractBaseUser):
Expand All @@ -13,3 +24,31 @@ class BasicUser(BasicUserFieldsMixin, AbstractBaseUser):

class VerifyEmailUser(VerifyEmailMixin):
pass


class CustomBasicUserFieldsMixin(
NameUserMethodsMixin,
EmailUserMixin,
DateJoinedUserMixin,
IsStaffUserMixin,
):
name = models.TextField()

USERNAME_FIELD = 'email'

class Meta:
abstract = True


class CustomVerifyEmailMixin(EmailVerifyUserMixin):
class Meta:
abstract = True


class CustomNameUser(
AvatarMixin,
CustomBasicUserFieldsMixin,
CustomVerifyEmailMixin,
AbstractBaseUser,
):
pass
39 changes: 39 additions & 0 deletions user_management/models/tests/test_models.py
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
# -*- coding: utf-8 -*-

import unittest

import django
from django.contrib.auth.tokens import default_token_generator
from django.contrib.sites.models import Site
from django.core import checks
from django.db.models import TextField
from django.db.utils import IntegrityError
from django.test import TestCase
from django.utils import timezone
Expand Down Expand Up @@ -283,3 +286,39 @@ class InvalidUser(self.model):
]
errors = InvalidUser.check()
self.assertEqual(errors, expected)


class TestCustomNameUser(TestCase):
model = models.CustomNameUser

def test_fields(self):
"""Do we have the fields we expect?"""
fields = self.model._meta.get_all_field_names()
expected = {
# On model
'id',
'name',
'date_joined',
'email',
'email_verification_required',
'is_active',
'is_staff',
'last_login',
'password',
'avatar',
}

try:
# python 3 only:
self.assertCountEqual(fields, expected)
except AttributeError:
# python 2 only:
self.assertItemsEqual(fields, expected)

def test_name(self):
expected = 'Cú Chulainn'
model = self.model(name=expected)

self.assertEqual(model.get_full_name(), expected)
field, *rest = self.model._meta.get_field_by_name('name')
self.assertIsInstance(field, TextField)

0 comments on commit 179bf9e

Please sign in to comment.