I am trying to manually render options for a select filed in a django template. When I submit the form I get an error: "Select a valid choice. That choice is not one of the available choices." The error message also asks for required fields which I have provided.

locations models.py

class Location(models.Model):
    name = models.CharField(max_length=20)
    is_source = models.BooleanField(default=False)
    is_destination = models.BooleanField(default=False)

    def __str__(self):
        return self.name

orders models.py

class Order(models.Model):
    order_number = models.IntegerField(unique=True)
    order_date = models.DateField(auto_now_add=True)
    type = models.CharField(max_length=15, choices=TYPES)
    source = models.ForeignKey(Location, default=1, on_delete=models.SET_DEFAULT, related_name='ordered_here')
    destination = models.ForeignKey(Location, default=1, on_delete=models.SET_DEFAULT, related_name='delivered_here')
    items = models.TextField()
    assigned_to = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, blank=True, on_delete=models.SET_NULL, related_name='orders_to_serve')
    customer = models.ForeignKey(settings.AUTH_USER_MODEL, null=True, blank=True, on_delete=models.SET_NULL, related_name='orders_made')
    status = models.CharField(max_length=15, choices=STATUSES)

orders forms.py

class OrderForm(ModelForm):
    source = forms.ModelChoiceField(queryset=Location.objects.filter(is_source=True))
    destination = forms.ModelChoiceField(queryset=Location.objects.filter(is_destination=True))

    class Meta:
        model = Order
        fields = ['source', 'destination', 'items']


    def save(self, commit=True):
        instance = super().save(commit=False)
        instance.order_number = math.floor(time.time())
        instance.type = 'Purchase'
        instance.customer = self.context.get('request').user
        instance.status = 'New'
        if commit:
            instance.save()

        return instance

orders create.html

<form class="" method="POST">
                {% csrf_token %}
                <h1 class='text-center'>Make an order</h1>
                <div class='row'>
                    <div class='col-md-6 px-2'>
                        <span class="fw-bold mx-2">Buy from</span>
                        <div class="control-container  border-primary d-flex align-items-center">
                            <i class="fa fa-map"></i>
                            <select class="control ms-1 flex-grow-1" type="text" name="{{form.source.html_name}}"  required >
                                {% for value,label in form.source.field.choices %}
                                <option value="{{value}}">{{label}}</option>
                                {% endfor %}
                            </select>
                        </div>
                    </div>
                    <div class='col-md-6 px-2'>
                        <span class="fw-bold mx-2">Receive in</span>
                        <div class="control-container  border-primary d-flex align-items-center">
                            <i class="fa fa-map"></i>
                            <select class="control ms-1 flex-grow-1" type="text" name="{{form.destination.html_name}}"  required >
                                {% for value,label in form.destination.field.choices %}
                                <option value="{{value}}">{{label}}</option>
                                {% endfor %}
                            </select>
                        </div>
                    </div>
                </div>
                <div class='row'>
                    <div class='col-12 px-2'>
                        <span class="fw-bold mx-2">List items (e.g. 2 X Luxaire Double Bed matress)</span>
                        <div class="control-container  border-primary d-flex align-items-center">
                            <textarea class="control ms-1 flex-grow-1" rows="10" name="{{form.items.html_name}}" placeholder='e.g. 2 X Luxaire Double Bed matress' required></textarea>
                        </div>
                    </div>
                </div>
                <button type="submit" class="btn btn-primary w-100 ">Order</button>
            </form> 

orders view.py

class OrderUpdateView(generic.edit.UpdateView):
    model = Order
    template_name = 'orders/update.html'
    context_object_name = 'order'
    form_class = OrderForm
2

There are 2 best solutions below

0
On

I have eventually solved the problem by making the customer field in the order model nullable. I also had given my textarea in the order create template a wrong field name. All is well now.

0
On

you cannot do this even if you managed to make the form ignore this error the model will raise the same error elso because you just tell him to select a value from given values ... if you wanna make it dynammic then make it as noraml CharFied()