2011-12-30 1 views
0

DVD/BDをデータベースに保存するDjangoベースのムービーコレクションを作成しています。アプリケーションは、これらのムービーをアーカイブに保存します。ユーザーは1つのアーカイブを持つことができますが、複数のユーザーがアーカイブを使用できます(たとえば、家族は同じアーカイブを共有できます)。そして、Djangoモデルと同じ:ユーザーのみが映画やユーザーのアーカイブに属するその他の情報を見ることができることを、確認してくださいすることをお勧めDjangoのユーザーIDに基づいてコンテンツをフィルタリングするベストプラクティスはありますか?

class UserProfile(models.Model): 
    user = models.ForeignKey(User, unique=True) 
    archive = models.ForeignKey(Archive, blank=True, null=True) 

class Archive(models.Model): 
    name = models.CharField(max_length=200) 

class Movie(models.Model): 
    archive = models.ForeignKey(Archive) 
    title = models.CharField(max_length=200, null=True, blank=True) 

は何ですか?

もちろん、filter()はジョブを実行しますが、すべてのビューに対して1回だけ行われるようにフィルタリングする方法はありますか?ミドルウェアは?またはデコレータ?

答えて

2

あなたのURLスタイルがちょうど/movies/some-movie/のようなものなら、@ jknuppの答え​​はおそらくあなたの最善の策ですが、もしあなたが/user/some-user/movies/some-movie/のようなものをやっているのであれば。ユーザーに属する映画だけが表示されるようにするのはビューの責任です。

いずれの場合でも、何らかの形でビューの責任がかなりあります。これは、MVCデザインパターンの自然な分割です(Djangoはゆるやかではありますが)。モデルはユーザーについて何も知らないし、知るべきでもない。すべてのシナリオでデータの格納と検索を単純に許可するのが目的です。ただし、要求は処理されているためセッションは処理されているため、セッション固有の処理(パーミッションと認証など)がそこに属しているため、ビューはユーザーを認識します。

ただし、それでもモデルに作業負荷をかけられないというわけではありません。私の提案は、特定のユーザのためにアイテムをフィルタリングするカスタムマネージャメソッドを作成し、それをあなたのビューで使用できるようにすることです。たとえば、次のように管理方法はかなり単純化され、それはまだあなたが映画のアーカイブ外部キーを介してユーザに照会しなければならない知識を必要とし、知識のそのタイプは、モデル/マネージャーの範囲であることを、確かに

class MovieQuerySet(models.query.QuerySet): 
    def allowed_for_user(self, user): 
     return self.filter(archive__user=user) 

class MovieManager(models.Manager): 
    use_for_related_fields = True 

    def get_query_set(self): 
     return MovieQuerySet(self.model) 

    def allowed_for_user(self, *args, **kwargs): 
     return self.get_query_set().allowed_for_user(*args, **kwargs) 

class Movie(models.Model): 
    ... 
    objects = MovieManager() 

。あなたの見解では、あなたはただしなければならないでしょう:

movies = Movie.objects.allowed_for_user(request.user) 
関連する問題