[REF] puchase: merge order wizard

bzr revid: hmo@tinyerp.com-20100325082511-k3ri4500pjd7kwsz
This commit is contained in:
Harry (Open ERP) 2010-03-25 13:55:11 +05:30
parent 58bbc77726
commit c5b08dc354
2 changed files with 143 additions and 127 deletions

View File

@ -32,7 +32,7 @@ from tools import config
from tools.translate import _
import decimal_precision as dp
from osv.orm import browse_record, browse_null
#
# Model definition
@ -446,6 +446,114 @@ class purchase_order(osv.osv):
})
return super(purchase_order, self).copy(cr, uid, id, default, context)
def do_merge(self, cr, uid, ids, context):
"""
To merge similar type of purchase orders.
Orders will only be merged if:
* Purchase Orders are in draft
* Purchase Orders belong to the same partner
* Purchase Orders are have same stock location, same pricelist
Lines will only be merged if:
* Order lines are exactly the same except for the quantity and unit
@param self: The object pointer.
@param cr: A database cursor
@param uid: ID of the user currently logged in
@param ids: the ID or list of IDs
@param context: A standard dictionary
@return: new purchase order id
"""
wf_service = netsvc.LocalService("workflow")
def make_key(br, fields):
list_key = []
for field in fields:
field_val = getattr(br, field)
if field in ('product_id', 'move_dest_id', 'account_analytic_id'):
if not field_val:
field_val = False
if isinstance(field_val, browse_record):
field_val = field_val.id
elif isinstance(field_val, browse_null):
field_val = False
elif isinstance(field_val, list):
field_val = ((6, 0, tuple([v.id for v in field_val])),)
list_key.append((field, field_val))
list_key.sort()
return tuple(list_key)
# compute what the new orders should contain
new_orders = {}
for porder in [order for order in self.browse(cr, uid, ids) if order.state == 'draft']:
order_key = make_key(porder, ('partner_id', 'location_id', 'pricelist_id'))
new_order = new_orders.setdefault(order_key, ({}, []))
new_order[1].append(porder.id)
order_infos = new_order[0]
if not order_infos:
order_infos.update({
'origin': porder.origin,
'date_order': time.strftime('%Y-%m-%d'),
'partner_id': porder.partner_id.id,
'partner_address_id': porder.partner_address_id.id,
'dest_address_id': porder.dest_address_id.id,
'warehouse_id': porder.warehouse_id.id,
'location_id': porder.location_id.id,
'pricelist_id': porder.pricelist_id.id,
'state': 'draft',
'order_line': {},
'notes': '%s' % (porder.notes or '',),
})
else:
#order_infos['name'] += ', %s' % porder.name
if porder.notes:
order_infos['notes'] = (order_infos['notes'] or '') + ('\n%s' % (porder.notes,))
if porder.origin:
order_infos['origin'] = (order_infos['origin'] or '') + ' ' + porder.origin
for order_line in porder.order_line:
line_key = make_key(order_line, ('name', 'date_planned', 'taxes_id', 'price_unit', 'notes', 'product_id', 'move_dest_id', 'account_analytic_id'))
o_line = order_infos['order_line'].setdefault(line_key, {})
if o_line:
# merge the line with an existing line
o_line['product_qty'] += order_line.product_qty * order_line.product_uom.factor / o_line['uom_factor']
else:
# append a new "standalone" line
for field in ('product_qty', 'product_uom'):
field_val = getattr(order_line, field)
if isinstance(field_val, browse_record):
field_val = field_val.id
o_line[field] = field_val
o_line['uom_factor'] = order_line.product_uom and order_line.product_uom.factor or 1.0
allorders = []
for order_key, (order_data, old_ids) in new_orders.iteritems():
# skip merges with only one order
if len(old_ids) < 2:
allorders += (old_ids or [])
continue
# cleanup order line data
for key, value in order_data['order_line'].iteritems():
del value['uom_factor']
value.update(dict(key))
order_data['order_line'] = [(0, 0, value) for value in order_data['order_line'].itervalues()]
# create the new order
neworder_id = self.create(cr, uid, order_data)
allorders.append(neworder_id)
# make triggers pointing to the old orders point to the new order
for old_id in old_ids:
wf_service.trg_redirect(uid, 'purchase.order', old_id, neworder_id, cr)
wf_service.trg_validate(uid, 'purchase.order', old_id, 'purchase_cancel', cr)
return allorders
purchase_order()
class purchase_order_line(osv.osv):

View File

