diff --git a/addons/stock/models/stock_move_line.py b/addons/stock/models/stock_move_line.py index cea0b0ae1fe..77332513df7 100644 --- a/addons/stock/models/stock_move_line.py +++ b/addons/stock/models/stock_move_line.py @@ -1000,6 +1000,8 @@ class StockMoveLine(models.Model): def action_revert_inventory(self): move_vals = [] + # remove inventory mode + self = self.with_context(inventory_mode=False) processed_move_line = self.env['stock.move.line'] for move_line in self: if move_line.is_inventory and not float_is_zero(move_line.qty_done, precision_digits=move_line.product_uom_id.rounding): diff --git a/addons/stock/models/stock_quant.py b/addons/stock/models/stock_quant.py index 832eabc8ff0..5432317de7d 100644 --- a/addons/stock/models/stock_quant.py +++ b/addons/stock/models/stock_quant.py @@ -316,16 +316,20 @@ class StockQuant(models.Model): 'template': '/stock/static/xlsx/stock_quant.xlsx' }] + @api.model + def _get_forbidden_fields_write(self): + """ Returns a list of fields user can't edit when he want to edit a quant in `inventory_mode`.""" + return ['product_id', 'location_id', 'lot_id', 'package_id', 'owner_id'] + def write(self, vals): """ Override to handle the "inventory mode" and create the inventory move. """ - allowed_fields = self._get_inventory_fields_write() - if self._is_inventory_mode() and any(field for field in allowed_fields if field in vals.keys()): + forbidden_fields = self._get_forbidden_fields_write() + if self._is_inventory_mode() and any(field for field in forbidden_fields if field in vals.keys()): if any(quant.location_id.usage == 'inventory' for quant in self): # Do nothing when user tries to modify manually a inventory loss return - if any(field for field in vals.keys() if field not in allowed_fields): - raise UserError(_("Quant's editing is restricted, you can't do this operation.")) self = self.sudo() + raise UserError(_("Quant's editing is restricted, you can't do this operation.")) return super(StockQuant, self).write(vals) @api.ondelete(at_uninstall=False) diff --git a/addons/stock/tests/test_quant.py b/addons/stock/tests/test_quant.py index a6744a4bb62..9354d4ca3e5 100644 --- a/addons/stock/tests/test_quant.py +++ b/addons/stock/tests/test_quant.py @@ -889,6 +889,28 @@ class StockQuant(TransactionCase): self.assertEqual(len(quant), 1) self.assertEqual(quant.lot_id.name, 'Michel') + def test_update_quant_with_forbidden_field(self): + """ + Test that updating a quant with a forbidden field raise an error. + """ + product = self.env['product.product'].create({ + 'name': 'Product', + 'type': 'product', + 'tracking': 'serial', + }) + sn1 = self.env['stock.lot'].create({ + 'name': 'SN1', + 'product_id': product.id, + }) + self.env['stock.quant']._update_available_quantity(product, self.stock_subloc2, 1.0, lot_id=sn1) + self.assertEqual(len(product.stock_quant_ids), 1) + self.env['stock.quant']._update_available_quantity(product, self.stock_subloc3, 1.0, lot_id=sn1) + self.assertEqual(len(product.stock_quant_ids), 2) + quant_2 = product.stock_quant_ids[1] + self.assertEqual(quant_2.with_context(inventory_mode=True).sn_duplicated, True) + with self.assertRaises(UserError): + quant_2.with_context(inventory_mode=True).write({'location_id': self.stock_subloc2}) + def test_relocate(self): """ Test the relocation wizard. """ def _get_relocate_wizard(quant_ids):