Django Countries - unable to pre-select the right country in an edit form

671 Views Asked by At

Consider this model:

class Address(models.Model):
    line1 = models.CharField(max_length=255, db_index=True, blank=True, null=True)
    city = models.CharField(max_length=255, db_index=True, blank=True, null=True)
    state = models.CharField(max_length=255, db_index=True, blank=True, null=True)
    postcode = UppercaseCharField(max_length=64, blank=True, db_index=True, null=True)
    country = CountryField(db_index=True, blank=True, null=True)

I'm trying to populate this model using data that comes in through webhook call. I'm having trouble populating the country in two cases:

When the country is "United States" (this is what the webhook returns, I have no control over it) - django_countries does not recognize this, so I added an if condition to change "United States" to USA before creating a new Address object but, when the country is not United States, for example "Panama", I populate it directly into the model by doing this:

country = request.POST.get('country')    # returns something like "Panama"
Address.objects.create(line1=line1, city=city, state=state, country=country)

This works fine, except when I try to edit the Address form, the country field is blank, it isn't pre-selecting "Panama" from the options. I know the country field of this Address instance is a country object because I can do address_form.instance.country and it outputs Pa, if I do address_form.instance.country.name it outputs Panama. So why isn't the country field in the form pre-selecting the right Country, why does it show blank?

This is my model form:

class NewAddressForm(ModelForm):
    class Meta:
        model = Address
        fields = ['line1', 'city', 'state', 'postcode', 'country']

    def __init__(self, *args, **kwargs):
        super(NewAddressForm, self).__init__(*args, **kwargs)

This is my template [showing just the country field here]

 <div class="col-md-5">|

     {% comment %}
     COUNTRYCode: {{address_form.instance.country.code}} ---> Outputs Pa in case of Panama
     COUNTRYName: {{address_form.instance.country.name}} ---> Outputs Panama in case of Panama
     {% endcomment %}

     <div class="form-group">
         <label>{{address_form.country.label}}</label>
         {% render_field address_form.country class="form-control m-b" name="country" id="country_dropdown"%}
     </div>
 </div>
1

There are 1 best solutions below

1
On
  1. What about problem about United States: I think the best option for you to customise country names as described here.
from django.utils.translation import gettext_lazy as _

COUNTRIES_OVERRIDE = {
    'NZ': _('Middle Earth'),
    'AU': None,
    'US': {'names': [
        _('United States of America'),
        _('America'),
    ],
}
  1. Have you tried to use CountrySelectWidget like this? If no, could you try and say is it working for you correctly?
from django_countries.widgets import CountrySelectWidget

class PersonForm(forms.ModelForm):
    class Meta:
        model = models.Person
        fields = ('name', 'country')
        widgets = {'country': CountrySelectWidget()}