Skip to content

Gestion des erreurs ​

Depuis la 1.5.0, le SDK lève des classes d'erreur dédiées au lieu d'un Error générique — vous pouvez donc distinguer précisément pourquoi un appel a échoué avec instanceof, plutôt que d'analyser le texte du message.

Notation des signatures

Les signatures sont écrites en notation TypeScript, mais s'utilisent à l'identique en JavaScript — voir Utiliser le SDK en JavaScript.

Hiérarchie ​

BloumeChatError                 (classe de base — toutes les erreurs du SDK en héritent)
├── BloumeChatAuthError          (token manquant/invalide, ou méthode appelée sans connexion active)
├── BloumeChatTimeoutError       (requête REST expirée après `timeoutMs`)
├── BloumeChatGatewayError       (action socket avec ack — kick/ban/unban… — refusée ou expirée) — 4.2.0+
├── BloumeChatVoiceError         (échec de connexion/lecture vocale — voir ci-dessous)
└── BloumeChatAPIError           (réponse HTTP non-OK de l'API)
    └── RateLimitError           (spécifiquement un 429, avec `retryAfterMs`)

Toutes sont exportées directement depuis le package :

ts
import { BloumeChatError, BloumeChatAPIError, BloumeChatAuthError, BloumeChatTimeoutError, BloumeChatGatewayError, BloumeChatVoiceError, RateLimitError } from "bloumechat";
js
const { BloumeChatError, BloumeChatAPIError, BloumeChatAuthError, BloumeChatTimeoutError, BloumeChatGatewayError, BloumeChatVoiceError, RateLimitError } = require("bloumechat");

BloumeChatError ​

Classe de base — un catch (e) { if (e instanceof BloumeChatError) ... } attrape toute erreur intentionnellement levée par le SDK (par opposition à un bug interne inattendu ou une erreur tierce). Étend Error normalement : message, name (le nom de la classe concrète, ex. "RateLimitError"), stack sont tous disponibles.

BloumeChatAuthError ​

Levée quand :

  • login(token) reçoit un token vide, null/undefined, ou non-string.
  • Une méthode nécessitant une connexion active (sendMessage, setActivity, setStatus, setPresence, Channel.sendTyping/stopTyping, Message.edit/delete/react/clearReactions, Guild.unbanMember…) est appelée avant login() ou après destroy().
ts
import { BloumeChatAuthError } from "bloumechat";

try {
  await client.login("");
} catch (err) {
  if (err instanceof BloumeChatAuthError) {
    console.error("Token invalide :", err.message);
  }
}
js
const { BloumeChatAuthError } = require("bloumechat");

try {
  await client.login("");
} catch (err) {
  if (err instanceof BloumeChatAuthError) {
    console.error("Token invalide :", err.message);
  }
}

BloumeChatAPIError ​

Levée par client.apiCall() (et donc par toute méthode de haut niveau qui l'utilise en interne) quand l'API répond avec un statut HTTP non-OK, après épuisement des tentatives de retry automatique.

PropriétéTypeDescription
statusnumberLe code de statut HTTP renvoyé par l'API (404, 403, 500…).
pathstringLe chemin appelé (ex. "/servers/123/roles").
bodystringLe corps brut de la réponse (texte intégral, non tronqué — contrairement au message qui le tronque à 500 caractères pour rester lisible).
ts
import { BloumeChatAPIError } from "bloumechat";

try {
  await guild.deleteRole(roleId);
} catch (err) {
  if (err instanceof BloumeChatAPIError && err.status === 403) {
    await message.reply("Le bot n'a pas la permission de supprimer ce rôle.");
  } else {
    throw err;
  }
}
js
const { BloumeChatAPIError } = require("bloumechat");

try {
  await guild.deleteRole(roleId);
} catch (err) {
  if (err instanceof BloumeChatAPIError && err.status === 403) {
    await message.reply("Le bot n'a pas la permission de supprimer ce rôle.");
  } else {
    throw err;
  }
}

RateLimitError ​

Sous-classe de BloumeChatAPIError (donc err instanceof BloumeChatAPIError est aussi vrai pour une RateLimitError) — spécifique aux réponses 429. status vaut toujours 429.

PropriétéTypeDescription
retryAfterMsnumber | nullDurée d'attente (ms) suggérée par l'API via le header Retry-After, null si l'API n'en a pas fourni.

Le SDK retente déjà automatiquement

Un 429 déclenche déjà un retry automatique côté SDK (voir buckets de rate-limit ci-dessous) — RateLimitError ne surgit que si toutes les tentatives (maxRetries) ont été épuisées sans succès. Dans la plupart des bots, vous n'avez donc pas besoin de la gérer explicitement ; elle est surtout utile pour journaliser un abus persistant ou ajuster dynamiquement le rythme d'appels de votre bot.

ts
import { RateLimitError } from "bloumechat";

try {
  await channel.bulkDelete(messageIds);
} catch (err) {
  if (err instanceof RateLimitError) {
    console.warn(`Rate-limit persistant, réessayer dans ${err.retryAfterMs ?? "?"}ms`);
  }
}
js
const { RateLimitError } = require("bloumechat");

try {
  await channel.bulkDelete(messageIds);
} catch (err) {
  if (err instanceof RateLimitError) {
    console.warn(`Rate-limit persistant, réessayer dans ${err.retryAfterMs || "?"}ms`);
  }
}

BloumeChatVoiceError (2.1.0+) ​

Levée pour les échecs propres au système vocal : Channel.join() appelé sur un salon qui n'est pas de type "VOICE", timeout de confirmation de connexion, FFmpeg introuvable sur le PATH lors de connection.play(), ou play({ inputType: "raw" }) appelé avec une chaîne au lieu d'un flux.

ts
import { BloumeChatVoiceError } from "bloumechat";

try {
  await textChannel.join(); // pas un salon vocal
} catch (err) {
  if (err instanceof BloumeChatVoiceError) {
    console.error("Impossible de rejoindre :", err.message);
  }
}
js
const { BloumeChatVoiceError } = require("bloumechat");

try {
  await textChannel.join();
} catch (err) {
  if (err instanceof BloumeChatVoiceError) {
    console.error("Impossible de rejoindre :", err.message);
  }
}

BloumeChatTimeoutError ​

Levée quand une requête REST dépasse timeoutMs (15 secondes par défaut, configurable via client.apiCall(path, { timeoutMs })) sans obtenir de réponse, après épuisement des tentatives de retry.

PropriétéTypeDescription
pathstringLe chemin appelé.
timeoutMsnumberLe délai configuré qui a été dépassé.

BloumeChatGatewayError (4.2.0+) ​

Levée par les actions qui passent par un événement Socket.IO avec accusé de réception (Member.kick()/ban(), Guild.unbanMember()) plutôt que par une route REST — soit le serveur a refusé l'action, soit aucun ack n'est arrivé dans les 10 secondes.

PropriétéTypeDescription
eventstringL'événement Socket.IO émis, ex. "server:kick".
codestringLe code brut renvoyé par le serveur, ou "TIMEOUT" si aucun ack n'est arrivé à temps.

code est une clé i18n brute, pas un message lisible

Ce canal Socket.IO est partagé avec l'application web, qui résout code (une clé pointée comme "servers.errors.cannot_kick_owner" ou "common.api.forbidden") elle-même côté client via ses propres fichiers de traduction. Le SDK ne les traduit pas — si vous voulez afficher un message convivial, faites correspondre code à votre propre texte.

ts
try {
  await member.kick();
} catch (error) {
  if (error instanceof BloumeChatGatewayError) {
    console.error(`Kick refusé (${error.event}): ${error.code}`);
  }
}
js
try {
  await member.kick();
} catch (error) {
  if (error instanceof BloumeChatGatewayError) {
    console.error(`Kick refusé (${error.event}): ${error.code}`);
  }
}

Limitation de débit par route ​

Depuis la 1.5.0, les requêtes REST sont regroupées en buckets par méthode + type de ressource + ID « majeur » (les deux premiers segments du chemin — par ex. POST:chat/salonA et POST:chat/salonB sont deux buckets distincts). Un 429 sur un bucket enregistre un délai d'attente partagé : toute requête suivante vers ce même bucket patiente automatiquement jusqu'à expiration du délai avant de partir, tandis que les requêtes vers des buckets différents (un autre salon, un autre serveur) ne sont pas affectées.

Aucune action requise de votre part

Ce mécanisme est entièrement interne à apiCall()/RestManager — vous n'avez rien à configurer. Il explique simplement pourquoi un pic d'appels sur un salon très actif ne ralentit jamais les appels vers un salon différent.

Voir aussi ​

SDK publié sous licence ISC.