Need help in django model

Viewed 49

I have written a model for my django project. This is my model

    from django.utils.translation import ugettext_lazy as _
from django.db import models
from django.utils.crypto import get_random_string
from django.db import models
from django.contrib.auth.models import(
                                        BaseUserManager,
                                        AbstractBaseUser,
                                        PermissionsMixin,
                                        )


def generate_vid():
    """Generates a vid for the users"""
    not_unique = True
    while not_unique:
        vid = get_random_string(10, 'abcdefg0123456789')
        if not User.objects.filter(v_id = vid).exists():
            not_unique=False

        return vid


class UserManager(BaseUserManager):
    """Model for user manager"""

    def create_user(self, username, password, **params):
        """Create and return a user"""
        u_type = params.pop('usertype','v')
        params.update({'usertype':u_type})
        p_username = params.pop('parent_username', 0)

        if(u_type=='v'):
            pass

        else:
            parent_id = User.objects.filter(username = p_username).values_list('v_id')
            params.update({'parent_id': parent_id})

        user = self.model(username=username, **params)
        user.set_password(password)
        user.save(using=self._db)

        return user

    def create_superuser(self, username, password, **params):
        """Create and return a user"""
        params.setdefault('is_staff',True)
        params.setdefault('is_superuser',True)
        params.setdefault('is_active',True)

        if params.get('is_staff') is not True:
            raise ValueError(_('Superuser must have is_staff=True.'))
        if params.get('is_superuser') is not True:
            raise ValueError(_('Superuser must have is_superuser=True.'))
        return self.create_user(username, password, **params)



class User(AbstractBaseUser, PermissionsMixin):
    """Models for user"""

    v_id = models.CharField(
                            max_length=10,
                            default=generate_vid,
                            primary_key = True,
    )

    username = models.CharField(max_length=20, unique=True)
    email = models.EmailField(blank=True, unique = True)
    parent_id = models.ForeignKey('User', on_delete=models.SET_DEFAULT, default=0)
    usertype = models.CharField(max_length=1, choices=[('f', 'family'), ('v', 'veteran')])


    REQUIRED_FIELDS = ['usertype']
    is_staff = models.BooleanField(default=False)
    is_active = models.BooleanField(default=True)
    USERNAME_FIELD = 'username'
    objects = UserManager()

    def __str__(self):
        return self.username

Now I want to impose the condition while creating a user such that every time I provide usertype=f, and I provide a username(say username='Test") the parent_id of that particular entry is automatically set as the v_id of the username provided. The parent_id is a self referential foreignkey.

This is the error showing while testing the feature

    File "/py/lib/python3.9/site-packages/rest_framework/serializers.py", line 205, in save
    self.instance = self.create(validated_data)
File "/app/user/serializers.py", line 17, in create
    return get_user_model().objects.create_user(**validated_data)
File "/app/base/models.py", line 39, in create_user
    user = self.model(username=username, **params)
File "/py/lib/python3.9/site-packages/django/db/models/base.py", line 485, in __init__
    _setattr(self, field.name, rel_obj)
File "/py/lib/python3.9/site-packages/django/db/models/fields/related_descriptors.py", line 215, in __set__
    raise ValueError(
ValueError: Cannot assign "<QuerySet []>": "User.parent_id" must be a "User" instance.
1 Answers

I think you can try signals to set data after creating a user account. You can choose from several types, but I would recommend you focus on pre_save and post_save.

UPDATE

I wrote examples, but the website will probably better illustrate it. In general, there are quite a few signals, but the most commonly used are pre_save and post_save.

#2 UPDATE

Try use a first or latest. Details in documentation.

parent_id = User.objects.filter(username = p_username).first()
Related