Декораторы в class-based views

У меня есть ошибка, когда декоратор использует @login_required в виде, основанном на классе, но эта функционирует хорошо в виде, основанном на функциях:

Views.py

from django.contrib.auth.decorators import login_required
from django.utils.decorators import method_decorator
from django.views.generic import ListView
from django.views.generic.detail import DetailView
from .forms import ElementForm
from .models import Element

@login_required()
class Home(ListView):
    model = Element

class ElementDetail(DetailView):
    model = Element

@login_required()
def new_element(request):
    if request.method == 'POST':
        form = ElementForm(request.POST, request.FILES)
        if form.is_valid():
            element = form.save()
            element.save()
            return HttpResponseRedirect('/')
    else:
        form = ElementForm()
    template = loader.get_template('new_element.html')
    context = {
        'form': form
    }
    return HttpResponse(template.render(context, request))

Urls.py

from django.conf.urls import url
from . import views
urlpatterns = [
    url(r'^elements$', views.Home.as_view(), name='home'),
    url(r'^detail/(?P<pk>[0-9]+)/$', views.ElementDetail.as_view(), name='detail'),
    url(r'^element/new$', views.new_element, name='new_element'),
]

Оставив @login_required только в функции, код прокручивает изображение в окне без проблем, но Home когда это добавляет к классу class, меня бросает следующая ошибка в консоли:

File "/home/didier/Documents/Projects/inventory/inv/elements/urls.py", line 4, in <module>
    url(r'^elements$', views.Home.as_view(), name='home'),
AttributeError: 'function' object has no attribute 'as_view'
2
задан 13.04.2016, 21:50
2 ответа

Чтобы украшать CBV, ты должен использовать декоратор method_decorator, уже habГ-схвати это импортируемое, одинокий ты должен использовать это:

from django.contrib.auth.decorators import login_required
from django.utils.decorators import method_decorator
from django.views.generic import ListView


@method_decorator(login_required, name='dispatch')
class Home(ListView):
    model = Element

то, что его делает method_decorator, состоит в том, чтобы украшать один mГ©todo класса especГ-fica и чтобы украшать CBV, ты это должен делать в mГ©todo dispatch из класса.

Предыдущее - эквивалентный этому:

class Home(ListView):
    model = Element

    @method_decorator(login_required)
    def dispatch(self, *args, **kwargs):
        return super(Home, self).dispatch(*args, **kwargs)

Другая opciГіn состоит в том, чтобы использовать декоратор в тебе urls.py:

from django.conf.urls import url
from django.contrib.auth.decorators import login_required
from . import views

urlpatterns = [
    url(r'^elements 

ActualizaciГіn

A partir de Джанго 1.9 возможный использовать LoginRequiredMixin:

from django.contrib.auth.mixins import LoginRequiredMixin

class MyView(LoginRequiredMixin, View):
    login_url = '/login/'
    redirect_field_name = 'redirect_to'
, login_required(views.Home.as_view()), name='home'), # ... ]

ActualizaciГіn

A partir de Джанго 1.9 возможный использовать LoginRequiredMixin:

from django.contrib.auth.mixins import LoginRequiredMixin

class MyView(LoginRequiredMixin, View):
    login_url = '/login/'
    redirect_field_name = 'redirect_to'
5
ответ дан 24.11.2019, 14:35
  • 1
    Большое спасибо, функция и # 243; верно – Didier 14.04.2016, 01:47

Adicionalmente ты можешь использовать один LoginRequiredMixin в твои совещания, я рекомендую тебе использовать axes .

1
ответ дан 24.11.2019, 14:35
  • 1
    Он мне кажется, что versi и # 243; n 1.9 уже приходит с этим Mixin – César 19.04.2016, 15:03