diff --git a/custom_mrp_descarga/__manifest__.py b/custom_mrp_descarga/__manifest__.py
index d85393f4..c4913762 100644
--- a/custom_mrp_descarga/__manifest__.py
+++ b/custom_mrp_descarga/__manifest__.py
@@ -22,6 +22,9 @@
"stock_move_in_out_qty",
"mrp_production_date",
"stock_inventory_import_cost",
+ "product_expiry",
+ "stock_move_line_product_lot_reader",
+ "product_multi_company_usability",
],
"data": [
"data/quartering_product.xml",
diff --git a/custom_mrp_descarga/models/stock_inventory_line.py b/custom_mrp_descarga/models/stock_inventory_line.py
index c9c64f5e..486a329f 100644
--- a/custom_mrp_descarga/models/stock_inventory_line.py
+++ b/custom_mrp_descarga/models/stock_inventory_line.py
@@ -31,9 +31,13 @@ def onchange_cost(self):
if entry_line and sum(entry_line.mapped("qty_done")) != 0:
dev_line_amount = sum(dev_line.mapped("amount")) or 0
dev_line_qty = sum(dev_line.mapped("qty_done")) or 0
- self.cost = (sum(entry_line.mapped("amount")) - dev_line_amount) / (
- sum(entry_line.mapped("qty_done")) - dev_line_qty
- )
+ if sum(entry_line.mapped("qty_done")) - dev_line_qty != 0:
+ cost = (sum(entry_line.mapped("amount")) - dev_line_amount) / (
+ sum(entry_line.mapped("qty_done")) - dev_line_qty
+ )
+ else:
+ cost = 0
+ self.cost = cost
elif self.product_id:
entry_line = self.inventory_id.batch_id.move_line_ids.filtered(
lambda c: c.product_id == self.product_id
diff --git a/custom_mrp_descarga/models/stock_move_line.py b/custom_mrp_descarga/models/stock_move_line.py
index 2f29a730..07eb1ecd 100644
--- a/custom_mrp_descarga/models/stock_move_line.py
+++ b/custom_mrp_descarga/models/stock_move_line.py
@@ -1,5 +1,8 @@
# Copyright 2022 Berezi Amubieta - AvanzOSC
# License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl.html).
+from datetime import datetime
+
+import pytz
from odoo import _, api, fields, models
from odoo.exceptions import ValidationError
@@ -52,6 +55,115 @@ def _compute_performance(self):
performance = (line.qty_done * 100) / line.production_id.consume_qty
line.performance = performance
+ @api.onchange("reader")
+ def onchange_reader(self):
+ if self.reader:
+ if (
+ len(self.reader) == 44
+ and self.reader[16] == "1"
+ and self.reader[17] == "5"
+ ):
+ self.reader_44_15(reader=self.reader)
+ elif (
+ len(self.reader) == 46
+ and self.reader[16] == "3"
+ and self.reader[17] == "1"
+ ):
+ self.reader_46_31(reader=self.reader)
+ else:
+ message = _("Unidentified barcode format : %(reader)s") % {
+ "reader": self.reader,
+ }
+ raise ValidationError(message)
+
+ def reader_44_15(self, reader):
+ self.ensure_one()
+ if reader and len(reader) == 44 and reader[16] == "1" and reader[17] == "5":
+ product_code = reader[2:16]
+ product_domain = [("default_code", "=", product_code)]
+ product = (
+ self.env["product.product"]
+ .search(product_domain)
+ .filtered(
+ lambda c: c.company_id == self.company_id
+ or self.company_id in c.company_ids
+ )
+ )
+ if not product:
+ message = _(
+ "Product not found, reader information for product code: %(reader)s"
+ ) % {
+ "reader": product_code,
+ }
+ raise ValidationError(message)
+ self.product_id = product.id
+ expiration_date = reader[18:24]
+ timezone = pytz.timezone(self._context.get("tz") or "UTC")
+ expiration_date = datetime.strptime(expiration_date, "%y%m%d")
+ expiration_date = timezone.localize(expiration_date).astimezone(pytz.UTC)
+ expiration_date = expiration_date.replace(tzinfo=None)
+ qty_done = reader[28:31]
+ qty_done_decimal = reader[31:34]
+ qty_done = qty_done + "." + qty_done_decimal
+ qty_done = float(qty_done)
+ lot_name = reader[36:44]
+ lot_domain = [
+ ("name", "=", lot_name),
+ ("company_id", "=", self.company_id.id),
+ ("product_id", "=", product.id),
+ ]
+ lot = self.env["stock.production.lot"].search(lot_domain)
+ if not lot:
+ lot = self.env["stock.production.lot"].action_create_lot(
+ product, lot_name, self.company_id
+ )
+ self.write(
+ {
+ "expiration_date": expiration_date,
+ "qty_done": qty_done,
+ "lot_id": lot.id,
+ }
+ )
+
+ def reader_46_31(self, reader):
+ self.ensure_one()
+ if reader and len(reader) == 46 and reader[16] == "3" and reader[17] == "1":
+ product_code = reader[2:16]
+ product_domain = [("default_code", "=", product_code)]
+ product = (
+ self.env["product.product"]
+ .search(product_domain)
+ .filtered(
+ lambda c: c.company_id == self.company_id
+ or self.company_id in c.company_ids
+ )
+ )
+ if not product:
+ message = _(
+ "Product not found, reader information for product code: %(reader)s"
+ ) % {
+ "reader": product_code,
+ }
+ raise ValidationError(message)
+ self.product_id = product.id
+ qty_done = reader[20:23]
+ qty_done_decimal = reader[23:26]
+ qty_done = qty_done + "." + qty_done_decimal
+ container = int(reader[28:36])
+ lot_name = reader[38:46]
+ lot_domain = [
+ ("name", "=", lot_name),
+ ("company_id", "=", self.company_id.id),
+ ("product_id", "=", product.id),
+ ]
+ lot = self.env["stock.production.lot"].search(lot_domain)
+ if not lot:
+ lot = self.env["stock.production.lot"].action_create_lot(
+ product, lot_name, self.company_id
+ )
+ vals = {"container": container, "qty_done": qty_done, "lot_id": lot.id}
+ self.write(vals)
+
@api.onchange("unit")
def onchange_unit(self):
super(StockMoveLine, self).onchange_unit()
diff --git a/custom_mrp_descarga/views/stock_move_line_view.xml b/custom_mrp_descarga/views/stock_move_line_view.xml
index 133030d7..81e29153 100644
--- a/custom_mrp_descarga/views/stock_move_line_view.xml
+++ b/custom_mrp_descarga/views/stock_move_line_view.xml
@@ -64,6 +64,12 @@
+
+