Adam Starrh Adam Starrh - 3 months ago 15
Python Question

Django - Correct way to pass arguments to CBV decorators?

The docs feature nice options for applying decorators such as

to Class Based Views.

However, I'm a little unclear about how to pass specific arguments along with the decorator, in this case I'd like to change the
login_url
of the decorator
.

Something like the following, only valid:

@login_required(login_url="Accounts:account_login")
@user_passes_test(profile_check)
class AccountSelectView(TemplateView):
template_name='select_account_type.html'

Answer

You should use @method_decorator with class methods:

A method on a class isn’t quite the same as a standalone function, so you can’t just apply a function decorator to the method – you need to transform it into a method decorator first. The method_decorator decorator transforms a function decorator into a method decorator so that it can be used on an instance method.

Then just call decorator with arguments you need and pass it to method decorator (by calling decorator function that can accept arguments you will get actual decorator on exit). Don't forget to pass the name of the method to be decorated as the keyword argument name (dispatch for example) if you will decorate the class instead of class method itself:

@method_decorator(login_required(login_url="Accounts:account_login"),
                  name='dispatch')
@method_decorator(user_passes_test(profile_check), name='dispatch')
class AccountSelectView(TemplateView):
    template_name='select_account_type.html'