Vue d'ensemble
Une campagne envoie les prompts d'un sujet à un ou plusieurs modèles LLM et extrait les mentions de la marque dans les réponses. Les crédits sont consommés au lancement en fonction du nombre de prompts, de modèles et d'exécutions par modèle.
Endpoints
| Méthode | Chemin | Description |
|---|
GET | /brands/{brandId}/campaigns | Lister les campagnes |
POST | /brands/{brandId}/campaigns | Lancer une campagne |
GET | /brands/{brandId}/campaigns/{campaignId} | Obtenir le statut d'une campagne |
GET /brands//campaigns
Liste toutes les campagnes d'une marque, triées par date de création décroissante.
Paramètres de requête
| Paramètre | Type | Défaut | Description |
|---|
limit | integer | 50 | Nombre maximum de résultats (max 200) |
offset | integer | 0 | Décalage de pagination |
curl "https://mentova.ai/api/v1/brands/clxabc123/campaigns?limit=10" \
-H "X-API-Key: mtv_live_votre_cle"
Réponse 200
{
"data": [
{
"id": "clxcampaign1",
"status": "COMPLETED",
"createdAt": "2026-06-01T09:00:00.000Z",
"completedAt": "2026-06-01T09:08:00.000Z",
"models": ["GPT4O_MINI", "CLAUDE_HAIKU"],
"runsPerModel": 3,
"topic": {
"id": "clxtopic1",
"seed": "Quel est le meilleur outil de gestion de projet pour les équipes à distance ?"
},
"_count": { "runs": 6 }
}
],
"total": 12,
"limit": 10,
"offset": 0
}
POST /brands//campaigns
Lance une nouvelle campagne sur un sujet. La campagne est traitée de manière asynchrone.
Corps de la requête
| Champ | Type | Requis | Description |
|---|
topicId | string | Oui | Identifiant du sujet sur lequel lancer la campagne |
models | string[] | Non | Valeurs d'enum des modèles LLM à utiliser. Par défaut : modèles sélectionnés pour la marque |
runsPerModel | integer | Non | Nombre d'exécutions par modèle (1-20). Par défaut : paramètre du plan |
maxPrompts | integer | Non | Limite de prompts à inclure. Par défaut : tous les prompts du sujet |
curl -X POST https://mentova.ai/api/v1/brands/clxabc123/campaigns \
-H "X-API-Key: mtv_live_votre_cle" \
-H "Content-Type: application/json" \
-d '{
"topicId": "clxtopic1",
"models": ["GPT4O_MINI", "CLAUDE_HAIKU"],
"runsPerModel": 3
}'
Réponse 201
{
"data": {
"id": "clxcampaign2",
"status": "PENDING",
"createdAt": "2026-06-01T10:00:00.000Z",
"completedAt": null,
"models": ["GPT4O_MINI", "CLAUDE_HAIKU"],
"runsPerModel": 3,
"topic": {
"id": "clxtopic1",
"seed": "Quel est le meilleur outil de gestion de projet pour les équipes à distance ?"
},
"_count": { "runs": 0 }
}
}
Erreurs
| HTTP | code | Cause |
|---|
404 | NOT_FOUND | Sujet introuvable ou n'appartenant pas à cette marque |
422 | QUOTA_EXCEEDED | Crédits insuffisants pour lancer la campagne |
422 | VALIDATION_ERROR | Corps de requête invalide |
GET /brands//campaigns/
Obtient le statut actuel et les détails d'une campagne. Interrogez cet endpoint pour suivre l'avancement.
curl https://mentova.ai/api/v1/brands/clxabc123/campaigns/clxcampaign2 \
-H "X-API-Key: mtv_live_votre_cle"
Réponse 200
{
"data": {
"id": "clxcampaign2",
"status": "RUNNING",
"createdAt": "2026-06-01T10:00:00.000Z",
"completedAt": null,
"models": ["GPT4O_MINI", "CLAUDE_HAIKU"],
"runsPerModel": 3,
"topic": {
"id": "clxtopic1",
"seed": "Quel est le meilleur outil de gestion de projet pour les équipes à distance ?"
},
"_count": { "runs": 4 }
}
}
Valeurs de statut
| Statut | Description |
|---|
PENDING | Accepté, en attente d'entrée dans la file de traitement |
QUEUED | Pris en charge par le worker, en attente d'un slot d'exécution |
RUNNING | Appels LLM en cours |
COMPLETED | Toutes les exécutions terminées, mentions extraites |
FAILED | Erreur de traitement - les crédits sont remboursés |
TIMEOUT | Le worker a expiré - les crédits sont remboursés |
Modèle de polling
const API_KEY = "mtv_live_votre_cle";
const BASE = "https://mentova.ai/api/v1";
// Lancer
const { data: campaign } = await fetch(`${BASE}/brands/${brandId}/campaigns`, {
method: "POST",
headers: { "X-API-Key": API_KEY, "Content-Type": "application/json" },
body: JSON.stringify({ topicId }),
}).then(r => r.json());
// Interroger jusqu'à la fin
let status = campaign.status;
while (status === "PENDING" || status === "QUEUED" || status === "RUNNING") {
await new Promise(r => setTimeout(r, 5000));
const { data } = await fetch(
`${BASE}/brands/${brandId}/campaigns/${campaign.id}`,
{ headers: { "X-API-Key": API_KEY } }
).then(r => r.json());
status = data.status;
}