Bienvenue dans l’API Billabex 👋 Ce guide vous mène pas à pas de l’authentification à vos premiers appels réussis.
À la fin, vous aurez :
- un client OAuth configuré ;
- un jeton d’accès ;
- l’identifiant de votre organisation ;
- vos premiers appels en lecture et en écriture.
Qu’est-ce que Billabex ?
Billabex est une plateforme d’automatisation du suivi des paiements propulsée par l’IA, qui aide les entreprises à encaisser plus vite leurs créances.
Notre agent :
- relance automatiquement les factures impayées ;
- communique avec les clients en plusieurs langues ;
- adapte son ton et son rythme avec tact et diplomatie.
Avec l’API Billabex, vous pouvez :
- gérer les factures et les avoirs par programme ;
- synchroniser les comptes clients et leurs contacts ;
- suivre les communications et les soldes ;
- intégrer Billabex à vos parcours de facturation.
Prérequis
Avant de commencer, assurez-vous d’avoir :
- un compte Billabex Créez-le sur https://next.billabex.com/auth/sign-up
- une organisation créée dans ce compte
- un client OAuth créé dans le portail développeur
Étape 1 : créer un client OAuth
Rendez-vous dans Portail développeur → Clients OAuth et créez un client.
Vous devrez fournir :
- Nom du client : le nom de votre application
- URI de redirection : votre URL de rappel OAuth
Par exemple
https://votreapp.com/callback - Scopes : les permissions dont votre application a besoin (voir le guide des scopes)
Une fois créé, vous recevez :
- un
client_id; - un
client_secret, affiché une seule fois.
Conservez le secret client en lieu sûr.
Étape 2 : implémenter l’authentification OAuth
Billabex utilise le flux OAuth 2.1 d’autorisation par code avec PKCE.
Sur le principe :
- votre application prouve son identité par PKCE ;
- l’utilisateur approuve l’accès ;
- vous recevez des jetons à durée de vie courte pour appeler l’API.
Concrètement, vous allez :
- générer un vérificateur et un défi PKCE ;
- rediriger l’utilisateur vers la page d’autorisation ;
- recevoir un code d’autorisation ;
- échanger ce code contre un jeton d’accès et un jeton de rafraîchissement.
Générer les paramètres PKCE
Générez un code_verifier et le code_challenge correspondant.
Gardez le vérificateur en mémoire : vous le réutiliserez à l’échange.
// Générer le vérificateur (chaîne aléatoire)
const codeVerifier = generateRandomString(128);
// Générer le défi (empreinte SHA256 du vérificateur, encodée en base64url)
const codeChallenge = base64UrlEncode(sha256(codeVerifier));
Rediriger vers la page d’autorisation
Construisez l’URL d’autorisation et redirigez l’utilisateur.
const authUrl = new URL('[baseURL]/api/oauth/authorize');
authUrl.searchParams.append('client_id', 'YOUR_CLIENT_ID');
authUrl.searchParams.append('redirect_uri', 'https://votreapp.com/callback');
authUrl.searchParams.append('response_type', 'code');
authUrl.searchParams.append('scope', 'invoices:read accounts:read');
authUrl.searchParams.append('code_challenge', codeChallenge);
authUrl.searchParams.append('code_challenge_method', 'S256');
authUrl.searchParams.append('state', generateRandomString(16));
// Rediriger l'utilisateur vers authUrl
Validez toujours le state renvoyé, pour vous protéger des attaques CSRF.
Échanger le code contre des jetons
Après approbation, votre URI de redirection reçoit un code d’autorisation. Échangez-le sur l’endpoint de jeton.
const response = await fetch('[baseURL]/api/oauth/token', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({
grant_type: 'authorization_code',
code: authorizationCode,
redirect_uri: 'https://votreapp.com/callback',
code_verifier: codeVerifier,
client_id: 'YOUR_CLIENT_ID',
client_secret: 'YOUR_CLIENT_SECRET',
}),
});
const tokens = await response.json();
Exemple de réponse :
{
"access_token": "...",
"token_type": "Bearer",
"expires_in": 3600,
"refresh_token": "...",
"scope": "invoices:read accounts:read"
}
Pour le détail, voyez le guide OAuth.
Étape 3 : récupérer l’identifiant de votre organisation
La plupart des endpoints exigent un organizationId.
Utilisez votre jeton d’accès pour lister les organisations auxquelles vous appartenez et choisir celle sur laquelle travailler.
const response = await fetch('[baseURL]/api/public/v1/organizations?first=10', {
headers: {
Authorization: `Bearer ${accessToken}`,
'Content-Type': 'application/json',
},
});
const data = await response.json();
const organizationId = data.nodes?.[0]?.id;
Étape 4 : votre premier appel
Avec un jeton d’accès et un identifiant d’organisation, vous pouvez appeler l’API publique.
Exemple : lister les comptes de votre organisation.
const response = await fetch('[baseURL]/api/public/v1/accounts?organizationId=YOUR_ORG_ID&first=10', {
headers: {
Authorization: `Bearer ${accessToken}`,
'Content-Type': 'application/json',
},
});
const data = await response.json();
console.log(data);
Avec cURL
curl -X GET "[baseURL]/api/public/v1/accounts?organizationId=YOUR_ORG_ID&first=10" \
-H "Authorization: Bearer YOUR_ACCESS_TOKEN" \
-H "Content-Type: application/json"
Étape 5 : gérer la pagination
L’API Billabex utilise une pagination par curseur.
- Lisez
pageInfo.endCursordans la réponse - Passez-le en paramètre
afterpour obtenir la page suivante - Quand
endCursorest absent, vous êtes au bout
const nextPageResponse = await fetch(`[baseURL]/api/public/v1/accounts?organizationId=YOUR_ORG_ID&first=10&after=${data.pageInfo.endCursor}`, {
headers: {
Authorization: `Bearer ${accessToken}`,
'Content-Type': 'application/json',
},
});
Le guide de la pagination entre dans le détail.
Étape 6 : créer une facture
Créer une facture est une opération d’écriture, qui exige le scope invoices:all.
Cet endpoint attend :
- du
multipart/form-data; - un fichier PDF ou image ;
- les métadonnées et les montants de la facture ;
- une adresse de facturation, dont les champs peuvent être vides mais doivent être présents.
Exemple :
const formData = new FormData();
formData.append('accountId', 'ACCOUNT_ID');
formData.append('number', 'INV-2024-001');
formData.append('issuedDate.year', '2024');
formData.append('issuedDate.month', '1');
formData.append('issuedDate.day', '15');
formData.append('dueDate.year', '2024');
formData.append('dueDate.month', '2');
formData.append('dueDate.day', '15');
formData.append('totalAmount', '1500.00');
formData.append('taxAmount', '300.00');
formData.append('paidAmount', '0');
formData.append('poNumber', 'PO-2024-001');
formData.append('billingAddress.street', '1 rue Exemple');
formData.append('billingAddress.city', 'Paris');
formData.append('billingAddress.postalCode', '75001');
formData.append('billingAddress.country', 'FR');
formData.append('file', fileBlob, 'facture.pdf');
const response = await fetch('[baseURL]/api/public/v1/invoices', {
method: 'POST',
headers: {
Authorization: `Bearer ${accessToken}`,
},
body: formData,
});
const invoice = await response.json();
Les champs inconnus sont refusés
L’API répond 400 Bad Request quand le corps d’une requête porte un champ que l’endpoint ne déclare pas, en nommant le champ fautif :
{
"statusCode": 400,
"message": "property phone should not exist"
}
C’est délibéré. Accepter le champ et l’ignorer laisserait un champ renommé ou mal orthographié disparaître derrière un 201 Created, et vous ne le découvririez qu’au moment où la donnée manque. Un 400 échoue tout de suite, dans vos tests d’intégration plutôt qu’en production.
En pratique : envoyez exactement les champs documentés pour l’endpoint. Ne renvoyez pas un objet de réponse entier dans une requête d’écriture, les réponses portant des champs en lecture seule (id, createdAt, totaux calculés) qu’aucun endpoint d’écriture ne déclare.
Pour aller plus loin
Vous êtes prêt à intégrer Billabex 🎉
Lectures recommandées :
- Authentification OAuth : OAuth en détail
- Scopes OAuth : les permissions disponibles
- Limites de débit : éviter de les atteindre
- Pagination : parcourir efficacement les données
- Sources de compte : relier un compte à un système externe
- Opérations upsert : créer ou mettre à jour de façon idempotente
- Contacts : gérer les personnes d’un compte
- Tâches et interactions : répondre aux tâches ouvertes par l’agent
- Envoi de fichiers : encodage binaire et base64
- Référence de l’API : documentation complète des endpoints
Support
Besoin d’aide, ou un retour sur ce guide ? Écrivez-nous via le formulaire de contact.