GPT Image 2.5 is live — OpenAI's newest image model, targeted edits that leave the rest of the frame alone
Tutoriel API de modération d'images : exemple en Python et JavaScript
2026/10/07

Tutoriel API de modération d'images : exemple en Python et JavaScript

Comment fonctionne une API de modération d'images : catégories de risque applicables aux images, entrée par URL uniquement, facturation par image, seuils de score, et code Python et JavaScript.

Une API de modération d'images prend une image, lui attribue un score pour une liste de catégories de risque et vous indique s'il faut la publier, la mettre en attente ou la bloquer. Le piège avec un modèle généraliste comme omni-moderation-latest, c'est que toutes les catégories qu'il renvoie ne regardent pas réellement l'image : la documentation d'OpenAI classe 6 de ses 13 catégories en « Text and images » et les 7 autres en « Text only »[1]. Si vous envoyez une photo sans légende, ces 7 catégories texte uniquement renvoient 0 par conception, et non parce que la photo est saine[1].

Ce guide explique ce que cela implique en pratique : sur quelles catégories vous pouvez compter pour les images, comment envoyer une image (reAPI n'accepte que des URL publiques), comment une requête est facturée, comment transformer les scores en décisions, et un exemple Python et JavaScript prêt à l'emploi qui soumet une image et interroge la tâche jusqu'au verdict. Il se termine par les différences avec les services spécialisés dans l'image comme Sightengine, Hive, Azure AI Content Safety et Amazon Rekognition.

TL;DR

  • omni-moderation-latest évalue les images sur 6 catégories : sexual, self-harm, self-harm/intent, self-harm/instructions, violence et violence/graphic. Les 7 autres, dont sexual/minors, ne concernent que le texte[1].
  • Sur reAPI, une image est envoyée sous forme de bloc image_url avec une URL http(s) publique. Le base64 et les URI data: sont refusés[2].
  • La facturation se fait par unité de modération : une unité par image, une par tranche de 1 000 mots de texte, au moins une unité par requête[2]. Les tarifs en vigueur figurent sur la page du modèle.
  • L'appel est asynchrone : POST /api/v1/moderations, puis interrogation de GET /api/v1/tasks/{id} jusqu'à ce que status vaille completed[2].
  • flagged est le verdict par défaut du modèle. Pour appliquer votre propre politique, fixez des seuils sur category_scores (de 0 à 1) catégorie par catégorie et recalibrez-les quand le modèle évolue[1].
  • La gratuité de l'endpoint d'OpenAI lui-même est traitée dans L'API de modération d'OpenAI est-elle gratuite ?.

Les catégories de risque qu'une API de modération d'images peut voir

OpenAI liste les types d'entrée pris en charge par chaque catégorie de omni-moderation-latest[1] :

CatégorieEntrées
sexualTexte et images
self-harm, self-harm/intent, self-harm/instructionsTexte et images
violence, violence/graphicTexte et images
sexual/minorsTexte uniquement
harassment, harassment/threateningTexte uniquement
hate, hate/threateningTexte uniquement
illicit, illicit/violentTexte uniquement

Deux conséquences comptent pour un pipeline d'images.

D'abord, un zéro n'est pas toujours une mesure. OpenAI indique que si vous n'envoyez que des images, sans texte d'accompagnement, le modèle renvoie un score de 0 pour les catégories texte uniquement[1]. Un symbole haineux dans un mème ou une menace écrite dans une capture d'écran ne sera pas détecté par le score hate ou harassment d'une requête contenant uniquement une image. La réponse indique, dans category_applied_input_types, sur quels types d'entrée chaque catégorie a été évaluée ; dans l'exemple d'OpenAI avec une image seule, les six catégories image affichent ["image"] et les autres un tableau vide[1]. Vérifiez ce champ avant de considérer un score faible comme un feu vert.

Ensuite, sexual/minors ne concerne que le texte[1]. Le guide d'OpenAI précise aussi de ne pas envoyer à la Moderation API de contenus pédopornographiques connus ou suspectés, car elle n'est pas conçue pour la détection de CSAM et ne remplace pas des protections dédiées à la sécurité des enfants[1]. Si votre plateforme accepte des uploads d'utilisateurs, prévoyez un contrôle distinct pour la protection de l'enfance.

OpenAI documente une limite de 20 Mo par fichier image pour ce modèle[1].

Envoyer des images : URL publiques uniquement

Le corps de la requête comporte un seul champ de contenu, input. Pour les images, vous envoyez un tableau de blocs de contenu[2] :

{
  "model": "omni-moderation-latest",
  "input": [
    { "type": "image_url", "image_url": { "url": "https://example.com/upload.jpg" } }
  ]
}

La référence de l'API d'OpenAI indique que image_url.url peut être soit une URL d'image, soit des données d'image encodées en base64[3]. reAPI n'accepte que la première forme : image_url.url doit être une URL http(s) publique, et le base64 ou les URI data: échouent à la validation avec l'erreur 20003[2]. Cette règle s'applique aux entrées média de tous les modèles reAPI.

Pour les uploads d'utilisateurs, l'ordre des opérations est donc le suivant : stocker le fichier, obtenir une URL accessible depuis Internet, puis modérer. Les URL signées fonctionnent tant qu'elles sont encore valides au moment où la tâche s'exécute[2]. Si l'URL ne peut pas être récupérée, la tâche échoue avec 80007 et le montant est remboursé[2]. Gardez l'objet privé et non publié jusqu'au retour du verdict.

Vous pouvez aussi placer une légende et sa photo dans le même tableau. La documentation de reAPI précise qu'un tableau de blocs de contenu renvoie un seul résultat pour l'ensemble, si bien que le modèle juge le texte et l'image ensemble[2]. C'est ce qu'il vous faut pour une publication accompagnée d'une légende. Ce n'est pas ce qu'il vous faut pour dix uploads sans rapport entre eux : un verdict combiné ne vous dira pas quelle image l'a déclenché, envoyez-les donc dans des requêtes séparées.

Comment la modération d'images est facturée

reAPI facture omni-moderation-latest par unité de modération[2] :

EntréeUnités
Chaque bloc image_url1 unité
Texte1 unité par tranche de 1 000 mots, cumulée sur la requête ; chaque élément de texte compte pour au moins 50 mots
Toute requêteAu moins 1 unité

Les unités sont converties en crédits une fois par requête et arrondies à l'unité supérieure, l'interrogation de la tâche est gratuite et les requêtes échouées sont remboursées automatiquement[2]. Une requête accepte jusqu'à 500 éléments[2]. Le tarif par unité figure sur la page du modèle. Pour une comparaison des prix et des offres gratuites entre fournisseurs, consultez L'API de modération d'OpenAI est-elle gratuite ?.

Exemple d'API de modération d'images en Python et JavaScript

Les deux exemples font la même chose : soumettre une image, interroger la tâche toutes les 3 secondes et renvoyer le premier résultat. La documentation des tâches de reAPI recommande de ne pas interroger plus souvent que toutes les 2 à 3 secondes, car l'endpoint d'interrogation est mis en cache pendant 5 secondes tant qu'une tâche est en cours[4]. Une vérification de modération se termine généralement en quelques secondes[2].

Python

import time
import requests

API = "https://reapi.ai/api/v1"
HEADERS = {
    "Authorization": "Bearer YOUR_API_KEY",
    "Content-Type": "application/json",
}

def moderate_image(image_url, timeout_s=60):
    submit = requests.post(
        f"{API}/moderations",
        headers=HEADERS,
        json={
            "model": "omni-moderation-latest",
            "input": [{"type": "image_url", "image_url": {"url": image_url}}],
        },
        timeout=30,
    )
    submit.raise_for_status()
    task_id = submit.json()["id"]

    deadline = time.time() + timeout_s
    while time.time() < deadline:
        time.sleep(3)
        task = requests.get(f"{API}/tasks/{task_id}", headers=HEADERS, timeout=30).json()
        if task["status"] == "completed":
            return task["output"]["moderation"]["results"][0]
        if task["status"] == "failed":
            raise RuntimeError(f'{task["error"]["code"]}: {task["error"]["message"]}')
    raise TimeoutError(f"task {task_id} still processing")

result = moderate_image("https://example.com/upload.jpg")
print(result["flagged"], result["category_scores"]["violence"])

JavaScript (Node.js 18+, enregistré comme module .mjs)

const API = "https://reapi.ai/api/v1";
const headers = {
  Authorization: `Bearer ${process.env.REAPI_API_KEY}`,
  "Content-Type": "application/json",
};

async function moderateImage(imageUrl, timeoutMs = 60_000) {
  const submit = await fetch(`${API}/moderations`, {
    method: "POST",
    headers,
    body: JSON.stringify({
      model: "omni-moderation-latest",
      input: [{ type: "image_url", image_url: { url: imageUrl } }],
    }),
  });
  if (!submit.ok) throw new Error(`submit failed: ${submit.status} ${await submit.text()}`);
  const { id } = await submit.json();

  const deadline = Date.now() + timeoutMs;
  while (Date.now() < deadline) {
    await new Promise((r) => setTimeout(r, 3000));
    const task = await (await fetch(`${API}/tasks/${id}`, { headers })).json();
    if (task.status === "completed") return task.output.moderation.results[0];
    if (task.status === "failed") throw new Error(`${task.error.code}: ${task.error.message}`);
  }
  throw new Error(`task ${id} still processing`);
}

const result = await moderateImage("https://example.com/upload.jpg");
console.log(result.flagged, result.category_scores.violence);

Exécutez la version JavaScript sur votre serveur, pas dans le navigateur. La clé API est un Bearer token, et l'inclure dans le code front-end l'expose à quiconque ouvre les outils de développement. Il en va de même pour la question sur React dans la FAQ ci-dessous. Le schéma complet de la requête, y compris le texte et les entrées mixtes, se trouve dans la documentation de l'API.

Lire le résultat et fixer des seuils

Chaque résultat contient quatre champs[1][2] :

ChampCe qu'il vous indique
flaggedtrue lorsque le modèle juge l'entrée nuisible dans au moins une catégorie
categoriesLe verdict vrai/faux du modèle pour chaque catégorie
category_scoresLa confiance du modèle pour chaque catégorie, de 0 à 1
category_applied_input_typesLes types d'entrée (text, image) sur lesquels chaque catégorie a été évaluée

flagged est un premier filtre raisonnable, mais il reflète les réglages par défaut du modèle, qui peuvent être plus stricts ou plus souples que votre politique[2]. OpenAI recommande de traiter les scores comme des signaux au service de la politique de votre application plutôt que comme une décision de blocage automatique, et d'orienter si nécessaire le contenu signalé vers une revue[1].

Une approche courante consiste à définir trois zones par catégorie image : autoriser sous un score bas, envoyer en revue humaine entre les deux, bloquer au-dessus d'un score élevé. Une version minimale :

IMAGE_CATEGORIES = [
    "sexual", "self-harm", "self-harm/intent", "self-harm/instructions",
    "violence", "violence/graphic",
]
REVIEW_AT = 0.3   # example values only; calibrate on your own labeled images
BLOCK_AT = 0.8

def decide(result):
    applied = result["category_applied_input_types"]
    scores = result["category_scores"]
    checked = [c for c in IMAGE_CATEGORIES if "image" in applied.get(c, [])]
    top = max((scores[c] for c in checked), default=0.0)
    if top >= BLOCK_AT:
        return "block"
    if top >= REVIEW_AT or result["flagged"]:
        return "review"
    return "allow"

Les valeurs ci-dessus sont illustratives, pas des recommandations. Choisissez les vôtres en passant quelques centaines d'images que vous avez déjà étiquetées et en observant où tombent les scores. Refaites cette vérification régulièrement : OpenAI indique prévoir de continuer à améliorer le modèle sous-jacent et que les politiques personnalisées fondées sur category_scores pourront nécessiter une recalibration au fil du temps[1]. Les scores ne sont ni arrondis ni retransformés en passant par reAPI[2], si bien qu'une calibration faite une fois s'applique directement aux valeurs que lit votre code.

En quoi les API de modération spécialisées dans l'image diffèrent

Un modèle généraliste et un service spécialisé dans l'image ne répondent pas à la même question. omni-moderation-latest évalue six catégories visuelles et peut juger une légende et son image ensemble[1]. Les API spécialisées dans l'image détectent beaucoup plus de classes visuelles, comme les armes, la drogue, les symboles haineux ou le texte présent dans l'image, et diffèrent dans la manière de recevoir le fichier et d'exprimer la confiance. D'après la documentation de chaque fournisseur :

ServiceCe qu'il détecte dans les imagesMode d'envoi de l'imageSortieUnité de facturation
omni-moderation-latest sur reAPIsexual, self-harm (3), violence (2)[1]URL http(s) publique[2]Booléen + score de 0 à 1 par catégorie[1]Par image (unité de modération)[2]
SightengineNudité sur 29 classes, violence, armes, signes haineux et offensants, gore, automutilation, drogue, alcool, tabac, jeux d'argent, texte dans les images, QR codes[5]Upload direct ou URL accessible publiquement[6]Résultats par modèle sélectionnéOpérations ; les modèles d'un même groupe ne comptent qu'une fois par requête[7]
Hive Visual ModerationContenu sexuel, images violentes, drogue, images haineuses et attributs d'image, répartis en classes nommées[8]URL publique ou signée, ou upload d'un fichier local[9]Confiance de 0 à 1 par classe[9]Contrat annuel ; Hive oriente les plus petits clients vers son VLM en libre-service[8]
Azure AI Content Safety (Analyze Image)Hate, SelfHarm, Sexual, Violence[10]Octets en base64 ou URL de blob, l'un ou l'autre[10]Gravité 0, 2, 4 ou 6 par catégorie[11]Par image soumise[12]
Amazon Rekognition (DetectModerationLabels)Taxonomie de labels à trois niveaux ; le premier niveau comprend Explicit, Violence, Visually Disturbing, Drugs & Tobacco, Alcohol, Rude Gestures, Gambling et Hate Symbols[13]Octets d'image en base64 ou objet Amazon S3 ; JPEG ou PNG[14]Labels avec confiance ; MinConfidence vaut 50 par défaut[14]Par image et par appel d'API[15]

Trois différences font généralement pencher la balance.

Couverture visuelle. Si vous devez repérer des armes, de la drogue, des symboles haineux ou du texte incrusté dans une image, les services spécialisés listent explicitement ces classes[5][8][13]. omni-moderation-latest n'a pas de catégories image pour elles[1].

Forme du score. Hive renvoie une confiance de 0 à 1 par classe et suggère de commencer autour de 0,90 pour signaler une classe[8]. Rekognition écarte les labels sous MinConfidence, qui vaut 50 par défaut sur une échelle de 0 à 100[14]. Azure renvoie pour les images des niveaux de gravité grossiers : 0, 2, 4 ou 6[11]. Un seuil réglé sur un service ne se transpose pas à un autre.

Gestion de l'entrée. Azure et Rekognition acceptent des octets en base64[10][14], et Sightengine et Hive acceptent l'upload direct d'un fichier[6][9]. reAPI n'accepte que des URL[2], ce qui convient aux pipelines où l'upload atterrit déjà dans un stockage objet.

omni-moderation-latest est adapté lorsque votre contenu est surtout du texte accompagné d'images, lorsque les six catégories visuelles correspondent à votre politique, ou lorsque vous appelez déjà d'autres modèles via reAPI avec la même clé. Pour une comparaison plus large par modalité et par cas d'usage, consultez Meilleure API de modération de contenu.

Questions fréquentes

API de modération d'images gratuite

OpenAI indique que son propre endpoint de modération est gratuit[1]. Sur reAPI, omni-moderation-latest est facturé à l'usage, à raison d'une unité par image, et les requêtes échouées sont remboursées[2]. Les offres gratuites et les limites de débit des différents fournisseurs sont comparées dans L'API de modération d'OpenAI est-elle gratuite ?.

API gratuite de modération d'images uploadées

Modérer un upload se fait en trois étapes : stocker le fichier en privé, créer une URL que l'API peut récupérer (une URL signée fonctionne tant qu'elle est valide), puis soumettre cette URL et ne publier qu'après le verdict[2]. reAPI n'accepte ni les octets du fichier ni une chaîne base64 directement[2]. Pour savoir quels services proposent un quota gratuit, consultez L'API de modération d'OpenAI est-elle gratuite ?.

