ビューがパブリック アクセスを持つものとしてリストされていることを確認したい場合、@login_required の反対であり、ビューが常にパブリックにアクセス可能であることを明確にする @public_access に相当するデコレータはありますか?
私が念頭に置いている 1 つの使用例は、ビューがパブリックにアクセス可能であることをコードで明確にすることに加えて、すべてのパブリック ビューに「@csrf_exempt」を自動的に追加することです。
ビューがパブリック アクセスを持つものとしてリストされていることを確認したい場合、@login_required の反対であり、ビューが常にパブリックにアクセス可能であることを明確にする @public_access に相当するデコレータはありますか?
私が念頭に置いている 1 つの使用例は、ビューがパブリックにアクセス可能であることをコードで明確にすることに加えて、すべてのパブリック ビューに「@csrf_exempt」を自動的に追加することです。
残念ながら、現在 Django にはこれに対する組み込みのサポートがなく、@login_required誤って忘れた場合に機密情報が公開される危険性があります。
私のプロジェクトの1つからの解決策は次のとおりです。
middleware/security.py:
def public(function):
"""
Decorator for public views that do not require authentication
"""
orig_func = function
while isinstance(orig_func, partial): # if partial - use original function for authorization
orig_func = orig_func.func
orig_func.is_public_view = True
return function
def is_public(function):
try: # cache is found
return function.is_public_view
except AttributeError: # cache is not found
result = function.__module__.startswith('django.') and not function.__module__.startswith('django.views.generic') # Avoid modifying admin and other built-in views
try: # try to recreate cache
function.is_public_view = result
except AttributeError:
pass
return result
class NonpublicMiddleware(object):
def process_view_check_logged(self, request, view_func, view_args, view_kwargs):
return
def process_view(self, request, view_func, view_args, view_kwargs):
while isinstance(view_func, partial): # if partial - use original function for authorization
view_func = view_func.func
request.public = is_public(view_func)
if not is_public(view_func):
if request.user.is_authenticated(): # only extended checks are needed
return self.process_view_check_logged(request, view_func, view_args, view_kwargs)
return self.redirect_to_login(request.get_full_path()) # => login page
def redirect_to_login(self, original_target, login_url=settings.LOGIN_URL):
return HttpResponseRedirect("%s?%s=%s" % (login_url, REDIRECT_FIELD_NAME, urlquote(original_target)))
settings.py:
MIDDLEWARE_CLASSES = (
#...
'middleware.security.NonpublicProfilefullMiddleware',
#...
)
最後に、コードを表示します。
from <projname>.middleware import publi
@public
def some_view(request):
#...
# Login required is added automatically
def some_private_view(request):
#...
また、「django プロジェクトのすべてのビューを自動的に装飾する」ブログ投稿も参照してください。
「ログイン不要」がデフォルトです。ビューがログイン制限されないように注釈を付けたい場合は、docstring でそれを行う必要があります。
@permission_classes([permissions.AllowAny])