Logo Peef

×
🏠 Accueil 📚 Tutoriels 👨🏽‍💻 Formations 🙋‍♂️ Communautés 👑 Premium
À propos de Peef Conditions d'utilisation Envoyez un feedback Sessions de mentorat Offres Premium
Créer un compte Se connecter

Odoo: Pourquoi vous devez éviter de créer vos propres modèles et privilégier les modèles existants ?

nasser 10/02/2021 (18:14) GMT

Le weekend dernier j'ai travaillé sur un projet Odoo: je suis parti d'un module développé par un camerounais pour ajouter 2 fonctionnalités. Avant de commencer, je me suis imprégné du module, je l'ai parcouru pour comprendre son organisation et j'ai lu certaines doctrings pour comprendre ce que faisaient certaines fonctions du module. Lors de mon inspection du code, j'ai repéré un truc bizarre qui a attiré mon attention (Je vous dirai de quoi il s'agit plus bas) puis je me suis dit: <<Ah! si un truc se comporte mal, tu vas gérer ça avec un attribut related>>. 

 

Ensuite, je commence à développer la première fonctionnalité qui consiste à enregistrer un partenaire à travers une fenêtre modale. Je plonge alors dans ma bulle, je code le modèle et la vue avant d'écrire la fonction create() qui sera chargée d'enregistrer le partenaire et j'affiche la fenêtre modale. Subitement, après presqu'une heure et demi de codage, je tombe sur un bug qui va me bouffer 2 heures de ma nuit: j'ai travaillé ce samedi là de minuit à 3 heures du matin.

 

En effet, lorsque je rempli les informations du formulaire et clique sur le bouton <<Enregistrer>> , Odoo m'affiche l'erreur suivante: IntegrityError - null value in column "type" violates not-null constraint. Face à un tel bug assez explicite, je comprend clairement que la colonne type est required , ce qui veut dire que dans mon cas il n'y a aucune donnée dans le formulaire pour cette colonne. Je me mets alors à chercher dans le code et je tombe sur le truc bizarre que j'ai mentionné en début d'article: Il s'agit d'un bout de code comme celui-ci:

 

class CustomPartner(models.Model):

    _name = 'custom.partner'

    _inherit = ['portal.mixin', 'mail.thread', 'mail.activity.mixin']

    _rec_name = 'name'

    _inherits = {"res.partner": "partner_id"}

    _order = 'name asc'

 

    nom = fields.Char('Nom',required=True,size=128, translate=True)

    ...

    partner_id = fields.Many2one('res.partner',

            'Partenaire',

            required=False,

            ondelete="cascade",

            readonly=True,

            states={'brouillon': [('readonly', False)]},

            store=True)

 

Ayant vu ce code, j'ai trouvé bizarre qu'il nomme son modèle 'custom.partner', en plus il fait un héritage du modèle 'res.partner' à partir du champ partner_id. Il faut aussi noter qu'il a ajouté dans ce modèle certains champs qui sont déjà présents dans res.partner à savoir le nom (name) et le compagnie (company_id). À ce moment là je me suis dis: s'il y'a un problème je vais juste utiliser un related pour associer cet enregistrement à res.partner. Je voulais alors écrire ceci

 

class CustomPartner(models.Model):

    _inherit = 'res.partner'

    _rec_name = 'name'

    _order = 'name asc'

 

    nom = fields.Char('Nom',required=True,size=128, translate=True)

    name = fields.Char(related='nom')

    type = fields.Selection(selection_add=[('vip', 'VIP')], default='vip')

 

Losrque j'essayaie, ça ne marchait pas. Il fallait absolument que j'ajoute le type sans avoir à refactorer tout son code tout en conservant l'intégrité du modèle, mais ça ne marchait pas, il y'avait toujours une erreur qui apparaissait sur un champs du modèle res.partner (dans la vue, ou le modèle, ou quelque part ailleurs). 

 

Faut avouer que sa façon de surcharger les modèles n'est pas bonne. 

 

C'est à ce moment que j'ai pris l'initiative de refactorer ça, de retirer le nouveau modèle qu'il a ajouté à tord (je vais expliquer pourquoi) et de faire simplement un héritage de res.partner: ce travail je devais le faire pour 3 autres modèles dont il a fait le même style de surcharge. Heureusement, je l'ai fait le jour suivant, c'était dimanche.

 

Solution au problème: toujours respecter les bonnes pratiques

 

Odoo est un ERP assez stable et qui donne la possibilité de tout personnaliser. La bonne nouvelle c'est qu'on peut tout faire avec Odoo et la mauvaise c'est que l'excès de personnalisation va faire souffrir votre projet.

 

Dans le cas que j'ai expliqué plus haut, il s'agissait d'une mauvaise utilisation de l'héritage: le développeur a écris son propre modèle de partenaire parce qu'il veut ajouter les partenaires VIP. Au lieu d'utiliser res.partner et d'ajouter un type à ce modèle, il a fait autrement. Par conséquent, certaines personnalisations étaient bloquées, en l'occurence les miennes. Et si je continuais en faisant par exemple un règlement à travers le modèle account.move, il y'aurait sûrement eu un problème, puisqu'Odoo utilise res.partner à ce niveau.

 

Pour vous simplifier la tâche,

  • ne créez votre propre modèle que si vous êtes persuadés que ce modèle n'existe pas et qu'il n'y a pas son équivalent sur Odoo ou dans un module de l'OCA (Odoo Community Association)
  • lorsque vous avez besoin de mettre en place un nouvelle fonctionnalité, aller sur GitHub ou sur Odoo App Store pour voir si elle existe ou pas. Si elle existe, utilisez le module que vous venez de découvrir. Je vous conseille toujours de privilégier les modules de l'OCA aux modules individuels, parce que ceux de l'OCA sont maintenus par une large communauté.
  • s'il arrive que vous ayez besoin d'un modèle pour vos produits et services, utilisez les modèles product.template et product.product
  • Si vous avez besoin d'un autre pour les commandes, les modèles sale.order et sale.order.line
  • Pour les écritures comptables et factures: account.move et account.move.line
  • Pour les inventaire: stock.inventory, stock.move, stock.move.line
  • etc...
  •  

En conclusion, la documentation officielle d'Odoo est là pour vous servir: lisez là et réfléchissez bien avant de créer votre modèle. Surtout respectez les standards présents dans Odoo Guidelines.

 


Veuillez-vous connecter pour poster un commentaire