From 54eb69d6c31cd73e928cd08fec10237742e85993 Mon Sep 17 00:00:00 2001 From: daniquilez <dani.quilez@gmail.com> Date: Mon, 10 Mar 2025 15:17:16 +0100 Subject: [PATCH] =?UTF-8?q?[IMP]=20=E2=9C=A8=20Metadata=20strategy=20on=20?= =?UTF-8?q?sale=20order=20contract=20activation?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../__manifest__.py | 1 + .../components/contract_utils.py | 64 ++++++++++++------- .../components/sale_order_utils.py | 58 +++++------------ .../models/pack_type_mixin.py | 1 + .../models/sale_order.py | 24 +++---- .../views/sale_order_views.xml | 3 - .../service_invoicing_action_create.py | 17 +++-- 7 files changed, 81 insertions(+), 87 deletions(-) diff --git a/energy_communities_service_invoicing/__manifest__.py b/energy_communities_service_invoicing/__manifest__.py index 1a6ac870a..f7b8a1d59 100644 --- a/energy_communities_service_invoicing/__manifest__.py +++ b/energy_communities_service_invoicing/__manifest__.py @@ -15,6 +15,7 @@ "base", "contract", "sale", + "sale_order_metadata", "sales_team", "purchase", "product", diff --git a/energy_communities_service_invoicing/components/contract_utils.py b/energy_communities_service_invoicing/components/contract_utils.py index bd18f5196..181c63508 100644 --- a/energy_communities_service_invoicing/components/contract_utils.py +++ b/energy_communities_service_invoicing/components/contract_utils.py @@ -5,6 +5,20 @@ class ContractUtils(Component): _inherit = "contract.utils" def setup_initial_data(self): + self._set_configuration_journal_if_defined() + self._set_start_date(self.work.record.sale_order_id.commitment_date) + if "discount" in self.work.record.sale_order_id.metadata_line_ids.mapped("key"): + self._set_discount( + self.work.record.sale_order_id.get_metadata_value("discount") + ) + contract_update_dict = {"status": "paused"} + for contract_update_data in self.work.record.sale_order_id.metadata_line_ids: + if contract_update_data.key not in ["discount"]: + value = contract_update_data.value + # TODO: Not a very robust condition. Assuming all Many2one fields are defined with _id at the end + if "_id" in contract_update_data.key: + value = int(contract_update_data.value) + contract_update_dict[contract_update_data.key] = value for line in self.work.record.contract_line_ids: line.write( { @@ -15,7 +29,24 @@ class ContractUtils(Component): "quantity": 0, } ) - self.work.record.write({"status": "paused"}) + self.work.record.write(contract_update_dict) + + def _set_start_date(self, date_start): + self.work.record.write({"date_start": date_start}) + for line in self.work.record.contract_line_ids: + line.write({"date_start": date_start}) + line._compute_state() + + def _set_discount(self, discount): + for line in self.work.record.contract_line_ids: + line.write({"discount": discount}) + + # method to be extended if using component for another pack_type + def _set_configuration_journal_if_defined(self): + if self.work.record.pack_type == "platform_pack": + journal_id = self.work.record.company_id.service_invoicing_sale_journal_id + if journal_id: + self.work.record.write({"journal_id": journal_id.id}) def _activate_contract_lines(self, execution_date): for line in self.work.record.contract_line_ids: @@ -34,7 +65,7 @@ class ContractUtils(Component): def set_contract_status_active(self, execution_date): self._activate_contract_lines(execution_date) - self.set_start_date(execution_date) + self._set_start_date(execution_date) self.work.record.write({"status": "in_progress"}) def set_contract_status_closed(self, execution_date): @@ -45,23 +76,6 @@ class ContractUtils(Component): line._compute_state() self.work.record.set_close_status_type_by_date() - def set_start_date(self, date_start): - self.work.record.write({"date_start": date_start}) - for line in self.work.record.contract_line_ids: - line.write({"date_start": date_start}) - line._compute_state() - - def set_discount(self, discount): - for line in self.work.record.contract_line_ids: - line.write({"discount": discount}) - - # method to be extended if using component for another pack_type - def set_configuration_journal_if_defined(self): - if self.work.record.pack_type == "platform_pack": - journal_id = self.work.record.company_id.service_invoicing_sale_journal_id - if journal_id: - self.work.record.write({"journal_id": journal_id.id}) - def clean_non_service_lines(self): for line in self.work.record.contract_line_ids: if not self._is_service_line(line): @@ -141,7 +155,6 @@ class ContractUtils(Component): executed_action_description_list = executed_action_description.split(",") return { "company_id": self.work.record.partner_id.related_company_id, - "community_company_id": self.work.record.community_company_id, "pack_id": pack_id if "modify_pack" in executed_action_description_list else self.work.record.pack_id, @@ -154,9 +167,14 @@ class ContractUtils(Component): "start_date": execution_date, "executed_action": executed_action, "executed_action_description": executed_action_description, - "discount": discount - if "modify_discount" in executed_action_description_list - else self.work.record.discount, + "metadata": { + "community_company_id": self.work.record.community_company_id.id + if self.work.record.community_company_id + else False, + "discount": discount + if "modify_discount" in executed_action_description_list + else self.work.record.discount, + }, } def _is_service_line(self, contract_line): diff --git a/energy_communities_service_invoicing/components/sale_order_utils.py b/energy_communities_service_invoicing/components/sale_order_utils.py index e3e241ddc..460a084b1 100644 --- a/energy_communities_service_invoicing/components/sale_order_utils.py +++ b/energy_communities_service_invoicing/components/sale_order_utils.py @@ -5,21 +5,21 @@ from odoo.addons.energy_communities.utils import contract_utils class SaleOrderUtils(Component): _inherit = "sale.order.utils" - def create_service_invoicing_sale_order( + def _create_service_invoicing_sale_order( self, company_id, - community_company_id, pack_id, pricelist_id, payment_mode_id, start_date, executed_action, executed_action_description, + metadata, ): so_creation_dict = { "partner_id": company_id.partner_id.id, - # "company_id": company_id.id, - "community_company_id": community_company_id.id, + "company_id": self.env.company.id, + "commitment_date": start_date, "pricelist_id": pricelist_id.id, "service_invoicing_action": executed_action, "service_invoicing_action_description": executed_action_description, @@ -42,70 +42,46 @@ class SaleOrderUtils(Component): so_creation_dict[ "team_id" ] = self.env.company.service_invoicing_sale_team_id.id + if metadata: + metadata_list = [] + for meta_key in metadata.keys(): + metadata_list.append( + (0, 0, {"key": meta_key, "value": metadata[meta_key]}) + ) + so_creation_dict["metadata_line_ids"] = metadata_list sale_order = self.env["sale.order"].create(so_creation_dict) # Trigger name computattion in oder to include product's description_sale for order_line in sale_order.order_line: order_line._compute_name() return sale_order - def _create_service_invoicing( - self, - company_id, - community_company_id, - pack_id, - pricelist_id, - payment_mode_id, - start_date, - discount, - executed_action, - executed_action_description="none", - ): - so = self.create_service_invoicing_sale_order( - company_id, - community_company_id, - pack_id, - pricelist_id, - payment_mode_id, - start_date, - executed_action, - executed_action_description, - ) - so.action_confirm() - service_invoicing_id = self._get_related_contracts(so) - # TODO: We must call contract_utils with a better component and workcontext modification approach - with contract_utils(self.env, service_invoicing_id) as component: - component.clean_non_service_lines() - component.set_start_date(start_date) - component.set_discount(discount) - component.set_configuration_journal_if_defined() - return service_invoicing_id - def create_service_invoicing_initial( self, company_id, - community_company_id, pack_id, pricelist_id, start_date, - discount, executed_action, executed_action_description="none", payment_mode_id=False, + metadata=False, ): - service_invoicing_id = self._create_service_invoicing( + so = self._create_service_invoicing_sale_order( company_id, - community_company_id, pack_id, pricelist_id, payment_mode_id, start_date, - discount, executed_action, executed_action_description, + metadata, ) + so.action_confirm() + service_invoicing_id = self._get_related_contracts(so) # TODO: We must call contract_utils with a better component and workcontext modification approach with contract_utils(self.env, service_invoicing_id) as component: component.setup_initial_data() + component.clean_non_service_lines() if service_invoicing_id.is_free_pack: component.set_contract_status_active(start_date) return service_invoicing_id diff --git a/energy_communities_service_invoicing/models/pack_type_mixin.py b/energy_communities_service_invoicing/models/pack_type_mixin.py index 7d3ce9e2a..786ec9561 100644 --- a/energy_communities_service_invoicing/models/pack_type_mixin.py +++ b/energy_communities_service_invoicing/models/pack_type_mixin.py @@ -13,6 +13,7 @@ class PackTypeMixin(models.AbstractModel): compute_sudo=True, string="Pack Type", store=True, + default="none", ) def _get_pack_type_from_product_category(self, pack_type, category_id): diff --git a/energy_communities_service_invoicing/models/sale_order.py b/energy_communities_service_invoicing/models/sale_order.py index ad4b23c5a..67447ae36 100644 --- a/energy_communities_service_invoicing/models/sale_order.py +++ b/energy_communities_service_invoicing/models/sale_order.py @@ -7,12 +7,6 @@ class SaleOrder(models.Model): _name = "sale.order" _inherit = "sale.order" - community_company_id = fields.Many2one( - "res.company", - string="Related community", - domain="[('hierarchy_level','=','community')]", - ) - service_invoicing_action = fields.Selection( selection=_SALE_ORDER_SERVICE_INVOICING_ACTION_VALUES, required=True, @@ -26,16 +20,14 @@ class SaleOrder(models.Model): def action_create_contract(self): contracts = super().action_create_contract() - if self.community_company_id: - for contract in contracts: - contract.write( - { - "community_company_id": self.community_company_id.id, - "pricelist_id": self.pricelist_id.id, - "payment_mode_id": self.payment_mode_id.id, - "sale_order_id": self.id, - } - ) + for contract in contracts: + contract.write( + { + "pricelist_id": self.pricelist_id.id, + "payment_mode_id": self.payment_mode_id.id, + "sale_order_id": self.id, + } + ) return contracts def action_show_contracts(self): diff --git a/energy_communities_service_invoicing/views/sale_order_views.xml b/energy_communities_service_invoicing/views/sale_order_views.xml index 72c636d92..632add91b 100644 --- a/energy_communities_service_invoicing/views/sale_order_views.xml +++ b/energy_communities_service_invoicing/views/sale_order_views.xml @@ -11,9 +11,6 @@ attrs="{'readonly': 1,'invisible': [('service_invoicing_action','not in', ['modification','activate'])]}" /> </xpath> - <xpath expr="//field[@name='partner_id']" position="after"> - <field name="community_company_id" /> - </xpath> <xpath expr="//field[@name='company_id']" position="attributes"> <attribute name="required">0</attribute> </xpath> diff --git a/energy_communities_service_invoicing/wizards/service_invoicing_action_create.py b/energy_communities_service_invoicing/wizards/service_invoicing_action_create.py index fd06a8e04..d0c803047 100644 --- a/energy_communities_service_invoicing/wizards/service_invoicing_action_create.py +++ b/energy_communities_service_invoicing/wizards/service_invoicing_action_create.py @@ -57,7 +57,9 @@ class ServiceInvoicingActionCreateWizard(models.TransientModel): store=False, ) platform_pack_product_categ_id = fields.Many2one( - "product.category", compute="_compute_platform_pack_product_categ_id", store=False + "product.category", + compute="_compute_platform_pack_product_categ_id", + store=False, ) def _compute_platform_pack_product_categ_id(self): @@ -126,16 +128,19 @@ class ServiceInvoicingActionCreateWizard(models.TransientModel): # If none of previous create a new contract else: with sale_order_utils(self.env) as component: + # TODO: pass community_company_id as metadata service_invoicing_id = component.create_service_invoicing_initial( company_id, - community_company_id, self.platform_pack_id, self.pricelist_id, self.execution_date, - self.discount, "activate", "active_platform_service_invocing", payment_mode_id, + { + "community_company_id": community_company_id.id, + "discount": self.discount, + }, ) return service_invoicing_id @@ -182,7 +187,11 @@ class ServiceInvoicingActionCreateWizard(models.TransientModel): # Check if already open one and raise error for record in impacted_records: existing_contract = get_existing_open_pack_contract( - self.env, record.parent_id.partner_id, "platform_pack", contract_id=False, custom_query=[("community_company_id", "=", record.id)] + self.env, + record.parent_id.partner_id, + "platform_pack", + contract_id=False, + custom_query=[("community_company_id", "=", record.id)], ) if existing_contract: -- GitLab