Documentation11 min de lecture

Contrats récurrents et abonnements dans Odoo Community

Le module OCA `contract` (dépôt `contract`, version 18.0.2.5.2, licence AGPL-3) ajoute 3 modèles, 225 champs et 10 menus à Odoo 18 Community : un cron quotidien facture automatiquement les contrats échus, clients comme fournisseurs, et le client suit ses contrats depuis le portail. Les trois modules de la famille, ce que chacun ajoute, et les deux réglages invisibles qui bloquent un démarrage.

Contrat et échéancier de facturation sur un bureau

Un revenu récurrent change la façon de piloter une entreprise : il se prévoit, il se renouvelle, et il se perd silencieusement. Odoo Community n'a pas de module d'abonnement natif ; la communauté a construit le dépôt contract, et c'est l'un des domaines où elle est allée le plus loin.

Trois modules du socle couvrent l'essentiel : le contrat lui-même, la quantité variable calculée au moment de facturer, et la génération de commandes de vente à la place des factures. Ils se complètent sans se recouvrir.

Résumé

Odoo Community n'a pas de module d'abonnement. Le dépôt contract le fournit : contrats clients et fournisseurs, lignes, gabarits, portail client, et un cron quotidien qui facture les échéances.

Trois réglages invisibles bloquent les démarrages : le droit « Discount on lines », sans lequel le champ remise n'apparaît pas ; le bouton de facturation immédiate, réservé au mode développeur ; et l'abonnement du client au contrat, sans lequel il ne le voit pas sur le portail.

L'essentiel

  • contract : contrats clients et fournisseurs, lignes, gabarits, et un cron quotidien qui facture les échéances.
  • Portail client : le client voit ses contrats et leur détail — à condition d'être abonné (follower) au contrat.
  • contract_variable_quantity : une quantité calculée par formule Python au moment de la facturation.
  • contract_sale_generation : le contrat génère une commande de vente au lieu d'une facture, pour passer par une validation commerciale.
  • Deux réglages invisibles bloquent les démarrages : le droit « Discount on lines », et le bouton de facturation immédiate réservé au mode développeur.

Ce que les trois modules ajoutent à l'instance

contract_variable_quantity_sale_generation
Modèles créés310
Modèles étendus735
Champs ajoutés2252120
Menus1010
Vues3161
Version18.0.2.5.218.0.1.0.018.0.1.0.2
LicenceAGPL-3AGPL-3AGPL-3

225 champs et 31 vues pour le seul module central : c'est un domaine fonctionnel entier, pas un utilitaire. Les objets à connaître sont peu nombreux :

ObjetCe qu'il est
contract.contractLe contrat, client (sale) ou fournisseur (purchase)
contract.lineUne ligne : produit, quantité, prix unitaire
contract.templateUn gabarit, pour préremplir un contrat
contract.tagUne étiquette de classement
contract.modificationL'historique des modifications du contrat
contract.recurring.mixinLe mixin de récurrence, réutilisé par les autres modules du dépôt

La distinction client / fournisseur est portée par un champ unique (contract_type), mais chaque sens a ses propres menus et ses propres vues. Un contrat d'achat récurrent — une maintenance que vous payez, un loyer — se gère donc comme un contrat de vente, et c'est une bonne nouvelle pour la prévision de trésorerie.

Où le trouver dans Odoo

MenuCe qu'on y fait
Facturation ▸ Clients ▸ Contrats clientsLes contrats de vente
Facturation ▸ Clients ▸ Facturer les contrats de vente manuellementForcer la facturation d'un lot d'échéances
Facturation ▸ Fournisseurs ▸ Contrats d'achatsLes contrats fournisseurs
Facturation ▸ Fournisseurs ▸ Facturer les contrats fournisseurs manuellementIdem, côté achats
Facturation ▸ Analyse ▸ Contrats ▸ Lignes de contrat client / fournisseurL'analyse par ligne, pour le prévisionnel
Facturation ▸ Configuration ▸ Contrats ▸ Modèles de contratLes gabarits
… ▸ Étiquette du contratLes étiquettes de classement

Les deux menus Facturation ▸ Analyse ▸ Contrats ▸ Lignes de contrat sont ceux qu'on découvre le plus tard et qui servent le plus : ils donnent le revenu récurrent ligne par ligne, donc la base d'un prévisionnel — ce que la liste des contrats ne montre pas.

Attention : les menus de facturation manuelle sont réservés au groupe Facturation : Administrateur (account.group_account_manager).

Cas d'usage

Créer un contrat client à facturation mensuelle

  1. Facturation ▸ Clients ▸ Contrats clients, puis Nouveau.
  2. Renseigner Customer, et éventuellement un Contract Template pour préremplir.
  3. Onglet Recurring Invoices : ajouter une ligne avec Product, Quantity, Unit Price — ou cocher Auto-price? pour suivre la liste de prix.
  4. Onglet Invoicing : vérifier Invoicing contact, Journal, Invoicing type et Invoice Every.
  5. Enregistrer.

