2010-12-05 10 views

cevap

2

Uygun HTTP üstbilgilerini denetleyen ve uygun yanıtı döndüren bir görüntü dekoratör yazın (yanıt kodu 401 için built-in type yoktur).

10
class HttpResponseUnauthorized(HttpResponse): 
    def __init__(self): 
     self.status_code = 401 

... 
return HttpResponseUnauthorized() 
+2

'__init__' yöntemine eklemeniz gerekmez, yalnızca özniteliği sınıf tanımında ayarlayın. –

+0

@Matthew: Genelde bunu yapmıyorum. İstenmeyen paylaşımlı nesne tuzağına düşmeyi çok kolay hale getirir ve sınıf gövdesinde ve bazılarında __init__'de bazı başlatmaların yapılması açık değildir. –

+1

Bu, aşağıdaki hatayı döndürür: 'HttpResponseUnauthorized 'nesnesinin' _headers'' özniteliği yok ' – btk

96

Zaten django.http.HttpResponse ithal ettik varsayarsak ... Bu eski bir tanesidir biliyorum ama "401 django" için en iyi Google sonucu, bu yüzden ben bu işaret düşündüm , tek satırda yapabilirsiniz:

return HttpResponse('Unauthorized', status=401) 

'Unauthorized' dize isteğe bağlıdır. Kolay.

+3

Bu feragat edilebilir ve onu bastı; ancak benzer bir senaryo için bunun yerine 403 (Yasak) hatası kullanmayı düşünebilirim - bunun için hazır bir mekanizma var: https://docs.djangoproject.com/en/dev/topics/http/views/#the-403- http-yasak görünümü - sadece "urls.py" kökünde "handler403" öğesini tanımlayın ve sonra "django.core.exceptions.PermissionDenied" öğesini kaldırın. –

+0

@TomaszGandor Yep, veya 'HttpResponseForbidden 'özelliği de 403s için çalışıyor (genellikle daha uygun olduğunu düşündüğünüz bir istisna geliştirme). Bazıları kesin farkı tartışsa da, 401 ve 403 oldukça aynı değildir. –

+0

Vikipedi'ye göre, 401 cevabı bir WWW-Authenticate başlık alanı içermelidir. Yani, 403 kullanmak daha kolaydır. Https://en.wikipedia.org/wiki/List_of_HTTP_status_codes –

8
class HttpResponseUnauthorized(HttpResponse): 
    status_code = 401 

... 
return HttpResponseUnauthorized() 

Normalde, __init__ yılında örneğini belirlesin ya da tüm örnekleri arasında paylaşılır sınıf değişkenleri ile bitirmek. Ancak, Django zaten sizin için yapar:

class HttpResponse(object): 
    """A basic HTTP response, with content and dictionary-accessed headers.""" 

    status_code = 200 

    def __init__(self, content='', mimetype=None, status=None, 
      content_type=None): 
     # snip... 
     if status: 
      self.status_code = status 

(see the Django code in context) bir util.py içinde

2

Kalıtım çözüm

from django.http import HttpResponse 

class Http401(HttpResponse): 
    def __init__(self): 
     super().__init__('401 Unauthorized', status=401) 

birden fazla çağrı yerine:

return HttpResponse('401 Unauthorized', status=401) 

inte istirahatte 1.9.6 https://github.com/django/django/blob/1.9.6/django/http/response.py#L443 içinde başka adlandırılmış yanıtlar var ama 401 değil.

+2

Bu yanıtı beğeniyorum. Fakat '__init __ (self):' bu gibi değişmeli \t \t 'süper (Http401, self) .__ init __ (ileti, durum = 401)' – Hobaak

+0

@Hobaak In Python 3 sadece 'super() .__ init__ yazabiliriz ': http://stackoverflow.com/a/33191175/895245. Bir 'mesaj' eklenebilir, ancak API yapmıyorsanız, sadece HTTP tarayıcı uç noktaları, çok gerekli değildir. –

+1

Tamam. Çözüm bana 1.8.6 Django'da 2.7 Python ile bir hata attı. Benim önerim, sorunun giderilmesine yardımcı oldu. Belki de Python 3 ile çalışır. Yine de bu cevaplardan en çok bu çözümü beğenirim. – Hobaak

İlgili konular