1

So I have the following:

Person - first_name, last_name

Puzzle - puzzle_name

Level - (bronze, silver, gold)

Persons can have permissions to various Puzzles, and then have permissions to various levels at those puzzles.

So on puzzle1, you can have silver level and On puzzle2 you can have bronze level. Etc.

How do I do this with django's permissions? I was looking at django-guardian, but I have no idea how to do it.

Limon Monte
  • 52,539
  • 45
  • 182
  • 213
petFoo
  • 407
  • 1
  • 6
  • 16

1 Answers1

2

A single Puzzle model should be enough for that. The default User model already has first and last name fields. The levels would be the permissions.

Hope this helps:

In some models.py:

from django.db import models


BRONZE_LEVEL = 'access_to_bronze_level_puzzle'
SILVER_LEVEL = 'access_to_silver_level_puzzle'
GOLD_LEVEL = 'access_to_gold_level_puzzle'


class Puzzle(models.Model):
    name = models.Charfield(max_length=30)

    class Meta:
        permissions = (
            (BRONZE_LEVEL, 'Can play the puzzle in bronze level'),
            (SILVER_LEVEL, 'Can play the puzzle in silver level'),
            (GOLD_LEVEL, 'Can play the puzzle in gold level'),
        )

With django's built-in permissions this will allow you to give access to the gold level in ALL the puzzles to a given user (or group of users).

If you want to have individual level restrictions for each of the puzzle instances you need an external app. django-guardian is indeed appropriate.

To set up guardian in your project add the following in settings.py:

# The auth middleware:

AUTHENTICATION_BACKENDS = (
    'django.contrib.auth.backends.ModelBackend',  # default
    'guardian.backends.ObjectPermissionBackend',  # django-guardian per object permissions
)

# Add 'guardian' to `INSTALLED_APPS`.
INSTALLED_APPS = (
    # All the other apps
    # ...
    'guardian',
)

# Define the ID for the anonymous user
# Required because guardian supports permissions for users not logged in
ANONYMOUS_USER_ID = -1`

Now, after a manage.py syncdb (or migrate in case you're using south), everything should be ok. You can assign or remove access to users or groups with:

from guardian.shortcuts import assign_perm, remove_perm
from yourapp.models import BRONZE_LEVEL, SILVER_LEVEL, GOLD_LEVEL


assign_perm(GOLD_LEVEL, some_user_instance, some_puzzle_instance)
remove_perm(GOLD_LEVEL, some_group_instance, some_puzzle_instance)
Adrián
  • 6,135
  • 1
  • 27
  • 49
  • Thank you! Now how do I list out what puzzles a user has access to at each level? – petFoo Sep 23 '13 at 14:26
  • @petFoo You have that answered from the main django-guardian author itself [here](http://stackoverflow.com/questions/4663694/how-can-i-get-all-objects-a-user-has-specific-permissions-to-in-django-guardian) – Adrián Sep 23 '13 at 16:13
  • In case anyone is trying to do this, it seems assign_perm actually works this way: assign_perm(GOLD_LEVEL, some_user_instance, some_puzzle_instance) – petFoo Sep 23 '13 at 22:23
  • @petFoo my bad, fixed – Adrián Sep 23 '13 at 23:42