Home > Back-end >  Why can I choose only decimal multiple of 0.5 in admin panel?
Why can I choose only decimal multiple of 0.5 in admin panel?

Time:01-13

I created a model in Django with multiple choice of numbers from 0 to 14 with steps 0.1. I can see them all in the admin panel, but can choose only numbers multiple 0.5.

My model:

class SoilPh(models.Model):
    SOIL_PH_CHOICES = (
        (i / 10, str(i / 10)) for i in range(MAX_PH_LEVEL * 10   1)
    )
    name = models.DecimalField(
        max_digits=2,
        decimal_places=1,
        validators=[
            MinValueValidator(0, '0'),
            MaxValueValidator(MAX_PH_LEVEL, f'{MAX_PH_LEVEL}')
        ],
        choices=SOIL_PH_CHOICES,
        unique=True,
        null=True,
    )


class Deciduous(Plant):
    soil_ph = models.ManyToManyField(
        SoilPh,
        related_name='soil_ph',
    )

Error: Select a valid choice. 0.3 is not one of the available choices.

Where is my mistake?

CodePudding user response:

SOIL_PH_CHOICES is a generator expression.

You are assigning it to choices

SOIL_PH_CHOICES = ((i / 10, str(i / 10)) for i in range(MAX_PH_LEVEL * 10   1))

if you want to see the values present in SOIL_PH_CHOICES, we can use list comprehension and change the value of MAX_PH_LEVEL from 0 to 14.

When MAX_PH_LEVEL = 0:

[(i / 10, str(i / 10)) for i in range(0 * 10   1)]
#output
[(0.0, '0.0')]

When MAX_PH_LEVEL = 14:

[(i / 10, str(i / 10)) for i in range(14 * 10   1)]
#output
[(0.0, '0.0'), (0.1, '0.1'), (0.2, '0.2'), (0.3, '0.3'), (0.4, '0.4'), (0.5, '0.5'), (0.6, '0.6'), (0.7, '0.7'), (0.8, '0.8'), (0.9, '0.9'), (1.0, '1.0'), (1.1, '1.1'), (1.2, '1.2'), (1.3, '1.3'), (1.4, '1.4'), (1.5, '1.5'), (1.6, '1.6'), (1.7, '1.7'), (1.8, '1.8'), (1.9, '1.9'), (2.0, '2.0'), (2.1, '2.1'), (2.2, '2.2'), (2.3, '2.3'), (2.4, '2.4'), (2.5, '2.5'), (2.6, '2.6'), (2.7, '2.7'), (2.8, '2.8'), (2.9, '2.9'), (3.0, '3.0'), (3.1, '3.1'), (3.2, '3.2'), (3.3, '3.3'), (3.4, '3.4'), (3.5, '3.5'), (3.6, '3.6'), (3.7, '3.7'), (3.8, '3.8'), (3.9, '3.9'), (4.0, '4.0'), (4.1, '4.1'), (4.2, '4.2'), (4.3, '4.3'), (4.4, '4.4'), (4.5, '4.5'), (4.6, '4.6'), (4.7, '4.7'), (4.8, '4.8'), (4.9, '4.9'), (5.0, '5.0'), (5.1, '5.1'), (5.2, '5.2'), (5.3, '5.3'), (5.4, '5.4'), (5.5, '5.5'), (5.6, '5.6'), (5.7, '5.7'), (5.8, '5.8'), (5.9, '5.9'), (6.0, '6.0'), (6.1, '6.1'), (6.2, '6.2'), (6.3, '6.3'), (6.4, '6.4'), (6.5, '6.5'), (6.6, '6.6'), (6.7, '6.7'), (6.8, '6.8'), (6.9, '6.9'), (7.0, '7.0'), (7.1, '7.1'), (7.2, '7.2'), (7.3, '7.3'), (7.4, '7.4'), (7.5, '7.5'), (7.6, '7.6'), (7.7, '7.7'), (7.8, '7.8'), (7.9, '7.9'), (8.0, '8.0'), (8.1, '8.1'), (8.2, '8.2'), (8.3, '8.3'), (8.4, '8.4'), (8.5, '8.5'), (8.6, '8.6'), (8.7, '8.7'), (8.8, '8.8'), (8.9, '8.9'), (9.0, '9.0'), (9.1, '9.1'), (9.2, '9.2'), (9.3, '9.3'), (9.4, '9.4'), (9.5, '9.5'), (9.6, '9.6'), (9.7, '9.7'), (9.8, '9.8'), (9.9, '9.9'), (10.0, '10.0'), (10.1, '10.1'), (10.2, '10.2'), (10.3, '10.3'), (10.4, '10.4'), (10.5, '10.5'), (10.6, '10.6'), (10.7, '10.7'), (10.8, '10.8'), (10.9, '10.9'), (11.0, '11.0'), (11.1, '11.1'), (11.2, '11.2'), (11.3, '11.3'), (11.4, '11.4'), (11.5, '11.5'), (11.6, '11.6'), (11.7, '11.7'), (11.8, '11.8'), (11.9, '11.9'), (12.0, '12.0'), (12.1, '12.1'), (12.2, '12.2'), (12.3, '12.3'), (12.4, '12.4'), (12.5, '12.5'), (12.6, '12.6'), (12.7, '12.7'), (12.8, '12.8'), (12.9, '12.9'), (13.0, '13.0'), (13.1, '13.1'), (13.2, '13.2'), (13.3, '13.3'), (13.4, '13.4'), (13.5, '13.5'), (13.6, '13.6'), (13.7, '13.7'), (13.8, '13.8'), (13.9, '13.9'), (14.0, '14.0')]

Now, you can compare and check your values.

CodePudding user response:

I changed DecimalField to FloatField and now it works.

class SoilPh(models.Model):
    SOIL_PH_CHOICES = (
        (i / 10, str(i / 10)) for i in range(MAX_PH_LEVEL * 10   1)
    )
    name = models.FloatField(
        validators=[
            MinValueValidator(0, '0'),
            MaxValueValidator(MAX_PH_LEVEL, f'{MAX_PH_LEVEL}')
        ],
        choices=SOIL_PH_CHOICES,
        unique=True,
        null=True,
    )


class Deciduous(Plant):
    soil_ph = models.ManyToManyField(
        SoilPh,
        related_name='soil_ph',
    )

But who can explain what is the problem with DecimalField?

  • Related