| | 77 | |
|---|
| | 78 | Let's create a simple role-based implementation of has_permission that allows |
|---|
| | 79 | change and delete access to the creator of an object, but denies access to |
|---|
| | 80 | everyone else. The creator is just a foreign key from the object in question |
|---|
| | 81 | to the django.contrib.auth.models.User model. |
|---|
| | 82 | |
|---|
| | 83 | First, we create the actual implementation. |
|---|
| | 84 | |
|---|
| | 85 | >>> def is_creator(user, permission, object): |
|---|
| | 86 | ... if user.is_superuser: |
|---|
| | 87 | ... return True |
|---|
| | 88 | ... # if no object was provided, fall back to Model level permissions |
|---|
| | 89 | ... if not object: |
|---|
| | 90 | ... return permission in user.user_permissions.select_related() |
|---|
| | 91 | ... return user == object.creator |
|---|
| | 92 | ... |
|---|
| | 93 | |
|---|
| | 94 | |
|---|
| | 95 | The we register is_creator to handle calls to has_permission for the |
|---|
| | 96 | appropriate models (in this case User, Permision, and Article). |
|---|
| | 97 | |
|---|
| | 98 | >>> from django.contrib.auth.models import User, Permission |
|---|
| | 99 | >>> from django.contrib.auth import has_permission |
|---|
| | 100 | >>> from regressiontests.generic_auth.models import Article |
|---|
| | 101 | |
|---|
| | 102 | >>> has_permission.register(is_creator, User, Permission, Article) |
|---|
| | 103 | |
|---|
| | 104 | |
|---|
| | 105 | Create an Article for our tests, and set it's `owner` attribute to the user we |
|---|
| | 106 | created above. |
|---|
| | 107 | |
|---|
| | 108 | >>> article = Article(name='test', body='test', creator=user) |
|---|
| | 109 | >>> article.save() |
|---|
| | 110 | |
|---|
| | 111 | |
|---|
| | 112 | Set up some convenient reverences to the various permission objects. |
|---|
| | 113 | |
|---|
| | 114 | >>> add_permission = Article._meta.get_add_permission() |
|---|
| | 115 | >>> change_permission = Article._meta.get_change_permission() |
|---|
| | 116 | >>> delete_permission = Article._meta.get_delete_permission() |
|---|
| | 117 | |
|---|
| | 118 | Adding isn't tied to a particular object, and we haven't given the user |
|---|
| | 119 | permission to add Articles yet, so this should fail. |
|---|
| | 120 | |
|---|
| | 121 | >>> has_permission(user, add_permission) |
|---|
| | 122 | False |
|---|
| | 123 | |
|---|
| | 124 | But the user *is* the creator of `article`, so they *should* have change and |
|---|
| | 125 | delete permissions for that article. |
|---|
| | 126 | |
|---|
| | 127 | >>> has_permission(user, change_permission, article) |
|---|
| | 128 | True |
|---|
| | 129 | >>> has_permission(user, delete_permission, article) |
|---|
| | 130 | True |
|---|
| | 131 | |
|---|
| | 132 | |
|---|
| | 133 | Give the user add Article permissions. |
|---|
| | 134 | |
|---|
| | 135 | >>> user.user_permissions.add(add_permission) |
|---|
| | 136 | >>> user.save() |
|---|
| | 137 | |
|---|
| | 138 | |
|---|
| | 139 | Make sure it worked. |
|---|
| | 140 | |
|---|
| | 141 | >>> has_permission(user, add_permission, article) |
|---|
| | 142 | True |
|---|
| | 143 | |
|---|
| | 144 | |
|---|