API de modération d'images OpenAI

Oui, le modèle de modération d'OpenAI traite les images. omni-moderation-latest accepte des entrées texte et image, ne classe pas l'audio et n'évalue les images que pour les catégories sexual, self-harm et violence[1]. L'identifiant du modèle sur reAPI est le même, omni-moderation-latest, derrière un endpoint de tâche asynchrone[2].

API de modération d'images Python

L'exemple Python ci-dessus est complet : il envoie un bloc image_url à /api/v1/moderations, interroge /api/v1/tasks/{id} et renvoie output.moderation.results[0]. Il ne nécessite que le paquet requests. La documentation de l'API montre le même appel en cURL, Node.js et Go.

API de modération d'images React

Appelez l'API de modération depuis votre backend, pas depuis un composant React. Votre application React envoie le fichier à votre serveur ou à votre stockage, votre serveur appelle l'API avec la clé, et le client ne reçoit que la décision. Placer la clé Bearer dans le code du navigateur l'expose à chaque visiteur.

L'API ChatGPT peut-elle analyser des images ?

Oui. Les modèles d'OpenAI dotés de vision analysent les images via la Responses API et la Chat Completions API, à partir d'une URL, d'une data URL en base64 ou d'un identifiant de fichier[16]. Il s'agit de compréhension d'image ouverte. Pour un ensemble fixe de catégories de risque avec des scores de 0 à 1, l'endpoint de modération est l'option conçue pour cela[1].

