diff options
| author | amoyaux <arm@odoo.com> | 2017-08-21 09:34:34 +0200 |
|---|---|---|
| committer | amoyaux <arm@odoo.com> | 2017-09-26 09:31:26 +0200 |
| commit | 03559629ee3f8ef28e51d8ed659fc7c09b176955 (patch) | |
| tree | aced1bf0f5be1b2d64ae7b2c178981273d67ed58 | |
| parent | 9edab0dbb4716b04cf2cb3120d2f85ad3d9ef877 (diff) | |
[IMP] stock: make immediate transfer and backorder multi
The purpose of this commit is to allow future modules that need
immediate transfer and back order function on multiples picking
to do it.
This commit does not modify the behavior of single picking processing
| -rw-r--r-- | addons/purchase/test/average_price.yml | 8 | ||||
| -rw-r--r-- | addons/purchase/test/fifo_price.yml | 18 | ||||
| -rw-r--r-- | addons/purchase/test/fifo_returns.yml | 4 | ||||
| -rw-r--r-- | addons/stock/models/stock_picking.py | 19 | ||||
| -rw-r--r-- | addons/stock/wizard/stock_backorder_confirmation.py | 18 | ||||
| -rw-r--r-- | addons/stock/wizard/stock_immediate_transfer.py | 53 |
6 files changed, 61 insertions, 59 deletions
diff --git a/addons/purchase/test/average_price.yml b/addons/purchase/test/average_price.yml index c4871884087..6b3c61b0293 100644 --- a/addons/purchase/test/average_price.yml +++ b/addons/purchase/test/average_price.yml @@ -41,7 +41,7 @@ - !python {model: purchase.order, id: purchase_order_average1}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Check the average price of the product (average icecream). - @@ -70,7 +70,7 @@ - !python {model: purchase.order, id: purchase_order_average2}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Check the standard price - @@ -96,7 +96,7 @@ - !python {model: stock.picking, id: outgoing_average_shipment}: | self.action_assign() - self.env['stock.immediate.transfer'].create({'pick_id': self.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, self.id)]}).process() - Check the standard price (60 * 10 + 30 * 80) / 40 = 75.0 did not change - @@ -125,7 +125,7 @@ - !python {model: purchase.order, id: purchase_order_average3}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Check price is (75.0*20 + 200*0.5) / 20.5 = 78.04878 - diff --git a/addons/purchase/test/fifo_price.yml b/addons/purchase/test/fifo_price.yml index f8d41482668..0042d136542 100644 --- a/addons/purchase/test/fifo_price.yml +++ b/addons/purchase/test/fifo_price.yml @@ -49,7 +49,7 @@ - !python {model: purchase.order, id: purchase_order_fifo1}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Check the standard price of the product (fifo icecream), that should have not changed because the standard price is supposed to be updated only when goods are going out of the stock - @@ -78,7 +78,7 @@ - !python {model: purchase.order, id: purchase_order_fifo2}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Check the standard price of the product, that should have not changed because the standard price is supposed to be updated only when goods are going out of the stock - @@ -110,7 +110,7 @@ Process the delivery of the outgoing shipment - !python {model: stock.picking, id: outgoing_fifo_shipment}: | - self.env['stock.immediate.transfer'].create({'pick_id': self.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, self.id)]}).process() - Check stock valuation is 1600 - @@ -141,7 +141,7 @@ Process the delivery of the outgoing shipment - !python {model: stock.picking, id: outgoing_fifo_shipment_uom}: | - self.env['stock.immediate.transfer'].create({'pick_id': self.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, self.id)]}).process() - Check stock valuation and qty in stock - @@ -186,7 +186,7 @@ - !python {model: purchase.order, id: purchase_order_fifo_usd}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - We create delivery order of 49.5 kg - @@ -212,7 +212,7 @@ Process the delivery of the outgoing shipment - !python {model: stock.picking, id: outgoing_fifo_shipment_cur}: | - self.env['stock.immediate.transfer'].create({'pick_id': self.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, self.id)]}).process() - Do a delivery of an extra 10 kg - @@ -238,7 +238,7 @@ Process the delivery of the outgoing shipment - !python {model: stock.picking, id: outgoing_fifo_shipment_ret}: | - self.env['stock.immediate.transfer'].create({'pick_id': self.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, self.id)]}).process() - Check rounded price is 150.0 / 1.2834 - @@ -340,7 +340,7 @@ - !python {model: purchase.order, id: purchase_order_fifo_neg}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Receive purchase order with 600 kg FIFO Ice Cream at 80 euro/kg - @@ -363,7 +363,7 @@ - !python {model: purchase.order, id: purchase_order_fifo_neg2}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() original_out_move = self.env['stock.picking'].browse(ref('outgoing_fifo_shipment_neg')).move_lines[0] outgoing_shipment_fifo_icecream_neg2 = self.env['stock.picking'].browse(ref('outgoing_fifo_shipment_neg2')).move_lines[0] original_out_move._fifo_vacuum() diff --git a/addons/purchase/test/fifo_returns.yml b/addons/purchase/test/fifo_returns.yml index 9712b2c2b07..5845ea3ab41 100644 --- a/addons/purchase/test/fifo_returns.yml +++ b/addons/purchase/test/fifo_returns.yml @@ -49,7 +49,7 @@ - !python {model: purchase.order, id: purchase_order_fiforet1}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Check the standard price of the product (fifo icecream) - @@ -65,7 +65,7 @@ - !python {model: purchase.order, id: purchase_order_fiforet2}: | picking = self.picking_ids[0] - self.env['stock.immediate.transfer'].create({'pick_id': picking.id}).process() + self.env['stock.immediate.transfer'].create({'pick_ids': [(4, picking.id)]}).process() - Return the goods of purchase order 2 - diff --git a/addons/stock/models/stock_picking.py b/addons/stock/models/stock_picking.py index f731754bf05..1d24653db4f 100644 --- a/addons/stock/models/stock_picking.py +++ b/addons/stock/models/stock_picking.py @@ -649,7 +649,7 @@ class Picking(models.Model): if no_quantities_done: view = self.env.ref('stock.view_immediate_transfer') - wiz = self.env['stock.immediate.transfer'].create({'pick_id': self.id}) + wiz = self.env['stock.immediate.transfer'].create({'pick_ids': [(4, self.id)]}) return { 'name': _('Immediate Transfer?'), 'type': 'ir.actions.act_window', @@ -686,7 +686,7 @@ class Picking(models.Model): def action_generate_backorder_wizard(self): view = self.env.ref('stock.view_backorder_confirmation') - wiz = self.env['stock.backorder.confirmation'].create({'pick_id': self.id}) + wiz = self.env['stock.backorder.confirmation'].create({'pick_ids': [(4, p.id) for p in self]}) return { 'name': _('Create Backorder?'), 'type': 'ir.actions.act_window', @@ -706,19 +706,26 @@ class Picking(models.Model): return True def _check_backorder(self): - self.ensure_one() + """ This method will loop over all the move lines of self and + check if creating a backorder is necessary. This method is + called during button_validate if the user has already processed + some quantities and in the immediate transfer wizard that is + displayed if the user has not processed any quantities. + + :return: True if a backorder is necessary else False + """ quantity_todo = {} quantity_done = {} - for move in self.move_lines: + for move in self.mapped('move_lines'): quantity_todo.setdefault(move.product_id.id, 0) quantity_done.setdefault(move.product_id.id, 0) quantity_todo[move.product_id.id] += move.product_uom_qty quantity_done[move.product_id.id] += move.quantity_done - for ops in self.move_line_ids.filtered(lambda x: x.package_id and not x.product_id and not x.move_id): + for ops in self.mapped('move_line_ids').filtered(lambda x: x.package_id and not x.product_id and not x.move_id): for quant in ops.package_id.quant_ids: quantity_done.setdefault(quant.product_id.id, 0) quantity_done[quant.product_id.id] += quant.qty - for pack in self.move_line_ids.filtered(lambda x: x.product_id and not x.move_id): + for pack in self.mapped('move_line_ids').filtered(lambda x: x.product_id and not x.move_id): quantity_done.setdefault(pack.product_id.id, 0) quantity_done[pack.product_id.id] += pack.qty_done return any(quantity_done[x] < quantity_todo.get(x, 0) for x in quantity_done) diff --git a/addons/stock/wizard/stock_backorder_confirmation.py b/addons/stock/wizard/stock_backorder_confirmation.py index 2ddbbe30ba5..94fe84b47de 100644 --- a/addons/stock/wizard/stock_backorder_confirmation.py +++ b/addons/stock/wizard/stock_backorder_confirmation.py @@ -8,22 +8,16 @@ class StockBackorderConfirmation(models.TransientModel): _name = 'stock.backorder.confirmation' _description = 'Backorder Confirmation' - pick_id = fields.Many2one('stock.picking') - - @api.model - def default_get(self, fields): - res = super(StockBackorderConfirmation, self).default_get(fields) - if 'pick_id' in fields and self._context.get('active_id') and not res.get('pick_id'): - res = {'pick_id': self._context['active_id']} - return res + pick_ids = fields.Many2many('stock.picking', 'stock_picking_backorder_rel') @api.one def _process(self, cancel_backorder=False): - self.pick_id.do_transfer() + self.pick_ids.action_done() if cancel_backorder: - backorder_pick = self.env['stock.picking'].search([('backorder_id', '=', self.pick_id.id)]) - backorder_pick.action_cancel() - self.pick_id.message_post(body=_("Back order <em>%s</em> <b>cancelled</b>.") % (backorder_pick.name)) + for pick_id in self.pick_ids: + backorder_pick = self.env['stock.picking'].search([('backorder_id', '=', pick_id.id)]) + backorder_pick.action_cancel() + pick_id.message_post(body=_("Back order <em>%s</em> <b>cancelled</b>.") % (backorder_pick.name)) def process(self): self._process() diff --git a/addons/stock/wizard/stock_immediate_transfer.py b/addons/stock/wizard/stock_immediate_transfer.py index b66ce187222..7621ad305bb 100644 --- a/addons/stock/wizard/stock_immediate_transfer.py +++ b/addons/stock/wizard/stock_immediate_transfer.py @@ -1,7 +1,7 @@ # -*- coding: utf-8 -*- # Part of Odoo. See LICENSE file for full copyright and licensing details. -from odoo import api, fields, models, _ +from odoo import fields, models, _ from odoo.exceptions import UserError @@ -9,30 +9,31 @@ class StockImmediateTransfer(models.TransientModel): _name = 'stock.immediate.transfer' _description = 'Immediate Transfer' - pick_id = fields.Many2one('stock.picking') - - @api.model - def default_get(self, fields): - res = super(StockImmediateTransfer, self).default_get(fields) - if not res.get('pick_id') and self._context.get('active_id'): - res['pick_id'] = self._context['active_id'] - return res + pick_ids = fields.Many2many('stock.picking', 'stock_picking_transfer_rel') def process(self): - self.ensure_one() - # If still in draft => confirm and assign - if self.pick_id.state == 'draft': - self.pick_id.action_confirm() - if self.pick_id.state != 'assigned': - self.pick_id.action_assign() - if self.pick_id.state != 'assigned': - raise UserError(_("Could not reserve all requested products. Please use the \'Mark as Todo\' button to handle the reservation manually.")) - for move in self.pick_id.move_lines: - if move.move_line_ids: - for move_line in move.move_line_ids: - move_line.qty_done = move_line.product_uom_qty - else: - move.quantity_done = move.product_uom_qty - if self.pick_id._check_backorder(): - return self.pick_id.action_generate_backorder_wizard() - self.pick_id.do_transfer() + pick_to_backorder = self.env['stock.picking'] + pick_to_do = self.env['stock.picking'] + for picking in self.pick_ids: + # If still in draft => confirm and assign + if picking.state == 'draft': + picking.action_confirm() + if picking.state != 'assigned': + picking.action_assign() + if picking.state != 'assigned': + raise UserError(_("Could not reserve all requested products. Please use the \'Mark as Todo\' button to handle the reservation manually.")) + for move in picking.move_lines: + if move.move_line_ids: + for move_line in move.move_line_ids: + move_line.qty_done = move_line.product_uom_qty + else: + move.quantity_done = move.product_uom_qty + if picking._check_backorder(): + pick_to_backorder |= picking + continue + pick_to_do |= picking + # Process every picking that do not require a backorder, then return a single backorder wizard for every other ones. + if pick_to_do: + pick_to_do.action_done() + if pick_to_backorder: + return pick_to_backorder.action_generate_backorder_wizard() |
