Skip to content
Extraits de code Groupes Projets
res_partner.py 62,4 ko
Newer Older
  • Learn to ignore specific revisions
  • Juliana's avatar
    Juliana a validé
    # © 2019 Le Filament (<http://www.le-filament.com>)
    # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html).
    
    
    
    import logging
    
    import time
    
    from datetime import datetime, timedelta
    
    from odoo import _, api, fields, models
    
    from odoo.exceptions import UserError, ValidationError
    
    from lxml import etree
    
    Juliana's avatar
    Juliana a validé
    
    
    _logger = logging.getLogger(__name__)
    
    
    Juliana's avatar
    Juliana a validé
    class ScopPartner(models.Model):
        _inherit = "res.partner"
    
    
        def _default_ur(self):
    
            return self.env["res.company"]._ur_default_get()
    
        def _default_country(self):
    
            return self.env.ref("base.fr", False)
    
        @api.model
        def _get_domain_incubator_id(self):
            try:
    
                incubator_id = self.env.ref("cgscop_partner.incubator").id
    
                    ("is_company", "=", True),
                    ("organization_subtype_id", "=", incubator_id),
    
            except Exception:
    
                return [("is_company", "=", True)]
    
    
        @api.model
        def _get_domain_revision_company_id(self):
            try:
    
                rev_id = self.env.ref("cgscop_partner.riga_14953").id
                com_id = self.env.ref("cgscop_partner.riga_16433").id
    
                    ("is_company", "=", True),
                    ("organization_subtype_id", "in", [com_id, rev_id]),
    
            except Exception:
    
                return [("is_company", "=", True)]
    
        # Inherit parent
        active = fields.Boolean(
            tracking=True,
        )
    
    
        # Infos générales - champs non affichés
    
        is_cooperative = fields.Boolean("Est une coopérative")
    
        parent_is_cooperative = fields.Boolean(
            string="Parent est une coopérative",
            related="parent_id.is_cooperative",
        )
    
    Rémi - Le Filament's avatar
    Rémi - Le Filament a validé
        current_user_ur_id = fields.Many2one(
    
    Rémi - Le Filament's avatar
    Rémi - Le Filament a validé
            string="Union Régionale de l'utilisateur",
    
            compute="_compute_current_user_ur_id",
            search="_search_current_user_ur_id",
        )
    
        # Informations organisme - champs non affichés
    
        id_ur = fields.Char("Identifiant UR")
    
        # Informations Bandeau
    
        project_status = fields.Selection(
    
            [
                ("1_information", "Phase d'information"),
                ("2_pre-diagnostic", "Phase de pré-diagnostic"),
                ("3_accompagnement", "Phase d'accompagnement projet"),
    
    Juliana's avatar
    Juliana a validé
                ("4_suivi", "Phase de suivi"),
                ("5_abandonne", "Projet abandonné"),
                ("6_decede", "Coop Décédée"),
    
            ],
            tracking=True,
            string="Statut projet",
            index=True,
        )
    
        name = fields.Char(index=True, tracking=True, string="Dénomination Sociale")
        nickname = fields.Char(string="Dénomination interne")
    
        cooperative_form_id = fields.Many2one(
    
            string="Cooperative form",
    
        partner_company_type_id = fields.Many2one(
    
            comodel_name="res.partner.company.type",
            string="Statut Juridique",
            ondelete="restrict",
            tracking=True,
        )
    
        membership_status = fields.Selection(
    
    Juliana's avatar
    Juliana a validé
                ("adhesion", "Phase d'Adhésion"),
                ("soumis_cg", "Soumis CG"),
                ("member", "Adhérent"),
    
            string="Statut d'adhésion",
    
    Juliana's avatar
    Juliana a validé
            default="not_member",
    
        member_number = fields.Char(
    
            "No adhérent (texte)", compute="_compute_membership_number", store=True
    
        member_number_int = fields.Integer(
            "No adhérent",
    
        member_start = fields.Date(
    
            "Date d'adhésion", compute="_compute_membership", store=True
        )
        cae = fields.Boolean("CAE", tracking=True)
    
        dissolution_date = fields.Date("Date de Décès", tracking=True)
    
    Rémi - Le Filament's avatar
    Rémi - Le Filament a validé
        dissolution_reason_id = fields.Many2one(
    
            string="Motif Décès",
    
    Rémi - Le Filament's avatar
    Rémi - Le Filament a validé
    
    
        # Infos générales / Contact
    
        sigle = fields.Char("Sigle")
    
        street = fields.Char("Rue", tracking=1)
        street2 = fields.Char("Rue 2", tracking=1)
        street3 = fields.Char("Rue 3", tracking=1)
        zip = fields.Char("CP", change_default=True, tracking=1)
    
        zip_departement = fields.Char(
    
            "Num Département", compute="_compute_num_departement", store=True
        )
    
            comodel_name="res.country.state",
            string="Région",
            compute="_compute_region",
            store=True,
        )
    
        city = fields.Char("Ville", tracking=1)
        cedex = fields.Char("Cedex", tracking=1)
    
        country_id = fields.Many2one(
            "res.country",
            string="Pays",
            ondelete="restrict",
            default=_default_country,
            tracking=True,
        )
    
        # Adresse postale
        postal_street = fields.Char("Adresse postale - Rue", tracking=1)
        postal_street2 = fields.Char("Adresse postale - Rue 2", tracking=1)
        postal_street3 = fields.Char("Adresse postale - Rue 3", tracking=1)
        postal_zip = fields.Char("Adresse postale - CP", tracking=1)
        postal_city = fields.Char("Adresse postale - Ville", tracking=1)
        postal_cedex = fields.Char("Adresse postale - Cedex", tracking=1)
    
        phone = fields.Char("Téléphone 1", tracking=True)
        mobile = fields.Char("Téléphone 2", tracking=True)
        email = fields.Char("eMail administratif", tracking=True)
    
        facebook = fields.Char("Facebook")
        linkedin = fields.Char("LinkedIn")
        twitter = fields.Char("Twitter")
    
    Hervé Silvant - CGScop's avatar
    Hervé Silvant - CGScop a validé
        instagram = fields.Char("Instagram")
    
    
        # Infos générales / Suivi UR
    
        ur_id = fields.Many2one(
    
            "union.regionale",
            string="Union Régionale",
    
            default=_default_ur,
    
        creation_delegate_id = fields.Many2one(
    
            "res.users",
            string="Délégué de création",
            ondelete="restrict",
            tracking=True,
        )
    
        followup_delegate_id = fields.Many2one(
    
            "res.users",
            string="Délégué de suivi",
            domain=[("active", "=", True)],
            ondelete="restrict",
            tracking=True,
        )
    
        support_delegate_id = fields.Many2one(
    
            "res.users",
            string="Délégué en support",
            domain=[("active", "=", True)],
            ondelete="restrict",
            tracking=True,
        )
        segment_1_id = fields.Many2many(
            "res.partner.segment1",
            column1="partner_id",
            column2="segment_id",
            string="Segmentation 1",
        )
        segment_2_id = fields.Many2many(
            "res.partner.segment2",
            column1="partner_id",
            column2="segment_id",
            string="Segmentation 2",
        )
        segment_3_id = fields.Many2many(
            "res.partner.segment3",
            column1="partner_id",
            column2="segment_id",
            string="Segmentation 3",
        )
        segment_4_id = fields.Many2many(
            "res.partner.segment4",
            column1="partner_id",
            column2="segment_id",
            string="Segmentation 4",
        )
    
        segment_1_nb = fields.Integer(
    
            string="Nb de segments 1", compute="_compute_segment_nb"
        )
    
        segment_2_nb = fields.Integer(
    
            string="Nb de segments 2", compute="_compute_segment_nb"
        )
    
        segment_3_nb = fields.Integer(
    
            string="Nb de segments 3", compute="_compute_segment_nb"
        )
    
        segment_4_nb = fields.Integer(
    
            string="Nb de segments 4", compute="_compute_segment_nb"
        )
        filiere_ids = fields.Many2many(
            "res.partner.filiere",
            column1="partner_id",
            column2="filiere_id",
            string="Filière",
        )
    
        is_mucs = fields.Boolean(string="Est adhérent Mucs", tracking=True)
    
        is_mucs_update_date = fields.Date(string="Date MAJ Mucs", tracking=True)
    
        is_union_sociale = fields.Boolean(
            string="Est adhérent Union Sociale", tracking=True
        )
        is_union_sociale_update_date = fields.Date(
    
            string="Date MAJ Union Sociale", tracking=True
    
        # Infos générales / Infos activité
    
        creation_origin_id = fields.Many2one(
    
            string="Origine création en coop",
    
            domain=[("parent_id", "=", False)],
            ondelete="restrict",
            tracking=True,
        )
    
        creation_suborigin_id = fields.Many2one(
    
            string="Sous-Origine création en coop",
    
            domain=[("child_ids", "=", False)],
            ondelete="restrict",
            tracking=True,
        )
    
        date_1st_sign = fields.Date("Date 1ère signature coop", tracking=True)
        registration_date = fields.Date(string="Date d'immatriculation RCS", tracking=True)
    
        social_object = fields.Text("Objet Social", tracking=True)
    
    Rémi - Le Filament's avatar
    Rémi - Le Filament a validé
        naf_id = fields.Many2one(
    
            "res.partner.naf",
            string="Code NAF",
            ondelete="restrict",
            tracking=True,
        )
    
        secteur_id = fields.Many2one(
    
            string="Secteur d'activité",
    
        activity_desc = fields.Text("Description de l'activité", tracking=True)
    
        activity_customers = fields.Selection(
            [
                ("ND", "Non définie"),
                ("PR", "Clients professionnels"),
                ("PA", "Clients particuliers"),
                ("PP", "Clients professionnels et particuliers"),
            ],
            string="Relation commerciale",
            default="ND",
            tracking=True,
        )
    
        certification_ids = fields.Many2many(
    
            comodel_name="res.partner.certification",
            string="Agréments",
            ondelete="restrict",
        )
        other_certification = fields.Char(string="Autre agrément", required=False)
    
        siret = fields.Char(string="SIRET du siège", size=14, index=True, tracking=True, copy=False)
    
        formatted_siret = fields.Char(
            string="SIRET formaté", compute="_compute_formatted_siret"
        )
        siren = fields.Char(string="SIREN", size=11, compute="_compute_siren")
    
        pappers_url = fields.Char(string="URL Pappers", compute="_compute_siren")
    
        capital = fields.Integer("Capital (en €)")
    
        first_closeout = fields.Date("1er bilan en coop")
    
        closeout_month = fields.Selection(
    
                ("1", "Janvier"),
                ("2", "Février"),
                ("3", "Mars"),
                ("4", "Avril"),
                ("5", "Mai"),
                ("6", "Juin"),
                ("7", "Juillet"),
                ("8", "Août"),
                ("9", "Septembre"),
                ("10", "Octobre"),
                ("11", "Novembre"),
                ("12", "Décembre"),
    
        is_seed_scop = fields.Boolean("Est une SCOP d'amorçage")
    
        seed_end = fields.Date("Date de fin du dispositif d'amorçage")
    
        is_incubated = fields.Boolean("Est incubé")
        incubator_id = fields.Many2one(
    
            "res.partner",
            string="Incubateur",
            domain=_get_domain_incubator_id,
            ondelete="restrict",
        )
        is_ag_constitution = fields.Boolean("AG constitutive réalisée")
    
        is_registration_in_progress = fields.Boolean(
            string="En cours d'immatriculation", default=False
        )
    
        is_federation_com = fields.Boolean(
    
            string="Fédération de la Communication",
            compute="_compute_federation",
    
        is_federation_btp = fields.Boolean(
    
            string="Fédération du BTP",
            compute="_compute_federation",
    
        is_federation_indus = fields.Boolean(
            string="Fédération de l'Industrie",
    
        is_federation_cae = fields.Boolean(
    
            string="Fédération des CAE",
            compute="_compute_federation",
    
        activity_federation_com_ids = fields.Many2many(
    
            comodel_name="scop.federation.com.activity",
            relation="res_partner_federation_com_activity_rel",
            column1="partner_id",
            column2="com_activity_id",
    
            string="Domaine d'activité Com",
    
            help="Fédération de la Com - Domaine d'activité",
        )
    
        activity_federation_indus_ids = fields.Many2many(
    
            comodel_name="scop.federation.indus.activity",
            relation="res_partner_federation_indus_activity_rel",
            column1="partner_id",
            column2="indus_activity_id",
    
            string="Domaine d'activité Industrie",
    
            help="Fédération de l'Industrie - Domaine d'activité",
        )
    
        copadev_member = fields.Boolean(string="Adhérent copadev", tracking=True)
    
        # Contacts
        director_ids = fields.One2many(
    
            "res.partner",
            "parent_id",
            string="Contacts Dirigeants",
    
            domain=[("mandate_id", "!=", False)],
    
        other_child_ids = fields.One2many(
    
            "res.partner",
            "parent_id",
            string="Autres Contacts",
    
            domain=[("mandate_id", "=", False)],
    
    Juliana's avatar
    Juliana a validé
        # Révisions
    
        revision_contract = fields.Date(
            string="Début du contrat de révision",
            tracking=True,
        )
        revision_contract_end = fields.Date(
            string="Fin du contrat de révision",
            tracking=True,
        )
        revision_contract_tacite = fields.Boolean(
            string="Tacite reconduction",
            tracking=True,
            default=False
        )
        revision_mandat_cac = fields.Boolean(
            string="Mandat CAC actif",
            tracking=True,
            default=False
        )
    
        revision_company_id = fields.Many2one(
    
            "res.partner",
            string="Organisme de révision",
            domain=_get_domain_revision_company_id,
            ondelete="restrict",
            tracking=True,
        )
    
        revision_backup_company_id = fields.Many2one(
    
            "res.partner",
            string="Organisme de révision suppléant",
            domain=_get_domain_revision_company_id,
            ondelete="restrict",
    
        revision_person_id = fields.Many2one(
    
            comodel_name="res.users",
            string="Réviseur",
            ondelete="restrict",
            tracking=True,
        )
    
        revision_certified_person_id = fields.Many2one(
    
            comodel_name="res.users",
            string="Réviseur agréé",
            ondelete="restrict",
            tracking=True,
    
        revision_person_assign_date = fields.Date(
    
            string="Date de nomination du réviseur", tracking=True
        )
    
        revision_person_assign_end = fields.Date(
            string="Date de fin nomination réviseur", tracking=True
        )
    
        revision_type = fields.Selection(
    
            [
                ("1y", "Annuelle"),
                ("5y", "Quinquennale"),
                ("5ys", "Quinquennale séquencée (annuel)"),
                ("5ys23", "Quinquennale séquencée (2 ans et 3 ans)"),
            ],
            string="Périodicité de la révision",
    
            tracking=True,
    
        revision_type_ok = fields.Boolean(
            string="Périodicité de révision ok",
            tracking=True,
            compute="_compute_revision_type_ok",
        )
        revision_quinq_exercice = fields.Integer(
            "Quinquénnale exercice à réviser",
            compute="_compute_revision_quinq_exercice",
        )
    
        revision_next_date = fields.Date("Prochain exercice révisable (old)")
    
    Benjamin's avatar
    Benjamin a validé
        revision_format_id = fields.Many2one(
    
            "scop.revision.format",
            string="Format de révision",
            ondelete="restrict",
    
            tracking=True,
    
        )
        revision_tarif = fields.Integer(
            "Tarif de vente", related="revision_format_id.tarif", store=False
        )
        revision_next_exercice = fields.Integer(
            "Prochain exercice révisable",
            compute="_compute_revision_next_exercice",
            store=True,
    
        revision_same_exercice = fields.Boolean(
            string="Révision sur l'année de cloture",
            tracking=True,
        )
    
        revision_next_year = fields.Integer(
            "Année prochaine révision",
            compute="_compute_revision_next_year",
            store=True,
    
    Juliana's avatar
    Juliana a validé
        revision_ids = fields.One2many(
    
            comodel_name="scop.revision",
            inverse_name="partner_id",
            string="Liste des Révisions",
        )
    
        revision_quinq_A1 = fields.Integer(
            "Quinquénnale année 1",
            compute="_compute_revision_quinq_annee",
        )
        revision_quinq_A2 = fields.Integer(
            "Quinquénnale année 2",
            compute="_compute_revision_quinq_annee",
        )
        revision_quinq_A3 = fields.Integer(
            "Quinquénnale année 3",
            compute="_compute_revision_quinq_annee",
        )
        revision_quinq_A4 = fields.Integer(
            "Quinquénnale année 4",
            compute="_compute_revision_quinq_annee",
        )
        revision_quinq_A5 = fields.Integer(
            "Quinquénnale année 5",
            compute="_compute_revision_quinq_annee",
        )
    
        revision_activite_A1 = fields.Integer(
            "Activité révision année 1",
            tracking=True,
        )
        revision_activite_A2 = fields.Integer(
            "Activité révision année 2",
            tracking=True,
        )
        revision_activite_A3 = fields.Integer(
            "Activité révision année 3",
            tracking=True,
        )
        revision_activite_A4 = fields.Integer(
            "Activité révision année 4",
            tracking=True,
        )
        revision_activite_A5 = fields.Integer(
            "Activité révision année 5",
            tracking=True,
        )
    
    Juliana's avatar
    Juliana a validé
    
    
        # Action RSE et TE
    
        action_rse_ids = fields.One2many(
            comodel_name="scop.action.rse",
            inverse_name="partner_id",
            string="Liste des Actions RSE",
        )
    
        action_te_ids = fields.Many2many(
            "scop.action.te",
            column1="partner_id",
            column2="action_id",
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
            string="Expertises transition éco.",
    
        is_rse = fields.Boolean(
    
            string="Engagement TE", compute="_compute_is_rse", store=True, default=False
    
        # Historique
        scop_period_ids = fields.One2many(
    
            comodel_name="scop.period",
            inverse_name="partner_id",
            string="Historique",
        )
    
    
        # Période d'adhésion
        membership_period_ids = fields.One2many(
    
            comodel_name="scop.membership.period",
            inverse_name="partner_id",
            string="Périodes d'adhésion",
        )
    
    
            comodel_name="scop.partner.staff",
            inverse_name="partner_id",
            string="Effectifs",
        )
    
        staff_last = fields.Integer(
            string="Dernier effectif connu",
            compute="_compute_last_effective",
    
        staff_shareholder_last = fields.Integer(
            string="Dernier effectif associés connu",
            compute="_compute_last_effective",
    
        staff_last_date = fields.Date(
            string="Date dernier effectif connu",
            compute="_compute_last_effective",
    
        # Champs pour personnes
    
        birthyear = fields.Integer("Année de naissance")
    
        subscription_ids = fields.One2many(
    
            comodel_name="res.partner.newsletter.subscription",
            inverse_name="partner_id",
            string="Abonnements",
        )
    
        contact_origin_id = fields.Many2one(
    
            string="Origine du contact",
    
        mandate_id = fields.Many2one(
    
            "res.partner.mandate", string="Mandat", ondelete="restrict"
        )
    
        function_lst_id = fields.Many2one(
    
            "res.partner.function_lst", string="Fonction", ondelete="restrict"
        )
    
        contact_legality = fields.Selection(
    
            [
                ("employee", "Salarié"),
                ("customer", "Client en contrat"),
                ("supplier", "Fournisseur en contrat"),
                ("consent", "Consentement"),
                ("legitimate", "Intérêt légitime"),
                ("none", "Aucune"),
            ],
    
    Rémi - Le Filament's avatar
    Rémi - Le Filament a validé
            string="Licéité du contact",
            compute="_compute_contact_legality",
    
            selection=[
                ("asso", "Associé extérieur"),
                ("coop", "Associé coopérateur"),
                ("none", "Non associé"),
            ],
            string="Associé",
        )
        employee = fields.Boolean(string="Salarié", default=True)
    
        has_mvt_mandate = fields.Boolean(string="Elu du mouvement", default=False)
    
        mvt_mandate_ids = fields.Many2many(
            comodel_name="res.partner.mvt.mandate",
            relation="res_partner_mvt_mandate_rel",
            column1="partner_id",
            column2="mvt_mandate_id",
            string="Mandats mouvement",
        )
    
    
        mvt_vip_ids = fields.Many2many(
            comodel_name="res.partner.mvt.vip",
            relation="res_partner_mvt_vip_rel",
            column1="partner_id",
            column2="mvt_vip_id",
            string="Etiquettes VIP",
        )
    
        # Champs pour partenaires
        organization_type_id = fields.Many2one(
    
            ondelete="restrict",
            compute="_compute_org_type_id",
            tracking=True,
        )
    
        organization_subtype_id = fields.Many2one(
    
            string="Type",
    
            domain=[("child_ids", "=", False)],
            ondelete="restrict",
            tracking=True,
        )
    
        is_administrative = fields.Boolean(compute="_compute_is_administrative")
    
        # Hack pour la création de contacts depuis la fiche organisme
    
        parent_id_onchange = fields.Many2one("res.partner")
    
        # ------------------------------------------------------
        # Constrains
        # ------------------------------------------------------
    
        @api.constrains("zip_id", "country_id", "city_id", "state_id")
    
        def _check_zip(self):
            return
    
    
        @api.constrains("revision_contract", "revision_contract_end")
        def _check_revision_contract(self):
            for rec in self:
                if rec.revision_contract and \
                   rec.revision_contract_end and \
                   rec.revision_contract > rec.revision_contract_end:
                    raise ValidationError(
                        _(
                            "La date de fin du contrat de révision doit être supérieure"
                            " à la date de début du contrat de révision"
                        )
                    )
            return
    
        @api.constrains("revision_person_assign_date", "revision_person_assign_end")
        def _check_revision_person_assign(self):
            for rec in self:
                if rec.revision_person_assign_date and \
                   rec.revision_person_assign_end and \
                   rec.revision_person_assign_date > rec.revision_person_assign_end:
                    raise ValidationError(
                        _(
                            "La date de fin de nomination du réviseur doit être supérieure"
                            " à la date de début de nomination du réviseur"
                        )
                    )
            return
    
    
            if self.siret and not self.env.context.get("import_file"):
    
                siren = self.siret[:3] + " " + self.siret[3:6] + " " + self.siret[6:9]
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
                if (
                    not self.siret.isdigit()
                    and self.siret != "En attente d'immatriculation"
                ):
    
                    raise ValidationError(_("Ce SIRET n'est pas valide"))
    
                    raise ValidationError(_("La longueur du SIRET doit être égale à 14"))
    
                if (
                    self.search_count(
                        [
                            ("siret", "=like", siren + "%"),
                            ("is_cooperative", "=", True),
                        ]
                    )
                    > 1
                ):
    
                    raise ValidationError(_("Ce SIREN existe déjà parmi les coopératives"))
    
                elif self.search_count([("siret", "=", self.siret)]) > 1:
    
                    raise ValidationError(_("Ce SIRET existe déjà"))
    
        @api.constrains("is_company", "type", "email", "phone", "mobile", "user_ids")
        def _check_contact_info(self):
            # Contrainte de tel ou mail lors de la modification d'un contact
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
            if not self.is_company and self.type == "contact" and not self.user_ids:
    
                if not self.email and not self.phone and not self.mobile:
                    raise UserError(
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
                        _("Vous devez saisir au moins un e-mail ou un téléphone pour %s")
                        % self.name
    
        # ------------------------------------------------------
        # Onchange
        # ------------------------------------------------------
    
        # Hack pour la création de contacts depuis la fiche organisme
    
        def _onchange_parent_id_onchange(self):
            self.parent_id = self.parent_id_onchange
    
    
        @api.onchange("nickname")
        def onchange_nickname(self):
            if (
                self.is_cooperative
                and self.project_status in ["1_information", "2_pre-diagnostic", "3_accompagnement"]
            ):
                self.lastname = self.nickname
    
    
        # TODO: à vérifier
        @api.onchange("parent_id")
    
        def _onchange_parent_id(self):
    
            if self.parent_id.ur_id:
                self.ur_id = self.parent_id.ur_id
    
        def _onchange_ur_id(self):
            if self.child_ids:
                for child in self.child_ids:
                    child.ur_id = self.ur_id
    
    
        def onchange_creation_origin_id(self):
            for coop in self:
                coop.creation_suborigin_id = False
    
    
        # TODO: à vérifier
        @api.onchange("is_seed_scop")
    
        def onchange_is_seed_scop(self):
            for coop in self:
    
                if coop.is_seed_scop:
    
                    if coop.date_1st_sign:
                        coop.seed_end = coop.date_1st_sign + timedelta(2556)
                    else:
                        coop.seed_end = datetime.today().date() + timedelta(2556)
                else:
                    coop.seed_end = False
    
    
        def onchange_name(self):
    
            if self.search_count([("name", "=ilike", self.name)]) > 0:
    
                    "warning": {
                        "title": "Attention",
                        "message": "Ce nom / cette raison sociale existe déjà, "
                        + "merci de vérifier que vous n'êtes pas en "
                        + "train de créer un doublon",
                    }
                }
    
        @api.onchange("mobile")
    
    Benjamin's avatar
    Benjamin a validé
        def onchange_mobile(self):
    
            if self.mobile and len(self.mobile) > 0 and len(self.mobile) < 10:
    
    Benjamin's avatar
    Benjamin a validé
                raise ValidationError(
    
                    _("Le numéro de téléphone doit contenir au moins 10 caractères")
    
    Benjamin's avatar
    Benjamin a validé
    
    
    Benjamin's avatar
    Benjamin a validé
        def onchange_phone(self):
    
    Benjamin's avatar
    Benjamin a validé
            if self.phone and len(self.phone) > 0 and len(self.phone) < 10:
    
    Benjamin's avatar
    Benjamin a validé
                raise ValidationError(
    
                    _("Le numéro de téléphone doit contenir au moins 10 caractères")
    
    Benjamin's avatar
    Benjamin a validé
    
    
        def onchange_siret(self):
            if self.siret:
    
                siren = self.siret[:3] + " " + self.siret[3:6] + " " + self.siret[6:9]
    
                if self.search_count([("siret", "=like", self.siret)]) > 0:
    
                        "warning": {
                            "title": "Attention",
                            "message": "Ce SIRET existe déjà, merci de vérifier "
                            + "que vous n'êtes pas en train de créer un"
                            + " doublon",
                        }
                    }
                elif self.search_count([("siret", "=like", siren + "%")]) > 0:
    
                        "warning": {
                            "title": "Attention",
                            "message": "Ce SIREN existe déjà, merci de vérifier "
                            + "que vous n'êtes pas en train de créer un"
                            + " doublon",
                        }
                    }
    
        @api.onchange("cooperative_form_id")
        def onchange_cooperative_form_id(self):
            if self.cooperative_form_id == self.env.ref(
                "cgscop_partner.form_noncooperative"
            ):
    
                self.creation_origin_id = None
                self.creation_suborigin_id = None
                self.is_ag_constitution = None
                self.date_1st_sign = None
                self.first_closeout = None
    
    
        # ------------------------------------------------------
        # Common functions
        # ------------------------------------------------------
    
        def _create_period(self, partner):
    
            new_period = self._add_period(partner)
            partner.scop_period_ids = new_period
    
        def _add_period(self, partner):
    
            new_period = self.env["scop.period"].with_context().create(
    
                {
                    "partner_id": partner.id,
                    "start": partner.registration_date or fields.Date.today(),
                    "name": partner.name,
                    "cooperative_form_id": partner.cooperative_form_id.id,
                    "partner_company_type_id": partner.partner_company_type_id.id,
    
                    "siret": (
                        partner.siret
                        if partner.siret or not partner.is_registration_in_progress
                        else "En attente d'immatriculation"
                    ),
    
                    "street": partner.street,
                    "street2": partner.street2,
                    "street3": partner.street3,
                    "zip": partner.zip,
                    "zip_id": partner.zip_id.id,
                    "city": partner.city,
                    "cedex": partner.cedex,
                    "state_id": partner.state_id.id,
                    "country_id": partner.country_id.id,
                    "naf_id": partner.naf_id.id,
                    "ur_id": partner.ur_id.id,
                    "cae": partner.cae,
                }
            )
    
            return new_period
    
        # ------------------------------------------------------
        # Override ORM
        # ------------------------------------------------------
    
        def _name_search(
            self, name, args=None, operator="ilike", limit=100, name_get_uid=None
        ):
    
            args = args or []
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
                "|",
    
                "|",
                ("name", operator, name),
                ("member_number", "ilike", name),
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
                ("nickname", operator, name),
    
                ("sigle", operator, name),
    
            return self._search(domain + args, limit=limit, access_rights_uid=name_get_uid)
    
    
        # Creation d'une periode lorsque le statut passe en Phase de Suivi
        def write(self, vals):
    
            if vals.get("name"):
                vals["name"] = vals.get("name").title()
            if vals.get("lastname"):
                vals["lastname"] = vals.get("lastname").title()
            if vals.get("firstname"):
                vals["firstname"] = vals.get("firstname").title()
            if vals.get("city"):
                vals["city"] = vals.get("city").upper()
    
            if len(self) == 1 and self.parent_id:
    
                if self.type in ("contact", "invoice", "private"):
    
                    parent_ur_id = self.parent_id.ur_id.id
    
            result = super(ScopPartner, self).write(vals)
    
            # Hack pour notification lors de la modification du logo
    
            if "image_128" in vals:
    
                self.message_post(
    
                    body=_("Modification Logo"),
    
                    subtype="cgscop_base.cg_values_change",
    
            for partner in self:
    
                # Création d'une période lors du changement de statut en Suivi
    
    Juliana's avatar
    Juliana a validé
                if vals.get("project_status") == "4_suivi" and not self.env.context.get(
    
                    if not partner.scop_period_ids:
    
                partners_to_subscribe = []
                if partner.followup_delegate_id != partner.create_uid:
                    partners_to_subscribe.append(partner.followup_delegate_id.partner_id.id)
                if partner.creation_delegate_id != partner.create_uid:
                    partners_to_subscribe.append(partner.creation_delegate_id.partner_id.id)
    
                if partners_to_subscribe:
                    partner.message_subscribe(partner_ids=partners_to_subscribe)
    
            return result
    
        @api.model_create_multi
        def create(self, vals_list):
    
    Benjamin - Le Filament's avatar
    Benjamin - Le Filament a validé
            """
            Création d'une période lors de la création d'une coopérative
            """
    
                if vals.get("name"):
                    vals["name"] = vals.get("name").title()
                if vals.get("lastname"):
                    vals["lastname"] = vals.get("lastname").title()
                if vals.get("firstname"):
                    vals["firstname"] = vals.get("firstname").title()
                if vals.get("city"):
                    vals["city"] = vals.get("city").upper()
    
            partners = super(ScopPartner, self).create(vals_list)
    
            for vals in vals_list:
    
                # Création d'une période si la coop est en statut en Suivi
    
                if vals.get("is_cooperative") and vals.get("project_status") == "4_suivi":
                    for partner in partners:
    
                        if not partner.scop_period_ids:
    
                            partner.sudo()._create_period(partner)
    
        @api.model
        def _address_fields(self):
            address_fields = super(ScopPartner, self)._address_fields()
    
            address_fields.append("cedex")
    
            return address_fields
    
    
        # ------------------------------------------------------
        # Override parent
        # ------------------------------------------------------
        def _get_contact_name(self, partner, name):
    
            super(ScopPartner, self)._get_contact_name(partner, name)
    
                partner.commercial_company_name or partner.sudo().parent_id.name,
    
        def action_archive(self):
            """
            Lève une erreur si une coopérative qui n'est pas à l'état abandonné fait partie des
            items à archiver
            """
            coop_ids = self.filtered(
    
                lambda p: p.is_cooperative and p.project_status != "5_abandonne"
    
            )
            if coop_ids:
                raise UserError(
                    _(
                        "Il n'est pas possible d'archiver une coopérative qui n'est pas en "