2011-08-20 56 views
1

我一直在試驗Django的基於類的視圖,並試圖編寫一個簡單的基於類的視圖來處理request中的某些信息,以便「處理器」方法可以使用處理過的信息。使用基於類的視圖來處理信息?

我似乎並沒有完全理解文檔所說的內容,我不確定這應該是Mixin,通用視圖還是其他內容。我想製作一個像這樣的類:

class MyNewGenericView(View): 

    redirect_on_error = 'home' 
    error_message = 'There was an error doing XYZ' 

    def dispatch(self, request, *args, **kwargs): 
     try: 
      self.process_information(request) 
      # self.process_information2(request) 
      # self.process_information3(request) 
      # etc... 
     except ValueError: 
      messages.error(request, self.error_message) 
      return redirect(self.redirect_on_error) 
     return super(MyNewGenericView, self).dispatch(request, *args, **kwargs) 

    def process_information(self, request): 
     # Use get/post information and process it using 
     # different models, APIs, etc. 
     self.useful_information1 = 'abc' 
     self.useful_information2 = 'xyz' 

    def get_extra_info(self): 
     # Get some extra information on something 
     return {'foo':'bar'} 

這將允許有人寫這樣一個觀點:

class MyViewDoesRealWork(MyNewGenericView): 
    def get(self, request, some_info): 
     return render(request, 'some_template.html', 
      {'info':self.useful_information1}) 

    def post(self, request, some_info): 
     # Store some information, maybe using get_extra_info 
     return render(request, 'some_template.html', 
      {'info':self.useful_information1}) 

是上面的代碼,以正確的方式去?有沒有更簡單/更好的方法來做到這一點?這是否會阻止上述功能在另一個通用視圖中使用(例如,內置的通用視圖)?

回答

0

看來我只是問了一個愚蠢的問題。使用舊式函數觀點或新的基於類的意見

class ProcessFooInformation(object): 
    def __init__(self, request): 
     self.request = request 
    @property 
    def bar(self): 
     baz = self.request.GET.get('baz', '') 
     # do something cool to baz and store it in foobar 
     return foobar 
    # etc... 

然後:

def my_view(request): 
    foo = ProcessFooInformation(request) 
    # use foo in whatever way and return a response 
    return render(request, 'foobar.html', {'foo':foo}) 

我還做這更

這可以很容易地通過使該處理信息類來實現通過使用屬性的懶惰評估來提高效率。

我改編自lazy property evaluation recipe和意見或建議寫一個包裝:

def lazy_prop(func): 
    def wrap(self, *args, **kwargs): 
     if not func.__name__ in self.__dict__: 
      self.__dict__[func.__name__] = func(self, *args, **kwargs) 
     return self.__dict__[func.__name__] 
    return property(wrap) 

這每個實例評估方法包裹的價值只有一次,並使用在後續調用存儲的值。如果屬性評估緩慢,這很有用。

+0

如果您認爲有更好的方法,請發表一個答案。 – Umang