Démarrage

Envoyez votre premier SMS canadien en moins de 5 minutes.

Démarrage rapide

  1. Créer un compte gratuit — obtenez des clés API live et de test instantanément.
  2. Enregistrez le consentement LCAP pour chaque numéro de téléphone que vous allez contacter.
  3. Provisionnez optionnellement un numéro canadien à code long pour l'envoi.
  4. Envoyez votre premier message via l'API REST.

Authentification

Toutes les requêtes API nécessitent un jeton Bearer dans l'en-tête Authorization. Utilisez test keys (mk_test_...) pour le développement — aucun vrai SMS n'est envoyé, aucuns frais. Utilisez live keys (mk_live_...) pour la production.

⚠️ Ne jamais exposer les clés API dans du code côté client ou dans des dépôts publics.

Numéros de téléphone

Recherchez les numéros canadiens disponibles, provisionnez-en un et utilisez-le comme champ from lors de l'envoi.

bash
curl https://api.honkio.ca/v1/phone-numbers/search?area_codes=416 \
  -H "Authorization: Bearer mk_live_YOUR_KEY"

# Response 200 (per result): what buying it charges now and monthly, in CAD cents
# { "phone_number": "+14165550100", "region": "Ontario",
#   "upfront_cost_cents": 250, "activation_fee_cents": 100, "monthly_cost_cents": 250, ... }

# Provision a number
curl -X POST https://api.honkio.ca/v1/phone-numbers \
  -H "Authorization: Bearer mk_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{"phone_number": "+14165550100"}'

# Accounts hold a limited number of numbers. GET /v1/accounts/me reports
# phone_number_limit and phone_numbers_used — check them before buying, or
# handle the 403 NUMBER_LIMIT_REACHED that a purchase past the cap returns.

# Ask HonkIO staff to raise the limit. One request may be pending at a time.
curl -X POST https://api.honkio.ca/v1/phone-numbers/allowance-requests \
  -H "Authorization: Bearer mk_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{"requested_limit": 10, "reason": "Onboarding three new clinics this quarter"}'

# Response 201: { "status": "PENDING", "requested_limit": 10, ... }
# You are emailed if it is approved; the decision also shows in the dashboard.

# Check on it
curl https://api.honkio.ca/v1/phone-numbers/allowance-requests \
  -H "Authorization: Bearer mk_live_YOUR_KEY"

Consentement LCAP (requis avant l'envoi)

En vertu de la LCAP, vous devez enregistrer le consentement avant d'envoyer un message commercial à tout destinataire. L'API bloquera les envois vers des numéros de téléphone sans consentement valide (HTTP 451).

bash
curl -X POST https://api.honkio.ca/v1/compliance/consents \
  -H "Authorization: Bearer mk_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "phone_number": "+16135550199",
    "consent_type": "express",
    "source_description": "Website opt-in form",
    "source_ip": "203.0.113.1"
  }'

Consentement tacite pour un client existant, le délai courant à partir de sa dernière transaction :

bash
curl -X POST https://api.honkio.ca/v1/compliance/consents \
  -H "Authorization: Bearer mk_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "phone_number": "+16135550199",
    "consent_type": "implied",
    "relationship_type": "purchase",
    "last_transaction_date": "2025-11-04"
  }'

# → { "status": "recorded", "phone_number": "+16135550199", "expires_at": "2027-11-04T00:00:00.000Z" }

Le consentement exprès n'expire jamais. Le consentement tacite expire après 2 ans selon l'art. 10(9) de la LCAP. Fournissez last_transaction_date pour que le délai de deux ans coure à partir de la relation réelle plutôt que du jour de l'enregistrement, ou indiquez directement expires_at si vous avez déjà calculé l'expiration. La réponse renvoie expires_at pour que vous puissiez le vérifier.

Envoi de SMS

Envoyez un message en utilisant un numéro provisionné. L'API valide le numéro de destination canadien, vérifie le consentement LCAP avant la livraison (vérification LNNTE du CRTC à venir).