Le cron quotidien Generate Recurring Invoices from Contracts facturera à la Date of Next Invoice. Il est actif par défaut : aucun paramétrage n'est nécessaire, à condition qu'un journal comptable soit correctement défini par société et par type de contrat.

Pour forcer une facturation immédiate, le bouton Create invoices existe dans l'en-tête — mais il n'est visible qu'en mode développeur. C'est le premier réglage invisible qui déroute : on cherche un bouton qui est là, sans être affiché.

Facturer en lot les contrats arrivés à échéance

  1. Facturation ▸ Clients ▸ Facturer les contrats de vente manuellement.
  2. Sélectionner la date d'échéance de référence, puis lancer la facturation.

C'est le chemin à privilégier plutôt que d'attendre le cron quand on veut contrôler le lot avant émission — par exemple en fin de mois, avant une clôture.

Facturer une quantité qui dépend d'une donnée vivante

Le cas d'un abonnement facturé au nombre d'utilisateurs actifs, de sites surveillés, de documents traités. La quantité n'est pas connue à la signature.

  1. Installer contract_variable_quantity.
  2. Sur la ligne de contrat, basculer le type de quantité de Fixed quantity à Variable quantity.
  3. Rattacher une Formule (quantité) — une expression Python évaluée à chaque génération de facture.
  4. Sur le contrat, cocher l'option qui évite de créer une ligne de facture quand la quantité calculée est nulle.

Formulaire d'une formule de quantité : le code Python évalué à chaque génération de facture pour déterminer la quantité à facturer
Formulaire d'une formule de quantité : le code Python évalué à chaque génération de facture pour déterminer la quantité à facturer

La dernière option est celle qui évite les factures à zéro euro envoyées à un client, qui font toujours mauvais effet.

Passer par une commande de vente avant de facturer

Le cas d'un contrat dont chaque échéance doit déclencher une livraison, ou passer par une validation commerciale.

  1. Installer contract_sale_generation (il installe contract_sale, qui installe contract).
  2. Sur le contrat, onglet Invoicing, section Recurring Type : passer Generation Type de « Invoice » à « Sale ».
  3. Cocher Sale Autoconfirm si les commandes doivent être confirmées automatiquement ; le laisser décoché pour une validation manuelle.
  4. Enregistrer.

Le cron devient alors Generate Recurring sales from Contracts, actif par défaut à l'installation, et un compteur sur la fiche du contrat donne accès aux commandes déjà générées.

Les deux réglages invisibles

Ce sont les deux points qui font perdre une demi-journée à un démarrage, et ils ne sont pas documentés dans l'interface.

  1. Le champ Discount n'apparaît pas sur les lignes de contrat sans le droit d'accès « Discount on lines ». Si vos contrats comportent des remises négociées, c'est le premier droit à attribuer — sinon le champ est simplement absent, sans message.
  2. Le bouton Create invoices est réservé au mode développeur (groupe technique base.group_no_one). On peut l'attribuer explicitement à un utilisateur plutôt que d'activer le mode développeur, ce qui est la bonne pratique pour une personne qui facture chaque mois.

Un troisième point, côté portail cette fois : un client ne voit ses contrats que s'il est abonné (follower) au contrat. Créer le contrat ne suffit pas à le rendre visible côté client — il faut ajouter le contact en abonné, et c'est l'oubli le plus fréquent quand on promet un portail au client.

Configuration

  1. Installer contract — aucune configuration préalable obligatoire, les menus apparaissent avec la facturation standard.
  2. Définir un journal comptable par société et par type de contrat : c'est la seule condition au bon fonctionnement du cron.
  3. Attribuer le droit « Discount on lines » si vos contrats portent des remises.
  4. Attribuer le menu de facturation manuelle au groupe account.group_account_manager.
  5. Ajouter les contacts clients en abonnés des contrats qu'ils doivent voir sur le portail.
  6. Installer contract_variable_quantity et/ou contract_sale_generation selon le besoin — ils s'activent contrat par contrat, pas globalement.

L'étape 6 mérite d'être soulignée : ces deux modules n'ont aucun effet global. Installés, ils ajoutent une option sur chaque contrat ; les contrats existants continuent de se comporter comme avant. C'est un bon profil de risque pour une installation en production.

Limites connues

Le dépôt répertorie deux souhaits d'évolution sur le module central, qui sont autant de limites actuelles.

  • Récupérer les états et d'autres champs fonctionnels sur les contrats : le module ne porte pas de workflow d'états riche — un contrat n'a pas de cycle brouillon / actif / suspendu / terminé aussi explicite qu'on l'attendrait d'un module d'abonnement.
  • Ajouter un indicateur de récurrence au niveau du gabarit : la récurrence se définit contrat par contrat, pas sur le modèle de contrat.

