Ir al contenido principal
Crawlswarm

Documentation

API REST

Lisez vos leads, lancez des scrapes et ingérez depuis vos outils existants. L'API tourne sur la même infrastructure que le dashboard, avec la même quota mensuelle.

Authentification

Toutes les requêtes nécessitent un header Authorization: Bearer sa_live_…. Générez une clé depuis Paramètres → API.

Chaque clé porte un ou plusieurs scopes : leads:read · jobs:read · jobs:write. Une requête sans le bon scope renvoie 403 Forbidden.

curl https://crawlswarm.com/api/v1/leads \
  -H "Authorization: Bearer sa_live_<48hex>" \
  -H "Content-Type: application/json"

GET /api/v1/leads

Liste paginée des leads de l'utilisateur, du plus récent au plus ancien. Scope requis : leads:read.

limit1–100, défaut 50.
cursorTimestamp ISO 8601 d'un lead précédemment renvoyé (next_cursor). Renvoie les leads scrapés strictement avant.
statusFiltre exact : new · contacted · no_reply · won · lost · disqualified.
{
  "data": [
    {
      "id": "lead_abc123",
      "name": "Boulangerie Émile",
      "city": "Rouen",
      "phone": "0235038884",
      "email": "contact@emile.fr",
      "score": 78,
      "status": "new",
      "tags": [],
      "credits_total": 1.5,
      "scraped_at": "2026-05-10T08:30:00.000Z"
    }
  ],
  "pagination": { "next_cursor": "2026-05-10T08:29:43.000Z", "limit": 50 }
}

POST /api/v1/leads

Ingère un ou plusieurs leads sans passer par un scrape Maps. Chaque lead consomme 1 crédit de base. Scope : jobs:write. Maximum 100 leads par requête.

leadObjet unique : { name, city, … }
leadsTableau d'objets, max 100.

Champs obligatoires par lead : name et city. Optionnels :address, phone, email, website, postal_code, tags.

curl -X POST https://crawlswarm.com/api/v1/leads \
  -H "Authorization: Bearer sa_live_<48hex>" \
  -H "Content-Type: application/json" \
  -d '{
    "leads": [
      { "name": "Boulang. X", "city": "Rouen", "email": "contact@x.fr" },
      { "name": "Plomberie Y", "city": "Lille", "phone": "0612345678" }
    ]
  }'
{
  "ingested": 2,
  "job_id": "job_d3f8a1",
  "leads": [
    { "id": "lead_abc", "name": "Boulang. X" },
    { "id": "lead_def", "name": "Plomberie Y" }
  ]
}

GET /api/v1/jobs

Historique des tâches (Maps + imports + ingest API). Mêmes paramètres que /api/v1/leads. Scope : jobs:read.

POST /api/v1/jobs

Lance un scrape Maps. Renvoie immédiatement { id, status: "queued" } — un worker prend le job dans les secondes qui suivent. Scope : jobs:write.

curl -X POST https://crawlswarm.com/api/v1/jobs \
  -H "Authorization: Bearer sa_live_<48hex>" \
  -H "Content-Type: application/json" \
  -d '{
    "query": "boulangeries",
    "city": "Rouen",
    "max_leads": 30,
    "enrichment_options": {
      "siren": true,
      "social": true,
      "emailPerso": true
    },
    "require_filters": { "social": true }
  }'

Webhooks (sortants)

Configurés depuis Paramètres → Webhooks. Trois événements :

  • lead.created— un lead vient d'être inséré (scrape ou import).
  • job.completed — une tâche se termine avec succès.
  • job.failed — une tâche tombe en erreur.

Chaque envoi inclut une signature HMAC-SHA256 dans le header X-Crawlswarm-Signature: t=<ts>,v1=<hex> calculée sur $`${ts}.${rawBody}` avec le secret du webhook.

// Vérification côté receveur (Node)
import { createHmac, timingSafeEqual } from "node:crypto";

function isValid(rawBody, header, secret) {
  const m = /t=(\d+),v1=([a-f0-9]+)/.exec(header);
  if (!m) return false;
  const [, ts, sig] = m;
  // Reject older than 5 min to prevent replay attacks.
  if (Math.abs(Date.now() / 1000 - Number(ts)) > 300) return false;
  const expected = createHmac("sha256", secret)
    .update(`${ts}.${rawBody}`)
    .digest("hex");
  return timingSafeEqual(Buffer.from(sig), Buffer.from(expected));
}

Quotas & rate limits

Le quota mensuel est partagé entre dashboard et API. Une requête qui ferait dépasser le quota renvoie 402 Payment Required avec quota_remaining dans le corps.

Pas de rate limit dur en V0, mais le serveur se réserve le droit de 429en cas d'abus. Recommandé : ≤ 5 requêtes / seconde.

Codes d'erreur

400Body invalide ou champs requis manquants.
401Header Bearer absent ou clé inconnue.
403La clé n'a pas le scope requis.
402Quota mensuel atteint.
429Rate limit (rare en V0).
5xxErreur serveur — retry exponentiel recommandé.

Dernière mise à jour : 10 mai 2026 · Questions : contact@initial-infrastructures.com