Search code examples
pythondjangodjango-modelsdjango-migrations

Avrage rating calculation not working after migration django


My code was doing what it should before the migration of calculating the avrage rating. After a migration it just dident calculate the avrage rating. It seems like the migration dident notice the code i had in choices= RATINGS) . Anyone got any idea how i can fix it and get the code to notice the choices again? Since it worked fine when testing it just before migrations.

code from model.py

class Product(models.Model):
    category = models.ForeignKey('Category', null=True, blank=True, on_delete=models.SET_NULL)
    sku = models.CharField(max_length=254, null=True, blank=True)
    name = models.CharField(max_length=254)
    description = models.TextField()
    has_sizes = models.BooleanField(default=False, null=True, blank=True)
    price = models.DecimalField(max_digits=6, decimal_places=2)
    rating = models.DecimalField(max_digits=6, decimal_places=2, null=True, blank=True)
    image_url = models.URLField(max_length=1024, null=True, blank=True)
    image = models.ImageField(null=True, blank=True)

    def __str__(self):
        return self.name

    def get_rating(self):
        reviews_total = 0

        for review in self.reviews.all():
            reviews_total += review.rating

        if reviews_total > 0:
            return reviews_total / self.reviews.count()

        return 0


class Review(models.Model):
    product = models.ForeignKey(Product, related_name='reviews', on_delete=models.CASCADE)
    rating = models.IntegerField(default=3)
    content = models.TextField()
    created_by = models.ForeignKey(User, related_name='reviews', on_delete=models.CASCADE)
    created_at = models.DateTimeField(auto_now_add=True)
    RATINGS = (('1 ',1),('2 ',2),
          ('3 ',3),('4 ',4),('5 ',5))
    rating = models.CharField(max_length=7,choices= RATINGS)

    def __str__(self):
        return '%s - %s' % (self.product.name, self.created_by)

code in the migration file:

class Migration(migrations.Migration):

    dependencies = [
        ('products', '0004_review'),
    ]

    operations = [
        migrations.AlterField(
            model_name='review',
            name='rating',
            field=models.CharField(choices=[('1 ', 1), ('2 ', 2), ('3 ', 3), ('4 ', 4), ('5 ', 5)], max_length=7),
        ),
    ]

And this a snippet of the migration after i notice the avrage rating was gone even tho the code was same after migration in models.py:

enter image description here


Solution

  • As @Willem said in comment, you cannot sum Charfield, because if you want to add:

    '1' + '1'
    

    You will get:

    '11'
    

    The problem is that you changed this:

    rating = models.IntegerField(default=3)
    

    To that:

    RATINGS = (('1 ', 1), ('2 ', 2), ('3 ', 3), ('4 ', 4), ('5 ', 5))
    rating = models.CharField(max_length=7,choices= RATINGS)
    

    And you didn't even delete the old one.

    If you want it to work, change it to:

    class Review(models.Model):
        ...
        RATINGS = ((1, '1'), (2, '2'), (3, '3'), (4, '4'), (5, '5'))
        rating = models.IntegerField(default=RATINGS[2], choices=RATINGS)
    

    Be aware, that the first should be integer one, and the second can be as string.