はじめに
DjangoのFixtureでdjango.contrib.authのUserやGroupにPermissionを設定する方法を確認しました。
パーミッションの作成
まずは適当なパーミッション をModel.Meta.permissionsで作成します。
myapp
アプリの MyPermission
モデルに perm1
と perm2
を用意しました。
class MyPermission(models.Model): class Meta: managed = False default_permissions = () permissions = ( ('perm1', '権限1'), ('perm2', '権限2'), )
マイグレーションすると、以下の通りPermissionモデルに perm1
と perm2
が追加されています。
$ python manage.py makemigrations $ python manage.py migrate $ python manage.py dbshell sqlite> .header on sqlite> select * from auth_permission where codename == 'perm1' or codename == 'perm2'; id|content_type_id|codename|name 33|9|perm1|権限1 34|9|perm2|権限2
ユーザの作成
以下のように model
に auth.user
、 pk
に1からインクリメントした数値、 fields
にユーザの情報を設定すればユーザを登録できます。
[ { "model":"auth.user", "pk":1, "fields":{ "last_name":"テスト", "first_name":"ユーザ", "email":"foo@example.com", "username":"foo@example.com" } } ]
では権限をどのようにして割り当てるかというと、user_permissionsフィールドに Permissionオブジェクトのキーを指定することになります。
"fields":{ ... "user_permissions": [...] }
しかしPermissionオブジェクトの id
値はマイグレーション時に動的に決定されるため推測することは困難です。
例えば上記で作成した権限 perm1
と perm2
の id
はそれぞれ 33
と 34
です。
ではどうするかというと、 id
値の代わりにナチュラルキーを使用します。
まさにこのような場面を想定し、Djangoはモデルのシリアライズでナチュラルキーを使用する仕組みを実装しています。
PermissionManagerには get_by_natural_key
が実装されているため、静的な情報である codename
、 app_label
および model
でオブジェクトを特定することができます。
class PermissionManager(models.Manager): use_in_migrations = True def get_by_natural_key(self, codename, app_label, model): return self.get( codename=codename, content_type=ContentType.objects.db_manager(self.db).get_by_natural_key(app_label, model), )
例えば perm1
の権限を与える場合には、 user_permissions
に ["perm1", "myapp", "mypermission"]
を指定すれば良いわけです。なお model
は小文字で指定する必要があります。
[ { "model":"auth.user", "pk":1, "fields":{ "last_name":"テスト", "first_name":"ユーザ", "email":"foo@example.com", "username":"foo@example.com", "user_permissions": [ ["perm1", "myapp", "mypermission"], ["perm2", "myapp", "mypermission"] ] } } ]
これで、権限を割り当てたユーザを作成することができました。
$ python manage.py loaddata auth_user.json Installed 1 object(s) from 1 fixture(s) $ python manage.py dbshell sqlite> .header on sqlite> select * from auth_user_user_permissions where user_id = 1; id|user_id|permission_id 1|1|33 2|1|34
グループの作成
グループの場合は権限のフィールド名がpermissionsに変わるだけです。
[ { "model":"auth.group", "pk":1, "fields":{ "permissions":[ ["perm1", "myapp", "mypermission"], ["perm2", "myapp", "mypermission"] ], "name":"テストグループ" } } ]