Skip to content
Permalink
Browse files

[FIX] base: check that the state matches the country at partner create

Import a list of partners with their addresses.
The state_id field is usually filled with the state codes.
E.g. 'CA' is used for California, but also for Cádiz (Spain), etc.
The import function (db_id_for) uses a name_search on the res.country.state,
and takes the first matching result.
It follows that the state does not necessarily match the country.

Therefore we add a _check_import_consistency in the create.
Here we check that the country matches the state's country,
try to find a correct match, and if we can't we put the state to False.
Note that if the country is not set both fields will end up set to False:
this is because only a state would mean using a code could give an abitrary
country.

opw 1943904

closes #31599

Signed-off-by: Nans Lefebvre (len) <len@odoo.com>
  • Loading branch information...
len-odoo committed Mar 5, 2019
1 parent 4b8e0d8 commit 215c4a6b5d71c56315f09ce388a8316b76a3a23e
Showing with 22 additions and 0 deletions.
  1. +22 −0 odoo/addons/base/models/res_partner.py
@@ -543,6 +543,8 @@ def write(self, vals):

@api.model_create_multi
def create(self, vals_list):
if self.env.context.get('import_file'):
self._check_import_consistency(vals_list)
for vals in vals_list:
if vals.get('website'):
vals['website'] = self._clean_website(vals['website'])
@@ -864,6 +866,26 @@ def get_import_templates(self):
'template': '/base/static/xls/res_partner.xls'
}]

@api.model
def _check_import_consistency(self, vals_list):
"""
The values created by an import are generated by a name search, field by field.
As a result there is no check that the field values are consistent with each others.
We check that if the state is given a value, it does belong to the given country, or we remove it.
"""
States = self.env['res.country.state']
states_ids = {vals['state_id'] for vals in vals_list if vals.get('state_id')}
state_to_country = States.search([('id', 'in', list(states_ids))]).read(['country_id'])
for vals in vals_list:
if vals.get('state_id'):
country_id = next(c['country_id'][0] for c in state_to_country if c['id'] == vals.get('state_id'))
state = States.browse(vals['state_id'])
if state.country_id.id != country_id:
state_domain = [('code', '=', state.code),
('country_id', '=', country_id)]
state = States.search(state_domain, limit=1)
vals['state_id'] = state.id # replace state or remove it if not found

@api.multi
def _get_country_name(self):
return self.country_id.name or ''

0 comments on commit 215c4a6

Please sign in to comment.
You can’t perform that action at this time.