회원관리 7. 잡다 기능

Pywiki
둘러보기로 가기 검색하러 가기

1 로그인 후 기존 화면으로 돌아오기[편집 | 원본 편집]

로그인 하게 되면 설정에 지정된 화면으로 돌아가고 만다. 다시 보던 페이지로 돌아와야 한다는 불편이 있는데... 이를 위해선 다양한 방법이 있다.

몇시간을 고민하고 시도하다 만족스런 답을 찾았다.

  1. 뷰 : 최악의 선택. 모든 뷰에서 기존화면을 저장하게 할 수는 없다.
  2. 데코레이터 상속 : login_requeired 데코레이터를 변형해서 진행해보려 했는데... 나는 모달로 바로 소셜로그인페이지로 넘어가게끔 만들어둬서 데코레이터를 거치지 않는 경우가 발생했다.(단순 로그인 버튼을 쓴다면 좋은 전략일듯. 버튼으로 작동하는 뷰 하나만 고쳐 데코레이터를 달면 되니까. + 일반 데코레이터가 달린 뷰에서도 자연스레 작동할 테니까.) 다만, 외부링크로 로그인이 필요한 페이지를 보낼 때 사용하면 좋은 전략일 듯하다.
  3. 미들웨어 : 단일 로그인이라면 괜찮지만... 소셜로그인이라든가 외부 기능을 사용하게 되면 이전 페이지를 저장할 때 외부 페이지가 저장되어버린다.
  4. 탬플릿 필터 이용 : 그나마 이게 범용적으로 사용 가능할듯.

1.1 데코레이터 조작[편집 | 원본 편집]

과정 설명 비고
데코레이터 .py 작성. 적절히 관리할 곳에 작성.
from django.shortcuts import redirect
from functools import wraps

def custom_login_required():
    '''로그인 데코레이터의 기능에 현재 페이지를 저장하기 위해.'''
    def _decorator(view_func):
        @wraps(view_func)
        def _wrapped_view(request, *args, **kwargs):
            # 로그인 하지 않았을 때에만.
            if not request.user.is_authenticated:
                request.session['before_login'] = request.path
                return redirect('custom_account:login_social')  # 로그인 페이지로 이동.
            return view_func(request, *args, **kwargs)

        return _wrapped_view

    return _decorator
데코레이터 사용 기존에 사용하던 login_required를 일일이 바꿔주긴 쉽지 않아 다음과 같이 처리한다. from custom_account.decorator import custom_login_required as login_required
뷰에서 리다이렉트 다른 것과 동일. 세션에서 befroe_login 을 불러와 리다이렉트.

1.2 탬플릿 필터 이용[편집 | 원본 편집]

과정 설명 비고
탬플릿 태그.py 작성. 앱 하위의 templatetag 디렉토리 하위에 태그명.py 를 작성한다.
from django import template

register = template.Library()

@register.simple_tag(takes_context=True)
def store_current_url(context):
    request = context['request']
    if not request.user.is_authenticated:
        request.session['before_login'] = request.path
    return ''  # 탬플릿에 None이라고 떠서 문자열 반환이라도...
탬플릿에 반영 주소를 저장할 탬플릿에 탬플릿필터를 반영하든가, 네비바 등 모든 페이지에 관여할 수 있는 곳에 기입한다.
{% load 태그명 %}
{% store_current_url %}
로그인 리다이렉트뷰 로그인 후 리다이렉트되는 페이지가 있을텐데, 그 페이지를 제어하는 뷰에서 다음과 같은 코드를 추가한다.
url = request.session.get('before_login')  # 기존 주소 획득.
        if url != None:
            del request.session['before_login']
            return redirect(url)
        return render(request, 'main/main.html', context)