2017-07-29 71 views
0

我想要簡單的方法來檢查是否有人是postproposal等的所有者或管理員,他正在嘗試編輯\ delete。Django(drf)動態權限從BasePermission

所以,每次我用IsAuthenticated許可,並在ModelViewSet的方法,我得到的實例和時間是否instance.author或有時是誰要求它(在某些對象是request.user == instance.authorrequest.user == instance.owner)的用戶。

問題

的主要問題是:我怎麼可以創建許可類,它可以檢查這種動態用戶擁有對實例屬性的名字嗎?

一礦的解決方案(不是最好的,我認爲)

我創建功能需要用戶屬性實例名稱返回權限類:

def is_owner_or_admin_permission_factory(owner_prop_name): 
    class IsOwnerOrAdmin(BasePermission): 
     def has_permission(self, request, view, *args, **kwargs): 
      instance = view.get_object() 
      try: 
       owner = getattr(instance, owner_prop_name) 
      except AttributeError: 
       return False 
      return (
       request.user and request.user.id and (owner == request.user or request.user.is_staff) 
      ) 

    return IsOwnerOrAdmin 

回答

0

我也一直在受挫幾天之後的確切問題,並且在處理具有用戶屬性的不同查找名稱的多個模型時,我設法找到了適合的解決方法(至少對我來說當然是這樣)。

解決方法是這樣的,在ModelViewSet定義一個單獨的屬性user_lookup_kwarg在視圖中,它可以用於檢查適當的權限。

例如,

class YourViewSet(viewsets.ModelViewSet): 
    queryset = YourModel.objects.all() 
    serializer_class = YourSerializer 
    user_lookup_kwarg = 'user' #or 'account/created_by' whatever. 

現在,你permission_class會有點像這樣,

class CustomPermission(BasePermission): 

    def has_object_permission(self, request, view, obj): 
     try: 
      return request.user.is_superuser or getattr(obj, view.user_lookup_kwarg) == request.user 
     except: 
      pass 
     return request.user.is_superuser 

你只只需要重寫has_object_permission()方法來檢查實例級別的權限。

+0

這對我來說完美無缺!再次感謝! – Dionid

+0

有一點:當你檢查'request.user.is_superuser'和它的返回'True'時,它將從方法返回,如果它是'False'並且第二個參數產生異常,你可以返回'False',因爲'request .user.is_superuser'必須已經是'False'。 – Dionid

+0

另外,我認爲最好檢查用戶是否被授權,因爲(在大多數情況下)'AnonymousUser'不能是對象的所有者,所以他需要被授權。 – Dionid