Développeurs
Une API REST pour les mêmes clients, factures, soumissions, reçus et dépenses que vous gérez dans InvoiceCast. Avec le forfait Affaires, reliez vos propres outils au moyen d’une clé d’API.
Tous les points de terminaison partagent une même URL de base. Utilisez le domaine sur lequel vous vous connectez :
https://invoicecast.ca/api/v1
Content-Type: application/json (ou multipart/form-data pour téléverser un fichier).{"amount": 15000, "currency": "CAD", "formatted": "150,00 $"}, où amount est un entier en sous-unités (cents). Calculez avec amount et n’analysez jamais formatted. Pour envoyer un montant, utilisez des unités décimales, p. ex. 150.00.AAAA-MM-JJ. Les horodatages suivent la RFC 3339, en UTC.Envoyez un identifiant comme jeton « bearer » à chaque requête, avec un en-tête X-IC-Client indiquant le nom et la version de votre application :
Authorization: Bearer ick_live_…
X-IC-Client: my-app/1.0
Les propriétaires et administrateurs du compte créent les clés dans Paramètres → Clés d’API. Chaque clé a un nom, une date d’expiration facultative et une liste de permissions, comme invoices:read ou clients:write, pour qu’une intégration ne fasse que ce dont elle a besoin. La clé n’est affichée qu’une fois, à sa création. Conservez-la comme un mot de passe. La révocation d’une clé prend effet dès sa requête suivante.
Une clé agit au nom du compte. Elle peut lire et modifier les données du compte dans la limite de ses permissions, mais elle ne peut pas modifier les paramètres du compte ni gérer les utilisateurs, la facturation ni les autres clés.
Listez vos clients :
curl https://invoicecast.ca/api/v1/clients \
-H "Authorization: Bearer $INVOICECAST_API_KEY" \
-H "X-IC-Client: my-app/1.0"
Créez un client. Chaque requête POST et PATCH qui modifie vos données exige un en-tête Idempotency-Key : un UUID que vous générez et réutilisez si vous relancez la même requête.
curl -X POST https://invoicecast.ca/api/v1/clients \
-H "Authorization: Bearer $INVOICECAST_API_KEY" \
-H "X-IC-Client: my-app/1.0" \
-H "Idempotency-Key: $(uuidgen)" \
-H "Content-Type: application/json" \
-d '{"name": "Northwind Ltd", "email": "[email protected]"}'
Créez une facture brouillon pour ce client, puis envoyez-la :
curl -X POST https://invoicecast.ca/api/v1/invoices \
-H "Authorization: Bearer $INVOICECAST_API_KEY" \
-H "X-IC-Client: my-app/1.0" \
-H "Idempotency-Key: $(uuidgen)" \
-H "Content-Type: application/json" \
-d '{
"client_uuid": "<client uuid>",
"issue_date": "2026-10-25",
"currency": "CAD",
"items": [{"description": "Consulting", "quantity": 2, "unit_price": 150.00}]
}'
curl -X POST https://invoicecast.ca/api/v1/invoices/<invoice uuid>/send \
-H "Authorization: Bearer $INVOICECAST_API_KEY" \
-H "X-IC-Client: my-app/1.0" \
-H "Idempotency-Key: $(uuidgen)"
Chaque requête porte un en-tête X-IC-Client indiquant le nom et la version de votre application, par exemple acme-sync/3.1 : au plus 100 caractères ASCII imprimables. Sans lui, vous recevez 400 client_header_required. Il nous permet de retrouver vos requêtes lorsque vous nous écrivez et de vous prévenir avant qu’un changement touche votre version, et il est consigné dans le journal d’audit du compte à côté de la clé qui a fait chaque modification. Seuls le document OpenAPI et les liens de téléchargement PDF signés en sont exemptés.
Les listes renvoient une page de résultats avec meta.next_cursor et meta.has_more. Renvoyez le curseur avec ?cursor= pour obtenir la page suivante. Les numéros de page (?page=) ne sont pas pris en charge et renvoient une erreur 400.
Chaque liste renvoie aussi meta.server_time. Conservez-le et, la fois suivante, envoyez-le avec ?updated_since= pour ne recevoir que ce qui a changé, y compris les enregistrements supprimés, qui reviennent avec deleted_at renseigné.
Relancer une requête POST ou PATCH avec la même Idempotency-Key et le même corps dans les 24 heures renvoie la réponse d’origine au lieu d’agir deux fois. Réutiliser une clé avec un corps différent renvoie une erreur 422.
Un PATCH est partiel : envoyez seulement les champs que vous modifiez, les autres restent tels quels. Chaque enregistrement porte un ETag. Renvoyez-le dans If-Match lors d’un PATCH : si l’enregistrement a changé entre-temps, vous recevez 409 stale avec la version actuelle au lieu d’écraser la modification de quelqu’un d’autre. If-None-Match sur un GET renvoie 304 si rien n’a changé.
Si votre compte compte plus d’un profil d’entreprise, choisissez celui qui émet un document avec l’en-tête X-IC-Business-Profile (l’UUID d’un profil d’entreprise). Sans lui, une clé d’API utilise l’entreprise par défaut du compte.
La version 1 ne fait que s’enrichir : nous ajoutons des points de terminaison et des champs, mais nous ne renommons, ne retirons ni ne changeons jamais le sens de ceux qui existent. Ignorez les champs que vous ne reconnaissez pas. Un changement incompatible serait publié sous /api/v2.
Les limites s’appliquent par clé, par minute. En cas de dépassement, vous recevez 429 rate_limited avec un en-tête Retry-After en secondes.
| Identifiant | Lectures | Écritures |
|---|---|---|
| Clé d’API | 120 | 30 |
Les téléchargements de PDF sont limités à 20 par minute.
Toutes les erreurs ont la même forme. code est stable et fiable pour votre logique. message est traduit et peut être affiché à une personne. Mentionnez request_id si vous nous contactez.
{
"error": {
"code": "validation_failed",
"message": "The given data was invalid.",
"details": {"errors": {"name": ["The name field is required."]}},
"request_id": "b3b918fb-0b34-4018-9e85-54b770f8980d"
}
}
| Statut | Codes | Signification |
|---|---|---|
| 400 |
bad_request
client_header_required
client_header_invalid
idempotency_key_required
idempotency_key_invalid
|
La requête est mal formée : X-IC-Client ou Idempotency-Key absente ou invalide, valeur de filtre incorrecte ou numéro de page. |
| 401 |
unauthenticated
invalid_credentials
|
L’identifiant est absent, erroné, expiré ou révoqué. |
| 403 |
forbidden
insufficient_scope
upgrade_required
limit_reached
|
Action non permise : la clé n’a pas la permission, le forfait n’inclut pas la fonction ou une limite du forfait est atteinte. |
| 404 |
not_found
|
L’enregistrement n’existe pas ou appartient à un autre compte. |
| 409 |
stale
not_editable
idempotency_key_in_progress
|
L’enregistrement a changé depuis votre lecture, le document ne peut plus être modifié, ou la même Idempotency-Key est encore en traitement. |
| 422 |
validation_failed
idempotency_key_reused
|
Un champ n’a pas passé la validation (détails dans error.details.errors), ou une Idempotency-Key a été réutilisée avec un corps différent. |
| 429 |
rate_limited
|
Trop de requêtes. Attendez Retry-After secondes. |
La liste complète des points de terminaison, des champs, des permissions et des forfaits requis est publiée sous forme de document OpenAPI 3.1, généré à partir du code même qui sert l’API. Chargez-le dans Postman, Insomnia ou un générateur de client :
https://invoicecast.ca/api/v1/openapi.json
Il manque quelque chose, ou un point n’est pas clair? Écrivez-nous en indiquant le request_id de la requête concernée.