From f3a9a91ae57c7338313ea69d79932f222ffd0418 Mon Sep 17 00:00:00 2001 From: Rifakat Date: Fri, 22 Jun 2012 12:14:59 +0530 Subject: [PATCH 1/7] [FIX] sale,purchase: fix uom problem when doing product onchange for sale item or purchase items, it did not automatically set the proper UoM while chnaging the product when products UoM are in the same category bzr revid: rha@tinyerp.com-20120622064459-d4xxyaz6rey8aou0 --- addons/purchase/purchase.py | 16 +++++++++++----- addons/sale/sale.py | 13 ++++++++----- 2 files changed, 19 insertions(+), 10 deletions(-) diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py index a3135935045..70ecd495e8c 100644 --- a/addons/purchase/purchase.py +++ b/addons/purchase/purchase.py @@ -705,9 +705,13 @@ class purchase_order_line(osv.osv): """ if not uom_id: return {'value': {'price_unit': price_unit or 0.0, 'name': name or '', 'notes': notes or'', 'product_uom' : uom_id or False}} - return self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, - partner_id, date_order=date_order, fiscal_position_id=fiscal_position_id, date_planned=date_planned, - name=name, price_unit=price_unit, notes=notes, context=context) + context.update(uom_change=True) + res = self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, + partner_id, date_order=date_order, fiscal_position_id=fiscal_position_id, date_planned=date_planned, + name=name, price_unit=price_unit, notes=notes, context=context) + if 'product_uom' in res['value']: + del res['value']['product_uom'] + return res def _get_date_planned(self, cr, uid, supplier_info, date_order_str, context=None): """Return the datetime value to use as Schedule Date (``date_planned``) for @@ -764,11 +768,13 @@ class purchase_order_line(osv.osv): product_uom_po_id = product.uom_po_id.id if not uom_id: uom_id = product_uom_po_id - + + if not context.get('uom_change'): + uom_id = product.uom_id.id if product.uom_id.category_id.id != product_uom.browse(cr, uid, uom_id, context=context).category_id.id: res['warning'] = {'title': _('Warning'), 'message': _('Selected UOM does not belong to the same category as the product UOM')} uom_id = product_uom_po_id - + res['value'].update({'product_uom': uom_id}) # - determine product_qty and date_planned based on seller info diff --git a/addons/sale/sale.py b/addons/sale/sale.py index 82bfda7b580..81e5fec0856 100644 --- a/addons/sale/sale.py +++ b/addons/sale/sale.py @@ -1197,7 +1197,7 @@ class sale_order_line(osv.osv): product_uom_obj = self.pool.get('product.uom') partner_obj = self.pool.get('res.partner') product_obj = self.pool.get('product.product') - context = {'lang': lang, 'partner_id': partner_id} + context.update(lang=lang, partner_id=partner_id) if partner_id: lang = partner_obj.browse(cr, uid, partner_id).lang context_partner = {'lang': lang, 'partner_id': partner_id} @@ -1213,12 +1213,10 @@ class sale_order_line(osv.osv): result = res.get('value', {}) warning_msgs = res.get('warning') and res['warning']['message'] or '' product_obj = product_obj.browse(cr, uid, product, context=context) - + uom2 = False - if uom: + if uom and context.get('uom_change'): uom2 = product_uom_obj.browse(cr, uid, uom) - if product_obj.uom_id.category_id.id != uom2.category_id.id: - uom = False if uos: if product_obj.uos_id: uos2 = product_uom_obj.browse(cr, uid, uos) @@ -1252,6 +1250,10 @@ class sale_order_line(osv.osv): [('category_id', '=', product_obj.uom_id.category_id.id)], 'product_uos': [('category_id', '=', uos_category_id)]} + + if not context.get('uom_change'): + res['value'].update(product_uom=product_obj.uom_id.id) + uom = product_obj.uom_id.id elif uos and not uom: # only happens if uom is False result['product_uom'] = product_obj.uom_id and product_obj.uom_id.id @@ -1309,6 +1311,7 @@ class sale_order_line(osv.osv): lang=False, update_tax=True, date_order=False, context=None): context = context or {} lang = lang or ('lang' in context and context['lang']) + context.update(uom_change=True) res = self.product_id_change(cursor, user, ids, pricelist, product, qty=qty, uom=uom, qty_uos=qty_uos, uos=uos, name=name, partner_id=partner_id, lang=lang, update_tax=update_tax, From e4c36049c771c283ede2b6df24ac830c3e50fb6e Mon Sep 17 00:00:00 2001 From: Rifakat Date: Fri, 22 Jun 2012 12:59:05 +0530 Subject: [PATCH 2/7] [IMP] purchase: improved code bzr revid: rha@tinyerp.com-20120622072905-ybxqziwrpemn0q5a --- addons/purchase/purchase.py | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py index 70ecd495e8c..98907edf6c2 100644 --- a/addons/purchase/purchase.py +++ b/addons/purchase/purchase.py @@ -706,12 +706,9 @@ class purchase_order_line(osv.osv): if not uom_id: return {'value': {'price_unit': price_unit or 0.0, 'name': name or '', 'notes': notes or'', 'product_uom' : uom_id or False}} context.update(uom_change=True) - res = self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, + return self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, partner_id, date_order=date_order, fiscal_position_id=fiscal_position_id, date_planned=date_planned, name=name, price_unit=price_unit, notes=notes, context=context) - if 'product_uom' in res['value']: - del res['value']['product_uom'] - return res def _get_date_planned(self, cr, uid, supplier_info, date_order_str, context=None): """Return the datetime value to use as Schedule Date (``date_planned``) for From a9bdf5918460ebf3beae65e91d16dcb2e69acc7f Mon Sep 17 00:00:00 2001 From: Rifakat Date: Fri, 22 Jun 2012 13:20:30 +0530 Subject: [PATCH 3/7] [IMP] purchase: fix indentation for onchange of uom bzr revid: rha@tinyerp.com-20120622075030-x3qgudjfnr02pxzr --- addons/purchase/purchase.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py index 98907edf6c2..6242c850a5d 100644 --- a/addons/purchase/purchase.py +++ b/addons/purchase/purchase.py @@ -707,8 +707,8 @@ class purchase_order_line(osv.osv): return {'value': {'price_unit': price_unit or 0.0, 'name': name or '', 'notes': notes or'', 'product_uom' : uom_id or False}} context.update(uom_change=True) return self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, - partner_id, date_order=date_order, fiscal_position_id=fiscal_position_id, date_planned=date_planned, - name=name, price_unit=price_unit, notes=notes, context=context) + partner_id, date_order=date_order, fiscal_position_id=fiscal_position_id, date_planned=date_planned, + name=name, price_unit=price_unit, notes=notes, context=context) def _get_date_planned(self, cr, uid, supplier_info, date_order_str, context=None): """Return the datetime value to use as Schedule Date (``date_planned``) for From aacd608c2aac859e9d81dbd76f721dae75374f39 Mon Sep 17 00:00:00 2001 From: Xavier ALT Date: Tue, 2 Oct 2012 18:14:36 +0200 Subject: [PATCH 4/7] [IMP] improve preceding fix a little + use real context guard bzr revid: xal@openerp.com-20121002161436-kyhuh9l8jdlbduzm --- addons/purchase/purchase.py | 12 ++++++------ addons/sale/sale.py | 23 ++++++++++++----------- 2 files changed, 18 insertions(+), 17 deletions(-) diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py index 6242c850a5d..78980c82cf7 100644 --- a/addons/purchase/purchase.py +++ b/addons/purchase/purchase.py @@ -703,9 +703,11 @@ class purchase_order_line(osv.osv): """ onchange handler of product_uom. """ + if context is None: + context = {} + context = dict(context, uom_change=True) if not uom_id: return {'value': {'price_unit': price_unit or 0.0, 'name': name or '', 'notes': notes or'', 'product_uom' : uom_id or False}} - context.update(uom_change=True) return self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, partner_id, date_order=date_order, fiscal_position_id=fiscal_position_id, date_planned=date_planned, name=name, price_unit=price_unit, notes=notes, context=context) @@ -763,15 +765,13 @@ class purchase_order_line(osv.osv): # - check that uom and product uom belong to the same category product_uom_po_id = product.uom_po_id.id - if not uom_id: + if not uom_id or not context.get('uom_change'): uom_id = product_uom_po_id - - if not context.get('uom_change'): - uom_id = product.uom_id.id + if product.uom_id.category_id.id != product_uom.browse(cr, uid, uom_id, context=context).category_id.id: res['warning'] = {'title': _('Warning'), 'message': _('Selected UOM does not belong to the same category as the product UOM')} uom_id = product_uom_po_id - + res['value'].update({'product_uom': uom_id}) # - determine product_qty and date_planned based on seller info diff --git a/addons/sale/sale.py b/addons/sale/sale.py index 81e5fec0856..c676fd185fa 100644 --- a/addons/sale/sale.py +++ b/addons/sale/sale.py @@ -1189,7 +1189,8 @@ class sale_order_line(osv.osv): def product_id_change(self, cr, uid, ids, pricelist, product, qty=0, uom=False, qty_uos=0, uos=False, name='', partner_id=False, lang=False, update_tax=True, date_order=False, packaging=False, fiscal_position=False, flag=False, context=None): - context = context or {} + if context is None: + context = {} lang = lang or context.get('lang',False) if not partner_id: raise osv.except_osv(_('No Customer Defined !'), _('You have to select a customer in the sales form !\nPlease set one customer before choosing a product.')) @@ -1197,7 +1198,7 @@ class sale_order_line(osv.osv): product_uom_obj = self.pool.get('product.uom') partner_obj = self.pool.get('res.partner') product_obj = self.pool.get('product.product') - context.update(lang=lang, partner_id=partner_id) + context = dict(context, lang=lang, partner_id=partner_id) if partner_id: lang = partner_obj.browse(cr, uid, partner_id).lang context_partner = {'lang': lang, 'partner_id': partner_id} @@ -1213,10 +1214,13 @@ class sale_order_line(osv.osv): result = res.get('value', {}) warning_msgs = res.get('warning') and res['warning']['message'] or '' product_obj = product_obj.browse(cr, uid, product, context=context) - + uom2 = False - if uom and context.get('uom_change'): + if uom: uom2 = product_uom_obj.browse(cr, uid, uom) + if product_obj.uom_id.category_id.id != uom2.category_id.id or not context.get('uom_change',False): + uom = False + uom2 = False if uos: if product_obj.uos_id: uos2 = product_uom_obj.browse(cr, uid, uos) @@ -1250,10 +1254,6 @@ class sale_order_line(osv.osv): [('category_id', '=', product_obj.uom_id.category_id.id)], 'product_uos': [('category_id', '=', uos_category_id)]} - - if not context.get('uom_change'): - res['value'].update(product_uom=product_obj.uom_id.id) - uom = product_obj.uom_id.id elif uos and not uom: # only happens if uom is False result['product_uom'] = product_obj.uom_id and product_obj.uom_id.id @@ -1309,9 +1309,10 @@ class sale_order_line(osv.osv): def product_uom_change(self, cursor, user, ids, pricelist, product, qty=0, uom=False, qty_uos=0, uos=False, name='', partner_id=False, lang=False, update_tax=True, date_order=False, context=None): - context = context or {} - lang = lang or ('lang' in context and context['lang']) - context.update(uom_change=True) + if context is None: + context = {} + lang = lang or context.get('lang',False) + context = dict(context, uom_change=True) res = self.product_id_change(cursor, user, ids, pricelist, product, qty=qty, uom=uom, qty_uos=qty_uos, uos=uos, name=name, partner_id=partner_id, lang=lang, update_tax=update_tax, From a7928073589d5f187eee4765f7af670eb54c5261 Mon Sep 17 00:00:00 2001 From: Xavier ALT Date: Tue, 2 Oct 2012 18:21:11 +0200 Subject: [PATCH 5/7] [FIX] sale: add missing usage of context within product_id_change() method bzr revid: xal@openerp.com-20121002162111-y5bgiali8eukze07 --- addons/sale/sale.py | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/addons/sale/sale.py b/addons/sale/sale.py index c676fd185fa..d5a8fbdd904 100644 --- a/addons/sale/sale.py +++ b/addons/sale/sale.py @@ -1200,8 +1200,8 @@ class sale_order_line(osv.osv): product_obj = self.pool.get('product.product') context = dict(context, lang=lang, partner_id=partner_id) if partner_id: - lang = partner_obj.browse(cr, uid, partner_id).lang - context_partner = {'lang': lang, 'partner_id': partner_id} + lang = partner_obj.browse(cr, uid, partner_id, context=context).lang + context_partner = dict(context, lang=lang) if not product: return {'value': {'th_weight': 0, 'product_packaging': False, @@ -1217,20 +1217,20 @@ class sale_order_line(osv.osv): uom2 = False if uom: - uom2 = product_uom_obj.browse(cr, uid, uom) + uom2 = product_uom_obj.browse(cr, uid, uom, context=context) if product_obj.uom_id.category_id.id != uom2.category_id.id or not context.get('uom_change',False): uom = False uom2 = False if uos: if product_obj.uos_id: - uos2 = product_uom_obj.browse(cr, uid, uos) + uos2 = product_uom_obj.browse(cr, uid, uos, context=context) if product_obj.uos_id.category_id.id != uos2.category_id.id: uos = False else: uos = False if product_obj.description_sale: result['notes'] = product_obj.description_sale - fpos = fiscal_position and self.pool.get('account.fiscal.position').browse(cr, uid, fiscal_position) or False + fpos = fiscal_position and self.pool.get('account.fiscal.position').browse(cr, uid, fiscal_position, context=context) or False if update_tax: #The quantity only have changed result['delay'] = (product_obj.sale_delay or 0.0) result['tax_id'] = self.pool.get('account.fiscal.position').map_tax(cr, uid, fpos, product_obj.taxes_id) @@ -1288,10 +1288,10 @@ class sale_order_line(osv.osv): warning_msgs += _("No Pricelist ! : ") + warn_msg +"\n\n" else: price = self.pool.get('product.pricelist').price_get(cr, uid, [pricelist], - product, qty or 1.0, partner_id, { - 'uom': uom or result.get('product_uom'), - 'date': date_order, - })[pricelist] + product, qty or 1.0, partner_id, dict(context, + uom=uom or result.get('product_uom'), + date=date_order, + ))[pricelist] if price is False: warn_msg = _("Couldn't find a pricelist line matching this product and quantity.\n" "You have to change either the product, the quantity or the pricelist.") From c633eccd5eb778dc97afaa8d38901b8d5e9ae1c3 Mon Sep 17 00:00:00 2001 From: Xavier ALT Date: Tue, 9 Oct 2012 12:18:10 +0200 Subject: [PATCH 6/7] [IMP] sale/purchase: add explaination for context 'uom_change' key bzr revid: xal@openerp.com-20121009101810-yzb8so96ln14t6ri --- addons/purchase/purchase.py | 5 +++++ addons/sale/sale.py | 9 +++++++++ 2 files changed, 14 insertions(+) diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py index 78980c82cf7..918cc545047 100644 --- a/addons/purchase/purchase.py +++ b/addons/purchase/purchase.py @@ -732,6 +732,11 @@ class purchase_order_line(osv.osv): name=False, price_unit=False, notes=False, context=None): """ onchange handler of product_id. + + :param dict context: 'uom_change' key in context override default onchange + behaviour which force product's UoM, allowing to + specify an 'uom_id' of the same category as product's + UoM (ex: set when called from product_uom's onchange). """ if context is None: context = {} diff --git a/addons/sale/sale.py b/addons/sale/sale.py index d5a8fbdd904..064ae7d2b2e 100644 --- a/addons/sale/sale.py +++ b/addons/sale/sale.py @@ -1189,6 +1189,15 @@ class sale_order_line(osv.osv): def product_id_change(self, cr, uid, ids, pricelist, product, qty=0, uom=False, qty_uos=0, uos=False, name='', partner_id=False, lang=False, update_tax=True, date_order=False, packaging=False, fiscal_position=False, flag=False, context=None): + """ + onchange handler for product_id. + + :param dict context: 'uom_change' key in context override default onchange + behaviour which force product's UoM, allowing to + specify an 'uom_id' of the same category as product's + UoM (ex: set when called from product_uom's onchange). + + """ if context is None: context = {} lang = lang or context.get('lang',False) From 2d207c5d5d7a56ddc63a0428507de8cd951e736b Mon Sep 17 00:00:00 2001 From: Xavier ALT Date: Tue, 9 Oct 2012 13:06:00 +0200 Subject: [PATCH 7/7] [FIX] sale/purchase: invert check - simplify forcing product's UoM only when changing 'product_id' field bzr revid: xal@openerp.com-20121009110600-0d19szr59l2a0pw4 --- addons/purchase/purchase.py | 12 ++++-------- addons/purchase/purchase_view.xml | 2 +- addons/sale/sale.py | 11 ++++------- addons/sale/sale_view.xml | 2 +- 4 files changed, 10 insertions(+), 17 deletions(-) diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py index 918cc545047..2cb8429724c 100644 --- a/addons/purchase/purchase.py +++ b/addons/purchase/purchase.py @@ -703,9 +703,6 @@ class purchase_order_line(osv.osv): """ onchange handler of product_uom. """ - if context is None: - context = {} - context = dict(context, uom_change=True) if not uom_id: return {'value': {'price_unit': price_unit or 0.0, 'name': name or '', 'notes': notes or'', 'product_uom' : uom_id or False}} return self.onchange_product_id(cr, uid, ids, pricelist_id, product_id, qty, uom_id, @@ -733,10 +730,9 @@ class purchase_order_line(osv.osv): """ onchange handler of product_id. - :param dict context: 'uom_change' key in context override default onchange - behaviour which force product's UoM, allowing to - specify an 'uom_id' of the same category as product's - UoM (ex: set when called from product_uom's onchange). + :param dict context: 'force_product_uom' key in context override + default onchange behaviour to force using the UoM + defined on the provided product """ if context is None: context = {} @@ -770,7 +766,7 @@ class purchase_order_line(osv.osv): # - check that uom and product uom belong to the same category product_uom_po_id = product.uom_po_id.id - if not uom_id or not context.get('uom_change'): + if not uom_id or context.get('force_product_uom'): uom_id = product_uom_po_id if product.uom_id.category_id.id != product_uom.browse(cr, uid, uom_id, context=context).category_id.id: diff --git a/addons/purchase/purchase_view.xml b/addons/purchase/purchase_view.xml index 1c936055aff..88d92af5bdd 100644 --- a/addons/purchase/purchase_view.xml +++ b/addons/purchase/purchase_view.xml @@ -359,7 +359,7 @@
- + diff --git a/addons/sale/sale.py b/addons/sale/sale.py index 064ae7d2b2e..7d35ec7918b 100644 --- a/addons/sale/sale.py +++ b/addons/sale/sale.py @@ -1192,11 +1192,9 @@ class sale_order_line(osv.osv): """ onchange handler for product_id. - :param dict context: 'uom_change' key in context override default onchange - behaviour which force product's UoM, allowing to - specify an 'uom_id' of the same category as product's - UoM (ex: set when called from product_uom's onchange). - + :param dict context: 'force_product_uom' key in context override + default onchange behaviour to force using the UoM + defined on the provided product """ if context is None: context = {} @@ -1227,7 +1225,7 @@ class sale_order_line(osv.osv): uom2 = False if uom: uom2 = product_uom_obj.browse(cr, uid, uom, context=context) - if product_obj.uom_id.category_id.id != uom2.category_id.id or not context.get('uom_change',False): + if product_obj.uom_id.category_id.id != uom2.category_id.id or context.get('force_product_uom'): uom = False uom2 = False if uos: @@ -1321,7 +1319,6 @@ class sale_order_line(osv.osv): if context is None: context = {} lang = lang or context.get('lang',False) - context = dict(context, uom_change=True) res = self.product_id_change(cursor, user, ids, pricelist, product, qty=qty, uom=uom, qty_uos=qty_uos, uos=uos, name=name, partner_id=partner_id, lang=lang, update_tax=update_tax, diff --git a/addons/sale/sale_view.xml b/addons/sale/sale_view.xml index 90d3838f5a0..9f109286205 100644 --- a/addons/sale/sale_view.xml +++ b/addons/sale/sale_view.xml @@ -128,7 +128,7 @@