Files
odoo_source/addons/stock/wizard/product_label_layout.py
T
clesgow b159190c7e [IMP] stock: display right number of labels in a ready pickings
When printing labels in a `ready` picking, if no quantities are set it
will only print the reserved quantities as labels.
Then, if a product has no reserved quantity, it will not have any
move_lines. Which means its initial demand won't be able to be fetched,
and the default behavior will be used, which is to print a single label.

By giving the moves instead of the move_lines to the wizard, we allow to
fetch for moves that have no reservation and print labels correctly
using their initial demand if no reservation is found.

The standard behavior once quantities are set remains untouched.

closes odoo/odoo#106414

Related: odoo/upgrade#4091
Signed-off-by: William Henrotin (whe) <whe@odoo.com>
2022-12-12 18:16:04 +01:00

48 lines
2.5 KiB
Python

# -*- coding: utf-8 -*-
# Part of Odoo. See LICENSE file for full copyright and licensing details.
from collections import defaultdict
from odoo import fields, models
from odoo.tools import float_compare, float_is_zero
class ProductLabelLayout(models.TransientModel):
_inherit = 'product.label.layout'
move_ids = fields.Many2many('stock.move')
picking_quantity = fields.Selection([
('picking', 'Transfer Quantities'),
('custom', 'Custom')], string="Quantity to print", required=True, default='custom')
print_format = fields.Selection(selection_add=[
('zpl', 'ZPL Labels'),
('zplxprice', 'ZPL Labels with price')
], ondelete={'zpl': 'set default', 'zplxprice': 'set default'})
def _prepare_report_data(self):
xml_id, data = super()._prepare_report_data()
if 'zpl' in self.print_format:
xml_id = 'stock.label_product_product'
quantities = defaultdict(int)
uom_unit = self.env.ref('uom.product_uom_categ_unit', raise_if_not_found=False)
if self.picking_quantity == 'picking' and self.move_ids and all(float_is_zero(ml.qty_done, precision_rounding=ml.product_uom_id.rounding) for ml in self.move_ids.move_line_ids):
for move in self.move_ids:
if move.product_uom.category_id == uom_unit:
use_reserved = float_compare(move.reserved_availability, 0, precision_rounding=move.product_uom.rounding) > 0
useable_qty = move.reserved_availability if use_reserved else move.product_uom_qty
if not float_is_zero(useable_qty, precision_rounding=move.product_uom.rounding):
quantities[move.product_id.id] += useable_qty
data['quantity_by_product'] = {p: int(q) for p, q in quantities.items()}
elif self.picking_quantity == 'picking' and self.move_ids.move_line_ids:
custom_barcodes = defaultdict(list)
for line in self.move_ids.move_line_ids:
if line.product_uom_id.category_id == uom_unit:
if (line.lot_id or line.lot_name) and int(line.qty_done):
custom_barcodes[line.product_id.id].append((line.lot_id.name or line.lot_name, int(line.qty_done)))
continue
quantities[line.product_id.id] += line.qty_done
# Pass only products with some quantity done to the report
data['quantity_by_product'] = {p: int(q) for p, q in quantities.items() if q}
data['custom_barcodes'] = custom_barcodes
return xml_id, data