@ -28,135 +28,43 @@ import wizard
from osv.orm import browse_record, browse_null
class purchase_order_group(osv.osv_memory):
_name = "purchase.order.group"
_description = "Purchase Wizard"
_columns = {
}
_name = "purchase.order.group"
_description = "Purchase Wizard"
_columns = {
}
def merge_orders(self, cr, uid, ids, context):
"""
To merge similar type of purchase orders.
@param self: The object pointer.
@param cr: A database cursor
@param uid: ID of the user currently logged in
@param ids: the ID or list of IDs
@param context: A standard dictionary
@return: purchase order view
"""
order_obj = self.pool.get('purchase.order')
mod_obj =self.pool.get('ir.model.data')
result = mod_obj._get_id(cr, uid, 'purchase', 'view_purchase_order_filter')
id = mod_obj.read(cr, uid, result, ['res_id'])
def merge_orders(self, cr, uid, ids, context):
"""
To merge similar type of purchase orders.
@param self: The object pointer.
@param cr: A database cursor
@param uid: ID of the user currently logged in
@param ids: the ID or list of IDs
@param context: A standard dictionary
@return: purchase order view
"""
order_obj = self.pool.get('purchase.order')
mod_obj =self.pool.get('ir.model.data')
result = mod_obj._get_id(cr, uid, 'purchase', 'view_purchase_order_filter')
id = mod_obj.read(cr, uid, result, ['res_id'])
def make_key(br, fields):
"""
Returns tuple indicating the value corresponding to fields
@param br: record object
@param fields: name of fields
@return: Returns tuple indicating the value corresponding to fields
"""
list_key = []
for field in fields:
field_val = getattr(br, field)
if field in ('product_id', 'move_dest_id', 'account_analytic_id'):
if not field_val:
field_val = False
if isinstance(field_val, browse_record):
field_val = field_val.id
elif isinstance(field_val, browse_null):
field_val = False
elif isinstance(field_val, list):
field_val = ((6, 0, tuple([v.id for v in field_val])),)
list_key.append((field, field_val))
list_key.sort()
return tuple(list_key)
allorders = order_obj.do_merge(cr, uid, context.get('active_ids',[]), context)
# compute what the new orders should contain
new_orders = {}
for porder in [order for order in order_obj.browse(cr, uid, context['active_ids']) if order.state == 'draft']:
order_key = make_key(porder, ('partner_id', 'location_id', 'pricelist_id'))
new_order = new_orders.setdefault(order_key, ({}, []))
new_order[1].append(porder.id)
order_infos = new_order[0]
if not order_infos:
order_infos.update({
'origin': porder.origin,
'date_order': time.strftime('%Y-%m-%d'),
'partner_id': porder.partner_id.id,
'partner_address_id': porder.partner_address_id.id,
'dest_address_id': porder.dest_address_id.id,
'warehouse_id': porder.warehouse_id.id,
'location_id': porder.location_id.id,
'pricelist_id': porder.pricelist_id.id,
'state': 'draft',
'order_line': {},
'notes': '%s' % (porder.notes or '',),
})
else:
#order_infos['name'] += ', %s' % porder.name
if porder.notes:
order_infos['notes'] = (order_infos['notes'] or '') + ('\n%s' % (porder.notes,))
if porder.origin:
order_infos['origin'] = (order_infos['origin'] or '') + ' ' + porder.origin
for order_line in porder.order_line:
line_key = make_key(order_line, ('name', 'date_planned', 'taxes_id', 'price_unit', 'notes', 'product_id', 'move_dest_id', 'account_analytic_id'))
o_line = order_infos['order_line'].setdefault(line_key, {})
if o_line:
# merge the line with an existing line
o_line['product_qty'] += order_line.product_qty * order_line.product_uom.factor / o_line['uom_factor']
else:
# append a new "standalone" line
for field in ('product_qty', 'product_uom'):
field_val = getattr(order_line, field)
if isinstance(field_val, browse_record):
field_val = field_val.id
o_line[field] = field_val
o_line['uom_factor'] = order_line.product_uom and order_line.product_uom.factor or 1.0
wf_service = netsvc.LocalService("workflow")
allorders = []
for order_key, (order_data, old_ids) in new_orders.iteritems():
# skip merges with only one order
if len(old_ids) < 2:
allorders += (old_ids or [])
continue
# cleanup order line data
for key, value in order_data['order_line'].iteritems():
del value['uom_factor']
value.update(dict(key))
order_data['order_line'] = [(0, 0, value) for value in order_data['order_line'].itervalues()]
# create the new order
neworder_id = order_obj.create(cr, uid, order_data)
allorders.append(neworder_id)
# make triggers pointing to the old orders point to the new order
for old_id in old_ids:
wf_service.trg_redirect(uid, 'purchase.order', old_id, neworder_id, cr)
wf_service.trg_validate(uid, 'purchase.order', old_id, 'purchase_cancel', cr)
return {
'domain': "[('id','in', [" + ','.join(map(str, allorders)) + "])]",
'name': 'Purchase Orders',
'view_type': 'form',
'view_mode': 'tree,form',
'res_model': 'purchase.order',
'view_id': False,
'type': 'ir.actions.act_window',
'search_view_id': id['res_id']
}
return {
'domain': "[('id','in', [" + ','.join(map(str, allorders)) + "])]",
'name': 'Purchase Orders',
'view_type': 'form',
'view_mode': 'tree,form',
'res_model': 'purchase.order',
'view_id': False,
'type': 'ir.actions.act_window',
'search_view_id': id['res_id']
}
purchase_order_group()