오늘 개발한 내용은 Django 프로젝트에서 구글 쇼설 로그인을 적용한 것으로, django 웹 어플리케이션에 구글 OAuth 2.0을 통한 소셜 로그인 기능을 추가한 것입니다.
이를통해 별도의 회원가입 절차를 간소화할 수 있습니다.
하지만 구글 쇼셜 로그인을 설정했을 때, Django의 기본 사용자 모델은 비밀번호를 필요로 하지 않기에 , 소셜 로그인 방식에서는 사용자가 구글 계정을 사용하여 로그인 하기 때문에 Django의 사용자 모델에는 비밀번호가 저장되지 않습니다.
이에 소셜 로그인 계정을 사용하는 경우, 해당 사용자들에게만 (소셜 로그인 계정을 사용한 경우 = 비밀번호가 설정되어 있지 않은 사람들의 경우 개인페이지에 비밀번호 인증 전에 버튼을 만들어 비밀번호를 설정할 수 있는 페이지를 만들었고, 만약 비밀번호가 있는 사용자 즉, 정당한 회원가입 절차에 의해 설정된 사람은 버튼을 누를시 403.html 을 만들어 403오류가 나도록 유도하였습니다.
1. 소셜 로그인 설정
- 먼저 소셜 로그인 구현을 위해 python-social-auth 라이브러리를 사용했고, 이를 통해서 구글 OAuth 2.0을 사용한 로그인 처리를 할 수 있었습니다.
# settings.py # 소셜 인증 백엔드 설정 AUTHENTICATION_BACKENDS = ( 'social_core.backends.google.GoogleOAuth2', # 구글 OAuth 2.0 인증 백엔드 'django.contrib.auth.backends.ModelBackend', # 기본 Django 인증 백엔드 ) # 구글 OAuth 2.0 설정 SOCIAL_AUTH_GOOGLE_OAUTH2_KEY = os.getenv("GOOGLE_CLIENT_ID") # 구글 클라이언트 ID SOCIAL_AUTH_GOOGLE_OAUTH2_SECRET = os.getenv("GOOGLE_CLIENT_SECRET") # 구글 클라이언트 비밀 SOCIAL_AUTH_GOOGLE_OAUTH2_REDIRECT_URI = 'http://127.0.0.1:8000/auth/complete/google-oauth2/' # 리디렉션 URI SOCIAL_AUTH_URL_NAMESPACE = 'social' # 로그인 및 로그아웃 URL 설정 LOGIN_URL = 'login' LOGOUT_URL = 'logout' LOGIN_REDIRECT_URL = 'index' # 로그인 후 리디렉션할 URL # 구글 OAuth 2.0을 통해 필요한 사용자 정보 스코프 설정 SOCIAL_AUTH_GOOGLE_OAUTH2_SCOPE = [ 'email', 'profile', ] |
https://developers.google.com/identity/protocols/oauth2/scopes?hl=ko
위 내용은 구글 OAuth2.0의 범위를 나타낸 것으로 해당 범위 컬렉션 사용을 위해 어떠한 것을 가져올 것인지에 대한 내용
- AUTHENTICATION_BACKENDS: 구글 OAuth 2.0 인증을 위한 백엔드와 Django의 기본 인증 백엔드를 설정한 것으로 백엔드 설정을 통해 사용자는 구글 계정을 이용해 로그인할 수 있습니다.
- SOCIAL_AUTH_GOOGLE_OAUTH2_KEY 및 SECRET: 구글 API에서 제공하는 클라이언트 ID와 클라이언트 비밀 키를 사용하여 OAuth 2.0 인증을 처리합니다. (마지막 쯤에 해당 방법 소개)
- SOCIAL_AUTH_GOOGLE_OAUTH2_REDIRECT_URI: 사용자가 구글 로그인을 성공적으로 마친 후 리디렉션될 URL을 지정합니다.
- SOCIAL_AUTH_GOOGLE_OAUTH2_SCOPE: 사용자로부터 요청할 권한 범위(이메일 및 프로필 정보)를 설정합니다.
2. 소셜 로그인 URL 설정
# urls.py path('auth/', include('social_django.urls', namespace='social')), # 소셜 로그인 URL |
- 소셜 로그인 URL 패턴을 추가하여 /auth/ 경로를 통해 소셜 로그인이 가능하도록 설정합니다.
3. 소셜 로그인 사용자를 위한 비밀번호 설정 기능
- 구글 소셜 로그인 사용자에게 비밀번호가 설정되어 있지 않기 때문에, 사용자가 비밀번호를 설정할 수 있는 페이지를 추가했고, 이를 위해 set_password 뷰와 템플릿을 작성했습니다.
# users/views.py from django.contrib.auth.hashers import make_password from django.contrib.auth.forms import SetPasswordForm from django.contrib.auth import update_session_auth_hash from django.shortcuts import render, redirect from django.contrib.auth.decorators import login_required @login_required def set_password(request): if request.user.social_auth.exists(): # 소셜 로그인 여부 확인 if request.method == 'POST': form = SetPasswordForm(user=request.user, data=request.POST) if form.is_valid(): user = form.save() update_session_auth_hash(request, user) # 비밀번호 변경 후 세션 업데이트 return redirect('index') # 비밀번호 설정 후 리디렉션할 URL else: form = SetPasswordForm(user=request.user) return render(request, 'users/set_password.html', {'form': form}) return render(request, '403.html', status=403) # 소셜 로그인이 아닌 경우 403 에러 |
- set_password 뷰는 사용자가 소셜 로그인을 했는지 확인한 후, 비밀번호 설정 폼을 제공하며, 소셜 로그인을 한 사용자에게만 비밀번호 설정 폼을 보여주고, 비밀번호를 설정한 후에는 세션을 업데이트하여 새로운 비밀번호로 로그인 상태를 유지하도록 했습니다.
- 소셜 로그인이 아닌 사용자가 이 페이지에 접근하려 하면 403 Forbidden 페이지로 리디렉션되게 유도하였습니다.
4. 비밀번호 설정 페이지
비밀번호를 설정할 수 있도록 HTML 템플릿
<!-- set_password.html --> <!DOCTYPE html> <html lang="ko"> <head> <meta charset="UTF-8"> <title>비밀번호 설정</title> <style> .error { color: red; /* 오류 메시지 스타일 */ } </style> </head> <body> <h1>비밀번호 설정</h1> <form method="post"> {% csrf_token %} <div> <label for="id_new_password1">새 비밀번호:</label> {{ form.new_password1 }} <!-- 비밀번호 입력란 --> {% if forhttp://m.new_password1.errors %} <div class="error">{{ forhttp://m.new_password1.errors }}</div> {% endif %} </div> <div> <label for="id_new_password2">비밀번호 확인:</label> {{ form.new_password2 }} <!-- 비밀번호 확인 입력란 --> {% if forhttp://m.new_password2.errors %} <div class="error">{{ forhttp://m.new_password2.errors }}</div> {% endif %} </div> <button type="submit">비밀번호 설정</button> </form> </body> </html> |
- 사용자에게 새 비밀번호와 비밀번호 확인을 입력받는 폼을 만들었고. 오류 메시지가 있는 경우 빨간색으로 표시됩니다.
5. 비밀번호 설정 버튼 추가
소셜 로그인 사용자가 마이페이지 비밀번호 인증 부분에서 버튼을 통해 비밀번호를 설정할 수 있도록 추가한 것입니다.
<!-- personal_page.html 일부 --> <div class="button-container"> <a href="{% url 'set_password' %}" class="set-password-button">구글 로그인 하신분들 비밀번호 설정</a> </div> <p class="set-password-message">구글로그인 아닌분들은 403오류 페이지로 이동됩니다</p> |
위에서 말씀드린 SOCIAL_AUTH_GOOGLE_OAUTH2_KEY 및 SECRET 키 방법에 대해서 정리해보았습니다.
https://cloud.google.com/identity-platform/docs/use-rest-api?hl=ko#section-verify-custom-token
자세한 내용은 위에 구글 개발자 센터 API문서를 참고 하면 좋다.
일단 내가 한 방법을 설명하면
구글 로그인 API 연동은 크게 3가지로 나눌 수 있다.
1. Google Decelopers 설정
2. 개발 환경 설정
3. 초기화 및 로그인 구현
1. Google Decelopers 설정
https://console.cloud.google.com
위 사이트 접속해서 검색란에 "Oauth"검색 후 "OAuth 동의 화면 " 클릭
좌측 상단 프로젝트 선택
나오는 정보들 입력 후 프로젝트 만들기
좌측 OAuth 동의 화면 탭 진입 후 User Type 으로 '외부' 선택 후 만들기 클릭
앱 필수 정보 입력 하고 저장 (도메인 및 홈페이지는 나중에 작성해도 무관)
범위 추가 또는 삭제 버튼 클릭 후 최상단 3개 항목 선택 후 저장해줌
Google 로그인 테스트를 위한 계정 추가
여기서 누구나 사용하게 하기 위해서는 별도의 애플케이션 심사가 필요함
OAuth 동의 화면 에서 앱 게시 클릭
사용자 인증 정보 탭에서 OAuth 클라이언트 ID를 생성해줌
여기서 필수정보를 입력해주어야 하는데
우선 애플리케이션 유형 항목에서 웹 애플리케이션을 선택해줌
이후 애플리케이션 이름을 입력하고 승인된 자바스크립트 원본 항목에 구글 로그인을 사용할 홈페이지 주소를 입력
승인된 리디렉션 URI 항목에는 구글 로그인 한 후 Redirect 할 주소를 입력해줌
저장 누르면 구글 로그인 연동 API 정보가 나오게 된다.
위 과정을 완료하면 구글 로그인 API 사용에 필요한 설정은 끝이난 것이다.
여기서 확인한 아이디와 비밀번호를 settings.py 에
SOCIAL_AUTH_GOOGLE_OAUTH2_KEY = os.getenv("GOOGLE_CLIENT_ID") # 구글 클라이언트 ID SOCIAL_AUTH_GOOGLE_OAUTH2_SECRET = os.getenv("GOOGLE_CLIENT_SECRET") # 구글 클라이언트 비밀 |
해당 부분에 입력을 해주면 된다.
나의 경우 보안때문에 .env 파일을 만들어서 해당 파일에 로그인 정보를 넣고
from dotenv import load_dotenv # .env 파일 로드 load_dotenv() |
를 통해서 불러와서 사용하는 쪽으로 개발을 진행하였다. (그냥 아이디 비밀번호 올렸다가 git에 보안성으로 인해 코드가 올라가지 않아서 급하게 수정함)
'PYTHON-BACK' 카테고리의 다른 글
# 24.10.28_ 마켓컬리 클론코딩8_최종 마무리 (3) | 2024.10.28 |
---|---|
# 24.10.25_ 마켓컬리 클론코딩7_git hub 정리 (2) | 2024.10.28 |
# 24.10.23_ 마켓컬리 클론코딩5_회원탈퇴 (2) | 2024.10.23 |
# 24.10.22_ 마켓컬리 클론코딩4_선물특가 타이머 (0) | 2024.10.22 |
# 24.10.21_ 마켓컬리 클론코딩3_Google SMTP (1) | 2024.10.21 |