[TIL | 240116] Django - 로그인, 로그아웃

sun_U·2024년 1월 18일
0

TIL

목록 보기
17/21
post-thumbnail
  • Django에서는 django.contrib.auth 앱을 활용하여 로그인, 로그아웃 구현 가능
    • Django 프로젝트 생성 시 자동으로 생성 (settings.py 에서 확인 가능)

1. common 앱

  • 별도의 앱으로 생성

(1) django-admin startapp common

(2) common 앱 등록

config/settings.py

(... 생략 ...)

INSTALLED_APPS = [
    'common.apps.CommonConfig',  
    'pybo.apps.PyboConfig',
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',
]

(... 생략 ...)

(3) url 등록

config/urls.py 수정

from django.contrib import admin
from django.urls import path, include

urlpatterns = [
    path('admin/', admin.site.urls),
    path('pybo/', include('pybo.urls')),
    path('common/', include('common.urls')),
]

http://localhost:8000/common/ 으로 시작하는 URL은 모두 common/urls.py 파일을 참조

common/urls.py 생성

app_name = 'common'

urlpatterns = [
]

2. 로그인

templates/navbar.html

(... 생략 ...)
<ul class="navbar-nav">
    <li class="nav-item ">
        <a class="nav-link" href="{% url 'common:login' %}">로그인</a>
    </li>
</ul>
(... 생략 ...)

→ 로그인 버튼 클릭시 화면 이동

1) 로그인 뷰

common/urls.py 수정

from django.urls import path
from django.contrib.auth import views as auth_views

app_name = 'common'

urlpatterns = [
    path('login/', auth_views.LoginView.as_view(), name='login'),
]

→ 매핑 규칙 추가. 뷰를 따로 만들지 않고 내장된 LoginView 사용

2) 로그인 템플릿

(1) common/urls.py 수정

from django.urls import path
from django.contrib.auth import views as auth_views

app_name = 'common'

urlpatterns = [
    path('login/', auth_views.LoginView.as_view(template_name='common/login.html'), name='login'),
]
  • LoginView는 registration이라는 템플릿 디렉터리에서 login.html 파일을 찾지만 common앱에서 구현하므로 경로를 common/login.html 로 수정 및 생성

(2) templates/common/login.html 생성

{% extends "base.html" %}
{% block content %}
<div class="container my-3">
    <form method="post" action="{% url 'common:login' %}">
        {% csrf_token %}
        {% include "form_errors.html" %}
        <div class="mb-3">
            <label for="username">사용자ID</label>
            <input type="text" class="form-control" name="username" id="username"
                   value="{{ form.username.value|default_if_none:'' }}">
        </div>
        <div class="mb-3">
            <label for="password">비밀번호</label>
            <input type="password" class="form-control" name="password" id="password"
                   value="{{ form.password.value|default_if_none:'' }}">
        </div>
        <button type="submit" class="btn btn-primary">로그인</button>
    </form>
</div>
{% endblock %}
  • username , passworddjango.contrib.auth 앱이 요구하는 필수항목

(3) templates/form_errors.html 작성

<!-- 필드 오류와 넌필드 오류를 출력한다. -->
{% if form.errors %}
<div class="alert alert-danger">
    {% for field in form %}
    <!-- 필드 오류 -->
    {% if field.errors %}
    <div>
        <strong>{{ field.label }}</strong>
        {{ field.errors }}
    </div>
    {% endif %}
    {% endfor %}
    <!-- 넌필드 오류 -->
    {% for error in form.non_field_errors %}
    <div>
        <strong>{{ error }}</strong>
    </div>
    {% endfor %}
</div>
{% endif %}
  • 로그인 실패시 오류 사항 확인 페이지
    • field.errors : 사용자 입력 필드 값에 대한 오류(값 누락, 필드 형식 불일치 등)
    • form.non_field_errors : 필드 값 상관없이 다른 이유로 발생하는 오류

3) 로그인 수행

→ 오류 메시지 표시

→ 슈퍼유저 계정으로 로그인

(1) config/settings.py 수정

(... 생략 ...)

# 로그인 성공후 이동하는 URL
LOGIN_REDIRECT_URL = '/'
  • django.contrib.auth 패키지는 디폴트로 /accounts/profile/ 이라는 URL로 이동하지만 성공시 / 로 이동하도록 변경

(2) config/urls.py 수정

from django.contrib import admin
from django.urls import path, include
from pybo import views

urlpatterns = [
    path('admin/', admin.site.urls),
    path('pybo/', include('pybo.urls')),
    path('common/', include('common.urls')),
    path('', views.index, name='index'),  # '/' 에 해당되는 path
]
  • / 페이지에 대응하는 URL 매핑 규칙 추가

3. 로그아웃

  • 로그인 후 “로그인” 링크가 “로그아웃” 링크로 바뀌고, “로그아웃” 링크일 때 “로그인” 링크로 바뀌도록

(1) templates/navbar.html 수정

(... 생략 ...)
<li class="nav-item">
    {% if user.is_authenticated %}
    <a class="nav-link" href="{% url 'common:logout' %}">{{ user.username }} (로그아웃)</a>
    {% else %}
    <a class="nav-link" href="{% url 'common:login' %}">로그인</a>
    {% endif %}
</li>
(... 생략 ...)
  • {% if user.is_authenticated %} → 현재 사용자가 로그인 되었는지 판별

(2) common/urls.py

from django.urls import path
from django.contrib.auth import views as auth_views
from . import views

app_name = 'common'

urlpatterns = [
    path('login/', auth_views.LoginView.as_view(template_name='common/login.html'), name='login'),
    path('logout/', views.logout_view, name='logout'),
]
  • URL 매핑 추가

(3) common/views.py

from django.contrib.auth import logout
from django.shortcuts import redirect

def logout_view(request):
    logout(request)
    return redirect('index')
  • logout_view 함수 호출시 django.contrib.auth 모듈의 로그아웃 함수를 사용해 로그아웃 수행 후 ‘index’ 페이지로 리다이렉트하도록 설정

[ 로그인 완료 후 화면 ]

profile
Data Engineer🐣

0개의 댓글