2012-04-05 6 views
11

ajaxリクエストに応答するためにいくつかのビューを書くと、login_requiredデコレータが認証されていないユーザに対して302のステータスコードを返すのは幾分奇妙です。これらのビューはajaxビューなので、これはやや不適切です。私はこのような場合にユーザがログインするのを望んでいませんが、私はDjangoがそのようなビューにアクセスするために認証が必要であることをクライアントに伝えたい(401は正しいステータスコードでなければなりません)。login_requiredデコレータがajaxビュー上で302の代わりに401を返す

これを達成するために、私は自分のデコレータlogin_required_ajaxを書き始めましたが、何とかこれは私のスキルを超えています。これは私がこれまでに出ているものです:

def login_required_ajax(function=None,redirect_field_name=None): 
    """ 
    Just make sure the user is authenticated to access a certain ajax view 

    Otherwise return a HttpResponse 401 - authentication required 
    instead of the 302 redirect of the original Django decorator 
    """ 
    def _decorator(view_func): 
     def _wrapped_view(request, *args, **kwargs): 
      if request.user.is_authenticated(): 
       return view_func(request, *args, **kwargs) 
      else: 
       return HttpResponse(status=401) 

     if function is None: 
      return _decorator 
     else: 
      return _decorator(function) 

ビューでこのデコレータを使用して、私はできるだけ早く私は、サイト上の任意のページにアクセスしようとしてViewDoesNotExist例外を取得します。

最初に、応答オブジェクトが呼び出し可能でないため、ユーザーが認証されていないときにHttpResponseが直接返される可能性があると私は考えました。しかし、デコレータは、問題のビューにアクセスしようとしない限り動作するはずです。そうではありませんか?これが本当に重要なのであれば、どうやってステータスコード401のHttpResponseを返すデコレータを書くことができますか?

+1

はあなたの取締役に関するものではありませんアイデア:あなたはまた、要求がAJAXリクエストであるかどうかを確認し、 '401を返すミドルウェアを導入する可能性'もし、ビューがログインのために' 302'を返すことを検出すれば、あなたはDjangoのデコレータを使い続け、ajaxと通常の要求を別々に扱うことができます... –

+3

それは本当に簡単ですか?それをajaxビューで使用しますか? ;) – marue

答えて

14

これはかなり良い試みです。ここに私が見つけたいくつかの問題があります:

  1. _decorator関数は_wrapped_viewを返さなければなりません。
  2. if function is Noneブロックのインデントがビットオフです - login_required_ajax関数は装飾された関数を返す必要があります。

ここで作られたこれらの変更とデコレータです:

def login_required_ajax(function=None,redirect_field_name=None): 
    """ 
    Just make sure the user is authenticated to access a certain ajax view 

    Otherwise return a HttpResponse 401 - authentication required 
    instead of the 302 redirect of the original Django decorator 
    """ 
    def _decorator(view_func): 
     def _wrapped_view(request, *args, **kwargs): 
      if request.user.is_authenticated(): 
       return view_func(request, *args, **kwargs) 
      else: 
       return HttpResponse(status=401) 
     return _wrapped_view 

    if function is None: 
     return _decorator 
    else: 
     return _decorator(function) 
+0

魅力的な作品です。ありがとうございました。 – marue

関連する問題