Meilleure API de modération d'images

Tout dépend de ce que vous devez détecter. Un modèle généraliste comme omni-moderation-latest couvre les contenus sexuels, d'automutilation et de violence dans les images et ajoute des catégories texte pour les légendes[1] ; les services spécialisés dans l'image couvrent davantage de classes visuelles (voir le tableau ci-dessus). Le guide de sélection complet se trouve dans Meilleure API de modération de contenu.

Intégrer la modération d'images dans un flux d'upload

Mettre en place une API de modération d'images fonctionnelle tient en peu d'étapes : uploader vers un stockage privé, modérer l'URL, agir selon les scores, puis publier. Avec omni-moderation-latest, rappelez-vous que seules six catégories regardent les pixels : ajoutez une légende ou du texte OCR à la requête si le texte présent dans les images compte pour vous, et gardez un contrôle distinct pour la sécurité des enfants. Commencez avec flagged, passez à des seuils par catégorie une fois que vous disposez de données étiquetées, et revérifiez ces seuils quand le modèle change.

Pour l'essayer, collez une URL d'image dans le playground de la page du modèle Content Moderation, puis transposez l'exemple Python ou JavaScript ci-dessus dans votre backend. La documentation de l'API liste tous les champs acceptés par cette API de modération d'images.

Références

  1. OpenAI. Moderation. Consulté en octobre 2026 sur developers.openai.com/api/docs/guides/moderation
  2. reAPI. omni-moderation-latest API docs. reapi.ai/docs/content-moderation
  3. OpenAI. Moderations API reference. Consulté en octobre 2026 sur developers.openai.com/api/reference/resources/moderations
  4. reAPI. Tasks API reference. reapi.ai/docs/api/tasks
  5. Sightengine. Visual Moderation models. Consulté en octobre 2026 sur sightengine.com/docs/models
  6. Sightengine. What are the ways to send an image to the API? Consulté en octobre 2026 sur sightengine.com/faq/ways-to-send-image-to-api
  7. Sightengine. What is an operation? Consulté en octobre 2026 sur sightengine.com/faq/what-is-an-operation
  8. Hive. Visual Moderation - Overview. Consulté en octobre 2026 sur docs.thehive.ai/docs/visual-content-moderation
  9. Hive. Using Hive's Visual Moderation API. Consulté en octobre 2026 sur docs.thehive.ai/docs/visual-moderation-api
  10. Microsoft. Image Operations - Analyze Image (REST API). Consulté en octobre 2026 sur learn.microsoft.com/en-us/rest/api/contentsafety/image-operations/analyze-image
  11. Microsoft. Harm categories in Azure AI Content Safety. Consulté en octobre 2026 sur learn.microsoft.com/en-us/azure/ai-services/content-safety/concepts/harm-categories
  12. Microsoft. Azure AI Content Safety pricing. Consulté en octobre 2026 sur azure.microsoft.com/en-us/pricing/details/content-safety
  13. Amazon Web Services. Using the image and video moderation APIs. Consulté en octobre 2026 sur docs.aws.amazon.com/rekognition/latest/dg/moderation-api.html
  14. Amazon Web Services. DetectModerationLabels. Consulté en octobre 2026 sur docs.aws.amazon.com/rekognition/latest/APIReference/API_DetectModerationLabels.html
  15. Amazon Web Services. Amazon Rekognition pricing. Consulté en octobre 2026 sur aws.amazon.com/rekognition/pricing
  16. OpenAI. Images and vision. Consulté en octobre 2026 sur developers.openai.com/api/docs/guides/images-vision