Extend django Groups and Permissions
Asked Answered
O

1

12

I've been searching Google and Stackoverflow for the last 3 days now and couldn't find anything similar. I'd like to extend or use the django groups and permissions.

Let's say we got some Projects with different Teams and Users.

class Project(models.Model):
    owner = models.ForeignKey(User)
    name = models.CharField(max_length=100)

class Team(models.Model):
    project = models.ForeignKey(Project)
    members = models.ManyToManyField(User)
    name = models.CharField(max_length=100)
    permission = models.ManyToManyField(Permission)

Now - everything's fine. Now what I want is to extend the existing Auth.Group delivered by django so I could use request.user.has_perm... the direct way.

So, let's change the Team-Model into

class Team(Group):
    project = models.ForeignKey(Project)
    members = models.ManyToManyField(User)

This extends the existing Group. The name and permissions field comes direct from the Group-Model. If I create a new Team, there will be a Group added, too. That's great.

With a custom save method I could also add, that the user listed in members, will be added to the created Group and gets the permissions granted to the Team/Group.

Now my problem is, the name field of the Group is unique - so I couldn't add an Admins-Team for each Project.

I thought about adding another name-field for the frontend and generate a unique string for the name field of the Group-Model. But hmmm....is there a better solution for multiple custom Groups? Maybe one got an idea? Thank you in advance!

Ophidian answered 15/10, 2012 at 9:36 Comment(1)
This unique name constraint makes the group system very very unfortunately limiting. I am not liking it.Byler
K
6

You need to make group names unique. So one way that you found out is having another name field, making it unique for all subgroups.

Another way would be to make use of existing name field and add special chars of yours. For example group name with admin#project1, members#project1 etc. (Note: I'm not sure '#' is allowed in group name, you can choose any special character that is allowed).

So whenever you create Team you update the name field with suffix #<project_name> in Team models save() method.

To display it more sanely, you can add __unicode__() method to return only first part of the group name. Example:

class Team(Group):
    ...
    def __unicode__(self):
        try:
            return self.name.split('#')[0]
        except:
            #something wrong!
            return self.name
Kassab answered 15/10, 2012 at 10:9 Comment(4)
Thank you for your answer. I already thought about this posibility. But maybe it would be cleaner to split those two fields - so I got the benefit of using longer names for the Team (Groupnames are limited to 80) and easily display them without reformatting. Also I'm able to use the full group-name to handle the project/team identifier for the backend. What do you think about that?Trangtranquada
Yes, having separate fields is better and has its own advantages. However, also give thought on queries that you would use.Kassab
Thats the biggest pain I'm thinking about. I wonder no one had some similar requirement to django - I still can't find something :(Trangtranquada
One must also see this answer since Django might create another table and won't pick up extended Group model: stackoverflow.com/a/7669063Tweeny

© 2022 - 2024 — McMap. All rights reserved.