Référence

Codes d’erreur

Une erreur dit toujours ce qui n’allait pas et, quand c’est possible, ce qu’il aurait fallu écrire à la place. Cette page liste les cas, canal par canal, et sépare ce qui mérite une nouvelle tentative de ce qui n’en mérite aucune.

#La forme d’une erreur

Le détail est porté par la clé detail. Sur les erreurs de validation, il nomme la valeur fautive et, quand une liste finie existe, l’énumère.

400
{
  "detail": "Symbole 'PEPEUSDT' inconnu. Valeurs acceptees : BTCUSDT, ETHUSDT, ..."
}

Les refus liés à l’offre ont une forme fixe, posée par la passerelle : status, timestamp et detail, plus retry_after sur les refus temporels (aussi présent dans l’en-tête Retry-After). L’en-tête X-Deny-Reason nomme la raison : rate, quota, family, websocket ou key.

{
  "status": "error",
  "timestamp": 1775648290510,
  "detail": "Debit depasse : votre offre autorise un nombre limite de requetes par minute.",
  "retry_after": 1
}

Le 403 de profondeur est renvoyé par la route elle-même, sans X-Deny-Reason : son detail commence toujours par « Profondeur d’historique hors offre » et donne la limit maximale utilisable sur cette unité de temps. Les fenêtres par offre sont sur la page Limites d’usage.

#Codes HTTP

CodeCauseCorrectif
400
Requête refusée
Un symbole inconnu ou désactivé, une profondeur au-delà du plafond du champ, un paramètre d’indicateur hors bornes.Le corps de la réponse nomme la valeur fautive et, pour un symbole, liste ceux qui sont acceptés.
403
Refusé par l’offre ou par la clé d’API
Quatre raisons, nommées par l’en-tête X-Deny-Reason : clé d’API absente, invalide ou révoquée (key) ; famille de données hors offre (family) ; flux WebSocket hors offre (websocket) ; ou une profondeur d’historique au-delà de la fenêtre de l’offre, dont le detail commence par « Profondeur d’historique hors offre ».Sur key, vérifiez que l’en-tête est bien envoyé : certains clients HTTP le perdent après une redirection. Sur family et websocket, la donnée existe mais n’est pas dans votre offre. Sur la profondeur, le detail donne la limite maximale à utiliser.
422
Paramètre manquant ou mal formé
symbol manquant, unité de temps hors liste, champ multi-unités demandé sans le suffixe @tf, champ inconnu dans ?fields=, corps JSON invalide.Sur ?fields=, la réponse suggère le champ le plus proche. Sur une unité de temps, elle liste les valeurs acceptées.
429
Débit ou quota dépassé
Soit plus de requêtes par minute que votre offre ne l’autorise, ou une rafale trop dense (X-Deny-Reason: rate, Retry-After: 1) ; soit le quota mensuel du compte est épuisé (X-Deny-Reason: quota, Retry-After: 3600).Sur rate, attendez la seconde indiquée par Retry-After. Sur quota, le compteur repart le premier jour du mois (UTC) ; vous pouvez aussi changer d’offre depuis la console.
503
Indisponibilité momentanée
Une dépendance de lecture redémarre, ou le plafond de connexions simultanées du flux est atteint.Réessayez après le délai porté par Retry-After. L’erreur est transitoire par construction.
500
Erreur inattendue
Une panne côté service, jamais causée par la requête.Réessayez ; si la réponse persiste, signalez-la avec l’horodatage porté par la réponse.

Les confusions les plus fréquentes

SymptômeVraie cause
403 alors que la clé est valideLisez X-Deny-Reason. family : la famille de cet endpoint n’est pas dans votre offre. websocket : le flux n’y est pas. Un detail « Profondeur d’historique hors offre » : la requête remonte au-delà de la fenêtre de l’offre. key sans raison apparente : un client HTTP qui perd les en-têtes personnalisés après une redirection ; appelez l’URL finale.
429 alors que le rythme est faibleC’est le quota mensuel du compte qui est épuisé (X-Deny-Reason: quota, Retry-After: 3600), pas la limite de débit. Il repart le premier jour du mois, en UTC, ou dès que l’offre change.
422 sans message clair sur un snapshotUn champ multi-unités de temps demandé sans son suffixe @tf, ou l’inverse sur un champ à forme unique.
400 sur une profondeur qui paraît raisonnableChaque champ du snapshot a son propre plafond, dans sa propre unité. Le CVD s’arrête à 200 fenêtres, les écarts entre places à 50.
422 sur une unité de temps valable ailleursLe ratio long/short refuse 1m, les instruments macro intrajournaliers refusent 30m, et la semaine n’existe que sur les indicateurs.
Une réponse vide qui n’est pas une erreurUn stablecoin sur une métrique futures, ou des options sur un autre actif que BTC et ETH. La clé unavailable du snapshot dit laquelle des trois raisons s’applique.
Un paramètre ignoréLes clés inconnues du snapshot sont ignorées en silence. Un champ mal orthographié est simplement absent de la réponse.

