Stefan Rijnhart
10 years ago
8 changed files with 355 additions and 0 deletions
-
1partner_street_number/__init__.py
-
49partner_street_number/__openerp__.py
-
47partner_street_number/i18n/nl.po
-
41partner_street_number/i18n/partner_street_number.pot
-
46partner_street_number/migrations/0.1/post-migrate.py
-
1partner_street_number/model/__init__.py
-
124partner_street_number/model/res_partner.py
-
46partner_street_number/view/res_partner.xml
@ -0,0 +1 @@ |
|||||
|
from . import model |
@ -0,0 +1,49 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################## |
||||
|
# |
||||
|
# OpenERP, Open Source Management Solution |
||||
|
# This module copyright (C) 2013-2014 Therp BV (<http://therp.nl>). |
||||
|
# |
||||
|
# This program is free software: you can redistribute it and/or modify |
||||
|
# it under the terms of the GNU Affero General Public License as |
||||
|
# published by the Free Software Foundation, either version 3 of the |
||||
|
# License, or (at your option) any later version. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU Affero General Public License for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU Affero General Public License |
||||
|
# along with this program. If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################## |
||||
|
{ |
||||
|
"name": "Split street name and number", |
||||
|
"version": "0.1", |
||||
|
"author": "Therp BV", |
||||
|
"category": 'Tools', |
||||
|
"description": """ |
||||
|
This module introduces separate fields for street name and street number. |
||||
|
|
||||
|
Changes to the OpenERP datamodel |
||||
|
================================ |
||||
|
|
||||
|
- Introduce two new fields for street name and number |
||||
|
- Keep 'Street' field as a function field to return street name + number |
||||
|
- Data written to the 'Street' field will be parsed into street name and number |
||||
|
if possible. This will be performed upon installation of the module for |
||||
|
existing partners. |
||||
|
|
||||
|
Compatibility |
||||
|
============= |
||||
|
This module is compatible with OpenERP 7.0. |
||||
|
""", |
||||
|
"depends": [ |
||||
|
'base' |
||||
|
], |
||||
|
"data": [ |
||||
|
'view/res_partner.xml', |
||||
|
], |
||||
|
'installable': True, |
||||
|
} |
@ -0,0 +1,47 @@ |
|||||
|
# Translation of OpenERP Server. |
||||
|
# This file contains the translation of the following modules: |
||||
|
# * partner_street_number |
||||
|
# |
||||
|
msgid "" |
||||
|
msgstr "" |
||||
|
"Project-Id-Version: OpenERP Server 7.0\n" |
||||
|
"Report-Msgid-Bugs-To: \n" |
||||
|
"POT-Creation-Date: 2013-12-07 13:50+0000\n" |
||||
|
"PO-Revision-Date: 2013-12-07 13:50+0000\n" |
||||
|
"Last-Translator: <>\n" |
||||
|
"Language-Team: \n" |
||||
|
"MIME-Version: 1.0\n" |
||||
|
"Content-Type: text/plain; charset=UTF-8\n" |
||||
|
"Content-Transfer-Encoding: \n" |
||||
|
"Plural-Forms: \n" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: field:res.partner,street_name:0 |
||||
|
msgid "Street name" |
||||
|
msgstr "Straatnaam" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: field:res.partner,street_number:0 |
||||
|
msgid "Street number" |
||||
|
msgstr "Huisnummer" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: view:res.partner:0 |
||||
|
msgid "Number..." |
||||
|
msgstr "Nummer..." |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: view:res.partner:0 |
||||
|
msgid "Street..." |
||||
|
msgstr "Straat..." |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: view:res.partner:0 |
||||
|
msgid "{'default_parent_id': active_id, 'default_street_name': street_name, 'default_street_number': street_number, 'default_street2': street2, 'default_city': city, 'default_state_id': state_id, 'default_zip': zip, 'default_country_id': country_id, 'default_supplier': supplier, 'default_customer': customer}" |
||||
|
msgstr "{'default_parent_id': active_id, 'default_street_name': street_name, 'default_street_number': street_number, 'default_street2': street2, 'default_city': city, 'default_state_id': state_id, 'default_zip': zip, 'default_country_id': country_id, 'default_supplier': supplier, 'default_customer': customer}" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: model:ir.model,name:partner_street_number.model_res_partner |
||||
|
msgid "Partner" |
||||
|
msgstr "Relatie" |
||||
|
|
@ -0,0 +1,41 @@ |
|||||
|
# Translation of OpenERP Server. |
||||
|
# This file contains the translation of the following modules: |
||||
|
# * partner_street_number |
||||
|
# |
||||
|
msgid "" |
||||
|
msgstr "" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: field:res.partner,street_name:0 |
||||
|
msgid "Street name" |
||||
|
msgstr "" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: field:res.partner,street_number:0 |
||||
|
msgid "Street number" |
||||
|
msgstr "" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: view:res.partner:0 |
||||
|
msgid "Number..." |
||||
|
msgstr "" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: view:res.partner:0 |
||||
|
msgid "Street..." |
||||
|
msgstr "" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: view:res.partner:0 |
||||
|
msgid "" |
||||
|
"{'default_parent_id': active_id, 'default_street_name': street_name, " |
||||
|
"'default_street_number': street_number, 'default_street2': street2, " |
||||
|
"'default_city': city, 'default_state_id': state_id, 'default_zip': zip, " |
||||
|
"'default_country_id': country_id, 'default_supplier': supplier, " |
||||
|
"'default_customer': customer}" |
||||
|
msgstr "" |
||||
|
|
||||
|
#. module: partner_street_number |
||||
|
#: model:ir.model,name:partner_street_number.model_res_partner |
||||
|
msgid "Partner" |
||||
|
msgstr "" |
@ -0,0 +1,46 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################## |
||||
|
# |
||||
|
# OpenERP, Open Source Management Solution |
||||
|
# This module copyright (C) 2013-2014 Therp BV (<http://therp.nl>). |
||||
|
# |
||||
|
# @autors: Stefan Rijnhart, Ronald Portier |
||||
|
# |
||||
|
# This program is free software: you can redistribute it and/or modify |
||||
|
# it under the terms of the GNU Affero General Public License as |
||||
|
# published by the Free Software Foundation, either version 3 of the |
||||
|
# License, or (at your option) any later version. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU Affero General Public License for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU Affero General Public License |
||||
|
# along with this program. If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################## |
||||
|
import logging |
||||
|
from openerp import pooler, SUPERUSER_ID |
||||
|
|
||||
|
|
||||
|
def migrate(cr, version): |
||||
|
""" |
||||
|
Post-install script. If version is not set, we are called at installation |
||||
|
time. Because 'street' is now a stored function field, we should be able |
||||
|
to retrieve its values from the cursor. We use those to fill the new |
||||
|
name/number fields using the street field's inverse function, which does |
||||
|
a basic street name/number split. |
||||
|
""" |
||||
|
if version: |
||||
|
return |
||||
|
logging.getLogger('openerp.addons.partner_street_number').info( |
||||
|
'Migrating existing street names') |
||||
|
cr.execute( |
||||
|
'SELECT id, street FROM res_partner ' |
||||
|
'WHERE street IS NOT NULL and street_name IS NULL' |
||||
|
) |
||||
|
partner_obj = pooler.get_pool(cr.dbname)['res.partner'] |
||||
|
for partner in cr.fetchall(): |
||||
|
partner_obj.write( |
||||
|
cr, SUPERUSER_ID, partner[0], {'street': partner[1]}) |
@ -0,0 +1 @@ |
|||||
|
from . import res_partner |
@ -0,0 +1,124 @@ |
|||||
|
# -*- coding: utf-8 -*- |
||||
|
############################################################################## |
||||
|
# |
||||
|
# OpenERP, Open Source Management Solution |
||||
|
# This module copyright (C) 2013-2014 Therp BV (<http://therp.nl>). |
||||
|
# |
||||
|
# @autors: Stefan Rijnhart, Ronald Portier |
||||
|
# |
||||
|
# This program is free software: you can redistribute it and/or modify |
||||
|
# it under the terms of the GNU Affero General Public License as |
||||
|
# published by the Free Software Foundation, either version 3 of the |
||||
|
# License, or (at your option) any later version. |
||||
|
# |
||||
|
# This program is distributed in the hope that it will be useful, |
||||
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of |
||||
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
||||
|
# GNU Affero General Public License for more details. |
||||
|
# |
||||
|
# You should have received a copy of the GNU Affero General Public License |
||||
|
# along with this program. If not, see <http://www.gnu.org/licenses/>. |
||||
|
# |
||||
|
############################################################################## |
||||
|
|
||||
|
import re |
||||
|
from openerp.osv import orm, fields |
||||
|
|
||||
|
|
||||
|
class ResPartner(orm.Model): |
||||
|
_inherit = 'res.partner' |
||||
|
|
||||
|
def get_street(self, cr, uid, partner, context=None): |
||||
|
""" |
||||
|
Allow to override the field function's value composition |
||||
|
|
||||
|
:param partner: res.partner browse record |
||||
|
:rtype: string |
||||
|
""" |
||||
|
return ' '.join(filter(None, [ |
||||
|
partner.street_name, |
||||
|
partner.street_number, |
||||
|
])) |
||||
|
|
||||
|
def _get_street(self, cr, uid, select, field_name, args, context=None): |
||||
|
""" Delegates the function field 'street' to an inheritable method""" |
||||
|
res = {} |
||||
|
for partner in self.browse(cr, uid, select, context=context): |
||||
|
res[partner.id] = self.get_street( |
||||
|
cr, uid, partner, context=context) |
||||
|
return res |
||||
|
|
||||
|
def _write_street(self, cr, uid, ids, name, value, arg, context=None): |
||||
|
""" |
||||
|
Simplistically try to parse in case a value should get written |
||||
|
to the 'street' field (for instance at import time, which provides |
||||
|
us with a way of easily restoring the data when this module is |
||||
|
installed on a database that already contains addresses). |
||||
|
""" |
||||
|
street_name = value and value.strip() or False |
||||
|
street_number = False |
||||
|
if value: |
||||
|
match = re.search('(.+)\s+(\d.*)', value.strip()) |
||||
|
if match and len(match.group(2)) < 6: |
||||
|
street_name = match.group(1) |
||||
|
street_number = match.group(2) |
||||
|
return self.write(cr, uid, ids, { |
||||
|
'street_name': street_name, |
||||
|
'street_number': street_number, |
||||
|
}, context=context) |
||||
|
|
||||
|
def _display_address( |
||||
|
self, cr, uid, address, without_company=False, context=None): |
||||
|
""" |
||||
|
Inject a context key to prevent the 'street' name to be |
||||
|
deleted from the result of _address_fields when called from |
||||
|
the super. |
||||
|
""" |
||||
|
local_context = dict(context or {}, display_address=True) |
||||
|
return super(ResPartner, self)._display_address( |
||||
|
cr, uid, address, without_company=without_company, |
||||
|
context=local_context) |
||||
|
|
||||
|
def _address_fields(self, cr, uid, context=None): |
||||
|
""" |
||||
|
Pass on the fields for address synchronisation to contacts. |
||||
|
|
||||
|
This method is used on at least two occassions: |
||||
|
|
||||
|
[1] when address fields are synced to contacts, and |
||||
|
[2] when addresses are formatted |
||||
|
|
||||
|
We want to prevent the 'street' field to be passed in the |
||||
|
first case, as it has a fallback write method which should |
||||
|
not be triggered in this case, while leaving the field in |
||||
|
in the second case. Therefore, we remove the field |
||||
|
name from the list of address fields unless we find the context |
||||
|
key that this module injects when formatting an address. |
||||
|
|
||||
|
Could have checked for the occurrence of the synchronisation |
||||
|
method instead, leaving the field in by default but that could |
||||
|
lead to silent data corruption should the synchronisation API |
||||
|
ever change. |
||||
|
""" |
||||
|
res = super(ResPartner, self)._address_fields(cr, uid, context=context) |
||||
|
if 'street' in res and not ( |
||||
|
context and context.get('display_address')): |
||||
|
res.remove('street') |
||||
|
return res + ['street_name', 'street_number'] |
||||
|
|
||||
|
_columns = { |
||||
|
'street_name': fields.char( |
||||
|
'Street name', size=118), |
||||
|
'street_number': fields.char( |
||||
|
'Street number', size=10), |
||||
|
'street': fields.function( |
||||
|
_get_street, fnct_inv=_write_street, |
||||
|
type='char', string="Street", |
||||
|
# Must be stored as per https://bugs.launchpad.net/bugs/1253200 |
||||
|
store={ |
||||
|
'res.partner': ( |
||||
|
lambda self, cr, uid, ids, context=None: ids, |
||||
|
['street_name', 'street_number'], 10), |
||||
|
}, |
||||
|
), |
||||
|
} |
@ -0,0 +1,46 @@ |
|||||
|
<?xml version="1.0" encoding="UTF-8"?> |
||||
|
<openerp> |
||||
|
<data> |
||||
|
|
||||
|
<record id="view_partner_form" model="ir.ui.view"> |
||||
|
<field name="name">Add separate fields for street name and number</field> |
||||
|
<field name="model">res.partner</field> |
||||
|
<field name="inherit_id" ref="base.view_partner_form"/> |
||||
|
<field name="arch" type="xml"> |
||||
|
|
||||
|
<xpath expr="/form/sheet//div/field[@name='street']" |
||||
|
position="replace"> |
||||
|
<div> |
||||
|
<field name="street_name" style="width: 80%%" |
||||
|
placeholder="Street..." |
||||
|
attrs="{'readonly': [('use_parent_address','=',True)]}" |
||||
|
/> |
||||
|
<field name="street_number" style="width: 19%%" |
||||
|
placeholder="Number..." |
||||
|
attrs="{'readonly': [('use_parent_address','=',True)]}" |
||||
|
/> |
||||
|
</div> |
||||
|
</xpath> |
||||
|
|
||||
|
<xpath expr="//form[@string='Contact']/sheet/group/div/field[@name='street']" |
||||
|
position="replace"> |
||||
|
<div> |
||||
|
<field name="street_name" style="width: 80%%" |
||||
|
placeholder="Street..." |
||||
|
attrs="{'readonly': [('use_parent_address','=',True)]}" |
||||
|
/> |
||||
|
<field name="street_number" style="width: 19%%" |
||||
|
placeholder="Number..." |
||||
|
attrs="{'readonly': [('use_parent_address','=',True)]}" |
||||
|
/> |
||||
|
</div> |
||||
|
</xpath> |
||||
|
|
||||
|
<xpath expr="//field[@name='child_ids']" position="attributes"> |
||||
|
<attribute name="context">{'default_parent_id': active_id, 'default_street_name': street_name, 'default_street_number': street_number, 'default_street2': street2, 'default_city': city, 'default_state_id': state_id, 'default_zip': zip, 'default_country_id': country_id, 'default_supplier': supplier, 'default_customer': customer}</attribute> |
||||
|
</xpath> |
||||
|
|
||||
|
</field> |
||||
|
</record> |
||||
|
</data> |
||||
|
</openerp> |
Write
Preview
Loading…
Cancel
Save
Reference in new issue