Enedis#
Une fois qu'un Ask est signé, commandez des données Enedis via POST/integration/enedis/order. Une commande (order) contient une liste de requêtes (requests), chacune ciblant un ou plusieurs PRM pour un type de données donné.
Passer une commande#
{
"requests": [
{
"type": "R63",
"direction": "SOUTIRAGE",
"prms": ["00046372994792", "00052989142094"]
},
{
"type": "C68_ASYNC",
"direction": "CONSUMPTION",
"prms": ["00046372994792", "00052989142094"]
}
]
}
Types de requêtes disponibles#
Le champ type de chaque requête détermine la donnée Enedis récupérée. Les types _SYNC sont synchrones (réponse en quelques secondes, 1 PRM maximum par requête) ; les autres sont asynchrones (la donnée arrive après quelques minutes, jusqu'à 500 PRM par requête). Une requête dépassant 500 PRM est rejetée avec une erreur 400 Bad Request : répartissez les PRM sur plusieurs requêtes.
| Code | Description | PRM max | Arguments optionnels | Latence médiane |
|---|---|---|---|---|
C68 | Données techniques et contractuelles (puissance souscrite, heures creuses / heures pleines…) | 1 | — | < 10 s |
C68_ASYNC | Données techniques et contractuelles, plus complet que C68 et supporte aussi les points en injection | 500 | direction | 1–2 min |
R63 | Courbe de charge (par défaut les 24 derniers mois jusqu'à la veille, au pas restitué par Enedis) | 500 | direction, since / until, enedisRetryAfterLoadcurveActivation | ~2–3 min |
R63_SYNC | Courbe de charge, 7 jours ou moins (par défaut les 7 derniers jours jusqu'à la veille) | 1 | direction, since / until, enedisRetryAfterLoadcurveActivation | < 10 s |
R64 | Index quotidiens | 500 | direction, since / until | ~2–3 min |
R64_SYNC | Index quotidiens | 1 | direction, since / until | < 10 s |
R65 | Énergies quotidiennes | 500 | direction, since / until | ~2–3 min |
R65_SYNC | Énergies quotidiennes (en général obtenues par différence d'index) | 1 | direction, since / until | < 10 s |
R66 | Puissances maximales quotidiennes | 500 | direction, since / until | ~2–3 min |
R66_SYNC | Puissances maximales quotidiennes | 1 | direction, since / until | < 10 s |
R67 | Mesures facturantes | 500 | direction, since / until | ~2–3 min |
LOADCURVE | (déprécié) Courbe de charge — utilisez plutôt R63 ou R63_SYNC | 500 | direction, since / until, enedisRetryAfterLoadcurveActivation | ~2–3 min |
Toutes les requêtes prennent les prms (obligatoire). Quelques précisions sur les arguments optionnels :
direction— pourC68_ASYNCetLOADCURVE, les valeurs sontCONSUMPTION(défaut) ouINJECTION. Pour les typesR6*, les valeurs sontSOUTIRAGE(défaut) ouINJECTION.since/until— par défaut en UTC si aucun fuseau horaire n'est précisé. Plusieurs formes sont acceptées :2024-12-10 2024-12-10T00:00:00 2024-12-10T12:00:00Z 2024-12-10T00:00:00+01:00 2024-12-10T00:00:00[Europe/Paris] 2024-12-10T00:00:00[CET]Il est conseillé d'utiliser le format
2024-12-10T00:00:00[Europe/Paris], car Enedis délivre les données de minuit à minuit en heure locale. Les données de la veille s'arrêtent à minuit heure locale.enedisRetryAfterLoadcurveActivation— voir Erreurs et stratégie de retry ci-dessous.
Réponse#
L'API répond avec la commande créée. Chaque requête a son propre status, qui évolue au fur et à mesure de la récupération des données.
{
"id": "47608cf7-1396-47fa-ada0-087de727b291",
"status": "PENDING_REQUESTS",
"requests": [
{
"type": "R63",
"status": "PENDING",
"orderedAt": "2024-11-13T13:46:38.385Z",
"completedAt": null,
"errorMessage": null
},
{
"type": "C68_ASYNC",
"status": "PENDING",
"orderedAt": "2024-11-13T13:46:38.392Z",
"completedAt": null,
"errorMessage": null
}
]
}
Consulter une commande#
Muni d'un orderId, vous pouvez connaître l'avancement de la/des requête(s) de données via GET/integration/enedis/order/{orderId}.
Enedis met généralement 2 à 5 minutes à répondre. Lorsque les données sont prêtes, la réponse renvoie, par requête, un ou plusieurs lien(s) vers les fichiers bruts renvoyés par Enedis dans dataUrl ou dataUrls :
{
"id": "904ae72d-fd16-446c-914f-fd5ff3eca689",
"status": "COMPLETED",
"requests": [
{
"type": "C68_ASYNC",
"status": "SUCCESS",
"orderedAt": "2024-01-01T10:20:30Z",
"completedAt": "2024-01-01T10:20:32Z",
"dataUrl": "https://...",
"errorMessage": null
},
{
"type": "R63",
"status": "SUCCESS",
"orderedAt": "2024-01-01T10:20:30Z",
"completedAt": "2024-01-01T10:20:32Z",
"dataUrl": "https://...",
"errorMessage": null
}
]
}
Pour les requêtes qui retournent beaucoup de données, Enedis peut les répartir en plusieurs fichiers. Dans ce cas, dataUrl est absent et remplacé par dataUrls, un tableau d'URLs signées vers de chacun des fichiers.
États d'une commande (order.status)#
| Statut | Signification |
|---|---|
CREATED | Commande enregistrée, traitement non encore démarré |
PENDING_REQUESTS | Récupération des données en cours |
COMPLETED | Toutes les requêtes sont terminées (certaines ont pu échouer) |
Le détail de chaque requête (requests[].status) indique lesquelles ont réussi ou échoué.
États d'une requête (requests[].status)#
NOT_STARTED, QUEUED, PENDING, puis SUCCESS ou FAILED. En cas d'échec, le champ errorMessage décrit l'erreur.
Erreurs et stratégie de retry#
En cas d'échec d'une requête, requests[].status vaut FAILED et errorMessage détaille la cause :
{
"id": "...",
"status": "SOME_REQUESTS_FAILED",
"requests": [
{
"type": "R63",
"status": "FAILED",
"orderedAt": "2024-07-29T07:52:19.903Z",
"completedAt": "2024-07-29T07:53:08.629Z",
"dataUrl": null,
"errorMessage": "La demande ne peut aboutir : aucun service souscrit de courbe de charge n'est présent pour la période demandée"
}
]
}
Cette section décrit ce que signifient ces erreurs, et quand il est utile — ou inutile — de réessayer.
Chaque tentative est un appel réel au SI d'Enedis. Réessayer une erreur fonctionnelle (point résilié, point inexistant, droits insuffisants…) ne produira jamais de donnée : cela consomme du quota, ralentit vos autres requêtes et nous expose collectivement à des remontées d'Enedis. La règle générale est donc : une erreur fonctionnelle ne se réessaie pas.
Où lire l'erreur#
Sur GET
/integration/enedis/order/{orderId}, chaque requête a sonstatus. En cas d'échec,statusvautFAILEDeterrorMessageporte la cause.Quand l'erreur vient d'Enedis,
errorMessagecommence par le code Enedis entre crochets :[SGT589]: La demande ne peut pas aboutir car le compteur n'est actuellement pas téléopérable.. Le code est donc directement exploitable par votre code :const code = request.errorMessage?.match(/^\[([A-Z0-9]+)\]/)?.[1] ?? null;Pour les requêtes asynchrones multi-PRM, une requête peut réussir pour certains PRM et échouer pour d'autres. Le détail par PRM se trouve dans
requests[].summaryPerContract[](prm,errorMessage,fileUrl). Dans ce cas, le motif renvoyé par Enedis est un texte libre, sans codeSGT…(voir Erreurs sans code).Le webhook
order.request_failedvous notifie de chaque requête en échec ; il ne contient que les identifiants, l'errorMessagese lit sur la commande.
Les cinq classes d'erreurs#
| Classe | Signification | Conduite à tenir |
|---|---|---|
| A. État du point / contrat | Le point ne peut plus (ou pas) fournir de données | Aucun retry. Arrêter les demandes sur ce PDL, refaire un parcours complet si besoin |
| B. Paramètres invalides | La demande est mal formée (période, sens, type de mesure) | Corriger la requête puis rejouer une fois. Un retry à l'identique échouera toujours |
| C. Droits / consentement | Le consentement ou l'habilitation ne couvre pas la demande | Aucun retry. Refaire signer un Ask |
| D. État du compteur | Transitoire, mais peut durer très longtemps (compteur injoignable, pas de mesures) | Au plus 1 tentative par jour, et au-delà d'une semaine espacer fortement (hebdomadaire, puis mensuel) |
| E. Technique / quota | Incident SI Enedis, quota journalier atteint | Switchgrid réessaie déjà automatiquement. Côté client : 1 tentative après 15 min, sinon le lendemain |
Catalogue des codes Enedis#
Les codes ci-dessous sont ceux que nous voyons réellement passer sur les requêtes de données. Le libellé est celui d'Enedis (il peut varier à la marge).
| Code | Libellé Enedis | Ce que ça veut dire | Classe | Retry ? |
|---|---|---|---|---|
SGT4M1 | Demande non recevable : le point est résilié. | Le contrat de fourniture du PDL a été résilié. Enedis refuse alors toute demande de mesures sur ce point, y compris sur des périodes passées. | A | Non |
SGT401 | Demande non recevable : point inexistant. | Le PRM n'existe pas (ou plus) dans le SI d'Enedis. | A | Non |
SGT589 | La demande ne peut pas aboutir car le compteur n'est actuellement pas téléopérable. | Le compteur n'est pas joignable à distance. Transitoire en théorie, mais cela peut durer très longtemps (voir ci-dessous). | D | 1×/jour max, puis espacer |
SGT4G3 | Aucune mesure trouvée sur ce point. | Enedis n'a rien à restituer sur la période demandée. | D | Seulement avec une autre période |
SGT476 | La demande n'est pas compatible avec le dispositif de comptage. | Le compteur ne sait pas produire cette donnée (typiquement courbe de charge en injection). | A | Non |
SGT583 | La demande ne peut pas aboutir, le sens de la mesure ne correspond pas. | direction demandée incohérente avec le point (soutirage / injection). | B | Après correction du direction |
SGT4L8 | La durée demandée n'est pas compatible avec le type de mesure demandé. | Période trop longue (ou trop courte) pour ce type de requête. | B | Après correction de since / until |
SGT509 | La date de fin doit être renseignée et la durée demandée … ne doit pas excéder 3 ans. | Fenêtre demandée > 3 ans. | B | Après correction de since / until |
SGT4K4 | La date de début doit être antérieure à la date de fin. | since / until inversés. | B | Après correction |
SGT211 | La demande ne peut aboutir : aucun service souscrit ACCES à la donnée pour la période demandée. | Pas de service d'accès actif chez Enedis sur la période. | C | Non |
SGT566 | Ce service nécessite l'accord du client. | Le cadre d'accès ne couvre pas la demande. | C | Non |
SGT4G2 | Le demandeur n'est pas éligible à la consultation des données de mesures sur le point. | Habilitation insuffisante sur ce point. | C | Non |
SGT720 | (libellé mentionnant le quota quotidien) | Quota journalier Enedis, distinct par type de donnée, atteint côté Switchgrid. | E | Le lendemain |
SGT500 | Une erreur technique est survenue. | Incident technique côté Enedis. | E | Switchgrid réessaie déjà (3 fois) |
SGT483 | L'utilisateur ne possède pas les habilitations nécessaires pour effectuer l'opération souhaitée. | Vu lors d'incidents d'habilitation côté Enedis — transitoire en pratique. | E | Nous contacter si cela persiste |
SGT589 — combien de temps ? « Actuellement pas téléopérable » est un état transitoire par nature, mais il peut durer très longtemps : quand le défaut de communication nécessite l'envoi d'une équipe sur le compteur, l'interruption se compte en mois. Enedis considère par ailleurs être déjà au courant de ces défauts de communication, et nous demande de ne pas les solliciter avant 6 mois d'interruption continue sur un point : un signalement plus tôt n'accélère rien. Concrètement : réessayer plusieurs fois dans la journée ne sert à rien ; une tentative par jour est un maximum, et passé une semaine mieux vaut espacer fortement (hebdomadaire, puis mensuel) que maintenir une boucle quotidienne. Si l'interruption dépasse 6 mois, signalez-nous le PDL : c'est à partir de là qu'un signalement à Enedis devient recevable.
Erreurs sans code (requêtes asynchrones)#
Pour les requêtes asynchrones (R63, R64, R65, R66, R67, C68_ASYNC), Enedis renvoie d'abord un compte-rendu par PRM. Les PRM refusés portent un motif en texte libre, restitué tel quel dans requests[].summaryPerContract[].errorMessage. Le plus fréquent :
La demande ne peut aboutir : aucun service souscrit de courbe de charge n'est présent pour la période demandée
Depuis le 10 juin 2026, ce motif n'existe plus. Enedis l'a remplacé par deux motifs génériques, qui ne disent plus pourquoi la demande échoue :
Absence de données de mesure
L'état contractuel du point ne permet pas de traiter cette demande
Un point dont la collecte de courbe de charge n'est pas souscrite reçoit désormais l'un de ces deux motifs, au milieu des points qui n'ont réellement aucune mesure sur la période. Voir ci-dessous comment nous levons l'ambiguïté.
Courbe de charge non disponible. Ce motif signifie en général que la courbe de charge n'a jamais été collectée pour ce compteur : sur un compteur Linky, Enedis ne publie la courbe que pour les périodes où la collecte (service CCDC) était souscrite.
Quand un de ces motifs tombe sur une demande de courbe de charge, Switchgrid interroge Enedis pour savoir si la collecte est souscrite sur le point :
elle l'est → le motif veut bien dire ce qu'il dit, il n'y a pas de mesure sur la période. Le motif d'Enedis vous est restitué tel quel ;
elle ne l'est pas → nous demandons immédiatement l'activation de la collecte quotidienne à Enedis, et l'échec vous est restitué avec un message explicite plutôt qu'avec le motif générique :
La collecte de courbe de charge n'était pas souscrite sur ce point : aucune donnée n'a donc été enregistrée pour la période demandée. L'activation de la collecte vient d'être demandée à Enedis ; relancez une demande identique dans quelques heures.
Le
reasonCodeassocié estENEDIS_CCDC_AUCUN_SERVICE_SOUSCRIT— le même qu'avant juin 2026, la signification n'ayant pas changé.
Recréez une commande identique quelques heures plus tard ou le lendemain ; vous pourrez alors récolter jusqu'à 3-4 mois de données historiques stockées dans le compteur Linky.
Pour automatiser cela, ajoutez enedisRetryAfterLoadcurveActivation: true à la requête de courbe de charge. Switchgrid réessaiera automatiquement la requête après l'activation, sans que vous ayez à repasser commande. La requête reste alors en statut PENDING le temps qu'Enedis active la collecte et nous remonte les données depuis le compteur — comptez une heure environ, parfois une dizaine, contre moins de deux minutes pour un échec immédiat.
{
"requests": [
{
"type": "R63",
"direction": "SOUTIRAGE",
"prms": ["00045855908792"],
"enedisRetryAfterLoadcurveActivation": true
}
]
}
Nous pouvons aussi activer ce comportement par défaut sur votre workspace : demandez-le nous. Une requête qui envoie explicitement le champ garde toujours la main, y compris avec enedisRetryAfterLoadcurveActivation: false pour rester sur l'échec immédiat sur une commande donnée.
L'activation de la collecte, elle, est déclenchée dans tous les cas : même sans l'option, un point non souscrit est activé pour vos prochaines commandes.
Erreurs renvoyées par Switchgrid#
Certaines demandes sont refusées avant tout appel à Enedis. Elles se reconnaissent à l'absence de code SGT… :
| Message | Cause | Conduite à tenir |
|---|---|---|
Duplicate request: an identical request (…) is already in progress… | Une requête strictement identique de votre projet est déjà en cours | Attendre son résultat — ne pas relancer |
Consent … has been revoked; no new order can be created for it. | Le consentement a été révoqué | Refaire signer un Ask |
Quota exceeded. Please try again tomorrow. | Quota quotidien de PRM de votre projet atteint | Le lendemain, ou nous contacter |
Sync requests can only take exactly one PRM | Une requête _SYNC porte plusieurs PRM | Une requête _SYNC par PRM |
400 Bad Request sur une requête de plus de 500 PRM | Limite de 500 PRM par requête asynchrone | Découper en plusieurs requêtes |
Stratégie de retry recommandée#
- Lire le code avant de décider. Aucun retry n'est justifié sans avoir regardé le code d'erreur : les classes A, B et C ne deviendront jamais des succès en réessayant.
- Plafonner le nombre de tentatives à 3, tous cas confondus, et espacer : 15 min, 1 h, puis le lendemain. Une boucle de 10 ou 20 tentatives ne récupère aucune donnée supplémentaire.
- Ne pas piloter les retries depuis le front. Un utilisateur qui rafraîchit sa page ne doit pas déclencher une nouvelle commande. Faites porter la décision par un job côté serveur, avec l'état de la commande en base.
- Écouter les webhooks plutôt que de repasser une commande. Une commande
PENDINGfinit toujours par se terminer (succès ou échec) ; la re-commander en parallèle double la charge sans accélérer quoi que ce soit. - Mémoriser les échecs définitifs par PDL. Un
SGT4M1ou unSGT401devrait sortir le PDL de votre boucle de rafraîchissement, définitivement.
Anticiper les échecs#
Deux des erreurs les plus fréquentes sont visibles avant de commander des données de consommation, dans la réponse d'une requête C68_ASYNC (données techniques et contractuelles) :
Champ (dans le fichier C68_ASYNC) | Valeur | Conséquence |
|---|---|---|
situationsContractuelles[].informationsContractuelles.etatContractuel | ≠ SERVC | Contrat non en service (résilié) → les requêtes de mesures échoueront en SGT4M1 |
situationComptage.dispositifComptage.teleoperable | false | Compteur non téléopérable → SGT589 sur les requêtes de mesures |
situationAlimentation.etatAlimentation | ≠ ALIM | Point non alimenté → pas de mesure à attendre |
Un C68_ASYNC en tête de parcours (et, pour un suivi au long cours, de temps en temps) permet donc de sortir les points morts de votre boucle avant de dépenser des requêtes de mesures dessus. Attention toutefois : teleoperable: false signale un compteur structurellement non télérelevé ; un compteur Linky temporairement injoignable peut rester à true et échouer quand même en SGT589. Le champ est un bon filtre négatif, pas une garantie de succès.
Ce que Switchgrid fait déjà de son côté#
- Retry automatique des erreurs techniques : un
SGT500(ou une erreur réseau) est rejoué jusqu'à 3 fois avant de vous être remonté. - Aucun retry automatique sur les erreurs fonctionnelles : elles vous sont remontées telles quelles, immédiatement.
- Réutilisation des données déjà récoltées : les requêtes
R64_SYNC/R65_SYNCpeuvent être servies depuis nos propres données quand elles couvrent la période demandée, sans appel à Enedis. Cette réutilisation ne s'applique pas aux requêtes asynchrones, qui sont toujours transmises à Enedis. - Garde-fou anti-doublon : sur demande, nous pouvons activer sur votre projet le rejet des requêtes strictement identiques à une requête déjà en cours (fenêtre de 2 h).
- Activation de la courbe de charge puis rejeu de la demande, quand la collecte n'était pas encore souscrite.
- Suivi des points en défaut : nous suivons les
SGT589,SGT476etSGT583récurrents. Pour les défauts de communication (SGT589), Enedis considère le problème déjà connu de ses services et n'accepte un signalement qu'au-delà de 6 mois d'interruption continue.
Récupérer les données de courbe de charge à pas constant#
Pour les courbes de charge (R63, R63_SYNC, LOADCURVE), GET/integration/enedis/request/{requestId}/data restitue les données mises à un pas de temps constant, au format json (défaut), csv ou xlsx. Le requestId correspond à l'id de la requête dans la commande.
Le paramètre period contrôle le pas de temps (défaut 1h). Les paramètres since / until permettent de borner la période, et prm de filtrer sur certains PRM.
Format CSV#
Les données sont en heure UTC, en « pas commençant » (la valeur correspond à l'intervalle qui démarre à startDate).
startDate,powerInWatts
2024-12-15T23:00:00.000Z,321
2024-12-15T23:10:00.000Z,294
Format JSON#
{
"period": "PT600S",
"startsAt": "2024-12-15T23:00:00.000Z",
"endsAt": "2024-12-16T23:00:00.000Z",
"values": [321, 294]
}
Format brut Enedis#
Pour les requêtes de type R6*, les données restent disponibles aux formats retournés par Enedis : téléchargez le(s) fichier(s) référencé(s) par dataUrl / dataUrls dans la réponse de la commande.
Prms de test pour Enedis#
Les PRM de test d'Enedis, la façon de provoquer un contrat NOT_VALID avec le header switchgrid-test-env: true, puis de rejouer le dépôt de justificatif, sont décrits dans le guide de consentement : Tester la création d'un Ask.