0

Our team is building an app that requires easy switching between user subclasses. Each user role has different fields, so they don't need to carry over, but each User instance should be attached to one of these subcalsses.

What is the most idiomatic way of switching these roles? Should we even be using subclasses in the first place?

I have seen these pages: Convert a subclass model instance to another subclass model instance in django? Change class of child on django models

We are pre-prod, and therefore open to changing schema if there is a better approach, unlike these two examples.

Community
  • 1
  • 1
mde
  • 3
  • 3
  • Why didnt you use django's own `permissions` framework which will enable you to create a group and `assign permissions to groups`, then add a user to group that user can have permission on models and you can check permission using permission_requited decorator or mixin? – cutteeth Nov 04 '16 at 08:41
  • Permissions aren't the only thing that differs. There are some components in one subclass that don't appear in others, which link these subclasses to specific tables in the schema. It seems like this would not solve our issue. – mde Nov 04 '16 at 20:51

1 Answers1

0

If you are okay with having a custom User model, you may achieve this by using GenericForeignKey.

You can have a single User model with common attributes/behaviour and multiple models that implement behaviour associated with those roles. So if you need to change said role for a User, you could just delete old related instance of one model and create an instance of another.

class CustomUser(AbstractUser):
    role_ct = models.ForeignKey(ContentType, on_delete=models.CASCADE)
    role_id = models.PositiveIntegerField()
    role = GenericForeignKey

class Role1(models.Model):
    """Some stuff here"""

class Role2(models.Model):
    """Some other stuff here"""

However, be aware of the caveats: GenericForeignKeys may be slightly slower and slightly harder to operate.

If that seems like an overkill for your case, you can just go with django admin permissions, as suggested by cutteeth.

Community
  • 1
  • 1