Deux limites d'usage, observées :

  • La formule de quantité variable est du Python évalué à chaque facturation. Une formule fausse produit une facture fausse, et le contrôle n'est pas bloquant. Testez-la sur un contrat de démonstration avant de l'appliquer à un client.
  • Le suivi du renouvellement n'est pas natif. C'est pourtant le chiffre qui compte dans un modèle d'abonnement : il faut le construire, par les menus d'analyse des lignes de contrat ou un rapport dédié.

Sur ce dernier point, un rapport SQL dédié est souvent la réponse la plus rapide — voir bi_sql_editor.

Identité technique

ModuleVersionLicenceDépend de
contract18.0.2.5.2AGPL-3account, base, portal, product
contract_variable_quantity18.0.1.0.0AGPL-3contract
contract_sale_generation18.0.1.0.2AGPL-3contract_sale

Les trois viennent du dépôt OCA contract, branche 18.0, et font partie de notre socle commun — avec product_contract, qui permet à un article de porter son modèle de contrat.

Pour le pilotage d'une activité d'abonnement, voir aussi les deux chiffres d'un club et la marge par mission en société de services.

Questions fréquentes

Odoo Community gère-t-il les abonnements ?

Pas nativement : il n'y a pas de module d'abonnement dans l'édition Community. Le dépôt OCA contract le fournit, avec les contrats clients et fournisseurs, les lignes, les gabarits, un cron quotidien de facturation et un portail client. C'est l'un des domaines où la communauté couvre l'essentiel du besoin d'une PME.

Pourquoi le champ Discount n'apparaît-il pas sur mes lignes de contrat ?

Parce qu'il dépend du droit d'accès « Discount on lines ». Sans ce droit, le champ est simplement absent, sans aucun message — c'est le réglage invisible qui fait perdre le plus de temps au démarrage. Attribuez-le aux personnes qui saisissent les contrats.

Comment forcer la facturation d'un contrat sans attendre le cron ?

Deux chemins : le bouton Create invoices sur le contrat, visible seulement en mode développeur — ou mieux, attribuez le groupe technique à la personne concernée. Et pour un lot, le menu Facturer les contrats de vente manuellement, réservé au groupe Facturation : Administrateur.

Mon client ne voit pas ses contrats sur le portail, pourquoi ?

Parce qu'il n'est pas abonné (follower) au contrat. Créer le contrat ne le rend pas visible côté client : il faut ajouter le contact en abonné. C'est l'oubli le plus fréquent quand on a promis un accès portail au client.

Peut-on facturer une quantité qui change chaque mois ?

Oui, avec contract_variable_quantity : la ligne passe en « Variable quantity » et une formule Python est évaluée à chaque génération de facture. Pensez à cocher l'option qui évite de créer une ligne quand la quantité calculée est nulle — une facture à zéro euro fait toujours mauvais effet.

Se faire accompagner

Deux choses ne sont pas dans le module et décident pourtant de la réussite : la formule de quantité variable, qui produit une facture fausse si elle est fausse, et le suivi du renouvellement, qui n'est pas natif alors que c'est le chiffre central d'un modèle d'abonnement.

Nous écrivons et testons les formules sur un contrat de démonstration, puis nous construisons le rapport de renouvellement par cohorte. Voir les prestations d'Atalios Consulting ou demander un rappel.

Pour aller plus loin

En résumé

Le dépôt contract apporte à Odoo Community ce qu'il n'a pas nativement : des contrats récurrents, clients et fournisseurs, facturés par un cron quotidien. Trois réglages invisibles à régler d'emblée — le droit « Discount on lines », le bouton de facturation immédiate, et l'abonnement du client au contrat pour le portail. Parlons de vos abonnements.

Documentation OCAFacturationServices

Partager

Fiches connexes

Relevés bancaires et pièces comptables sur un bureau
Relevé sur une instance Odoo 18 Community, le module OCA `account_reconcile_oca` (dépôt `account-reconcile`, version 18.0.1.1.14, licence AGPL-3) ajoute 2 modèles, 87 champs et 17 vues : il remplace le lettrage limité de la Community par deux écrans dédiés, bancaire et par compte. Ce qu'il ajoute à l'instance, où le trouver, ses quatre cas d'usage et ses limites connues.
Lire la suite
Documentation OCA, Comptabilité
Relevé bancaire et suivi des opérations sur un bureau
Odoo a retiré l'import de relevés bancaires de son édition Community à partir de la version 14 : les 3 modules OCA `account_statement_import_file` (18.0.1.0.3, LGPL-3), `_camt` et `_ofx` le rétablissent, avec la détection des transactions déjà importées. Comment ils s'articulent, ce que CAMT apporte de plus qu'OFX, et le piège du fichier sans IBAN.
Lire la suite
Documentation OCA, Comptabilité