bash
curl -X POST https://api.honkio.ca/v1/messages \
  -H "Authorization: Bearer mk_live_YOUR_KEY" \
  -H "Content-Type: application/json" \
  -d '{
    "from": "+14165550100",
    "to":   "+16135550199",
    "body": "Hello from HonkIO! 🇨🇦"
  }'

Vérification de numéro de téléphone (OTP)

Utilisez l'API Verify pour confirmer la propriété d'un numéro de téléphone avant d'envoyer des messages commerciaux. Votre utilisateur final reçoit un code à usage unique par SMS; soumettez-le au point de terminaison de vérification pour confirmer.

bash
# Start a verification (sends OTP SMS)
curl -X POST https://api.honkio.ca/v1/verify   -H "Authorization: Bearer mk_live_YOUR_KEY"   -H "Content-Type: application/json"   -d '{
    "from": "+14165550100",
    "to":   "+16135550199",
    "code_length": 6,
    "ttl_minutes": 10,
    "app_name": "Acme"
  }'
# Response: { "id": "clxxx...", "status": "pending", "code_length": 6, ... }

# Check the code submitted by your user
curl -X POST https://api.honkio.ca/v1/verify/clxxx.../check   -H "Authorization: Bearer mk_live_YOUR_KEY"   -H "Content-Type: application/json"   -d '{ "code": "483721" }'
# Response 200: { "status": "verified", ... }
# Response 422: { "code": "VERIFICATION_INVALID_CODE", "attempts_remaining": 4 }

# Fetch status at any time
curl https://api.honkio.ca/v1/verify/clxxx...   -H "Authorization: Bearer mk_live_YOUR_KEY"

En mode test, le code est toujours composé de zéros selon la longueur choisie (ex. 000000 pour 6 chiffres). Aucun SMS n'est envoyé et rien n'est facturé. Chaque vérification retourne un champ « mode » valant « LIVE » ou « TEST » afin de distinguer une vérification simulée d'une vérification réelle.

Tarification

Les prix sont définis à l'exécution et peuvent changer sans nouvelle version : lisez-les plutôt que de les coder en dur. Tous les montants sont en cents CAD. L'envoi est facturé par partie SMS : message_cost_cents × le nombre de parties en lesquelles l'opérateur découpe le texte. Les parties sont comptées comme l'opérateur les compte — guillemets typographiques, tirets et points de suspension sont convertis en GSM-7 (160 caractères, puis 153 par partie), tandis que les émojis et la plupart des lettres accentuées imposent des parties Unicode (70, puis 67). Le montant est ajusté au décompte de l'opérateur après l'envoi, un message refusé par l'opérateur ne coûte rien, et un texte de plus de 10 parties est rejeté avec 422 MESSAGE_TOO_LONG avant toute facturation. verification_cost_cents couvre un OTP typique d'une seule partie ; un app_name long ou non GSM peut ajouter une partie. phone_number_activation_fee_cents est facturé une seule fois, avec le premier mois, pour chaque numéro provisionné — local ou sans frais — et n'est pas remboursé à la libération. inbound_message_cost_cents est facturé par partie pour chaque SMS reçu sur un numéro provisionné, quel que soit l'expéditeur ou le transporteur, sauf les mots-clés STOP, START et HELP ; un message reçu est débité même si le solde passe sous zéro, ce qui suspend l'envoi jusqu'à la prochaine recharge.

bash
# Current prices, in CAD cents
curl https://api.honkio.ca/v1/pricing \
  -H "Authorization: Bearer mk_live_YOUR_KEY"

# Response 200:
# {
#   "message_cost_cents": 3,
#   "verification_upcharge_cents": 25,
#   "verification_cost_cents": 28,
#   "phone_number_upfront_cost_cents": 250,
#   "phone_number_monthly_cost_cents": 250,
#   "phone_number_activation_fee_cents": 100,
#   "inbound_message_cost_cents": 3
# }

