본문 바로가기
Backend/Python

[FastAPI] Project Levup - 회원가입과 로그인 기능 만들기

by 천우산__ 2023. 11. 16.

개인적으로 사용할 용도이긴 하지만, 주변 사람들에게 소개하면서 사용을 권장하기 위해 간단한 회원 가입 기능을 만들어 두려고 한다.

회원 가입 기능을 만들기 전 몇 가지 패키지 설치가 필요하다

pip install PyJWT
pip install hashlib

 

위의 패키지는 로그인 시 사용자 정보와 만료 기간을 담기 위한 토큰을 생성하기 위한 패키지와

사용자 암호를 DB 에서 조회했을 때 알아볼 수 없도록 해싱하기 위해 필요한 패키지이다.

 

1. 회원가입 기능 만들기

from pydantic import BaseModel

db = {}

class Users(BaseModel):
    id : str
    email : str
    password : str
    
@app.post("/api/signup")
def signup(Users: Users):
    id, email, password = Users.id, Users.email, Users.password
    
    if id in db:
        return {"error" : "이미 존재하는 ID입니다."}
    
    hash_pw = hashlib.sha256(password.encode("utf-8")).hexdigest()
    db[id] = {"email": email, "password": hash_pw}
    return db

먼저, Users 모델을 생성하여 어떤 필드를 받을 것이고 필드 별 데이터 유형은 무엇인지 지정해 준다.

다음으로, signup 로직을 통해 Users 모델을 받아 Users 에 넣어주고 각각의 정보를 뽑아낸다.

이 때 DB에 동일한 데이터가 있다면 ID가 중복된다는 점을 알려주고, 그렇지 않다면 비밀번호를 암호화하여 DB에 저장한다.

회원가입 로직을 테스트 하기위해 vscode extension 중 Thunder Client 를 통해 테스트를 진행해보자

회원가입 테스트, 완료 시 유저 정보 DB 반환

현재, 아직 DB와 서버를 연결한 것이 아니므로 서버를 재실행 할 때 마다 데이터는 초기화된다는 점을 유의하자

 

2. 로그인 로직 구현하기

class Users(BaseModel):
    id : str
    email : str
    password : str

@app.post("/api/login")
def login(Users: Users):
    id, email, password = Users.id, Users.email, Users.password
    
    hash_pw = hashlib.sha256(password.encode("utf-8")).hexdigest()
    
    if id not in db or db[id]["password"] != hash_pw:
        return {"error" : "아이디 혹은 비밀번호를 확인해주세요"}
    
    payload = {"id" : id,
               "exp" : datetime.datetime.now() + datetime.timedelta(minutes=30)}
    
    token = jwt.encode(payload, "1234", algorithm="HS256")
    return {"success" : "로그인 성공", "token" : token}

사용자 정보를 받아서, ID와 비밀번호가 맞는지 확인한다. 이 때, DB에 저장된 비밀번호는 암호화 되어있으므로

입력받은 비밀번호를 해싱한 후에 비교를 해야 한다.

ID 가 DB에 없는건지, 비밀번호가 틀린 것인지 명확하게 알려주지 않는 이유는 해킹을 위해 접속한 사람에게 정확한 정보 전달을 주는 것을 피하기 위함이다.

로그인 테스트 결과