oca-technical/odoo-bringout-oca-ddmrp-ddmrp/ddmrp/models/product_adu_calculation_method.py
2025-08-29 15:43:03 +02:00

99 lines
3.6 KiB
Python

# Copyright 2016-20 ForgeFlow S.L. (http://www.forgeflow.com)
# Copyright 2016 Aleph Objects, Inc. (https://www.alephobjects.com/)
# License LGPL-3.0 or later (https://www.gnu.org/licenses/lgpl.html).
from odoo import _, api, fields, models
from odoo.exceptions import ValidationError
class ProductAduCalculationMethod(models.Model):
_name = "product.adu.calculation.method"
_description = "Product Average Daily Usage calculation method"
@api.model
def _get_calculation_method(self):
return [
("fixed", _("Fixed ADU")),
("past", _("Past-looking")),
("future", _("Future-looking")),
("blended", _("Blended")),
]
@api.model
def _get_source_selection(self):
return [
("actual", "Use actual Stock Moves"),
("estimates", "Use Demand Estimates"),
("estimates_mrp", "Use Demand Estimates + Indirect Demand from MRP Moves"),
]
name = fields.Char(required=True)
method = fields.Selection(
selection="_get_calculation_method",
string="Calculation method",
)
source_past = fields.Selection(
selection="_get_source_selection",
string="Past Source",
help="Information source used for past calculation.",
)
horizon_past = fields.Float(
string="Past Horizon",
help="Length-of-period horizon in days looking past.",
)
factor_past = fields.Float(
string="Past Factor",
help="When using a blended method, this is the relative weight "
"assigned to the past part of the combination.",
default=0.5,
)
source_future = fields.Selection(
selection="_get_source_selection",
string="Future Source",
help="Information source used for future calculation.",
)
horizon_future = fields.Float(
string="Future Horizon",
help="Length-of-period horizon in days looking forward.",
)
factor_future = fields.Float(
string="Future Factor",
help="When using a blended method, this is the relative weight "
"assigned to the future part of the combination.",
default=0.5,
)
company_id = fields.Many2one(
comodel_name="res.company",
string="Company",
)
@api.constrains("method", "horizon_past", "horizon_future")
def _check_horizon(self):
for rec in self:
if rec.method in ["past", "blended"] and not rec.horizon_past:
raise ValidationError(_("Please indicate a Past Horizon."))
if rec.method in ["blended", "future"] and not rec.horizon_future:
raise ValidationError(_("Please indicate a Future Horizon."))
@api.constrains("method", "source_past", "source_future")
def _check_source(self):
for rec in self:
if rec.method in ["past", "blended"] and not rec.source_past:
raise ValidationError(_("Please indicate a Past Source."))
if rec.method in ["blended", "future"] and not rec.source_future:
raise ValidationError(_("Please indicate a Future Source."))
@api.constrains("method", "factor_past", "factor_future")
def _check_factor(self):
for rec in self.filtered(lambda r: r.method == "blended"):
if (
rec.factor_past + rec.factor_future != 1.0
or rec.factor_future < 0.0
or rec.factor_past < 0.0
):
raise ValidationError(
_(
"In blended method, past and future factors must be "
"positive and sum exactly 1,0."
)
)