0

i have adminprofile and userprofile models, i made restapi to update fields inside them when i use it with the userprofile it works , but with admin profile it give me this erorr error :

**Code Details 401 Undocumented Error: Unauthorized Response body Download { "detail" : "The user is invalid" } **

#inside model.py


class CustomAccountManager(BaseUserManager):

    def create_superuser(self, email, username, password, **other_fields):

        other_fields.setdefault('is_staff', True)
        other_fields.setdefault('is_superuser', True)
        other_fields.setdefault('is_active', True)

        if other_fields.get('is_staff') is not True:
            raise ValueError(
                'Superuser must be assigned to is_staff=True.')
        if other_fields.get('is_superuser') is not True:
            raise ValueError(
                'Superuser must be assigned to is_superuser=True.')

        return self.create_user(email, username, password, **other_fields)

    def create_user(self, email, username, password, **other_fields):

        if not email:
            raise ValueError(_('You must provide an email address'))

        email = self.normalize_email(email)
        user = self.model(email=email, username=username,password=None,**other_fields)
        other_fields.setdefault('is_normal', False)
        other_fields.setdefault('is_patient', False)
        other_fields.setdefault('is_farmer', False)
        other_fields.setdefault('is_suffer_heart', False)
        other_fields.setdefault('is_suffer_kidney', False)
        user.set_password(password)
        user.save(using=self._db)
        return user



def upload_to(instance,filename):
    return 'users_api/{filename}'.format(filename=filename)

def validate_phone_number(value):
    if not re.match(r"^01[0125]{1}", value):
        raise ValidationError("Phone number must start with 010 or 011 or 012 or 015")

    if not re.match(r"^\d{11}$", value):
        raise ValidationError("Phone number must be 11 numbers")

class CustomUser(AbstractBaseUser, PermissionsMixin):

    email = models.EmailField(_('email address'), unique=True)
    username = models.CharField(max_length=150)
    password= models.CharField(max_length=20)
    created_at = models.DateTimeField(default=timezone.now)
    is_staff = models.BooleanField(default=False)
    is_active = models.BooleanField(default=True)
    is_normal = models.BooleanField(default=False)
    is_patient = models.BooleanField(default=False)
    is_farmer = models.BooleanField(default=False)
    
    # user_permissions = models.ManyToManyField(
    #     Permission,
    #     verbose_name=_('user permissions'),
    #     blank=True,
    #     help_text=_('Specific permissions for this user.'),
    #     related_name="+",
    # )
   

    objects = CustomAccountManager()

    USERNAME_FIELD = 'email'
    REQUIRED_FIELDS = ['username']
    class Meta:
        ordering = ('-username',)
    

    def __str__(self):
        return self.username
        
class AdminProfile(models.Model):
    user = models.OneToOneField(CustomUser, on_delete=models.CASCADE)
    address=models.CharField(max_length=150,default='45 Potress ST')
    country=models.CharField(max_length=150,default=' Egypt')
    city=models.CharField(max_length=150,default=' Tanta')
    company=models.CharField(max_length=150,default=' SmartSips')
    phone_number=models.CharField(unique=True, null=True, blank=True, max_length=11, validators=[validate_phone_number])
    profile_photo=models.ImageField(upload_to='upload_to', default='upload_to/default.png')
    def __str__(self):
        return self.user.username
    
    @property
    def email(self):
            email=self.user.email
            return email
    @property
    def username(self):
            username=self.user.username
            return username
        
    @property
    def password(self):
            password=self.user.password
            return password


#inside serializers.py


class AdminProfileSerializer(serializers.ModelSerializer):
    password = serializers.CharField(
        min_length=8, max_length=68, write_only=True)
    email=serializers.EmailField()
    username= serializers.CharField(
        max_length=80, write_only=True)
    class Meta:
       model = AdminProfile
       fields = ['phone_number','profile_photo','address','country','city','company','username','password','email' ]
    
    
    def update(self,instance,val_data):
        '''update profile for Admin'''
        password=val_data.pop('password',None)
        user=super().update(instance,val_data)
        if password :
            user.set_password(password)
            user.save()
        return user
    
    #inside views.py
    class AdminProfileUpdate(generics.UpdateAPIView):
    queryset = AdminProfile.objects.all()
    serializer_class = AdminProfileSerializer
    lookup_field = 'pk'
    permission_classes = [AllowAny]

    def update(self, request, *args, **kwargs):
        instance = self.get_object()
        serializer = self.get_serializer(instance, data=request.data, partial=True)

        if serializer.is_valid():
            serializer.save()
            return Response({"message": "admin profile updated successfully"})

        else:
            return Response({"message": "failed", "details": serializer.errors})

#inside views.py

class AdminProfileUpdate(generics.UpdateAPIView):
    queryset = CustomUser.objects.all()
    serializer_class = AdminProfileSerializer
    lookup_field = 'pk'
    # permission_classes = [AllowAny]
    permission_classes = [IsAdminUser]

    def update(self, request, *args, **kwargs):
        instance = self.get_object()
        serializer = self.get_serializer(instance, data=request.data, partial=True)

        if serializer.is_valid():
            serializer.save()
            return Response({"message": "admin profile updated successfully"})

        else:
            return Response({"message": "failed", "details": serializer.errors})

i try to add allowany permission but it does not work , i wonder if there is way to override put and patch with adminprofile.

0 Answers0