Guide
Interfaces de modèles et de texte
Conventions de requête et de réponse pour la consultation des modèles disponibles et la conversation textuelle (y compris en streaming)
Interfaces de modèles et de texte
Le catalogue de modèles et la conversation textuelle utilisent tous deux la même clé API de plateforme. Pour les conventions communes (adresse de base, authentification, limitation de débit, nouvelles tentatives), voir Authentification et conventions de base.
Interroger la liste des modèles
/v1/modelsMéthode d'authentification
Authorization: Bearer <API_KEY>.
Paramètres de requête
Aucun corps de requête ; il suffit de fournir la clé API dans l'en-tête de requête.
Exemple de requête
Cette étape ne nécessite aucun corps de requête : il suffit d'inclure la clé API dans l'en-tête.
Le data[].id renvoyé est l'ID de modèle à utiliser pour tous les appels ultérieurs.
Requête
curl "https://locopalai.com/v1/models" \
-H "Authorization: Bearer $LOCOPAL_API_KEY"Paramètres de réponse
| Paramètre | Type | Description |
|---|---|---|
object | string | Fixe, vaut list |
success | boolean | Vaut true lorsque la requête réussit |
data | array | Liste des modèles appelables avec la clé actuelle |
data[].id | string | ID du modèle, à recopier tel quel lors de la soumission |
data[].object | string | Fixe, vaut model |
data[].created | integer | Heure d'enregistrement dans le catalogue (secondes Unix) |
data[].owned_by | string | Identifiant du fournisseur du modèle, à titre indicatif uniquement |
data[].supported_endpoint_types | string[] | Types d'interfaces disponibles pour ce modèle |
objectetsuccesssont des champs racine, et non des éléments dedata[].objectvaut fixementlist, etsuccessvauttrueen cas de succès. Pour déterminer si une requête a réussi, fiez-vous au code de statut HTTP ;successn'est qu'indicatif.
Corps de réponse
{
"data": [
{
"id": "doubao-seedance-2.0",
"object": "model",
"created": 1626777600,
"owned_by": "doubaovideo",
"supported_endpoint_types": ["openai"]
},
{
"id": "claude-sonnet-4-5-20250929",
"object": "model",
"created": 1626777600,
"owned_by": "claude",
"supported_endpoint_types": ["anthropic", "openai"]
}
],
"object": "list",
"success": true
}Un retour "data": [] signifie que le groupe d'appel auquel appartient la clé actuelle n'a aucun modèle disponible ; vérifiez d'abord la configuration du groupe ou contactez le support de la plateforme, et ne réessayez pas avec le nom d'affichage de la page. Le catalogue de modèles varie selon les autorisations et la disponibilité de la plateforme ; il est recommandé de l'actualiser au démarrage du service, lorsque l'utilisateur choisit un modèle ou lorsque vous recevez « modèle indisponible ».
Réponse d'erreur
| HTTP | Réponse | Description |
|---|---|---|
401 | {"error":{"code":"","message":"Invalid token (request id: ...)","type":"new_api_error"}} | Clé API absente, incorrecte ou expirée |
500 | {"error":{"message":"...","type":"new_api_error"}} | Échec de la requête du catalogue ; conservez l'identifiant de requête puis réessayez |
Conversation textuelle
/v1/chat/completionsMéthode d'authentification
Authorization: Bearer <API_KEY>.
Corps de requête · application/json
| Paramètre | Type | Obligatoire | Description |
|---|---|---|---|
model | string | Oui | ID du modèle de texte renvoyé par /v1/models |
messages | array | Oui | Messages ordonnés chronologiquement |
messages[].role | string | Oui | system, user ou assistant |
messages[].content | string | Oui | Contenu du message actuel |
stream | boolean | Non | Lorsque true, utilise un retour en streaming SSE, jusqu'à la lecture de [DONE] |
temperature | number | Non | La prise en charge dépend des capacités réelles du modèle actuel |
max_tokens | integer | Non | La prise en charge dépend des capacités réelles du modèle actuel |
Exemple de requête
model doit contenir l'id renvoyé par /v1/models, et non le nom d'affichage de la page.
Lorsque stream est défini sur true, la réponse est renvoyée par segments en SSE, jusqu'à la lecture de [DONE].
À droite, trois écritures équivalentes dans trois langages ; changez d'onglet pour les comparer.
curl -X POST "https://locopalai.com/v1/chat/completions" \
-H "Authorization: Bearer $LOCOPAL_API_KEY" \
-H "Content-Type: application/json" \
--data-binary @- <<'JSON'
{
"model": "从 /v1/models 选择的文本模型 ID",
"messages": [{ "role": "user", "content": "只回复两个字:你好" }],
"stream": false
}
JSONParamètres de réponse
| Paramètre | Type | Description |
|---|---|---|
id | string | Identifiant de cette réponse, utilisé pour le diagnostic et le rapprochement |
object | string | Vaut chat.completion en mode non streaming |
created | integer | Heure de la réponse (secondes Unix) |
model | string | ID du modèle utilisé pour cette requête |
choices | array | Liste des résultats |
choices[].index | integer | Numéro d'ordre du résultat |
choices[].message.role | string | Fixe, vaut assistant |
choices[].message.content | string | Texte généré |
choices[].finish_reason | string | Raison de fin ; length indique une troncature due à la longueur |
usage.prompt_tokens | integer | Usage en entrée |
usage.completion_tokens | integer | Usage en sortie |
usage.total_tokens | integer | Usage total |
choices[].message.refusal | string / null | Explication lorsque le modèle refuse le contenu ; généralement null pour une réponse normale |
choices[].message.annotations | array | Annotations supplémentaires du modèle, éventuellement vides |
usage peut également contenir des champs d'usage détaillés pour la facturation (cache, décomposition entrée/sortie, etc.) ; fiez-vous au retour réel. Certains canaux renvoient également des champs d'extension tels que latency_checkpoint, routing ou system_fingerprint ; le client doit ignorer les champs qu'il ne connaît pas et ne pas parser selon un ensemble de champs fixe.
Corps de réponse
{
"id": "msg_011CevNtsfivFKb6YP3WcL7A",
"model": "claude-haiku-4-5-20251001",
"object": "chat.completion",
"created": 1789071575,
"choices": [
{
"index": 0,
"message": { "role": "assistant", "content": "你好" },
"finish_reason": "stop"
}
],
"usage": {
"prompt_tokens": 20587,
"completion_tokens": 6,
"total_tokens": 20593
}
}Réponse en streaming (ajoutez "stream": true au corps de la requête ; la réponse est en text/event-stream) :
data: {"choices":[{"delta":{"content":"这是"}}]}
data: {"choices":[{"delta":{"content":"模型输出"}}]}
data: [DONE]Le client doit continuer à lire jusqu'à [DONE] ; la réponse en streaming ne doit pas être mise en cache par un intermédiaire ni concaténée en contenu dupliqué. Le dernier bloc de données peut ne contenir que usage, auquel cas choices peut être vide.
Un modèle de raisonnement peut renvoyer un contenu vide
Certains modèles de raisonnement consacrent en priorité leur quota de sortie au raisonnement masqué. Lors d'un test avec gpt-5-nano et un max_tokens trop petit, l'HTTP renvoie 200, mais message.content est vide, finish_reason vaut length et usage.completion_tokens_details.reasoning_tokens égale la limite de sortie. Dans ce cas, augmentez le quota ou utilisez un modèle de texte non raisonneur ; ne considérez pas une chaîne vide comme une panne du modèle ou un échec de l'interface.
Exemple côté serveur
const response = await fetch('https://locopalai.com/v1/chat/completions', {
method: 'POST',
headers: {
Authorization: `Bearer ${process.env.LOCOPAL_API_KEY}`,
'Content-Type': 'application/json',
},
body: JSON.stringify({
model: '从 /v1/models 选择的模型 ID',
messages: [{ role: 'user', content: '写一条产品简介。' }],
}),
})
if (!response.ok) throw new Error(await response.text())
const data = await response.json()N'intégrez pas la clé API dans le code du navigateur ; les requêtes frontend doivent d'abord passer par votre backend métier, qui les relaie ensuite.
Réponse d'erreur
{
"error": {
"code": "model_not_found",
"message": "No available channel for model xxx under group xxx (distributor) (request id: ...)",
"type": "new_api_error"
}
}| HTTP | Réponse / Cause | Traitement |
|---|---|---|
400 | {"error":{"code":"","message":"Model name not specified, model name cannot be empty (request id: ...)","type":"new_api_error"}} | Le corps de requête ne contient pas model |
401 | Invalid token | Clé API absente, incorrecte ou expirée |
503 | {"error":{"code":"model_not_found","message":"No available channel for model ..."}} | Le groupe actuel n'a aucun canal disponible pour ce modèle ; choisissez un modèle similaire ou contactez le support de la plateforme |
429 | Fréquence de requêtes limitée | Réessayez après un backoff |
Pour une description complète, voir Codes d'erreur et diagnostic.
