Flask 웹 서버 만들기

Flask로 웹개발: #12 기능 구현 - 회원 가입, 탈퇴, 로그인, 로그아웃

TitediosKW 2024. 7. 31. 19:00
반응형



Flask는 파이썬으로 작성된 마이크로 웹 프레임워크로, 간단하고 직관적인 웹 애플리케이션 개발을 가능하게 합니다. 이번 포스팅에서는 Flask를 사용하여 회원 가입, 탈퇴, 로그인, 로그아웃 기능을 구현하는 방법을 단계별로 설명하겠습니다.

1. 데이터베이스 모델 설정

회원 정보를 저장할 데이터베이스 모델을 설정합니다. 이전 포스팅에서 이와 같은 모델을 활용하여 User는 이미 생성하셨던거 기억하시죠? ㅎㅎ

...

class FlaskUser(db.Model):
    id = db.Column(db.Integer, primary_key=True)
    username = db.Column(db.String(80), unique=True, nullable=False)
    password = db.Column(db.String(200), nullable=False)

    def __repr__(self):
        return f'<User {self.username}>'

...

2. 회원 가입 기능 구현

회원 가입 폼 데이터를 받아서 데이터베이스에 새로운 사용자를 추가하는 기능을 구현합니다. 회원 가입 URL 라우트 추가하고 받아온 User의 데이터 중 비밀번호는 Hash로 만들어 데이터베이스에 저장합니다.

@app.route('/register', methods=['GET', 'POST'])
def register():
    if request.method == 'POST':
        username = request.form['username']
        password = request.form['password']
        hashed_password = generate_password_hash(password, method='pbkdf2:sha256') # Hash 생성

        new_user = FlaskUser(username=username, password=hashed_password) # 새로운 User 생성

        try:
            db.session.add(new_user) # 신규 사용자를 데이터베이스에 입력
            db.session.commit() # 커밋, 데이터베이스를 확정하는 의미
            flash('User registered successfully!')
            return redirect(url_for('index')) # 리다이렉션
        except Exception as e:
            db.session.rollback()
            flash(f'Error: {str(e)}')

    return render_template('register.html')

Hash 란?

정의

Hash는 데이터의 고유 식별자를 생성하기 위해 사용되는 함수입니다. 이 함수는 임의의 길이의 입력 데이터를 고정된 길이의 고유한 출력 데이터(해시값 또는 해시 코드)로 변환합니다. 해시 함수는 다양한 분야에서 사용되며, 주로 데이터 검색, 데이터 무결성 검증, 비밀번호 저장 등의 용도로 활용됩니다.

주요 특징

  • 고정된 길이 출력: 입력 데이터의 길이에 관계없이 해시 함수는 항상 고정된 길이의 출력을 생성합니다. 예를 들어, SHA-256 해시 함수는 입력 데이터가 무엇이든 항상 256비트(32바이트) 길이의 해시값을 생성합니다.

  • 단방향성: 해시 함수는 단방향 함수입니다. 즉, 해시값을 가지고 원래 입력 데이터를 복원하는 것은 매우 어렵습니다. 이는 비밀번호 저장 등에 유용합니다.

  • 고유성: 서로 다른 두 입력 데이터가 같은 해시값을 갖는 경우(이를 해시 충돌이라고 함)가 발생할 가능성은 매우 낮습니다. 좋은 해시 함수는 충돌을 최소화하도록 설계되어 있습니다.

  • 빠른 계산: 해시 함수는 입력 데이터에 대해 빠르게 계산할 수 있어야 합니다.

3. 로그인 기능 구현

사용자가 입력한 로그인 정보를 검증하고 세션을 생성하는 기능을 구현합니다. 여기서는 비밀번호가 맞는지만 검사합니다.

@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':
        username = request.form['username']
        password = request.form['password']

        user = FlaskUser.query.filter_by(username=username).first() # DB에서 쿼리. 첫 번째 결과만 반환
        if user and check_password_hash(user.password, password): # PW Hash 값 비교
            session['user'] = user.username
            flash('Logged in successfully.')
            return redirect(url_for('index'))
        else:
            flash('Invalid username or password')

    return render_template('login.html')

4. 로그아웃 기능 구현

로그아웃 시 세션을 종료하는 기능을 구현합니다. 사용자가 로그아웃을 하는 기능입니다. Session에서 user 영역을 None으로 설정하여 로그인 된 User를 제거하는 방식으로 동작합니다. 로그아웃 후 index 페이지로 리다이렉션 합니다.(아무동작도 하지 않으면 이상하겠죠?ㅎㅎ)

@app.route('/logout')
def logout():
    session.pop('user', None) # 세션에서 사용자 제거
    flash('You were successfully logged out')
    return redirect(url_for('index'))

5. 회원 탈퇴 기능 구현

로그인된 사용자가 자신의 계정을 삭제할 수 있는 기능을 구현합니다. ID와 PW를 입력하면 회원 정보를 대조해보고 맞는 회원을 데이터베이스와 세션에서 삭제합니다. 이후 index페이지로 리다이렉션합니다.

@app.route('/delete', methods=['GET', 'POST'])
def delete():
    if request.method == 'POST':
        username = request.form['username']
        password = request.form['password']

        user = FlaskUser.query.filter_by(username=username).first()
        if user and check_password_hash(user.password, password):
            try:
                db.session.delete(user) # DB에서 사용자를 삭제
                db.session.commit()
                flash('User deleted successfully!')
                session.pop('user', None)
                return redirect(url_for('index'))
            except Exception as e:
                db.session.rollback()
                flash(f'Error: {str(e)}')
        else:
            flash('Invalid username or password')

    return render_template('delete.html')

결론

이제 Flask 애플리케이션에 회원 가입, 로그인, 로그아웃, 회원 탈퇴 기능이 완성되었습니다. 이 코드들을 app.py 파일에 추가하고 Flask 서버를 실행하면 해당 기능들을 사용할 수 있습니다. 실제 서비스에서는 추가적인 보안 조치와 예외 처리가 필요하지만, 이번 포스팅에서는 기본적인 기능 구현에 중점을 두었습니다. Flask의 강력한 기능을 활용하여 더 다양한 기능을 추가해 보셔도 좋겠습니다.다음에는 이번에 만든 기능들을 테스트하기 위해 배포하고 이것 저것 해볼 예정입니다.

도움이 되셨다면 공감 부탁드리겠습니다. 여러분의 공감이 정말 큰 힘이 됩니다.

감사합니다!

반응형