# © 2019 Le Filament (<http://www.le-filament.com>) # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html). from datetime import datetime, timedelta from odoo import models, fields, api from odoo.exceptions import ValidationError 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) # Infos générales is_cooperative = fields.Boolean("Est une coopérative") current_user_ur_id = fields.Many2one( 'union.regionale', string="Union Régionale de l'utilisateur", compute='_compute_current_user_ur_id', search='_search_current_user_ur_id') # Informations organisme id_ur = fields.Char("Identifiant UR") id_riga = fields.Char("Identifiant RIGA") # Informations Bandeau project_status = fields.Selection( [('1_information', "Phase d'information"), ('2_pre-diagnostic', 'Phase de pré-diagnostic'), ('3_accompagnement', "Phase d'accompagnement"), ('4_adhesion', "Phase d'adhésion"), ('5_cg', 'Soumis CGScop'), ('6_suivi', 'Phase de suivi'), ('7_abandonne', 'Projet abandonné')], track_visibility='onchange', string='Statut projet', index=True) cooperative_form_id = fields.Many2one( 'res.partner.cooperative.form', string="Cooperative form", on_delete='restrict', track_visibility='onchange') partner_company_type_id = fields.Many2one( comodel_name='res.partner.company.type', string='Legal Form', on_delete='restrict', track_visibility='onchange') membership_status = fields.Selection( [('member', 'Adhérent'), ('not_member', 'Non Adhérent'), ('out', 'Radié')], string="Statut d'adhésion", default="not_member") member_number = fields.Char("No adhérent") cae = fields.Boolean("CAE", track_visibility='onchange') dissolution_date = fields.Date('Date de Décès', track_visibility='onchange') dissolution_reason_id = fields.Many2one( 'res.partner.dissolution.reason', string="Motif Décés", on_delete='restrict', track_visibility='onchange') # Infos générales / Contact cedex = fields.Char("Cedex") country_id = fields.Many2one('res.country', string='Country', ondelete='restrict', default=_default_country) admin_email = fields.Char('E-mail administratif') facebook = fields.Char("Facebook") linkedin = fields.Char("LinkedIn") twitter = fields.Char("Twitter") director_ids = fields.One2many( 'res.partner', 'parent_id', string='Contacts Dirigeants', domain=[('mandate_id', '!=', False)]) # Infos générales / Suivi UR ur_id = fields.Many2one( 'union.regionale', string='Union Régionale', index=True, on_delete='restrict', default=_default_ur, track_visibility='onchange') creation_delegate_id = fields.Many2one( 'res.partner', string='Délégué de création', domain=[('user_ids', '>', 0)], on_delete='restrict') followup_delegate_id = fields.Many2one( 'res.partner', string='Délégué de suivi', domain=[('user_ids', '>', 0)], on_delete='restrict', track_visibility='onchange') # Infos générales / Infos activité creation_origin_id = fields.Many2one( 'res.partner.creation.origin', string="Origine création en coop", domain=[('parent_id', '=', False)], on_delete='restrict') creation_suborigin_id = fields.Many2one( 'res.partner.creation.origin', string="Sous-Origine création en coop", domain=[('child_ids', '=', False)], on_delete='restrict') date_1st_sign = fields.Date( 'Date 1er signature coop', track_visibility='onchange') registration_date = fields.Date( string="Date d'immatriculation RCS", track_visibility='onchange') social_object = fields.Text('Objet Social', track_visibility='onchange') naf_id = fields.Many2one( 'res.partner.naf', string='Code NAF', on_delete='restrict', track_visibility='onchange') certification_ids = fields.Many2many( comodel_name='res.partner.certification', string='Agrément', on_delete='restrict') siret = fields.Char(string='SIRET', size=14, index=True, track_visibility='onchange') siren = fields.Char(string='SIREN', size=9, compute='_compute_siren') capital = fields.Integer("Capital (en €)") first_closeout = fields.Date( '1er bilan en coop') closeout_month = fields.Selection( [(12842, 'Janvier'), (12843, 'Février'), (12844, 'Mars'), (12845, 'Avril'), (12846, 'Mai'), (12847, 'Juin'), (12848, 'Juillet'), (12849, 'Août'), (12850, 'Septembre'), (12851, 'Octobre'), (12852, 'Novembre'), (12853, 'Décembre')], string='Mois clôture exercices', default=12853, track_visibility='onchange') is_seed_scop = fields.Boolean("Est une SCOP d'amorçage") seed_end = fields.Date("Date de fin du dispositif d'amorçage", default=str(datetime.today() + timedelta(2556)), compute='_compute_seen_end') is_incubated = fields.Boolean("Est incubé") incubator_id = fields.Many2one( 'res.partner', string='Incubateur', domain=[('is_company', '=', True), ('organization_subtype_id.name', '=', 'Incubateur')], on_delete='restrict') prescriber_canal_id = fields.Many2one( 'res.partner.prescriber.canal', string='Canal de Prescription', on_delete='restrict') sigle = fields.Char("Sigle") # Partenaires bank_id = fields.Many2one( 'res.partner', string='Banque principale', domain=[('is_company', '=', True), ('organization_subtype_id.name', '=', 'Banque')], on_delete='restrict') bank2_id = fields.Many2one( 'res.partner', string='Banque secondaire', domain=[('is_company', '=', True), ('organization_subtype_id.name', '=', 'Banque')], on_delete='restrict') accountant_id = fields.Many2one( 'res.partner', string='Expert-Comptable', domain=[('is_company', '=', True), '|', ('organization_subtype_id.name', '=', 'Expert-Comptable'), ('organization_subtype_id.name', '=', 'Organisme réviseur, ' + 'Expert-comptable / Commissaire au compte')], on_delete='restrict') accountant_person_id = fields.Many2one( 'res.partner', string='Expert-Comptable (personne)', domain=[('is_company', '=', False)], on_delete='restrict') auditor_id = fields.Many2one( 'res.partner', string='Commissaire aux Comptes', domain=[('is_company', '=', True), '|', ('organization_subtype_id.name', '=', 'Commissaire au compte'), ('organization_subtype_id.name', '=', 'Organisme réviseur, ' + 'Expert-comptable / Commissaire au compte')], on_delete='restrict') auditor_person_id = fields.Many2one( 'res.partner', string='Commissaire aux Comptes (personne)', domain=[('is_company', '=', False)], on_delete='restrict') # Périodes juridiques 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") # Cotisation contribution_ids = fields.One2many( comodel_name='scop.contribution', inverse_name='partner_id', string='Cotisations') # Liste Ministère direccte_id = fields.Many2one( 'res.partner', string='DIRECCTE rattachée', domain=[('is_company', '=', True), ('organization_subtype_id', '=', 'DIRECCTE')], on_delete='restrict') last_update_status = fields.Date('Dernière mise à jour des statuts') ministry_list_ids = fields.One2many( comodel_name='scop.ministry.list', inverse_name='partner_id', string='Liste Ministère') # Questionnaire questionnaire_ids = fields.One2many( comodel_name='scop.questionnaire', inverse_name='partner_id', string='Listes Ministrère') # Liasse fiscale liasse_fiscale_ids = fields.One2many( comodel_name='scop.liasse.fiscale', inverse_name='partner_id', string='Liasses Fiscales') # Révisions revision_contract = fields.Date("Date du contrat de révision", track_visibility='onchange') revision_company_id = fields.Many2one( 'res.partner', string='Organisme de révision', domain=[('is_company', '=', True), '|', ('organization_subtype_id.name', '=', 'Organisme réviseur'), ('organization_subtype_id.name', '=', 'Organisme réviseur, ' + 'Expert-comptable / Commissaire au compte')], on_delete='restrict', track_visibility='onchange') revision_backup_company_id = fields.Many2one( 'res.partner', string='Organisme de révision suppléant', domain=[('is_company', '=', True), '|', ('organization_subtype_id.name', '=', 'Organisme réviseur'), ('organization_subtype_id.name', '=', 'Organisme réviseur, ' + 'Expert-comptable / Commissaire au compte')], on_delete='restrict') revision_person_id = fields.Many2one( 'res.partner', string='Réviseur', domain=[('is_company', '=', False)], on_delete='restrict', track_visibility='onchange') revision_certified_person_id = fields.Many2one( 'res.partner', string='Réviseur agréé', domain=[('is_company', '=', False)], on_delete='restrict') revision_person_assign_date = fields.Date("Date de nomination du réviseur", track_visibility='onchange') revision_type = fields.Selection( [('1y', "Annuelle"), ('5y', 'Quinquennale'), ('5ys', "Quinquennale séquencée")], string='Périodicité de la révision') revision_format_id = fields.Many2one( 'scop.revision.format', string='Format de révision', on_delete='restrict') revision_last_date = fields.Date("Dernier exercice révisé", track_visibility='onchange') revision_next_date = fields.Date("Prochain exercice révisable", track_visibility='onchange') revision_staff = fields.Integer(string='Effectif révision', track_visibility='onchange') revision_ids = fields.One2many( comodel_name='scop.revision', inverse_name='partner_id', string='Liste des Révisions') # Outils financiers financial_tools_ids = fields.One2many( comodel_name='scop.financial.tools', inverse_name='partner_id', string='Outils financiers') # 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( 'res.partner.rgpd.origin', string="Origine du contact", on_delete='restrict') mandate_id = fields.Many2one( 'res.partner.mandate', string="Mandat", on_delete='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")], string="Licéité du contact", default="none") # Champs pour partenaires organization_type_id = fields.Many2one( 'res.partner.organization.type', string="Type", domain=[('parent_id', '=', False)], on_delete='restrict', track_visibility='onchange') organization_subtype_id = fields.Many2one( 'res.partner.organization.type', string="Sous-Type", domain=[('child_ids', '=', False)], on_delete='restrict', track_visibility='onchange') @api.multi def open_facebook(self): self.ensure_one() return { "type": "ir.actions.act_url", "url": self.facebook, } @api.multi def open_linkedin(self): self.ensure_one() return { "type": "ir.actions.act_url", "url": self.linkedin, } @api.multi def open_twitter(self): self.ensure_one() return { "type": "ir.actions.act_url", "url": self.twitter, } @api.onchange('creation_origin_id') def onchange_creation_origin_id(self): for coop in self: coop.creation_suborigin_id = False @api.onchange('organization_type_id') def onchange_organization_type_id(self): for partner in self: partner.organization_subtype_id = False def _create_period(self, partner): new_period = self.env['scop.period'].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, '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, 'cae': partner.cae }) partner.scop_period_ids = new_period # Creation d'une periode lorsque le statut passe en Phase de Suivi @api.multi def write(self, vals): result = super(ScopPartner, self).write(vals) if vals.get('project_status') == '6_suivi': for partner in self: self._create_period(partner) return result # Création d'une période lors de la création d'une coopérative @api.model_create_multi def create(self, vals_list): partners = super(ScopPartner, self).create(vals_list) for vals in vals_list: if vals.get('is_cooperative') and vals.get( 'project_status') == '6_suivi': for partner in partners: self._create_period(partner) return partners @api.model def _compute_siren(self): for company in self: if company.siret: company.siren = company.siret[:9] @api.model def _compute_seen_end(self): for company in self: if company.date_1st_sign: company.seed_end = company.date_1st_sign + timedelta(2556) else: company.seed_end = str(datetime.today() + timedelta(2556)) @api.model def _compute_current_user_ur_id(self): for partner in self: partner.current_user_ur_id = self.env.user.company_id.ur_id.id def _search_current_user_ur_id(self, operator, value): return [('ur_id', '=', self.env.user.company_id.ur_id.id)] @api.multi def scop_send_to_cg(self): # TODO - add call to API function self.write({ 'project_status': '5_cg', }) return True # TODO - remove temporary function once RIGA API in place @api.multi def scop_valid_cg(self): self.write({ 'project_status': '6_suivi', }) return True @api.multi def scop_abandonne(self): self.write({ 'project_status': '7_abandonne', }) return True class ScopPartnerCategory(models.Model): _inherit = "res.partner.category" def _default_ur(self): return self.env['res.company']._ur_default_get() id_riga = fields.Integer("ID RIGA") ur_id = fields.Many2one( 'union.regionale', string='Union Régionale', index=True, on_delete='restrict', default=_default_ur) class ResPartneCertification(models.Model): _name = "res.partner.certification" _description = "Certification" name = fields.Char('Certification') id_riga = fields.Integer("ID RIGA") color = fields.Integer('Couleur Index') class ScopPartnerCompanyType(models.Model): _inherit = "res.partner.company.type" id_riga = fields.Integer("ID RIGA") class ResPartnerCooperativeForm(models.Model): _name = "res.partner.cooperative.form" _description = "Cooperative form" name = fields.Char('Cooperative form') id_riga = fields.Integer("ID RIGA") class ResPartnerCreationOrigin(models.Model): _name = "res.partner.creation.origin" _description = "Creation Origin" _parent_name = "parent_id" _parent_store = True _rec_name = 'name' _order = 'id' name = fields.Char('Origine / Sous-Origine', index=True, required=True) parent_id = fields.Many2one( comodel_name='res.partner.creation.origin', string='Origine (parent)', index=True, ondelete='restrict') parent_path = fields.Char(index=True) child_ids = fields.One2many( comodel_name='res.partner.creation.origin', inverse_name='parent_id', string='Sous origines') id_riga = fields.Integer("ID RIGA") @api.constrains('parent_id') def _check_origin_recursion(self): if not self._check_recursion(): raise ValidationError( 'Vous ne pouvez pas créer des origines récursives.') return True class ResPartnerMandate(models.Model): _name = "res.partner.mandate" _description = "Mandat" name = fields.Char('Mandat') class ResPartnerOrganizationType(models.Model): _name = "res.partner.organization.type" _description = "Type of Organization" _parent_name = "parent_id" _parent_store = True _rec_name = 'name' _order = 'id' name = fields.Char('Type / Sous-Type', index=True, required=True) parent_id = fields.Many2one( comodel_name='res.partner.organization.type', string='Type (parent)', index=True, ondelete='restrict') parent_path = fields.Char(index=True) child_ids = fields.One2many( comodel_name='res.partner.organization.type', inverse_name='parent_id', string='Sous types') id_riga = fields.Integer("ID RIGA") @api.constrains('parent_id') def _check_origin_recursion(self): if not self._check_recursion(): raise ValidationError( 'Vous ne pouvez pas créer des types récursifs.') return True class ResPartnerDissolutionReason(models.Model): _name = "res.partner.dissolution.reason" _description = "Dissolution Reason" name = fields.Char('Dissolution Reason') class ResPartnerPrescriberCanal(models.Model): _name = "res.partner.prescriber.canal" _description = "Prescriber Canal" name = fields.Char('Prescriber Canal') class ResPartnerRgpdOrigin(models.Model): _name = "res.partner.rgpd.origin" _description = "Origin" name = fields.Char('Origin')