@plasm05280/whatsapp-sdk
v1.0.4
Published
A TypeScript SDK for Meta's WhatsApp Cloud API
Readme
WhatsApp API SDK
Un SDK TypeScript / JavaScript puissant et modulaire pour interagir facilement avec l'API WhatsApp Cloud (Meta Graph API). Conçu pour Bun et Node.js, il simplifie l'envoi de messages via des modèles (templates) et la gestion sécurisée des Webhooks.
📑 Table des matières
- Fonctionnalités
- Installation
- Variables d'environnement
- Utilisation Rapide
- Envoi de Templates (
wa.templates) - Gestion des Webhooks (
WhatsAppVerifier) - Gestion des Erreurs
- Accès direct au Client HTTP
- Build & Scripts
✨ Fonctionnalités
- 🚀 Initialisation rapide avec support des variables d'environnement (
.env). - 📄 Modèles WhatsApp (Templates) : Support complet des en-têtes texte, document (PDF), image et vidéo.
- 🔒 Vérification Webhook sécurisée : Traitement des challenges GET et validation des signatures HMAC-SHA256 (
x-hub-signature-256). - ⚡ Compatible avec les standards Web : Utilise l'API standard
Request/Response(idéal pour Bun, Edge Functions, Next.js, Hono, etc.). - 🛠️ Gestion rigoureuse des erreurs avec l'exception dédiée
WhatsAppAPIError.
📦 Installation
Avec Bun :
bun install whatsapp-apiAvec npm / yarn / pnpm :
npm install whatsapp-api⚙️ Variables d'environnement
Créez un fichier .env à la racine de votre projet :
ACCESS_TOKEN=votre_jeton_dacces_meta
PHONE_NUMBER_ID=votre_id_de_numero_de_telephone
API_VERSION=v20.0 # Optionnel, par défaut v20.0🚀 Utilisation Rapide
import { WhatsApp } from "whatsapp-api";
// Initialisation du client (charge les identifiants depuis le .env si non spécifiés)
const wa = new WhatsApp({
accessToken: process.env.ACCESS_TOKEN,
phoneNumberId: process.env.PHONE_NUMBER_ID,
});
// Envoi d'un template texte simple
const response = await wa.templates.withText.send({
to: "243851234567",
templateName: "hello_world",
language: "fr",
});
console.log("Message envoyé avec succès. ID :", response.messages[0]?.id);📩 Envoi de Templates (wa.templates)
Le module templates fournit des sous-modules spécialisés selon le type d'en-tête (header) du modèle Meta.
1. Template Texte (withText)
Utilisez withText pour les modèles n'ayant pas de média en en-tête (avec ou sans variables et texte dynamique de header).
await wa.templates.withText.send({
to: "243851234567",
templateName: "order_confirmation",
language: "fr", // Par défaut: 'fr'
headerText: "Commande #48592", // Optionnel (si le template accepte un header texte)
parameters: {
customer_name: "Jean Dupont",
delivery_date: "15 août 2026",
},
});2. Template Document / PDF (withDocument)
Utilisez withDocument pour joindre un fichier (PDF, DOCX, etc.) dans l'en-tête du modèle.
await wa.templates.withDocument.send({
to: "243851234567",
templateName: "send_customer_invoice",
language: "fr",
documentUrl: "https://example.com/invoices/INV-001.pdf",
filename: "Facture_INV001.pdf", // Optionnel, nom affiché sur WhatsApp
parameters: {
invoice_number: "INV-001",
amount: "150.00 EUR",
},
});3. Template Image (withImage)
Utilisez withImage pour inclure une image en en-tête.
await wa.templates.withImage.send({
to: "243851234567",
templateName: "promo_banner",
language: "fr",
imageUrl: "https://example.com/images/banner.jpg",
parameters: {
discount_code: "SUMMER2026",
expiry_date: "31 août 2026",
},
});4. Template Vidéo (withVideo)
Utilisez withVideo pour joindre une vidéo d'en-tête.
await wa.templates.withVideo.send({
to: "243851234567",
templateName: "welcome_onboarding",
language: "fr",
videoUrl: "https://example.com/videos/intro.mp4",
parameters: {
user_name: "Alice",
},
});5. Template Personnalisé (withCustom)
Utilisez withCustom pour construire manuellement la structure des composants d'un template (header, body, buttons) de façon simplifiée et intuitive.
await wa.templates.withCustom.send({
to: "243851234567",
templateName: "promo_notification",
language: "fr",
header: { type: "text", text: "Offre spéciale" },
body: { customer_name: "Jean Dupont", discount: "20%" },
buttons: [
{ type: "quick_reply", text: "J'en profite" },
{
type: "url",
text: "Voir l'offre",
url: "https://example.com/offre",
},
],
});Remarque: Vous pouvez aussi fournir directement le tableau complet components si vous souhaitez contrôler tous les détails.
🛡️ Gestion des Webhooks (WhatsAppVerifier)
Pour recevoir et valider les notifications envoyées par Meta vers votre serveur, utilisez la classe WhatsAppVerifier ou les fonctions helpers réexportées par la bibliothèque.
1. Gestionnaire automatique (handleWhatsAppRequest)
Cette méthode traite automatiquement :
- Les requêtes GET de vérification de souscription (Challenge Meta).
- Les requêtes POST de notification en contrôlant la signature HMAC-SHA256 (
x-hub-signature-256).
import { WhatsAppVerifier } from "whatsapp-api";
const verifier = new WhatsAppVerifier({
verifyToken:
process.env.WEBHOOK_VERIFY_TOKEN || "mon_secret_verify_token",
appSecret: process.env.META_APP_SECRET || "mon_meta_app_secret",
});
// Exemple avec le serveur HTTP natif de Bun ou un Edge Handler
Bun.serve({
port: 3000,
async fetch(req: Request) {
const url = new URL(req.url);
if (url.pathname === "/webhook") {
return await verifier.handleWhatsAppRequest(req);
}
return new Response("Not Found", { status: 404 });
},
});2. Vérification manuelle du Challenge GET
Si vous souhaitez valider manuellement la requête GET de Meta lors de la configuration du Webhook :
import { verifyWebhookSubscription } from "whatsapp-api";
// Dans votre contrôleur GET /webhook :
const params = {
mode: req.query["hub.mode"],
verifyToken: req.query["hub.verify_token"],
challenge: req.query["hub.challenge"],
};
try {
const challengeResponse = verifyWebhookSubscription(
params,
"mon_secret_verify_token",
);
// Renvoyer challengeResponse avec un statut 200 HTTP
} catch (error) {
// Renvoyer un statut HTTP 403 Forbidden
}3. Vérification manuelle de la signature POST (HMAC-SHA256)
Pour valider l'authenticité des messages POST entrants de Meta :
import { verifyWebhookSignature } from "whatsapp-api";
const isValid = verifyWebhookSignature({
rawBody: rawRequestBody, // Chaîne de caractères ou Buffer brut
signatureHeader: req.headers["x-hub-signature-256"],
appSecret: process.env.META_APP_SECRET!,
});
if (!isValid) {
console.error("Signature du Webhook invalide !");
}❌ Gestion des Erreurs
Lorsqu'une requête API échoue ou est rejetée par Meta, le SDK lève une instance de WhatsAppAPIError.
import { WhatsAppAPIError } from "whatsapp-api";
try {
await wa.templates.withText.send({
to: "243851234567",
templateName: "invalid_template_name",
});
} catch (error) {
if (error instanceof WhatsAppAPIError) {
console.error("Statut HTTP :", error.status); // ex: 400
console.error("Code d'erreur Meta :", error.code); // ex: 100
console.error("Message :", error.message);
console.error("Détails bruts :", error.rawError);
} else {
console.error("Erreur inattendue :", error);
}
}🔌 Accès direct au Client HTTP
Si vous avez besoin d'effectuer des appels personnalisés vers des points de terminaison Graph API non couverts directement par les méthodes de haut niveau, vous pouvez utiliser la méthode request du client HTTP sous-jacent :
const result = await wa.client.request({
messaging_product: "whatsapp",
to: "243851234567",
type: "text",
text: {
body: "Message texte direct sans template",
},
});🛠️ Build & Scripts
- Construire la bibliothèque (
dist/) :bun run build - Lancer l'exemple :
bun run example