#Indicateurs

La validation suit un ordre fixe (unité de temps, nombre de résultats, symbole, analyse des indicateurs, règle de plafond, lecture des bougies), et le premier échec l’emporte. Un corps corrigé peut donc révéler une seconde erreur.

CasCode
Unité de temps invalide, results inférieur à 1, symbole inconnu400
Liste indicators vide, ou une entrée qui n’est pas un objet400
Clé id ou type manquante, id mal formé pour ce type400
Type non pris en charge400
Paramètre inconnu pour ce type (obv avec une période, par exemple)400
Paramètre du mauvais type, ou inférieur à son minimum400
macd ou adosc avec fast supérieur ou égal à slow400
sar avec acceleration supérieure à maximum400
Identifiant en double400
Corps mal formé, plus de 50 instances, champ trop long422
results plus warm-up dépasse 1000422
Données insuffisantes pour cette unité de temps, stablecoins compris422

#Flux WebSocket

Toute demande impossible reçoit un message op: error qui dit ce qui était attendu : la liste des symboles valides, celle des canaux, les bornes de depth. Trois situations produisent non pas une erreur mais une fermeture :

CodeRaison
4003 · plafondPlafond de connexions simultanées de l’offre atteint. La raison donne le plafond. Une déconnexion libère aussitôt sa place.
4003 · client trop lentLa file d’envoi a débordé dix fois. Consommez plus vite, ou réduisez le nombre de canaux. La raison distingue les deux cas.
4001Trame d’auth explicite refusée : la clé qu’elle porte est invalide.
4002Session jamais authentifiée en cinq secondes. Un cas résiduel, puisque la clé est vérifiée à la poignée de main.

La clé est vérifiée à la poignée de main, avant l’ouverture : une clé absente ou invalide, ou une offre sans le flux (Free), reçoit un 403 à la poignée de main, avec X-Deny-Reason key ou websocket. Un 429 à ce moment-là signale un rythme d’ouverture trop élevé. Une fois connecté, un canal dont la famille n’est pas dans l’offre reçoit op: error (« canal … hors offre : la famille … n’est pas incluse dans votre abonnement ») et tout l’abonnement est refusé. Voir Limites d’usage.

#Serveur MCP

Les erreurs suivent un seul modèle, Erreur (HTTP NNN) : message, pour qu’un agent n’ait qu’un cas à reconnaître. Chaque appel d’outil est jugé comme une requête REST avec la clé du client : un 403 pour une famille hors offre ou un 429 pour le quota reviennent tels quels, avec leur detail. Deux familles lui sont propres :

  • Métrique inconnue : le message liste les quarante-six métriques valides.
  • Ciblage invalide : deux cibles à la fois, cible manquante, mauvaise cible, ou une cible passée à une métrique de tout le marché. L’erreur nomme le paramètre attendu, et elle est levée avant tout appel réseau.

Une panne du serveur donne lieu à une nouvelle tentative automatique avant d’être signalée. Un délai dépassé renvoie Erreur (HTTP 504) après trente secondes.

#Stratégie de nouvelle tentative

Tout ne se rejoue pas. Rejouer une requête fautive produit exactement la même réponse, et consomme du quota pour rien.

Python
def should_retry(code: int) -> bool:
    """What is transient, and what never will be."""
    # 429 and 503 will pass: the server says when.
    if code in (429, 503):
        return True
    # 500: a fault on the service side, a retry makes sense.
    if code == 500:
        return True
    # 400, 403, 422: the request is at fault. Replaying it as is will
    # produce exactly the same response.
    return False
  • Respectez Retry-After plutôt que d’inventer un délai : le serveur sait quand il sera prêt.
  • Bornez le nombre de tentatives. Trois ou quatre suffisent : au-delà, le problème n’est pas passager.
  • Ne rejouez pas un 4xx, 429 mis à part. Corrigez la requête.
  • Sur le flux, reconnectez-vous avec un délai croissant, et traitez une fermeture 4003 comme le signal d’une surcharge côté client : se reconnecter sans changer la consommation reproduira la coupure.