1. 혼자 만들어보는 Zara - 회원가입

Kiyong Lee·2021년 12월 5일
0

개인프로젝트

목록 보기
2/9

혼자 만들어보는 Zara - 회원가입


1. models.py


1-1. core/models.py

모델링의 경우, 우선 생성/수정/삭제에 대한 이력을 저장하기 위해
core라는 앱을 생성 후 TimeStampModel을 만들었습니다

python manage.py startapp core
'''
core/models.py
'''
from django.db import models

class TimeStampModel(models.Model) :
    created_at = models.DateTimeField(auto_now_add=True)
    updated_at = models.DateTimeField(null=True)
    deleted_at = models.DateTimeField(null=True)
    
    class Meta :
        abstract = True

updated_at, delete_atauto_now=True를 하려고 했는데
그렇게 되면 데이터 생성 시, 저 두 컬럼에 생성시간이 들어가버리게 됩니다.

그래서 null=True를 설정하여 데이터 생성시 null값이 되게 했으며,

views.py에서 수정/삭제에 대한 로직을 작성할 때 날짜를 기입하는 걸 기획했습니다.


1-2. users/models.py

유저 정보를 저장할 테이블을 만들기 위해 users 앱을 생성했습니다.

python manage.py startapp users
'''
users/models.py
'''
from django.db   import models

from core.models import TimeStampModel

class Role(TimeStampModel) :
    role = models.CharField(max_length=20)
    
    class Meta :
        db_table = 'roles'
        
class User(TimeStampModel) :
    role     = models.ForeignKey(Role, null=True, on_delete=models.SET_NULL)
    email    = models.EmailField(unique=True, max_length=40)
    password = models.CharField(max_length=500)
    
    class Meta :
        db_table = 'users'

Zara를 회원가입하려고 보면 이름도 필수입력인데, 굳이 컬럼에 추가하지 않았습니다.

이름이야 동명이인도 많고, 데이터 식별에 큰 비중이 있을 것 같지 않기 때문입니다.

또한, 항목체크하는 부분은 충분히 프론트엔드에서 통제 가능한 부분이기 때문에

그 부분도 생략했습니다.

Role의 경우, 관리자용 페이지를 알 수는 없지만 추후의 확장성을 고려한 것과 동시에

상품 추가하려면 관리자의 권한이 필요하여 만들게 되었습니다.

다만, User에서 참조를 할 때 on_delete 옵션에 대해 고민이 많았는데

종속시켜 삭제시키는 건 굉장히 위험하기 때문에 일단 null이 되게 설정 후

추후에 관리자를 이용해 바꾸도록 코드 작성할 예정입니다.

마지막으로, emailunique=True를 설정하여 무결성의 원칙을 지키도록 했습니다.


2. views.py

import json
import bcrypt
import jwt

from django.db    import IntegrityError
from django.http  import JsonResponse
from django.views import View

from users.models import (
    Role,
    User
)
class SignUpView(View) :
    def post(self, request) :
        try :
            data = json.loads(request.body)
            
            email    = data['email']
            password = data['password']
            role_id  = int(data['role_id'])
            
            password = bcrypt.hashpw(password.encode('utf-8'), bcrypt.gensalt()).decode('utf-8')
            
            role = Role.objects.get(id=role_id)
              
            User.objects.create(
                email    = email,
                password = password,
                role     = role
            )
            
            return JsonResponse({'message' : 'CREATE_USER'}, status=201)
 
        except KeyError :
            return JsonResponse({'message' : 'KEY_ERROR'}, status=400)
        
        except IntegrityError :
            return JsonResponse({'message' : 'INTEGRITY_ERROR'}, status=400)
        
        except Role.DoesNotExist :
            return JsonResponse({'message' : 'ROLE_DOES_NOT_EXIST'}, status=400)

role_id의 경우 2 or "2"와 같이 입력할 수 있어서 int로 변환하는 걸 설정해줬어야 했습니다.

비밀번호의 경우, 암호화가 진행됩니다.

role_id를 통해 객체를 가져오는 코드가 가장 봐야할 부분인데

원래 내가 받은 role_id값이 Role에 존재하지 않는다면 아래와 같이 작성했었습니다.

if not Role.objects.filter(id=role_id).exists() :
    return JsonResponse({'message' : 'ROLE_DOES_NOT_EXIST'}, status=400)

하지만 아래 예외처리에서 Role.DoesNotExist를 설정했기 때문에
굳이 조건문을 안써줘도 해당하는 객체를 못 가져온다면 예외처리문으로 가게 됩니다.

그리고 email의 경우도 회원가입하려는데 이미 존재한다면

if User.objects.filter(email=email).exists() :
    return JsonResponse({'message' : 'ALREADY_EXIST'}, status=400)

같이 작성해줘야하지만, 아래 예외처리에서 IntegrityError를 설정했기 때문에
굳이 조건문을 안써줘도 이미 존재하는 메일이라면 예외처리문으로 가게 됩니다.

다음 포스팅은 로그인입니다.

profile
ISTJ인 K-개발자

0개의 댓글

관련 채용 정보