0

私はdjango-guardianを使用しており、外部キーに直接接続されていない3つのテーブルがあります。Guardian_groupobjectpermission テーブルは、object_pk <-> table.pk によって任意のテーブルと接続できます。Auth_persmission には codename フィールドがあります。テーブルスキームの画像を見てください:

テーブルスキーム

codename = 'can_view' を持つ pybb_forum テーブルからデータを取得する必要があります。

SQL では、このクエリは次のようになります。

mysql> select * from pybb_forum as ff join guardian_groupobjectpermission as gg on ff.id = gg.object_pk join auth_permission as pp on gg.permission_id = pp.id where codename = 'view_forum';

しかし、django ORMを使用してこのクエリを作成する必要があるかどうかはわかりません。出来ますか ?

何かのようなもの

Forum.objects.filter(groupobjectpermission__permission__codename='view_forum')

?

モデルコードは次のとおりです。

# django auth permission model:
class Permission(models.Model):
    name = models.CharField(_('name'), max_length=50)
    content_type = models.ForeignKey(ContentType)
    codename = models.CharField(_('codename'), max_length=100)

# guardian group permission model
class GroupObjectPermissionBase(BaseObjectPermission):
    permission = models.ForeignKey(Permission)
    content_type = models.ForeignKey(ContentType)
    object_pk = models.CharField(_('object ID'), max_length=255)
    content_object = GenericForeignKey(fk_field='object_pk')
    group = models.ForeignKey(Group) # reference to django group

class Forum(models.Model):
    name = models.CharField(_('Name'), max_length=80, default='')
    slug = models.SlugField(default='', unique=True)
    hidden = models.BooleanField(_('Hidden'), blank=False, null=False, default=False)
    headline = models.TextField(_('Headline'), blank=True, null=True)

    class Meta(object):
        permissions = (
           ('view_forum', 'Only view forum'),
    )
4

2 に答える 2

0

もう1つの解決策を見つけました。djangoはジェネリック関係フィールド間の接続を処理できます。 http://docs.djangoproject.com/en/dev/ref/contrib/contenttypes/#reverse-generic-relations

そのため、フォーラム モデルにもう 1 つの属性を追加する必要があります。

  permissions =  generic.GenericRelation(GroupObjectPermission, object_id_field='object_pk') 

またはモンキーパッチを実行します:

 Forum.add_to_class('permissions', generic.GenericRelation(GroupObjectPermission, object_id_field='object_pk'))

 Forum.objects.all()[0].permissions.all() 

現在のフォーラムのすべての権限を返します

于 2013-08-16T22:57:57.800 に答える
0

私の場合、JOINS を使用せずに SQL クエリを書き直して、WHERE に置き換えます。

 SELECT * FROM pybb_forum as ff,guardian_groupobjectpermission as gg, 
           auth_permission as pp  
     WHERE codename = 'view_forum'      
     AND gg.group_id in (1,2,3)     
     AND gg.content_type_id = 9 
     AND  ff.id = gg.object_pk 
     AND gg.permission_id = pp.id;

そして今、extra を使用して ORM クエリを簡単に作成できます。

 Forum.objects.extra(
    tables = ['guardian_groupobjectpermission', 'auth_permission'],
    where = [
      """ codename = "view_forum"
      AND guardian_groupobjectpermission.group_id in (1,2,3)
      AND guardian_groupobjectpermission.content_type_id = 9
      AND pybb_forum.id = guardian_groupobjectpermission.object_pk
      AND guardian_groupobjectpermission.permission_id = auth_permission.id"""
    ])

しかし、そのようなクエリは、他の開発者にとって読みにくいものです:(

于 2013-08-15T20:34:14.213 に答える