diff --git a/models/__init__.py b/models/__init__.py
index c9f67d1029451187faac73b30248b565bd1340d9..b9c11d9d929c89108a38db6f9596ab8bfd372d52 100644
--- a/models/__init__.py
+++ b/models/__init__.py
@@ -1 +1,2 @@
+from . import acc_enedis_cdc
 from . import acc_operation
diff --git a/models/acc_enedis_cdc.py b/models/acc_enedis_cdc.py
new file mode 100644
index 0000000000000000000000000000000000000000..aefbdc9d551a1a6118304c5bfb8d8be5540789b2
--- /dev/null
+++ b/models/acc_enedis_cdc.py
@@ -0,0 +1,312 @@
+# Copyright 2021- Le Filament (https://le-filament.com)
+# License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html)
+import logging
+from datetime import date, datetime
+
+from dateutil.relativedelta import relativedelta
+
+from odoo import fields, models
+
+_logger = logging.getLogger(__name__)
+
+
+class AccEnedisCdc(models.Model):
+    _inherit = "acc.enedis.cdc"
+
+    # ------------------------------------------------------
+    # Fields declaration
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # SQL Constraints
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # Default methods
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # Computed fields / Search Fields
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # Onchange / Constraints
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # CRUD methods (ORM overrides)
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # Actions
+    # ------------------------------------------------------
+
+    # ------------------------------------------------------
+    # API functions
+    # ------------------------------------------------------
+    def _curves(
+        self,
+        operation,
+        start_date,
+        end_date,
+        usage_point_cons_ids=None,
+        usage_point_prod_ids=None,
+    ):
+        """
+        Vérifie les périodes, crée un log et appelle les courbes de conso / prod
+        à partir de l'API Enedis (cet appel passe par un job queue)
+
+        :param record operation : operation (model acc.operation)
+        :param date start_date : date de début à récupérer (incluse)
+        :param date end_date : date de fin à récupérer (exclue)
+        :param recordset usage_point_cons_ids : liste de PRMs de soutirage à récupérer
+        :param recordset usage_point_prod_ids : liste de PRMs d'injection à récupérer
+        Les PRMs sont optionnels,
+            si non renseignés, tous les PRMs liés à l'opération seront récupérés
+        """
+        operation._check_access_api()
+
+        # Si pas de PRM sélectionnés
+        if not usage_point_cons_ids and not usage_point_prod_ids:
+            usage_point_cons_ids = operation.acc_delivery_period_ids.mapped(
+                "acc_counter_id"
+            )
+            usage_point_prod_ids = operation.acc_injection_period_ids.mapped(
+                "acc_counter_id"
+            )
+
+        message = ""
+        message += (
+            "<h1>API Enedis OACC - Création des jobs de récupération des Courbes "
+            + str(fields.Datetime.now())
+            + "</h1>"
+            "Appels API pour la période "
+            "" + str(start_date) + " " + str(end_date) + "<br/>"
+        )
+
+        if usage_point_cons_ids:
+            # Traitement données de cons
+            message += (
+                "<br/><strong>Création des jobs de récupération des courbes "
+                "de consommation</strong><br/>"
+            )
+            for usage_point_id in usage_point_cons_ids:
+                # Vérification que le PRM est actif sur la période demandée
+                period_ids = self.env["acc.counter.period"]._get_periods_from_interval(
+                    [
+                        ("acc_operation_id", "=", operation.id),
+                        ("acc_counter_id", "=", usage_point_id.id),
+                        ("prm_type", "=", "delivery"),
+                    ],
+                    start_date,
+                    end_date,
+                )
+                # Si pas de période de PRM, on ne fait pas d'appel API
+                if not period_ids:
+                    message += (
+                        "Opération: "
+                        + operation.name
+                        + " - PRM: "
+                        + usage_point_id.name
+                        + " - aucune période trouvée du "
+                        + str(start_date)
+                        + " au "
+                        + str(end_date)
+                        + "<br/>"
+                    )
+                # Si période de PRM on vérifie les dates puis on appelle l'API
+                else:
+                    start_date_upd = max(start_date, period_ids[0].start_date)
+                    if period_ids[-1].end_date:
+                        end_date_upd = min(end_date, period_ids[-1].end_date)
+                    else:
+                        end_date_upd = end_date
+                    desc = (
+                        "Opération: "
+                        + operation.name
+                        + " - PRM: "
+                        + usage_point_id.name
+                        + " - Date: "
+                        + str(fields.Datetime.today())
+                        + " - Période: du "
+                        + str(start_date_upd)
+                        + " au "
+                        + str(end_date_upd)
+                    )
+                    message += desc + "<br/>"
+                    self.with_delay(description=desc)._get_definitive_load_curves(
+                        operation, start_date_upd, end_date_upd, usage_point_id, "cons"
+                    )
+
+        if usage_point_prod_ids:
+            # Traitement données de prod
+            message += (
+                "<br/><strong>Création des jobs de récupération des courbes "
+                "de production</strong><br/>"
+            )
+            for usage_point_id in usage_point_prod_ids:
+                # Vérification que le PRM est actif sur la période demandée
+                period_ids = self.env["acc.counter.period"]._get_periods_from_interval(
+                    [
+                        ("acc_operation_id", "=", operation.id),
+                        ("acc_counter_id", "=", usage_point_id.id),
+                        ("prm_type", "=", "injection"),
+                    ],
+                    start_date,
+                    end_date,
+                )
+                # Si pas de période de PRM, on ne fait pas d'appel API
+                if not period_ids:
+                    message += (
+                        "Opération: "
+                        + operation.name
+                        + " - PRM: "
+                        + usage_point_id.name
+                        + " - aucune période trouvée du "
+                        + str(start_date)
+                        + " au "
+                        + str(end_date)
+                        + "<br/>"
+                    )
+                # Si période de PRM on vérifie les dates puis on appelle l'API
+                else:
+                    start_date_upd = max(start_date, period_ids[0].start_date)
+                    if period_ids[-1].end_date:
+                        end_date_upd = min(end_date, period_ids[-1].end_date)
+                    else:
+                        end_date_upd = end_date
+                    desc = (
+                        "Opération: "
+                        + operation.name
+                        + " - PRM: "
+                        + usage_point_id.name
+                        + " - Date: "
+                        + str(fields.Datetime.today())
+                        + " - Période: du "
+                        + str(start_date_upd)
+                        + " au "
+                        + str(end_date_upd)
+                    )
+                    message += desc + "<br/>"
+                    self.with_delay(description=desc)._get_definitive_load_curves(
+                        operation,
+                        start_date_upd,
+                        end_date_upd,
+                        usage_point_id,
+                        "prod",
+                    )
+
+        message += (
+            "<br/><h1>Fin de création des jobs de récupération des courbes: "
+            + str(fields.Datetime.now())
+            + "</h1>"
+        )
+        if not operation.is_cdc_data_exists:
+            operation.is_cdc_data_exists = True
+        # Logs information
+        self.env["acc.logs"].create(
+            {
+                "name": "Appel API Enedis Courbes du "
+                + str(fields.Date.today())
+                + " - Période "
+                + str(start_date)
+                + " "
+                + str(end_date),
+                "date_launched": fields.Datetime.now(),
+                "type_log": "api",
+                "message": message,
+                "acc_operation_id": operation.id,
+            }
+        )
+
+    def _get_definitive_load_curves(
+        self, operation, start_date, end_date, usage_point_id, type_prm
+    ):
+        """
+        Appelle les courbes de conso / prod à partir de l'API Enedis
+
+        :param record operation : operation (model acc.operation)
+        :param date start_date : date de début à récupérer (incluse)
+        :param date end_date : date de fin à récupérer (exclue)
+        :param record usage_point_id : PRM à récupérer
+        :param char type_prm : type de PRM à récupérer ("cons" ou "prod")
+        """
+        message = ""
+        message += "PRM " + usage_point_id.name + "\n"
+        message += "Appel API ...\n"
+        # Transformation des dates naives en datetime UTC
+        start_datetime = self._convert_time(start_date)
+        end_datetime = self._convert_time(end_date)
+        curves_data = operation._get_definitive_load_curves(
+            operation.name,
+            start_datetime,
+            end_datetime,
+            usage_point_id.name,
+            operation.client_id,
+            operation.secret_id,
+            type_prm,
+        )
+        message += "Appel API terminé. Traitement des données ...\n"
+
+        curves = curves_data.get("curves")
+
+        if curves:
+            name = usage_point_id.name + "_" + str(start_date) + "_" + str(end_date)
+        for curve in curves:
+            type_curve = curve["type"]
+
+            for point in curve["interval_reading"]:
+                date_slot = datetime.strptime(point["timestamp"], "%Y-%m-%dT%H:%M:%SZ")
+                self.env["acc.enedis.cdc"].create(
+                    {
+                        "name": name,
+                        "acc_operation_id": operation.id,
+                        "acc_counter_id": usage_point_id.id or False,
+                        "comp_data_type": type_curve,
+                        "power": point["value"],
+                        "date_slot": date_slot,
+                    }
+                )
+            # Update partner_id for retrieved cdc
+            domain = [
+                ("acc_operation_id", "=", operation.id),
+                ("acc_counter_id", "=", usage_point_id.id or False),
+                ("prm_type", "=", "delivery" if type_prm == "cons" else "injection"),
+            ]
+            self.env["acc.counter.period"]._get_periods_from_interval(
+                domain, start_date, end_date
+            )._update_cdc_partner_id()
+        message += "Fin du traitement des données\n"
+        _logger.info(message)
+        return message
+
+    def _get_curves_all(
+        self, operation, usage_point_cons_ids=None, usage_point_prod_ids=None
+    ):
+        """
+        Récupère les données de l'opération depuis le début de la mise en place
+        de l'opération. A partir de la date de début de contrat, calcul du nombre
+        de mois entre la date de début de contrat et la date du jour. Puis
+        récupération des données de tous les mois
+        """
+        nb_months = (date.today().year - operation.date_start_contract.year) * 12 + (
+            date.today().month - operation.date_start_contract.month
+        )
+
+        start_date_it = operation.date_start_contract
+        end_date_it = operation.date_start_contract + relativedelta(months=1)
+
+        for _i in range(nb_months):
+            self._curves(
+                operation,
+                start_date_it,
+                end_date_it,
+                usage_point_cons_ids,
+                usage_point_prod_ids,
+            )
+            start_date_it = start_date_it + relativedelta(months=1)
+            end_date_it = start_date_it + relativedelta(months=1)
+
+    # ------------------------------------------------------
+    # Business methods
+    # ------------------------------------------------------
diff --git a/models/acc_operation.py b/models/acc_operation.py
index b6d81abca8ea60c16976649988bfd3b40b94a0b9..65edb73ccf523aa3bd31be637fa557b9e8ff6c41 100644
--- a/models/acc_operation.py
+++ b/models/acc_operation.py
@@ -1,9 +1,7 @@
 # Copyright 2021- Le Filament (https://le-filament.com)
 # License AGPL-3.0 or later (http://www.gnu.org/licenses/agpl.html)
 import logging
