본문 바로가기

프로그래밍/Django

[DJango] AbstractBaseUser vs AbstractUser 비교하기

AbstractUser vs AbstractBaseUser

AbstractUser vs AbstractBaseUser

스크린샷, 2017-06-22 20-00-08

스크린샷, 2017-07-06 23-30-56

AbstractBaseUser를 상속하게 되면

스크린샷, 2017-07-07 01-52-55

Class MyUser(AbstractBaseUser):
  pass

꼴랑 2개밖에 안던져준다(id는 자동생성 되는 필드니까). 이를 상속해서 유저 모델을 구축한다면 세밀한 컨트롤이 가능하지만 세그만큼 손도 많이 간다. 만약 페이스북 이메일 인증(permission)을 통한 가입을 하고 싶다면 AbstractBaseUser를 사용해야 한다. 상속받는 클래스틀 타고 들어가면 아래처럼 구현되어있다.

class AbstractBaseUser(models.Model)
    password =
    last_login =
 
    def get_username(self):
    def clean(self):
    def save(self, *args, **kwargs):
    def natural_key(self):
 
    @property
    def is_anonoymous(self):
    @property
    def is_authenticated(self):
 
    def set_password(self, raw_password):
    def check_password(self, raw_password):
    def set_unusable_password(self):
    def has_usable_password(self):
    def get_full_name(self):
    def get_short_name(self):
 
    def get_session_auth_hash(self):

AbstractUser를 상속하게 되면

스크린샷, 2017-07-07 01-51-07

class AbstractUser(AbstractBaseUser, PermissionMixin):
  username =
  first_name =
  last_name =
  email =
  is_staff =
  is_active =
  date_joined =
 
  def clean(self):
  def get_full_name(self):
  def get_short_name(self):
  def email_user(self, subject, message, from_email=None, **kwargs):
 

settings.py

(예시) AUTH_USER_MODEL = '앱이름.클래스이름'
 
AUTH_USER_MODEL = 'user.MyUser'

settings.pyAUTH_USER_MODEL='모듈.클래스이름'을 기입해줘야 한다. 이후 makemigrations, migrate를 해주게 되면 아래의 3개 테이블이 생긴다.

  1. user_myuser

  2. user_myuser_groups

  3. user_myuser_groups_permisson

AbstractBaseUser vs AbstractUser

User 모델 확장을 실험해보던 와중에 조금 특이한 점을 발견했다.
AbstarctBaseUser를 상속할 때는 settings.pyAUTH_USER_MODEL을 설정해줄 필요가 없었다.

그런데 AbstractUser를 상속할 때는 반드시 settings.py에 반드시 AUTH_USER_MODEL을 설정해줘야 migrate가 진행되었다.

스크린샷, 2017-07-15 18-26-15
AbstractBaseUser를 migrate했을 때 생겨나는 기본 테이블이다. 테이블이 12개다. auth_user도 있지만 user_myuser도 있다.

스크린샷, 2017-07-15 18-28-02
AbstractUser를 migrate했을 때 생겨나는 기본 테이블이다.

가장 큰 차이점은 groupsuser_permission 테이블이 myuser에게 넘어갔다.

왜 이런 차이가 발생할까?

그 이유를 곰곰히 생각해보니 createsuperuser를 할 때 이유가 있지 않을까 생각했다. AbstractBaseUser는 필드를 딸랑 2개(패스워드와 마지막 로그인)를 던져준다.

이때 createsuperuser를 하게 되면 usernamepassword를 기입해야하는데 이를 저장할 테이블이 없기 없다.

1. AbstarctUser 상속시 발생한 에러

현상
Add or change a related_name argument to the definition for ~ 문제가 발생한다.

from django.contrib.auth.models import AbstractUser
 
class MyUser(AbstractUser):
    pass

스크린샷, 2017-07-15 18-09-28

원인

참고한 글

  1. User 모델 확장 방법 4가지
    https://simpleisbetterthancomplex.com/tutorial/2016/07/22/how-to-extend-django-user-model.html

    • 영어로 되어있지만 아주아주 자세하게 나와있다.