From 54120e2e6908c6d81ce97f76cffd2d526fc7d805 Mon Sep 17 00:00:00 2001 From: benjamin <benjamin@le-filament.com> Date: Fri, 22 Nov 2024 15:22:16 +0100 Subject: [PATCH] [IMP] guarantee process --- README.md | 5 +- __manifest__.py | 7 +- models/__init__.py | 8 +- models/financial_contract.py | 23 --- models/financial_contract_guarantee.py | 150 ++++++++++++++++-- models/financial_contract_guarantee_line.py | 77 +++++++++ ...contract_guarantee_suspensive_condition.py | 33 ++++ ..._product_guarantee_suspensive_condition.py | 33 ++++ .../financial_product_template_guarantee.py | 20 +-- models/res_company.py | 63 ++++++++ models/res_partner.py | 63 ++++++++ security/ir.model.access.csv | 6 + static/description/icon.png | Bin 9161 -> 15590 bytes views/financial_contract_guarantee.xml | 69 +++++--- views/financial_contract_guarantee_line.xml | 127 +++++++++++++++ .../financial_product_template_guarantee.xml | 97 +++++++++++ views/menus.xml | 10 +- views/res_partner.xml | 37 +++++ 18 files changed, 753 insertions(+), 75 deletions(-) delete mode 100644 models/financial_contract.py create mode 100644 models/financial_contract_guarantee_line.py create mode 100644 models/financial_contract_guarantee_suspensive_condition.py create mode 100644 models/financial_product_guarantee_suspensive_condition.py create mode 100644 models/res_company.py create mode 100644 models/res_partner.py mode change 100755 => 100644 static/description/icon.png create mode 100644 views/financial_contract_guarantee_line.xml create mode 100644 views/financial_product_template_guarantee.xml create mode 100644 views/res_partner.xml diff --git a/README.md b/README.md index 45e0ef9..6b30e4c 100644 --- a/README.md +++ b/README.md @@ -1,8 +1,7 @@ -# Financial - Deal Flow +# Financial - Guarantee Contract ## Description -Ce module ajoute la gestion du deal flow des outils financiers - +Ajoute la gestion des garanties de prêt pour les contrats. ## Credits Le développement de ce module a été financé par / The development of this module has been financially supported by: diff --git a/__manifest__.py b/__manifest__.py index 008001a..e91974a 100644 --- a/__manifest__.py +++ b/__manifest__.py @@ -1,6 +1,6 @@ { - "name": "Financial - Contract", - "summary": "Gestion des contrats des outils financiers", + "name": "Financial - Guarantee Contract", + "summary": "Gestion des contrats de garantie des outils financiers", "author": "Le Filament, Odoo Community Association (OCA)", "website": "https://le-filament.com", "version": "16.0.1.0.0", @@ -14,6 +14,9 @@ # datas # views "views/financial_contract_guarantee.xml", + "views/financial_contract_guarantee_line.xml", + "views/financial_product_template_guarantee.xml", + "views/res_partner.xml", # views menu "views/menus.xml", # wizard diff --git a/models/__init__.py b/models/__init__.py index 4bc2b14..1de888b 100644 --- a/models/__init__.py +++ b/models/__init__.py @@ -1,3 +1,7 @@ -from . import financial_contract from . import financial_contract_guarantee -# from . import financial_product_template_guarantee +from . import financial_contract_guarantee_line +from . import financial_contract_guarantee_suspensive_condition +from . import financial_product_guarantee_suspensive_condition +from . import financial_product_template_guarantee +from . import res_company +from . import res_partner diff --git a/models/financial_contract.py b/models/financial_contract.py deleted file mode 100644 index f717a7e..0000000 --- a/models/financial_contract.py +++ /dev/null @@ -1,23 +0,0 @@ -# © 2019 Le Filament (<http://www.le-filament.com>) -# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). - -from odoo import fields, models - - -class FinancialContract(models.Model): - _inherit = "financial.contract" - - tool = fields.Selection( - selection_add=[ - ("financial.contract.guarantee", "Prêt"), - ], - ondelete={"financial.contract.guarantee": "cascade"}, - ) - - # ------------------------------------------------------ - # Computed fields / Search Fields - # ------------------------------------------------------ - - # ------------------------------------------------------ - # CRUD (Override ORM) - # ------------------------------------------------------ diff --git a/models/financial_contract_guarantee.py b/models/financial_contract_guarantee.py index 2e0dd0e..0353ebd 100644 --- a/models/financial_contract_guarantee.py +++ b/models/financial_contract_guarantee.py @@ -1,16 +1,16 @@ # © 2024 Le Filament (<http://www.le-filament.com>) # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). -from odoo import fields, models +from odoo import Command, api, fields, models class FinancialContractGuarantee(models.Model): _name = "financial.contract.guarantee" _inherit = [ + "financial.contract", "mail.thread", "mail.activity.mixin", ] - _inherits = {"financial.contract": "contract_id"} _description = "Financial contract guarantee" _check_company_auto = True _rec_names_search = [ @@ -21,21 +21,88 @@ class FinancialContractGuarantee(models.Model): ] _order = "create_date desc" + product_id = fields.Many2one( + comodel_name="financial.product.template.guarantee", + string="Gamme", + required=True, + ) + suspensive_condition_ids = fields.One2many( + comodel_name="financial.contract.guarantee.suspensive.condition", + inverse_name="contract_id", + compute="_compute_suspensive_condition_ids", + store=True, + readonly=False, + ) + # TODO: voir pour la gestion de ce champ avec le module contract external external_loan_id = fields.Many2one( - comodel_name="financial.contract", + comodel_name="financial.contract.external", string="Prêt lié", - domain="[('partner_id', '=', partner_id), ('type', '=', 'loan'), " - "('deal_type', '=', 'external')]", - financial_tool_type="guarantee", + domain="[('partner_id', '=', partner_id), ('tool', '=', 'loan')]", + ) + loan_contract_number = fields.Char( + string="Numéro de contrat de prêt", + related="external_loan_id.number", + store=True, ) - guarantee_rate = fields.Float("Quotité garantie", tracking=1) + is_counter_guarantee = fields.Boolean("Contre Garantie", default=False) - bdf_scoring = fields.Char("Cotations BDF") - loan_balance = fields.Monetary("Solde créance") - guarantee_balance = fields.Monetary("Solde Garantie") fmg_amount = fields.Monetary("Montant FMG") social_share_amount = fields.Monetary("Montant parts sociales") - final_risk_guarantee = fields.Monetary("Garantie risque final", tracking=1) + final_risk_guarantee = fields.Monetary( + string="Garantie risque final", + compute="_compute_final_risk_guarantee", + store=True, + tracking=1, + ) + + line_ids = fields.One2many( + comodel_name="financial.contract.guarantee.line", + inverse_name="guarantee_id", + string="Lignes de solde", + ) + + # loan_balance = fields.Monetary( + # string="Solde créance", + # compute="_compute_balance", + # store=True, + # tracking=2, + # ) + # guarantee_balance = fields.Monetary( + # string="Solde Garantie", + # compute="_compute_balance", + # store=True, + # tracking=2, + # ) + + # Loan Data + payment_date = fields.Date("Date de versement") + amount_initial = fields.Monetary("Montant initial") + amount_received = fields.Monetary("Montant reçu") + end_date = fields.Date("Date de fin de prêt") + remaining_capital = fields.Monetary("Capital restant dû") + loan_duration = fields.Integer("Durée du crédit") + guarantee_rate = fields.Float("Quotité garantie") + guarantee_amount = fields.Monetary("En cours garanti") + # Company Data + segment_code = fields.Char("Code Segment") + bdf_scoring = fields.Char( + string="Cotation BDF", + compute="_compute_guarantee_data", + store=True, + readonly=False, + tracking=2, + ) + bdf_date = fields.Char("Date Cotation BDF") + mcdo_scoring = fields.Char("Cotation MacDonough") + mcdo_date = fields.Date("Date Cotation MacDonough") + branch_code = fields.Char("Code branche") + + # Invoice Data + commission_amount = fields.Monetary( + string="Montant de commission", + compute="_compute_commission_amount", + store=True, + ) # ------------------------------------------------------ # Constrains functions @@ -44,6 +111,60 @@ class FinancialContractGuarantee(models.Model): # ------------------------------------------------------ # Computed fields / Search Fields # ------------------------------------------------------ + @api.depends( + "line_ids", + "line_ids.bdf_scoring", + ) + def _compute_guarantee_data(self): + for guarantee in self: + last_line = guarantee.line_ids.sorted("line_date desc") + guarantee.update({"bdf_scoring": last_line.bdf_scoring}) + + @api.depends( + "line_ids", + "line_ids.commission_amount", + ) + def _compute_guarantee_data(self): + for guarantee in self: + guarantee.commission_amount = sum( + guarantee.line_ids.mapped("commission_amount") + ) + + # @api.depends() + # def _compute_balance(self): + # for guarantee in self: + # guarantee.loan_balance = 0 + # guarantee.guarantee_balance = 0 + + @api.depends() + def _compute_final_risk_guarantee(self): + for guarantee in self: + guarantee.final_risk_guarantee = 0 + + @api.depends("product_id") + def _compute_suspensive_condition_ids(self): + for contract in self: + condition_to_create = [] + if contract.product_id: + for condition in self.product_id.suspensive_condition_ids: + condition_to_create.append( + Command.create( + { + "condition_id": condition.id, + "condition_comment": condition.condition_comment, + }, + ) + ) + if condition_to_create: + contract.suspensive_condition_ids.unlink() + contract.suspensive_condition_ids = condition_to_create + + # ------------------------------------------------------ + # Onchange + # ------------------------------------------------------ + @api.onchange("product_id") + def _onchange_product_id(self): + self._set_product_values() # ------------------------------------------------------ # Actions @@ -52,3 +173,10 @@ class FinancialContractGuarantee(models.Model): # ------------------------------------------------------ # CRUD (Override ORM) # ------------------------------------------------------ + + # ------------------------------------------------------ + # Business functions + # ------------------------------------------------------ + def _set_product_values(self): + if self.product_id: + self.guarantee_rate = self.product_id.guarantee_rate diff --git a/models/financial_contract_guarantee_line.py b/models/financial_contract_guarantee_line.py new file mode 100644 index 0000000..5ec0d82 --- /dev/null +++ b/models/financial_contract_guarantee_line.py @@ -0,0 +1,77 @@ +# © 2024 Le Filament (<http://www.le-filament.com>) +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). + +from odoo import fields, models + + +class FinancialContractGuaranteeLine(models.Model): + _name = "financial.contract.guarantee.line" + _description = "Financial contract guarantee line" + _check_company_auto = True + _rec_names_search = [ + "partner_id.name", + "partner_id.member_number", + ] + _order = "line_date desc" + + guarantee_id = fields.Many2one( + comodel_name="financial.contract.guarantee", + string="Contrat de garantie", + required=True, + index=True, + ) + partner_id = fields.Many2one( + comodel_name="res.partner", + related="guarantee_id.partner_id", + string="Contact", + store=True, + index=True, + ) + company_id = fields.Many2one( + comodel_name="res.company", + related="guarantee_id.company_id", + string="Société", + store=True, + index=True, + ) + currency_id = fields.Many2one( + comodel_name="res.currency", + related="guarantee_id.currency_id", + ) + # Loan Data + line_date = fields.Date("Date en cours") + payment_date = fields.Date("Date de versement") + amount_initial = fields.Monetary("Montant initial") + amount_received = fields.Monetary("Montant reçu") + end_date = fields.Date("Date de fin de prêt") + remaining_capital = fields.Monetary("Capital restant dû") + loan_duration = fields.Integer("Durée du crédit") + guarantee_rate = fields.Float("Quotité garantie") + guarantee_amount = fields.Monetary("En cours garanti") + # Company Data + segment_code = fields.Char("Code Segment") + bdf_scoring = fields.Char("Cotation BDF") + bdf_date = fields.Char("Date Cotation BDF") + mcdo_scoring = fields.Char("Cotation MacDonough") + mcdo_date = fields.Date("Date Cotation MacDonough") + branch_code = fields.Char("Code branche") + # Invoice Data + commission_rate = fields.Float("Taux de commission") + commission_amount = fields.Monetary("Montant de commission") + commission_date_due = fields.Date("Echeance de commission") + + # ------------------------------------------------------ + # Constrains functions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Computed fields / Search Fields + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Actions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # CRUD (Override ORM) + # ------------------------------------------------------ diff --git a/models/financial_contract_guarantee_suspensive_condition.py b/models/financial_contract_guarantee_suspensive_condition.py new file mode 100644 index 0000000..36a28f8 --- /dev/null +++ b/models/financial_contract_guarantee_suspensive_condition.py @@ -0,0 +1,33 @@ +# © 2024 Le Filament (<http://www.le-filament.com>) +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). + +from odoo import fields, models + + +class FinancialContractGuaranteeSuspensiveCondition(models.Model): + _name = "financial.contract.guarantee.suspensive.condition" + _inherit = ["financial.contract.suspensive.condition"] + _description = "Financial contract suspensive condition" + + contract_id = fields.Many2one( + comodel_name="financial.contract.guarantee", + string="Contrat", + required=True, + ondelete="cascade", + ) + + # ------------------------------------------------------ + # Constrains functions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Computed fields / Search Fields + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Actions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # CRUD (Override ORM) + # ------------------------------------------------------ diff --git a/models/financial_product_guarantee_suspensive_condition.py b/models/financial_product_guarantee_suspensive_condition.py new file mode 100644 index 0000000..51c67d7 --- /dev/null +++ b/models/financial_product_guarantee_suspensive_condition.py @@ -0,0 +1,33 @@ +# © 2024 Le Filament (<http://www.le-filament.com>) +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). + +from odoo import fields, models + + +class FinancialProductGuaranteeSuspensiveCondition(models.Model): + _name = "financial.product.guarantee.suspensive.condition" + _inherit = ["financial.product.suspensive.condition"] + _description = "Financial product guarantee suspensive condition" + + product_id = fields.Many2one( + comodel_name="financial.product.template.guarantee", + string="Produit", + required=True, + ondelete="cascade", + ) + + # ------------------------------------------------------ + # Constrains functions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Computed fields / Search Fields + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Actions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # CRUD (Override ORM) + # ------------------------------------------------------ diff --git a/models/financial_product_template_guarantee.py b/models/financial_product_template_guarantee.py index 06494db..92c61e3 100644 --- a/models/financial_product_template_guarantee.py +++ b/models/financial_product_template_guarantee.py @@ -7,25 +7,19 @@ from odoo import fields, models class FinancialProductTemplateGuarantee(models.Model): _name = "financial.product.template.guarantee" _inherit = [ + "financial.product.template", "mail.thread", "mail.activity.mixin", ] - _inherits = {"financial.product.template": "product_id"} _description = "Financial product template guarantee" - tool = fields.Selection( - selection_add=[ - ("financial.contract.guarantee", "Garantie"), - ], - ondelete={"financial.contract.guarantee": "cascade"}, - ) - product_id = fields.Many2one( - comodel_name="financial.product.template", - string="Produit", - required=True, - index=True, - ondelete="cascade", + guarantee_rate = fields.Float("Quotité garantie") + suspensive_condition_ids = fields.One2many( + comodel_name="financial.product.guarantee.suspensive.condition", + inverse_name="product_id", + string="Conditions suspensives", ) + # ------------------------------------------------------ # Constrains functions # ------------------------------------------------------ diff --git a/models/res_company.py b/models/res_company.py new file mode 100644 index 0000000..55698fe --- /dev/null +++ b/models/res_company.py @@ -0,0 +1,63 @@ +# Copyright 2023- Le Filament (https://le-filament.com) +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html) + +from odoo import api, fields, models + + +class ResCompany(models.Model): + _inherit = "res.company" + + contract_guarantee_sequence_id = fields.Many2one("ir.sequence") + + # ------------------------------------------------------ + # Fields declaration + # ------------------------------------------------------ + + # ------------------------------------------------------ + # SQL Constraints + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Default methods + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Computed fields / Search Fields + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Onchange / Constraints + # ------------------------------------------------------ + + # ------------------------------------------------------ + # CRUD methods (ORM overrides) + # ------------------------------------------------------ + @api.model_create_multi + def create(self, values): + """ + Crée une séquence dédiée à la société + """ + res = super().create(values) + for company in res: + company.contract_guarantee_sequence_id = self.env["ir.sequence"].create( + { + "name": f"Contrats Financiers : Garantie - {res.name}", + "company_id": res.id, + "number_next": 1, + "number_increment": 1, + "use_date_range": True, + "prefix": "G%(year)s%(month)s", + "padding": 4, + "implementation": "no_gap", + "code": f"financial.contract.guarantee.company_{res.id}", + } + ) + return res + + # ------------------------------------------------------ + # Actions + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Business methods + # ------------------------------------------------------ diff --git a/models/res_partner.py b/models/res_partner.py new file mode 100644 index 0000000..a53ea3a --- /dev/null +++ b/models/res_partner.py @@ -0,0 +1,63 @@ +# Copyright 2023- Le Filament (https://le-filament.com) +# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html) + +from odoo import fields, models + + +class ResPartner(models.Model): + _inherit = "res.partner" + + # ------------------------------------------------------ + # Fields declaration + # ------------------------------------------------------ + financial_contract_guarantee_ids = fields.One2many( + comodel_name="financial.contract.guarantee", + inverse_name="partner_id", + string="Contrats de garanties", + ) + financial_contract_guarantee_count = fields.Integer( + compute="_compute_financial_contract_guarantee_count" + ) + + # ------------------------------------------------------ + # SQL Constraints + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Default methods + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Computed fields / Search Fields + # ------------------------------------------------------ + def _compute_financial_contract_guarantee_count(self): + for partner in self: + partner.financial_contract_guarantee_count = ( + partner.financial_contract_guarantee_ids.__len__() + ) + + # ------------------------------------------------------ + # Onchange / Constraints + # ------------------------------------------------------ + + # ------------------------------------------------------ + # CRUD methods (ORM overrides) + # ------------------------------------------------------ + + # ------------------------------------------------------ + # Actions + # ------------------------------------------------------ + def action_view_contract_guarantee(self): + self.ensure_one() + return { + "type": "ir.actions.act_window", + "name": "Contrats de garantie", + "res_model": "financial.contract.guarantee", + "view_mode": "tree,form", + "domain": [("partner_id", "=", self.id)], + "flags": {"mode": "readonly"}, + } + + # ------------------------------------------------------ + # Business methods + # ------------------------------------------------------ diff --git a/security/ir.model.access.csv b/security/ir.model.access.csv index ac9637c..dd9292b 100644 --- a/security/ir.model.access.csv +++ b/security/ir.model.access.csv @@ -1,2 +1,8 @@ id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink access_financial_contract_guarantee,access_financial_contract_guarantee,model_financial_contract_guarantee,financial_contract.group_financial_user,1,1,1,1 +access_financial_contract_guarantee_line,access_financial_contract_guarantee_line,model_financial_contract_guarantee_line,financial_contract.group_financial_user,1,1,1,1 +access_financial_product_template_guarantee,access_financial_product_template_guarantee,model_financial_product_template_guarantee,financial_contract.group_financial_user,1,0,0,0 +access_financial_product_template_guarantee_admin,access_financial_product_template_guarantee,model_financial_product_template_guarantee,financial_contract.group_financial_admin,1,1,1,1 +access_financial_contract_guarantee_suspensive_condition,access_financial_contract_guarantee_suspensive_condition,model_financial_contract_guarantee_suspensive_condition,financial_contract.group_financial_user,1,1,1,1 +access_financial_product_guarantee_suspensive_condition,access_financial_product_guarantee_suspensive_condition,model_financial_product_guarantee_suspensive_condition,financial_contract.group_financial_user,1,0,0,0 +access_financial_product_guarantee_suspensive_condition_admin,access_financial_product_guarantee_suspensive_condition_admin,model_financial_product_guarantee_suspensive_condition,financial_contract.group_financial_admin,1,1,1,1 diff --git a/static/description/icon.png b/static/description/icon.png old mode 100755 new mode 100644 index 82ef47760a441cf229b5009f0a18ccf3842fbfa5..2b426e06b3a8f298795f598a50bcb1ae195d1c30 GIT binary patch literal 15590 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 delta 8989 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 OVDNPHb6Mw<&;$T47SMeF diff --git a/views/financial_contract_guarantee.xml b/views/financial_contract_guarantee.xml index 78d8e22..b37e019 100644 --- a/views/financial_contract_guarantee.xml +++ b/views/financial_contract_guarantee.xml @@ -5,23 +5,19 @@ <!-- Tree Guarantee --> <record id="financial_contract_guarantee_tree_view" model="ir.ui.view"> <field name="name">financial.contract.guarantee.tree</field> - <field name="model">financial.contract</field> + <field name="model">financial.contract.guarantee</field> <field name="arch" type="xml"> <tree> <field name="currency_id" invisible="1" /> - <field name="tool" invisible="1" /> <field name="partner_id" /> - <field name="product_id" /> <field name="state" /> <field name="expiration_date" /> <field name="amount" string="Montant" /> <field name="external_loan_id" /> <field name="fmg_amount" /> <field name="social_share_amount" /> - <field name="guarantee_rate" /> + <field name="guarantee_rate" widget="percentage" /> <field name="is_counter_guarantee" /> - <field name="loan_balance" /> - <field name="guarantee_balance" /> <field name="final_risk_guarantee" /> <field name="payment_date" /> <field name="company_id" /> @@ -39,19 +35,55 @@ /> <field name="mode">primary</field> <field name="arch" type="xml"> - <xpath expr="//group" position="inside"> - <group> - <field name="external_loan_id" /> - <field name="fmg_amount" /> - <field name="social_share_amount" /> - <field name="guarantee_rate" /> - <field name="is_counter_guarantee" /> - <field name="loan_balance" /> - <field name="guarantee_balance" /> - <field name="final_risk_guarantee" /> + <xpath expr="//field[@name='amount']" position="attributes"> + <attribute name="invisible">1</attribute> + </xpath> + + <xpath expr="//group[@name='contract_data']" position="inside"> + <field name="external_loan_id" options="{'no_create': 1}" /> + <field name="guarantee_rate" widget="percentage" /> + <field name="fmg_amount" /> + <field name="social_share_amount" /> + <field name="is_counter_guarantee" /> + </xpath> + <xpath expr="//group[@name='contract_data']" position="after"> +<!-- <group name="guarantee" string="Données de la garantie">--> +<!-- <field name="currency_id" invisible="1" />--> +<!-- --> +<!-- </group>--> + + <group name="loan_data" string="Données du prêt lié"> <field name="payment_date" /> - <field name="company_id" /> + <field name="amount_initial" /> + <field name="amount_received" /> + <field name="remaining_capital" /> + </group> + <group name="company_data" string="Notation"> + <field name="segment_code" /> + <field name="branch_code" /> + <field name="bdf_scoring" /> + <field name="bdf_date" /> + <field name="mcdo_scoring" /> + <field name="mcdo_date" /> </group> + <group name="invoice_data" string="Commissions"> + <field name="commission_amount" /> + </group> + </xpath> + <xpath expr="//field[@name='comment']" position="after"> + <separator string="Conditions suspensives" /> + <field + name="suspensive_condition_ids" + context="{'default_contract_id': active_id}" + > + <tree editable="top"> + <field name="contract_id" invisible="1" /> + <field name="condition_id" /> + <field name="condition_comment" /> + <field name="comment" /> + <field name="date_done" /> + </tree> + </field> </xpath> </field> </record> @@ -64,9 +96,6 @@ <field name="name">Garanties</field> <field name="res_model">financial.contract.guarantee</field> <field name="view_mode">tree,form</field> - <field - name="domain" - >[('state', 'in', ['proposal', 'contract', 'done', 'cancel'])]</field> </record> </odoo> diff --git a/views/financial_contract_guarantee_line.xml b/views/financial_contract_guarantee_line.xml new file mode 100644 index 0000000..d9be051 --- /dev/null +++ b/views/financial_contract_guarantee_line.xml @@ -0,0 +1,127 @@ +<?xml version="1.0" ?> +<!-- Copyright 2024 Le Filament + License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). --> +<odoo> + <!-- Tree --> + <record id="financial_contract_guarantee_line_tree_view" model="ir.ui.view"> + <field name="name">financial.contract.guarantee.line.tree</field> + <field name="model">financial.contract.guarantee.line</field> + <field name="arch" type="xml"> + <tree> + <field name="currency_id" invisible="1" /> + <field name="line_date" /> + <field name="partner_id" /> + <field name="guarantee_id" /> + <field name="payment_date" /> + <field name="amount_initial" optional="show" /> + <field name="amount_received" optional="show" /> + <field name="end_date" /> + <field name="remaining_capital" /> + <field name="loan_duration" /> + <field name="guarantee_rate" widget="percentage" /> + <field name="guarantee_amount" /> + <field name="segment_code" optional="show" /> + <field name="bdf_scoring" optional="show" /> + <field name="bdf_date" optional="show" /> + <field name="mcdo_scoring" optional="show" /> + <field name="mcdo_date" optional="show" /> + <field name="branch_code" optional="show" /> + <field + name="commission_rate" + widget="percentage" + optional="show" + /> + <field name="commission_amount" optional="show" /> + <field name="commission_date_due" optional="show" /> + </tree> + </field> + </record> + + <record + id="financial_contract_guarantee_line_light_tree_view" + model="ir.ui.view" + > + <field name="name">financial.contract.guarantee.line.tree</field> + <field name="model">financial.contract.guarantee.line</field> + <field name="arch" type="xml"> + <tree> + <field name="currency_id" invisible="1" /> + <field name="line_date" /> + <field name="partner_id" invisible="1" /> + <field name="guarantee_id" invisible="1" /> + <field name="payment_date" optional="hide" /> + <field name="amount_initial" optional="show" /> + <field name="amount_received" optional="show" /> + <field name="end_date" /> + <field name="remaining_capital" /> + <field name="loan_duration" /> + <field name="guarantee_rate" widget="percentage" /> + <field name="guarantee_amount" /> + <field name="segment_code" optional="hide" /> + <field name="bdf_scoring" optional="hide" /> + <field name="bdf_date" optional="hide" /> + <field name="mcdo_scoring" optional="hide" /> + <field name="mcdo_date" optional="hide" /> + <field name="branch_code" optional="hide" /> + <field + name="commission_rate" + widget="percentage" + optional="show" + /> + <field name="commission_amount" optional="show" /> + <field name="commission_date_due" optional="show" /> + </tree> + </field> + </record> + + <!-- Form --> + <record model="ir.ui.view" id="financial_contract_guarantee_line_form_view"> + <field name="name">financial.contract.guarantee.line.form</field> + <field name="model">financial.contract.guarantee.line</field> + <field name="mode">primary</field> + <field name="arch" type="xml"> + <form string="Guarantee Line"> + <sheet> + <group> + <group name="guarantee" string="Contrat"> + <field name="currency_id" invisible="1" /> + <field name="line_date" /> + <field + name="partner_id" + options="{'no_create': 1}" + /> + <field + name="guarantee_id" + options="{'no_create': 1}" + /> + </group> + <group name="loan_data" string="Données du prêt"> + <field name="payment_date" /> + <field name="amount_initial" /> + <field name="amount_received" /> + <field name="end_date" /> + <field name="remaining_capital" /> + <field name="loan_duration" /> + <field name="guarantee_rate" widget="percentage" /> + <field name="guarantee_amount" /> + </group> + <group name="company_data" string="Notation"> + <field name="segment_code" /> + <field name="branch_code" /> + <field name="bdf_scoring" /> + <field name="bdf_date" /> + <field name="mcdo_scoring" /> + <field name="mcdo_date" /> + </group> + <group name="invoice_data" string="Commissions"> + <field name="commission_rate" widget="percentage" /> + <field name="commission_amount" /> + <field name="commission_date_due" /> + </group> + </group> + </sheet> + </form> + </field> + </record> + +</odoo> diff --git a/views/financial_product_template_guarantee.xml b/views/financial_product_template_guarantee.xml new file mode 100644 index 0000000..6849748 --- /dev/null +++ b/views/financial_product_template_guarantee.xml @@ -0,0 +1,97 @@ +<?xml version="1.0" encoding="utf-8" ?> +<odoo> + <!-- Tree --> + <record + id="financial_product_template_guarantee_tree_view" + model="ir.ui.view" + > + <field name="name">financial.product.template.guarantee.tree</field> + <field name="model">financial.product.template.guarantee</field> + <field + name="inherit_id" + ref="financial_contract.financial_product_template_tree_view" + /> + <field name="mode">primary</field> + <field name="arch" type="xml"> + <xpath expr="//tree" position="attributes"> + <attribute name="create">1</attribute> + <attribute name="edit">1</attribute> + <attribute name="delete">1</attribute> + </xpath> + <xpath expr="//field[@name='category_id']" position="after"> + <field name="guarantee_rate" widget="percentage" /> + </xpath> + </field> + </record> + + <!-- Form --> + <record + id="financial_product_template_guarantee_form_view" + model="ir.ui.view" + > + <field name="name">financial.product.template.guarantee.form</field> + <field name="model">financial.product.template.guarantee</field> + <field + name="inherit_id" + ref="financial_contract.financial_product_template_form_view" + /> + <field name="mode">primary</field> + <field name="arch" type="xml"> + <!-- Loan Fields --> + <xpath expr="//notebook" position="before"> + <!-- Loan values --> + <group name="guarantee_data"> + <group + string="Données du de la garantie" + name="guarantee_values" + > + <field + name="guarantee_rate" + widget="percentage" + required="1" + /> + </group> + </group> + </xpath> + <!-- Suspensive conditions --> + <xpath expr="//page[@name='description']" position="before"> + <page + string="Conditions suspensives" + name="suspensive_condition" + > + <field + name="suspensive_condition_ids" + context="{'default_product_id': active_id}" + > + <tree editable="top"> + <field name="product_id" invisible="1" /> + <field + name="condition_id" + options="{'no_create': 1, 'no_edit': 1}" + /> + <field name="condition_comment" /> + </tree> + </field> + </page> + </xpath> + <!-- Chatter --> + <xpath expr="//sheet" position="after"> + <div class="oe_chatter"> + <field name="message_follower_ids" /> + <field name="message_ids" /> + </div> + </xpath> + </field> + </record> + + <!-- Action --> + <record + model="ir.actions.act_window" + id="financial_product_template_guarantee_action" + > + <field name="name">Garanties</field> + <field name="res_model">financial.product.template.guarantee</field> + <field name="view_mode">tree,form</field> + </record> + +</odoo> diff --git a/views/menus.xml b/views/menus.xml index 65baccc..2e507a9 100644 --- a/views/menus.xml +++ b/views/menus.xml @@ -4,9 +4,17 @@ <menuitem id="menu_financial_contract_guarantee" name="Garanties" - parent="financial_contact.financial_contract_menu_root" + parent="financial_contract.financial_contract_menu_root" action="financial_contract_guarantee_action" sequence="40" /> + <menuitem + id="menu_financial_product_template_guarantee" + name="Garanties" + parent="financial_contract.menu_financial_product_template" + action="financial_product_template_guarantee_action" + sequence="40" + /> + </odoo> diff --git a/views/res_partner.xml b/views/res_partner.xml new file mode 100644 index 0000000..c176314 --- /dev/null +++ b/views/res_partner.xml @@ -0,0 +1,37 @@ +<?xml version="1.0" encoding="utf-8" ?> +<!-- Copyright 2023- Le Filament (https://le-filament.com) + License AGPL-3.0 or later (https://www.gnu.org/licenses/agpl). --> +<odoo> + <!-- Form View --> + <record id="res_partner_financial_contract_loan_form" model="ir.ui.view"> + <field name="name">res.partner.financial.contract.loan.form</field> + <field name="model">res.partner</field> + <field name="inherit_id" ref="base.view_partner_form" /> + <field name="arch" type="xml"> + <xpath expr="//div[@name='button_box']" position="inside"> + <button + name="action_view_contract_guarantee" + class="oe_stat_button" + icon="fa-file-text-o" + attrs="{'invisible': [('financial_contract_guarantee_count', '=', 0)]}" + type="object" + > + <field + name="financial_contract_guarantee_count" + widget="statinfo" + string="Contrat(s) de garantie" + /> + </button> + </xpath> + <xpath expr="//notebook" position="inside"> + <page name="guarantee_contracts" string="Contrats de garantie"> + <field + name="financial_contract_guarantee_ids" + readonly="1" + /> + </page> + </xpath> + </field> + </record> + +</odoo> -- GitLab