-from datetime import date, datetime
-
-from dateutil.relativedelta import relativedelta
+from datetime import date
 
 from odoo import _, fields, models
 from odoo.exceptions import UserError, ValidationError
@@ -44,7 +42,6 @@ class AccOperation(models.Model):
     # ------------------------------------------------------
     # Actions
     # ------------------------------------------------------
-
     def get_perimeter(self):
         self.ensure_one()
         message = self.perimeter()
@@ -80,254 +77,6 @@ class AccOperation(models.Model):
     # ------------------------------------------------------
     # API functions
     # ------------------------------------------------------
-    def curves(
-        self, start_date, end_date, usage_point_cons_ids=None, usage_point_prod_ids=None
-    ):
-        """
-        Vérifie les périodes, crée un log et appelle les courbes de conso / prod
-        à partir de l'API Enedis (cet appel passe par un job queue)
-
-        :param date start_date : date de début à récupérer (incluse)
-        :param date end_date : date de fin à récupérer (exclue)
-        :param recordset usage_point_cons_ids : liste de PRMs de soutirage à récupérer
-        :param recordset usage_point_prod_ids : liste de PRMs d'injection à récupérer
-        Les PRMs sont optionnels,
-            si non renseignés, tous les PRMs liés à l'opération seront récupérés
-        """
-        self._check_access_api()
-        # TODO: Update to get curves only for existing periods
-
-        # Si pas de PRM sélectionnés
-        if not usage_point_cons_ids and not usage_point_prod_ids:
-            usage_point_cons_ids = self.acc_delivery_period_ids.mapped("acc_counter_id")
-            usage_point_prod_ids = self.acc_injection_period_ids.mapped(
-                "acc_counter_id"
-            )
-
-        message = ""
-        message += (
-            "<h1>API Enedis OACC - Création des jobs de récupération des Courbes "
-            + str(fields.Datetime.now())
-            + "</h1>"
-            "Appels API pour la période "
-            "" + str(start_date) + " " + str(end_date) + "<br/>"
-        )
-
-        if usage_point_cons_ids:
-            # Traitement données de cons
-            message += (
-                "<br/><strong>Création des jobs de récupération des courbes "
-                "de consommation</strong><br/>"
-            )
-            for usage_point_id in usage_point_cons_ids:
-                # Vérification que le PRM est actif sur la période demandée
-                period_ids = self.env["acc.counter.period"]._get_periods_from_interval(
-                    [
-                        ("acc_operation_id", "=", self.id),
-                        ("acc_counter_id", "=", usage_point_id.id),
-                        ("prm_type", "=", "delivery"),
-                    ],
-                    start_date,
-                    end_date,
-                )
-                # Si pas de période de PRM, on ne fait pas d'appel API
-                if not period_ids:
-                    message += (
-                        "Opération: "
-                        + self.name
-                        + " - PRM: "
-                        + usage_point_id.name
-                        + " - aucune période trouvée du "
-                        + str(start_date)
-                        + " au "
-                        + str(end_date)
-                        + "<br/>"
-                    )
-                # Si période de PRM on vérifie les dates puis on appelle l'API
-                else:
-                    start_date_upd = max(start_date, period_ids[0].start_date)
-                    if period_ids[-1].end_date:
-                        end_date_upd = min(end_date, period_ids[-1].end_date)
-                    else:
-                        end_date_upd = end_date
-                    desc = (
-                        "Opération: "
-                        + self.name
-                        + " - PRM: "
-                        + usage_point_id.name
-                        + " - Date: "
-                        + str(fields.Datetime.today())
-                        + " - Période: du "
-                        + str(start_date_upd)
-                        + " au "
-                        + str(end_date_upd)
-                    )
-                    message += desc + "<br/>"
-                    self.with_delay(description=desc).get_definitive_load_curves(
-                        start_date_upd, end_date_upd, usage_point_id, "cons"
-                    )
-
-        if usage_point_prod_ids:
-            # Traitement données de prod
-            message += (
-                "<br/><strong>Création des jobs de récupération des courbes "
-                "de production</strong><br/>"
-            )
-            for usage_point_id in usage_point_prod_ids:
-                # Vérification que le PRM est actif sur la période demandée
-                period_ids = self.env["acc.counter.period"]._get_periods_from_interval(
-                    [
-                        ("acc_operation_id", "=", self.id),
-                        ("acc_counter_id", "=", usage_point_id.id),
-                        ("prm_type", "=", "injection"),
-                    ],
-                    start_date,
-                    end_date,
-                )
-                # Si pas de période de PRM, on ne fait pas d'appel API
-                if not period_ids:
-                    message += (
-                        "Opération: "
-                        + self.name
-                        + " - PRM: "
-                        + usage_point_id.name
-                        + " - aucune période trouvée du "
-                        + str(start_date)
-                        + " au "
-                        + str(end_date)
-                        + "<br/>"
-                    )
-                # Si période de PRM on vérifie les dates puis on appelle l'API
-                else:
-                    start_date_upd = max(start_date, period_ids[0].start_date)
-                    if period_ids[-1].end_date:
-                        end_date_upd = min(end_date, period_ids[-1].end_date)
-                    else:
-                        end_date_upd = end_date
-                    desc = (
-                        "Opération: "
-                        + self.name
-                        + " - PRM: "
-                        + usage_point_id.name
-                        + " - Date: "
-                        + str(fields.Datetime.today())
-                        + " - Période: du "
-                        + str(start_date_upd)
-                        + " au "
-                        + str(end_date_upd)
-                    )
-                    message += desc + "<br/>"
-                    self.with_delay(description=desc).get_definitive_load_curves(
-                        start_date_upd,
-                        end_date_upd,
-                        usage_point_id,
-                        "prod",
-                    )
-
-        message += (
-            "<br/><h1>Fin de création des jobs de récupération des courbes: "
-            + str(fields.Datetime.now())
-            + "</h1>"
-        )
-        if not self.is_cdc_data_exists:
-            self.is_cdc_data_exists = True
-        # Logs information
-        self.env["acc.logs"].create(
-            {
-                "name": "Appel API Enedis Courbes du "
-                + str(fields.Date.today())
-                + " - Période "
-                + str(start_date)
-                + " "
-                + str(end_date),
-                "date_launched": fields.Datetime.now(),
-                "type_log": "api",
-                "message": message,
-                "acc_operation_id": self.id,
-            }
-        )
-
-    def get_definitive_load_curves(
-        self, start_date, end_date, usage_point_id, type_prm
-    ):
-        """
-        Appelle les courbes de conso / prod à partir de l'API Enedis
-
-        :param date start_date : date de début à récupérer (incluse)
-        :param date end_date : date de fin à récupérer (exclue)
-        :param record usage_point_id : PRM à récupérer
-        :param char type_prm : type de PRM à récupérer ("cons" ou "prod")
-        """
-        message = ""
-        message += "PRM " + usage_point_id.name + "\n"
-        message += "Appel API ...\n"
-        # Transformation des dates naives en datetime UTC
-        start_datetime = self._convert_time(start_date)
-        end_datetime = self._convert_time(end_date)
-        curves_data = self._get_definitive_load_curves(
-            self.name,
-            start_datetime,
-            end_datetime,
-            usage_point_id.name,
-            self.client_id,
-            self.secret_id,
-            type_prm,
-        )
-        message += "Appel API terminé. Traitement des données ...\n"
-
-        curves = curves_data.get("curves")
-
-        if curves:
-            name = usage_point_id.name + "_" + str(start_date) + "_" + str(end_date)
-        for curve in curves:
-            type_curve = curve["type"]
-
-            for point in curve["interval_reading"]:
-                date_slot = datetime.strptime(point["timestamp"], "%Y-%m-%dT%H:%M:%SZ")
-                self.env["acc.enedis.cdc"].create(
-                    {
-                        "name": name,
-                        "acc_operation_id": self.id,
-                        "acc_counter_id": usage_point_id.id or False,
-                        "comp_data_type": type_curve,
-                        "power": point["value"],
-                        "date_slot": date_slot,
-                    }
-                )
-            # Update partner_id for retrieved cdc
-            domain = [
-                ("acc_operation_id", "=", self.id),
-                ("acc_counter_id", "=", usage_point_id.id or False),
-                ("prm_type", "=", "delivery" if type_prm == "cons" else "injection"),
-            ]
-            self.env["acc.counter.period"]._get_periods_from_interval(
-                domain, start_date, end_date
-            )._update_cdc_partner_id()
-        message += "Fin du traitement des données\n"
-        _logger.info(message)
-        return message
-
-    def get_curves_all(self, usage_point_cons_ids=None, usage_point_prod_ids=None):
-        """
-        Récupère les données de l'opération depuis le début de la mise en place
-        de l'opération. A partir de la date de début de contrat, calcul du nombre
-        de mois entre la date de début de contrat et la date du jour. Puis
-        récupération des données de tous les mois
-        """
-        nb_months = (date.today().year - self.date_start_contract.year) * 12 + (
-            date.today().month - self.date_start_contract.month
-        )
-
-        start_date_it = self.date_start_contract
-        end_date_it = self.date_start_contract + relativedelta(months=1)
-
-        for _i in range(nb_months):
-            self.curves(
-                start_date_it, end_date_it, usage_point_cons_ids, usage_point_prod_ids
-            )
-            start_date_it = start_date_it + relativedelta(months=1)
-            end_date_it = start_date_it + relativedelta(months=1)
-
     def perimeter(self):
         """
         Récupère les données de l'opération concernant le périmètre:
diff --git a/wizards/acc_operation_wizard.py b/wizards/acc_operation_wizard.py
index e368b45db2f31df2f74013efbb7ec683279a372d..ab239b6f1d6f9858f02dc3a02d6bd722515ba50a 100644
--- a/wizards/acc_operation_wizard.py
+++ b/wizards/acc_operation_wizard.py
@@ -104,8 +104,8 @@ class AccOperationWizard(models.TransientModel):
             domain_extra_cdc = expression.OR([domain_cons_cdc, domain_prod_cdc])
 
         domain_periods = expression.AND([domain_base, domain_extra])
-        start_datetime = self.env["acc.operation"]._convert_time(self.start_date)
-        end_datetime = self.env["acc.operation"]._convert_time(self.end_date)
+        start_datetime = self.env["acc.enedis.cdc"]._convert_time(self.start_date)
+        end_datetime = self.env["acc.enedis.cdc"]._convert_time(self.end_date)
         domain_date = [
             ("date_slot", ">=", start_datetime),
             ("date_slot", "<", end_datetime),
@@ -150,8 +150,12 @@ class AccOperationWizard(models.TransientModel):
                 "target": "new",
             }
         else:
-            self.operation_id.curves(
-                self.start_date, self.end_date, self.prm_cons_ids, self.prm_prod_ids
+            self.env["acc.enedis.cdc"]._curves(
+                self.operation_id,
+                self.start_date,
+                self.end_date,
+                self.prm_cons_ids,
+                self.prm_prod_ids,
             )
             return {"type": "ir.actions.act_window_close"}
 
@@ -189,7 +193,9 @@ class AccOperationWizard(models.TransientModel):
                 "target": "new",
             }
         else:
-            self.operation_id.get_curves_all(self.prm_cons_ids, self.prm_prod_ids)
+            self.env["acc.enedis.cdc"]._get_curves_all(
+                self.operation_id, self.prm_cons_ids, self.prm_prod_ids
+            )
             return {"type": "ir.actions.act_window_close"}
 
     # ------------------------------------------------------
diff --git a/wizards/acc_operation_wizard_confirm.py b/wizards/acc_operation_wizard_confirm.py
index 03d49f2c44e385f8596f810484d48274a2a1d875..57177d2a8d8938d1c83be5bb512c2c38219b2aa0 100644
--- a/wizards/acc_operation_wizard_confirm.py
+++ b/wizards/acc_operation_wizard_confirm.py
@@ -61,12 +61,18 @@ class AccOperationWizardConfirm(models.TransientModel):
         # Appels API
         # Si date présente, appel pour la période
         if self.start_date:
-            self.operation_id.curves(
-                self.start_date, self.end_date, self.prm_cons_ids, self.prm_prod_ids
+            self.env["acc.enedis.cdc"]._curves(
+                self.operation_id,
+                self.start_date,
+                self.end_date,
+                self.prm_cons_ids,
+                self.prm_prod_ids,
             )
         else:
             # Pas de date renseignée, récupération de toutes les données
-            self.operation_id.get_curves_all(self.prm_cons_ids, self.prm_prod_ids)
+            self.env["acc.enedis.cdc"]._get_curves_all(
+                self.operation_id, self.prm_cons_ids, self.prm_prod_ids
+            )
         return {"type": "ir.actions.act_window_close"}
 
     # ------------------------------------------------------