diff --git a/mrp_bom_configurable/__manifest__.py b/mrp_bom_configurable/__manifest__.py index 370cee0d0a4..e2b1b582c3e 100644 --- a/mrp_bom_configurable/__manifest__.py +++ b/mrp_bom_configurable/__manifest__.py @@ -24,10 +24,6 @@ "demo": [ "demo/mrp_bom_configurable.xml", ], - 'assets': { - 'web.assets_backend': [ - 'mrp_bom_variable/static/src/**/*' - ] - }, + "assets": {"web.assets_backend": ["mrp_bom_variable/static/src/**/*"]}, "installable": True, } diff --git a/mrp_bom_configurable/demo/mrp_bom_configurable.xml b/mrp_bom_configurable/demo/mrp_bom_configurable.xml index 46e727849c4..dde657dbc06 100644 --- a/mrp_bom_configurable/demo/mrp_bom_configurable.xml +++ b/mrp_bom_configurable/demo/mrp_bom_configurable.xml @@ -49,17 +49,17 @@ test - + test line - - + + test line - - + + False diff --git a/mrp_bom_configurable/models/__init__.py b/mrp_bom_configurable/models/__init__.py index 9da69624163..7583ac3f979 100644 --- a/mrp_bom_configurable/models/__init__.py +++ b/mrp_bom_configurable/models/__init__.py @@ -5,5 +5,5 @@ from odoo.tools import config -if not config["without_demo"]: +if not config["without_demo"] or config["test_enable"]: from . import demo_input_mixin diff --git a/mrp_bom_configurable/models/demo_input_mixin.py b/mrp_bom_configurable/models/demo_input_mixin.py index 6e4cce7f11c..aaa30fc6381 100644 --- a/mrp_bom_configurable/models/demo_input_mixin.py +++ b/mrp_bom_configurable/models/demo_input_mixin.py @@ -7,12 +7,15 @@ class InputMixin(models.AbstractModel): test_config = fields.Boolean(default=False, required=True) + class InputConfig(models.Model): _name = "input.config" _inherit = ["input.config", "input.mixin"] + CONFIG_ELEMENTS = ["test_config"] + class InputLine(models.Model): _name = "input.line" _inherit = ["input.line", "input.mixin"] @@ -30,7 +33,7 @@ def create(self, vals_list): def ui_configure(self): self.ensure_one() # TODO - lines, data, elements = [], [], dict() + elements = [], [], dict() for elm in CONFIG_ELEMENTS: if self._fields[elm].type == "many2one": value = self[elm].display_name @@ -40,18 +43,24 @@ def ui_configure(self): bom = self.bom_id content = bom.check_domain(elements) - self.env["mrp.bom"].create({ + self.env["mrp.bom"].create( + { "product_tmpl_id": bom.product_tmpl_id.id, "product_id": bom.product_id.id, "product_qty": self.count, "product_uom_id": bom.product_uom_id.id, "configuration_type": "configured", "bom_line_ids": [ - (0, 0, { - "product_id": line.product_id.id, - "product_qty": self.count * line.product_qty, - "product_uom_id": line.product_uom_id.id - }) + ( + 0, + 0, + { + "product_id": line.product_id.id, + "product_qty": self.count * line.product_qty, + "product_uom_id": line.product_uom_id.id, + }, + ) for line in content ], - }) + } + ) diff --git a/mrp_bom_configurable/models/input_line.py b/mrp_bom_configurable/models/input_line.py index f859fb83cf2..32e57944f9b 100644 --- a/mrp_bom_configurable/models/input_line.py +++ b/mrp_bom_configurable/models/input_line.py @@ -8,7 +8,9 @@ class Inputline(models.Model): name = fields.Char(required=True) sequence = fields.Integer() bom_id = fields.Many2one( - comodel_name="mrp.bom", required=True, domain=lambda s: s.bom_id.configuration_type == "variable" + comodel_name="mrp.bom", + required=True, + domain=lambda s: s.bom_id.configuration_type == "variable", ) config_id = fields.Many2one(comodel_name="input.config", required=True) count = fields.Integer(default=1) diff --git a/mrp_bom_configurable/models/mrp_bom.py b/mrp_bom_configurable/models/mrp_bom.py index f4600004927..94f936bfbfe 100644 --- a/mrp_bom_configurable/models/mrp_bom.py +++ b/mrp_bom_configurable/models/mrp_bom.py @@ -4,10 +4,15 @@ class MrpBom(models.Model): _inherit = "mrp.bom" - configuration_type = fields.Selection([ - ('variable', 'Variable BOM'), - ('configured', 'BOM from variable BOM'), ('normal', 'Normal BOM')], 'Configuration Type', - default='normal', required=True) + configuration_type = fields.Selection( + selection=[ + ("variable", "Variable BOM"), + ("configured", "BOM from variable BOM"), + ("normal", "Normal BOM"), + ], + default="normal", + required=True, + ) def check_domain(self, values): result = [] diff --git a/mrp_bom_configurable/models/mrp_bom_line.py b/mrp_bom_configurable/models/mrp_bom_line.py index 6e3390e3ac5..0423e5954ef 100644 --- a/mrp_bom_configurable/models/mrp_bom_line.py +++ b/mrp_bom_configurable/models/mrp_bom_line.py @@ -1,4 +1,5 @@ from odoo import fields, models +from odoo.tools.safe_eval import safe_eval class MrpBomLine(models.Model): @@ -26,14 +27,16 @@ def execute_domain_element(self, element, values): param, operator, value = element code = f"{repr(values[param])} {operator} {repr(value)}" - return eval(code) + return safe_eval(code) def execute_domain(self, domain, values): if not isinstance(domain, list): domain = [domain] if domain[0] == "OR": - return self.execute_domain(domain[1], values) or execute_domain(domain[2], values) + return self.execute_domain(domain[1], values) or self.execute_domain( + domain[2], values + ) elif len(domain) > 1: return all(self.execute_domain(domain_elm, values) for domain_elm in domain) else: @@ -44,6 +47,6 @@ def execute(self, values): if not self.domain: return True else: - domain = eval(self.domain) + domain = safe_eval(self.domain) return self.execute_domain(domain, values) diff --git a/mrp_bom_configurable/report/bom_structure.py b/mrp_bom_configurable/report/bom_structure.py index 49dc68332b3..c25980123b9 100644 --- a/mrp_bom_configurable/report/bom_structure.py +++ b/mrp_bom_configurable/report/bom_structure.py @@ -1,16 +1,16 @@ from odoo import api, models -from odoo import fields, models, api + class ReportBomStructure(models.AbstractModel): - _name = 'mrp_bom_variable.report.mrp.report_bom_structure' - _inherit = 'report.mrp.report_bom_structure' + _name = "mrp_bom_variable.report.mrp.report_bom_structure" + _inherit = "report.mrp.report_bom_structure" @api.model def _get_bom_data(self, *args, **kwargs): bom_report_line = super(ReportBomStructure, self)._get_bom_data(*args, **kwargs) - bom_line = kwargs.get('bom_line', False) + bom_line = kwargs.get("bom_line", False) - bom_report_line['domain'] = bom_line.domain if bom_line else False + bom_report_line["domain"] = bom_line.domain if bom_line else False return bom_report_line @@ -30,21 +30,26 @@ def _get_bom_data(self, *args, **kwargs): @api.model def _get_byproducts_lines(self, *args, **kwargs): - byproducts = super(ReportBomStructure, self)._get_byproducts_lines(*args, **kwargs) + byproducts = super(ReportBomStructure, self)._get_byproducts_lines( + *args, **kwargs + ) bom = args[1] + product = args[0] index = 0 for byproduct in bom.byproduct_ids: if byproduct._skip_byproduct_line(product): continue - byproducts[index]['domain'] = byproduct.domain + byproducts[index]["domain"] = byproduct.domain return byproducts @api.model def _get_component_data(self, *args, **kwargs): - component_data = super(ReportBomStructure, self)._get_component_data(*args, **kwargs) + component_data = super(ReportBomStructure, self)._get_component_data( + *args, **kwargs + ) bom_line = args[2] - component_data['domain'] = bom_line.domain if bom_line else False + component_data["domain"] = bom_line.domain if bom_line else False return component_data diff --git a/mrp_bom_configurable/static/src/components/mrp_bom_variable_overview.js b/mrp_bom_configurable/static/src/components/mrp_bom_variable_overview.esm.js similarity index 83% rename from mrp_bom_configurable/static/src/components/mrp_bom_variable_overview.js rename to mrp_bom_configurable/static/src/components/mrp_bom_variable_overview.esm.js index c8f263063f1..572b7551e5b 100644 --- a/mrp_bom_configurable/static/src/components/mrp_bom_variable_overview.js +++ b/mrp_bom_configurable/static/src/components/mrp_bom_variable_overview.esm.js @@ -7,39 +7,38 @@ import {BomOverviewComponent} from "@mrp/components/bom_overview/mrp_bom_overvie import {useService} from "@web/core/utils/hooks"; import {patch} from "@web/core/utils/patch"; -const { EventBus, onWillStart, useSubEnv, useState } = owl; - +const {EventBus, onWillStart, useSubEnv, useState} = owl; patch(BomOverviewTable.prototype, "test patch", { get showDomain() { return this.props.showOptions.domain; - } + }, }); patch(BomOverviewTable.props.showOptions, "test patch 2", { shape: { ...BomOverviewTable.props.showOptions.shape, domain: Boolean, - } + }, }); patch(BomOverviewDisplayFilter.prototype, "test patch 2", { setup() { this.displayOptions = { - availabilities: this.env._t('Availabilities'), - domain: this.env._t('Domain'), - leadTimes: this.env._t('Lead Times'), - costs: this.env._t('Costs'), - operations: this.env._t('Operations'), + availabilities: this.env._t("Availabilities"), + domain: this.env._t("Domain"), + leadTimes: this.env._t("Lead Times"), + costs: this.env._t("Costs"), + operations: this.env._t("Operations"), }; - } + }, }); patch(BomOverviewDisplayFilter.props.showOptions, "test patch 2", { shape: { ...BomOverviewTable.props.showOptions.shape, domain: Boolean, - } + }, }); patch(BomOverviewLine.prototype, "test patch", { @@ -48,15 +47,15 @@ patch(BomOverviewLine.prototype, "test patch", { }, get hasDomain() { - return this.data.hasOwnProperty('domain'); - } + return this.data.hasOwnProperty("domain"); + }, }); patch(BomOverviewLine.props.showOptions, "test patch 2", { shape: { ...BomOverviewTable.props.showOptions.shape, domain: Boolean, - } + }, }); patch(BomOverviewComponent.prototype, "test patch 3", { @@ -103,16 +102,17 @@ patch(BomOverviewComponent.prototype, "test patch 3", { this.state.bomQuantity, this.state.currentVariantId, ]; - const context = this.state.currentWarehouse ? { warehouse: this.state.currentWarehouse.id } : {}; + const context = this.state.currentWarehouse + ? {warehouse: this.state.currentWarehouse.id} + : {}; const bomData = await this.orm.call( "mrp_bom_variable.report.mrp.report_bom_structure", "get_html", args, - { context } + {context} ); this.state.bomData = bomData["lines"]; this.state.showOptions.attachments = bomData["has_attachments"]; return bomData; - } + }, }); - diff --git a/mrp_bom_configurable/static/src/components/mrp_templates.xml b/mrp_bom_configurable/static/src/components/mrp_templates.xml index afc840c9e5f..fcd2c745d7d 100644 --- a/mrp_bom_configurable/static/src/components/mrp_templates.xml +++ b/mrp_bom_configurable/static/src/components/mrp_templates.xml @@ -1,15 +1,25 @@ - + - + Domain - + - + diff --git a/mrp_bom_configurable/tests/test_mrp_bom_configurable.py b/mrp_bom_configurable/tests/test_mrp_bom_configurable.py index 1e35e6010fa..6b735146a5f 100644 --- a/mrp_bom_configurable/tests/test_mrp_bom_configurable.py +++ b/mrp_bom_configurable/tests/test_mrp_bom_configurable.py @@ -1,7 +1,6 @@ from odoo.tests.common import TransactionCase, tagged -@tagged("-standard", "bom_configurable") class TestBomVariable(TransactionCase): @classmethod def setUpClass(cls): @@ -17,37 +16,57 @@ def setUpClass(cls): # Create product cls.product_1 = cls.product_obj.create({"name": "TEST 01", "type": "product"}) - cls.component_1 = cls.product_obj.create({"name": "Product True", "type": "product"}) - cls.component_2 = cls.product_obj.create({"name": "Product False", "type": "product"}) - cls.component_3 = cls.product_obj.create({"name": "Product None", "type": "product"}) + cls.component_1 = cls.product_obj.create( + {"name": "Product True", "type": "product"} + ) + cls.component_2 = cls.product_obj.create( + {"name": "Product False", "type": "product"} + ) + cls.component_3 = cls.product_obj.create( + {"name": "Product None", "type": "product"} + ) # Create bom cls.bom = cls.bom_obj.create( {"product_tmpl_id": cls.product_1.product_tmpl_id.id} ) cls.line_1 = cls.bom_line_obj.create( - {"product_id": cls.component_1.id, "bom_id": cls.bom.id, "product_qty": 2.0, "domain": "[('test_config', '==', True)]"} + { + "product_id": cls.component_1.id, + "bom_id": cls.bom.id, + "product_qty": 2.0, + "domain": "[('test_config', '==', True)]", + } ) cls.line_2 = cls.bom_line_obj.create( - {"product_id": cls.component_2.id, "bom_id": cls.bom.id, "product_qty": 5.0, "domain": "[('test_config', '==', False)]"} + { + "product_id": cls.component_2.id, + "bom_id": cls.bom.id, + "product_qty": 5.0, + "domain": "[('test_config', '==', False)]", + } ) cls.line_3 = cls.bom_line_obj.create( {"product_id": cls.component_3.id, "bom_id": cls.bom.id, "product_qty": 5.0} ) # Create config - cls.input_config = cls.input_config_obj.create({ - "name": "Test config", - }) - cls.input_line = cls.input_config_line_obj.create({ - "name": "test_1", - "bom_id": cls.bom.id, - "config_id": cls.input_config.id, - "test_config": True - }) + cls.input_config = cls.input_config_obj.create( + { + "name": "Test config", + } + ) + cls.input_line = cls.input_config_line_obj.create( + { + "name": "test_1", + "bom_id": cls.bom.id, + "config_id": cls.input_config.id, + "test_config": True, + } + ) def test_01_variable_bom(self): self.input_line.ui_configure() - boms = self.env['mrp.bom'].search([('configuration_type', '=', 'configured')]) + boms = self.env["mrp.bom"].search([("configuration_type", "=", "configured")]) self.assertEqual(len(boms), 1) self.assertEqual(len(boms[0].bom_line_ids), 2) diff --git a/mrp_bom_configurable/views/mrp_view.xml b/mrp_bom_configurable/views/mrp_view.xml index 2ef452568be..fbf35bac729 100644 --- a/mrp_bom_configurable/views/mrp_view.xml +++ b/mrp_bom_configurable/views/mrp_view.xml @@ -18,7 +18,9 @@ - {'default_company_id': allowed_company_ids[0], 'search_default_variable': True, 'search_default_configured': False} + {'default_company_id': allowed_company_ids[0], 'search_default_variable': True, 'search_default_configured': False} @@ -26,8 +28,16 @@ - - + + diff --git a/setup/mrp_bom_configurable/odoo/addons/mrp_bom_configurable b/setup/mrp_bom_configurable/odoo/addons/mrp_bom_configurable new file mode 120000 index 00000000000..705b912c2df --- /dev/null +++ b/setup/mrp_bom_configurable/odoo/addons/mrp_bom_configurable @@ -0,0 +1 @@ +../../../../mrp_bom_configurable \ No newline at end of file diff --git a/setup/mrp_bom_variable/setup.py b/setup/mrp_bom_configurable/setup.py similarity index 100% rename from setup/mrp_bom_variable/setup.py rename to setup/mrp_bom_configurable/setup.py diff --git a/setup/mrp_bom_variable/odoo/addons/mrp_bom_variable b/setup/mrp_bom_variable/odoo/addons/mrp_bom_variable deleted file mode 120000 index 8cf92a267db..00000000000 --- a/setup/mrp_bom_variable/odoo/addons/mrp_bom_variable +++ /dev/null @@ -1 +0,0 @@ -../../../../mrp_bom_variable \ No newline at end of file diff --git a/setup/mrp_input_config/odoo/addons/mrp_input_config b/setup/mrp_input_config/odoo/addons/mrp_input_config deleted file mode 120000 index 84a8cd2d6d5..00000000000 --- a/setup/mrp_input_config/odoo/addons/mrp_input_config +++ /dev/null @@ -1 +0,0 @@ -../../../../mrp_input_config \ No newline at end of file diff --git a/setup/mrp_input_config/setup.py b/setup/mrp_input_config/setup.py deleted file mode 100644 index 28c57bb6403..00000000000 --- a/setup/mrp_input_config/setup.py +++ /dev/null @@ -1,6 +0,0 @@ -import setuptools - -setuptools.setup( - setup_requires=['setuptools-odoo'], - odoo_addon=True, -)