Les requêtes en mode test sont tarifées de façon identique dans la réponse, mais ne sont jamais facturées : vous pouvez donc voir ce que coûterait une intégration sans rien dépenser.

Limites d’envoi

HonkIO est conçu pour la messagerie transactionnelle et relationnelle, pas pour les campagnes, et la délivrabilité de chaque client repose sur un profil opérateur partagé. Ces limites tiennent le marketing de masse à l’écart de la plateforme ; une clinique, un entrepreneur ou un SaaS envoyant des codes ne les remarqueront pas. Elles s’appliquent au mode réel ; le mode test n’est pas touché, sauf pour la règle sur les raccourcisseurs de liens.

  • Plafond quotidien : les nouveaux comptes peuvent envoyer 250 messages réels par 24 heures glissantes. Il ne se lève pas de lui-même. 30 jours après votre premier message réel, vous pouvez demander un volume plus élevé depuis le tableau de bord ; l’approbation fixe 1 000 par jour ou le chiffre demandé. Les envois refusés renvoient 429 DAILY_LIMIT_REACHED avec votre limite et votre compte.
  • Messages identiques : un même corps de message peut atteindre au plus 250 destinataires distincts par 24 heures (429 FANOUT_LIMIT_REACHED). Les messages personnalisés ne sont pas concernés.
  • Débit par numéro : 60 messages par minute par numéro d’envoi, ce que les opérateurs canadiens accordent de toute façon à un numéro long (429 NUMBER_RATE_LIMITED avec Retry-After).
  • Diffusions : jusqu’à 250 destinataires par diffusion de groupe et 3 diffusions par 24 heures (422 BROADCAST_TOO_LARGE, 429 BROADCAST_LIMIT_REACHED).
  • Les raccourcisseurs de liens (bit.ly, tinyurl et similaires) sont refusés dans les deux modes, car les opérateurs les filtrent (422 LINK_SHORTENER_BLOCKED). Utilisez l’URL complète.
  • Suspension automatique : si plus de 1 % des destinataires répondent STOP, ou si plus de 5 % des messages sont rejetés par les opérateurs, sur vos envois récents, l’envoi réel est suspendu 24 heures et vous recevez un courriel (403 SENDING_PAUSED avec l’heure de reprise).
  • Rechargements : le solde ne peut dépasser 500 $ et les rechargements sont limités à 1 000 $ par 30 jours. Relevés sur demande.
bash
curl https://api.honkio.ca/v1/send-limit \
  -H "Authorization: Bearer mk_live_YOUR_KEY"

# → { "daily_limit": 250, "sent_last_24h": 12, "remaining": 238,
#     "probation": { "ends_at": "2026-09-26T14:02:11.000Z", "eligible_to_request": false },
#     "paused_until": null, "requests": [] }

Consultez vos limites et votre utilisation avec GET /v1/send-limit, et déposez une demande avec POST /v1/send-limit/requests. Chaque chiffre ci-dessus est une valeur par défaut de la plateforme qui peut être relevée par compte.

Webhooks

Enregistrez un point de terminaison webhook pour recevoir les accusés de réception et les messages entrants. Chaque charge utile est signée avec HMAC-SHA256 — vérifiez l'en-tête X-HonkIO-Signature. Un événement message.received contient l'expéditeur, votre numéro, le texte, keyword_action (traitement STOP/START), ainsi que segment_count et cost_cents, le montant facturé pour ce message.

json
{
  "id": "evt_01HXYZ...",
  "type": "message.delivered",
  "created": "2024-01-15T12:00:00Z",
  "account_id": "acc_01HXYZ...",
  "data": {
    "message_id": "msg_01HXYZ...",
    "to": "+16135550199",
    "status": "delivered"
  }
}
// Headers: X-HonkIO-Signature, X-HonkIO-Timestamp, X-HonkIO-Event

Agents IA (MCP)

