django 기본 로그인

0

로그인을 시켜주는 함수 login (이하 login) 과
django.contrib.auth.login

def login(request, user, backend=None):
	"""
    Persist a user id and a backend in the request. This way a user doesn't
    have to reauthenticate on every request. Note that data set during
    the anonymous session is retained when the user logs in.
    """

로그인 정보를 확인하는 미들웨어 AuthenticationMiddleware (이하 authentication) 의 콜라보
django.contrib.auth.middleware.AuthenticationMiddleware

class AuthenticationMiddleware(MiddlewareMixin):
    def process_request(self, request):
        ...
        request.user = SimpleLazyObject(lambda: get_user(request))

login

login 은 인자로 넘어온 request 객체에서 session 을 가져와서 인증에 활용한다.

request.session

session

session 은 기본적으로 settings 에 설정된 SESSION_ENGINE 에 따라서, db, cache, file, signedcookie 등등을 활용한다.

디폴트 값은 db 이다. 'django.contrib.sessions.backends.db'

db 에 저장될 때 session 은 아래와 같은 필드 구성을 가진다.
id session_key created_at user_id

user_id 와 매칭되는 session_key 를 DB 에 저장해서, session_key 를 클라이언트에 cookie 로 저장하여, 유저 활동의 연속성을 보장하는 것.

created_at 은 session 만료 기준을 통해, db 에 존재하는 session 값이라도 유효하지 않다고 판단하게 해준다.

get_session_auth_hash

AbstractUser 를 상속받은 user 에서 사용할 수 있는 get_session_auth_hash 함수를 통해서 session_key 를 가져올 수 있다.

def login(request, user, backend=None):
	...
    if hasattr(user, "get_session_auth_hash"):
        session_auth_hash = user.get_session_auth_hash()

set session

session_key, hash_session_key, backend_session_key 를 나눠서 session 에 등록해준다.

이게 로그인이다.

def login(request, user, backend=None):
	...
    request.session[SESSION_KEY] = user._meta.pk.value_to_string(user)
    request.session[BACKEND_SESSION_KEY] = backend
    request.session[HASH_SESSION_KEY] = session_auth_hash

AuthenticationMiddleware

이제 저장된 session 값을 활용하는 걸 보자.

class AuthenticationMiddleware(MiddlewareMixin):
    def process_request(self, request):
    	...
        request.user = SimpleLazyObject(lambda: get_user(request))

django.contrib.auth.middlewareget_user 를 활용한다.

get_user

login 에서 세팅해준 session 값들을 이용해서 user 를 찾는다.

def get_user(request):
    try:
    	# request.session[SESSION_KEY] 사용
        user_id = _get_user_session_key(request)
        
        # request.session[BACKEND_SESSION_KEY] 사용
        backend_path = request.session[BACKEND_SESSION_KEY]
    except KeyError:
        pass
    
    ...
    
    if hasattr(user, "get_session_auth_hash"):
         # request.session[HASH_SESSION_KEY] 사용
         session_hash = request.session.get(HASH_SESSION_KEY)
	...
    
    return user or AnonymousUser()

다만 이 과정을 매 요청마다 하는 건 아니고, SimpleLazyObject 를 통해서, request.user 가 호출되어 사용될 때만 get_user 를 통해서 위 과정을 거친다.

class AuthenticationMiddleware(MiddlewareMixin):
    def process_request(self, request):
    	...
        request.user = SimpleLazyObject(lambda: get_user(request))
profile
영어영문학과 출신의 개발자 늘한입니다. Python 을 좋아합니다.

0개의 댓글