[IMP] product_expiry, stock: include product barcodes in package content
When a product's barcode is EAN compliant (i.e. EAN-8, EAN-13, GTIN-14}) and feature to create DataMatrix is fully installed then we would like to print its GS1 datamatrix on the package content report. Additionally, if the product is tracked, we would like to include its SN/Lot if assigned one + any "use by"/"expiration date" to make the overall usefulness of the report go up. Part of Task: 2494740 Part-of: odoo/odoo#82389
This commit is contained in:
@@ -63,6 +63,7 @@ class BarcodeNomenclature(models.Model):
|
||||
barcode_sizes = {
|
||||
'ean8': 8,
|
||||
'ean13': 13,
|
||||
'gtin14': 14,
|
||||
'upca': 12,
|
||||
}
|
||||
barcode_size = barcode_sizes[encoding]
|
||||
|
||||
@@ -27,6 +27,7 @@ Also implements the removal strategy First Expiry First Out (FEFO) widely used,
|
||||
'wizard/confirm_expiry_view.xml',
|
||||
'report/report_deliveryslip.xml',
|
||||
'report/report_lot_barcode.xml',
|
||||
'report/report_package_barcode.xml',
|
||||
'data/product_expiry_data.xml'],
|
||||
'license': 'LGPL-3',
|
||||
}
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
<odoo>
|
||||
<template id="report_package_barcode_expiry" inherit_id="stock.report_package_barcode">
|
||||
<xpath expr="//t[@name='product_barcode_lot_datamatrix']" position="before">
|
||||
<t t-if="l.use_expiration_date">
|
||||
<t t-if="l.lot_id.use_date" t-set="product_barcode" t-value="product_barcode + '15' + l.lot_id.use_date.strftime('%y%m%d')"/>
|
||||
<t t-if="l.lot_id.expiration_date" t-set="product_barcode" t-value="product_barcode + '17' + l.lot_id.expiration_date.strftime('%y%m%d')"/>
|
||||
</t>
|
||||
</xpath>
|
||||
</template>
|
||||
</odoo>
|
||||
@@ -101,12 +101,20 @@ class Product(models.Model):
|
||||
storage_category_capacity_ids = fields.One2many('stock.storage.category.capacity', 'product_id', 'Storage Category Capacity')
|
||||
show_on_hand_qty_status_button = fields.Boolean(compute='_compute_show_qty_status_button')
|
||||
show_forecasted_qty_status_button = fields.Boolean(compute='_compute_show_qty_status_button')
|
||||
valid_ean = fields.Boolean('Barcode is valid EAN', compute='_compute_valid_ean')
|
||||
|
||||
def _compute_show_qty_status_button(self):
|
||||
for product in self:
|
||||
product.show_on_hand_qty_status_button = product.product_tmpl_id.show_on_hand_qty_status_button
|
||||
product.show_forecasted_qty_status_button = product.product_tmpl_id.show_forecasted_qty_status_button
|
||||
|
||||
@api.depends('barcode')
|
||||
def _compute_valid_ean(self):
|
||||
self.valid_ean = False
|
||||
for product in self:
|
||||
if product.barcode:
|
||||
product.valid_ean = self.env['barcode.nomenclature'].check_encoding(product.barcode.rjust(14, '0'), 'gtin14')
|
||||
|
||||
@api.depends('stock_move_ids.product_qty', 'stock_move_ids.state')
|
||||
@api.depends_context(
|
||||
'lot_id', 'owner_id', 'package_id', 'from_date', 'to_date',
|
||||
|
||||
@@ -24,14 +24,16 @@
|
||||
<p t-field="o.package_type_id.name"/>
|
||||
</div>
|
||||
</div>
|
||||
<table class="table table-sm" style="border-bottom: 0px solid white !important;">
|
||||
<table class="table table-sm table-striped" style="border-bottom: 0px solid white !important;">
|
||||
<t t-set="has_serial_number" t-value="o.quant_ids.mapped('lot_id')" />
|
||||
<t t-set="has_ean_barcode" t-value="env['ir.actions.report'].datamatrix_available() and any(valid_ean for valid_ean in o.quant_ids.product_id.mapped('valid_ean'))" />
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Product</th>
|
||||
<th name="th_quantity" class="text-right">Quantity</th>
|
||||
<th name="th_uom" groups="uom.group_uom"/>
|
||||
<th name="th_serial" class="text-right" t-if="has_serial_number">Lot/Serial Number</th>
|
||||
<th name="th_barcode" class="text-right" t-if="has_ean_barcode"/>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@@ -48,6 +50,15 @@
|
||||
<td class="text-right" t-if="has_serial_number">
|
||||
<t t-if="l.lot_id"><span t-field="l.lot_id.name"/></t>
|
||||
</td>
|
||||
<td class="text-right" t-if="has_ean_barcode">
|
||||
<t t-if="l.product_id.valid_ean">
|
||||
<t t-set="product_barcode" t-value="'01' + '0' * (14 - len(l.product_id.barcode)) + l.product_id.barcode"/>
|
||||
<!-- TODO: lot/sn ALWAYS has to be last part of barcode since left padding '0's = different sn/lot name match when scanning => fix when FNC1 can be used, -->
|
||||
<t name="product_barcode_lot_datamatrix" t-if="l.product_id.tracking == 'lot' and l.lot_id" t-set="product_barcode" t-value="product_barcode + '10' + l.lot_id.name"/>
|
||||
<t t-elif="l.product_id.tracking == 'serial' and l.lot_id" t-set="product_barcode" t-value="product_barcode + '21' + l.lot_id.name"/>
|
||||
<span t-out="product_barcode" t-options="{'widget': 'barcode', 'symbology': 'DataMatrix', 'width': 45, 'height': 45}"/>
|
||||
</t>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
Reference in New Issue
Block a user