HonkIO fournit un serveur Model Context Protocol : un agent de codage IA peut ainsi envoyer des SMS, lancer une vérification téléphonique, acheter des numéros canadiens et vérifier le consentement LCAP en votre nom — en langage courant, sans SDK à brancher. Il s'exécute sur votre poste et communique avec cette même API REST au moyen de votre clé API.

Ajoutez-le à Claude Code, Claude Desktop, Cursor ou VS Code. Rien à installer : npx le télécharge à la première utilisation :

json
{
  "mcpServers": {
    "honkio": {
      "command": "npx",
      "args": ["-y", "@honkio/mcp"],
      "env": { "HONKIO_API_KEY": "mk_test_YOUR_KEY" }
    }
  }
}

Utilisez une clé de test pendant vos essais. Tous les outils fonctionnent en mode test : les messages sont marqués comme livrés, sans envoi réel ni facturation.

41 outils sont offerts, couvrant :

  • L'envoi de SMS, la liste des messages et l'état de livraison
  • La vérification téléphonique — lancer un code, le valider, lister les tentatives
  • La recherche, l'achat et la libération de numéros canadiens
  • L'enregistrement et la vérification du consentement LCAP, ainsi que les retraits
  • La gestion des webhooks et la relance des livraisons échouées
  • Les détails du compte, l'utilisation et la gestion des clés API
  • Limites d’envoi — consulter l’utilisation par rapport au plafond quotidien, demander un volume plus élevé, voir l’allocation de rechargement

Ensuite, demandez simplement

« Trouve un numéro 416 disponible, dis-moi son coût, et n'achète rien pour l'instant. »

Avec une clé de production, l'achat d'un numéro et l'envoi de messages engagent de vrais frais. Un agent agit sur des consignes parfois plus vagues que prévu — explorez d'abord avec une clé de test.
Référence complète des outils sur npm

Codes d'erreur

HTTPCodeSignification
401UNAUTHORIZEDClé API manquante ou invalide
402INSUFFICIENT_BALANCESolde du compte insuffisant
403NUMBER_LIMIT_REACHEDLe compte a atteint sa limite de numéros de téléphone
404VERIFICATION_NOT_FOUNDIdentifiant de vérification introuvable ou non associé à ce compte
409VERIFICATION_ALREADY_VERIFIEDCe numéro a déjà été vérifié
409PURCHASE_IN_PROGRESSUn autre achat de numéro est en cours — réessayez sous peu
409ALLOWANCE_REQUEST_PENDINGUne demande d'allocation est déjà en attente d'examen
410VERIFICATION_EXPIREDLe code de vérification a expiré
422VALIDATION_ERRORÉchec de la validation du corps ou de la requête — voir details
422NON_CANADIAN_NUMBERNuméro E.164 canadien invalide
422MESSAGE_TOO_LONGLe texte dépasserait la limite de 10 parties SMS de l'opérateur (≈1 530 caractères GSM-7 ou 670 caractères Unicode) — rien n'est facturé
422VERIFICATION_INVALID_CODECode incorrect — attempts_remaining indique le nombre de tentatives restantes
422ALLOW_LIST_BLOCKEDLe destinataire ne figure pas sur la liste AUTORISATION de cette clé API
422DENY_LIST_BLOCKEDLe destinataire figure sur la liste BLOCAGE de cette clé API
422INVALID_ALLOWANCE_REQUESTL'allocation demandée doit dépasser votre limite actuelle
429RATE_LIMITEDTrop de requêtes — veuillez ralentir
429VERIFICATION_MAX_ATTEMPTSTrop de tentatives incorrectes — cette vérification est verrouillée
451OPT_OUT_BLOCKEDLe destinataire a refusé le consentement — envoi bloqué par la loi
451NO_CONSENTPas de consentement LCAP valide en dossier
451CONSENT_EXPIREDConsentement tacite expiré (limite LCAP de 2 ans)
451DNCL_BLOCKEDNuméro sur la LNNTE du CRTC — aucune exemption applicable (à venir; non retourné actuellement)