Django e-commerce part20 Login Required Mixin
Login required の機能をmixinに移す。
mixinは、簡単に言うと、他のmodelなどとは独立して機能するclass・functionのこと
Login Required mixin は、staffメンバー、ログインしているユーザーでないと、variationを見れなくするための機能。これをmixinにする理由は、他のviewでも簡単に利用できるようにするため。
products/mixins.py を作成する。
以下のとおり。これは解説が必要。。。
from django.contrib.admin.views.decorators import staff_member_required from django.contrib.auth.decorators import login_required from django.utils.decorators import method_decorator # decoratorsをimportする。 from django.http import Http404 class StaffRequiedMixin(object): @classmethod def as_view(self, *args, **kwargs): view = super(StaffRequiedMixin, self).as_view(*args, **kwargs) return staff_member_required(view) @method_decorator(login_required) def dispatch(self, request, *args, **kwargs): if request.user.is_staff: return super(StaffRequiedMixin, self).dispatch(request, *args, **kwargs) else: raise Http404 class LoginRequiedMixin(object): @classmethod def as_view(self, *args, **kwargs): view = super(LoginRequiedMixin, self).as_view(*args, **kwargs) return login_required(view) @method_decorator(login_required) def dispatch(self, request, *args, **kwargs): return super(LoginRequiedMixin, self).dispatch(request, *args, **kwargs)
まず全体として何をしようとしているのかというと、as_view, dispatchというclass based viewに関する関数を上書きさせようとしているのだと考えられる。関数を上書きして、このmixin classを継承したclass based view に、ログイン認証によるページ表示制限機能を持たせる。
デコレーションの使い方と動作について。@classmethodは、その関数をクラスメソッドとして定義するためにつける。(クラスメソッドとインスタンスメソッドの違いはこちら )すごくわかりやすい!!
簡単に言うと、classmethodに設定しておくと、class名.メソッドで、直接インスタンスを呼び出せる!!例えば、as_viewメソッドも、class名.as_view で呼び出しOK。
その結果、classmethodに設定することによって、urls.py で設定してある、
ProductListView.as_view()
のところに、上記のmixin が適用されるようになる。正直、@method_decoratorの所はさっぱりわからん。
クラスベース汎用ビュー — Django 1.4 documentation
公式サイトをそのまま引用すると、
クラスベースビューの全インスタンスをデコレートするには、クラスの定義そのものを デコレートします。クラスの dispatch() メソッドにデコレータを適用することでできます。
クラスメソッドは単なる関数とは違います。メソッドに関数デコレータを適用することは できません。関数デコレータをメソッドデコレータに変換する必要があります。 method_decorator デコレータは関数デコレータをメソッドデコレータに変換する ので、これをインスタンスメソッドで使えます。
とのこと。つまり 1. @method_decoratorには、関数デコレーターをメソッドデコレーターに変換することができる 2. login_requiredは関数デコレーターのため、@method_decoratorでメソッドデコレーターに変換する 3. dispatch()に、login_required(デコレーター)を適用することで、viewを制限することができる
ということかな。うーん、全然わからん。
- デコレータについては以下のサイトが分かりやすかったです!
難しく考えすぎとのこと。単純に、
対象オブジェクトを差し替える技術
とのこと。
views.py
views.pyの該当viewに挿入する。
... from .mixins import StaffRequiedMixin ... class VariationListView(StaffRequiedMixin, ListView): ... ```` ### mixins.py return staff_member_required だと、ログイン失敗時に、adminが開いてしまうので、login_requiredにしておいて、通常のuserのログイン画面を開かせる。
class StaffRequiedMixin(object): ... return login_required(view) ...
### ecommerce2/urls.py adminのurlを隠しおきたい場合、適当にurls.pyの箇所を変更する。
url(r'^dj/hide/admin/', include(admin.site.urls)),