Прескокни до содржината
Структурирани излези

Структурирани излези

Побарајте го одговорот како JSON: кој било JSON објект, или JSON што следи schema што ја испраќате. Користете го кога одговорот го чита програма, а не човек.

POST https://api.shannon-ai.com/v1/chat/completions

import json
from openai import OpenAI

client = OpenAI(api_key="YOUR_API_KEY", base_url="https://api.shannon-ai.com/v1")

response = client.chat.completions.create(
    model="Kimi-K3-3BIT-REAP",
    messages=[
        {"role": "user", "content": "Extract the person: John Doe, 30 years old, engineer."}
    ],
    response_format={
        "type": "json_schema",
        "json_schema": {
            "name": "person",
            "strict": True,
            "schema": {
                "type": "object",
                "properties": {
                    "name": {"type": "string"},
                    "age": {"type": "integer"},
                    "occupation": {"type": "string"},
                },
                "required": ["name", "age", "occupation"],
            },
        },
    },
)

# The JSON arrives as text in message.content: parse it, then check it.
try:
    person = json.loads(response.choices[0].message.content)
except json.JSONDecodeError:
    person = None  # ask again, or report the failure

print(person)

JSON-от е текстот на одговорот, во choices[0].message.content:

200 JSON
{
  "id": "chatcmpl-0c4e7a1b9d2f4e6a8b3c5d7e9f1a2b3c",
  "object": "chat.completion",
  "created": 1791590400,
  "model": "Kimi-K3-3BIT-REAP",
  "choices": [
    {
      "index": 0,
      "message": {
        "role": "assistant",
        "content": "{\"name\":\"John Doe\",\"age\":30,\"occupation\":\"engineer\"}",
        "reasoning_content": null
      },
      "finish_reason": "stop"
    }
  ],
  "usage": {
    "prompt_tokens": 96,
    "completion_tokens": 19,
    "total_tokens": 115,
    "prompt_tokens_details": {"cached_tokens": 0},
    "completion_tokens_details": {"reasoning_tokens": 0}
  }
}

Режимите на response_format

response_format е поле на /v1/chat/completions. Без него одговорот е обичен текст.

Режим Вредност Што добивате
JSON објект {"type": "json_object"} Одговорот е JSON без пропишан облик. Во prompt-от кажете кои клучеви ги сакате.
JSON schema {"type": "json_schema", "json_schema": {"name": "…", "schema": {…}}} Одговорот ја следи schema што ја испраќате: нејзините клучеви, типови и задолжителни полиња.
Strict "strict": true Поле на json_schema, а не трет режим. Е true освен ако не испратите false.
Поле Тип Стандардно Опис Го применуваат
type string json_object или json_schema. Задолжително во response_format. text се прифаќа и дава обичен текстуален одговор. Секој модел што го прима режимот
json_schema.schema object JSON Schema што одговорот ја следи. Испратете ја секогаш кога type е json_schema. Секој модел што го прима режимот
json_schema.name string Ознака за schema, како во форматот на OpenAI. Хостирани open-weight модели
json_schema.strict boolean true Дали одговорот мора точно да ја следи schema. Моделите Shannon ја применуваат секоја schema како strict. Хостирани open-weight модели

Режимот JSON објект не бара schema. Наведете ги клучевите во prompt-от:

Тело на барање
{
  "model": "shannon-3",
  "messages": [
    {
      "role": "user",
      "content": "Name the capital of France. Answer as JSON with the keys city and country."
    }
  ],
  "response_format": {"type": "json_object"}
}

Поддршка по модел

Модел json_object json_schema
Секој модел Shannon (shannon-*) Да Да
Хостирани open-weight модели, освен оние наведени подолу Да Да
Laguna-S-2.1-W4A16-AUTOROUND-REAP — —
inkling-W4A16-AUTOROUND-REAP Да —

GET /v1/models го пријавува истото по ид: capabilities.json_schema на секој модел и capabilities.response_format на хостираните open-weight модели. Модели и цени

Поддржани клучни зборови на schema

Што моделот добива од вашата schema зависи од моделот и од ендпоинтот:

Модели /v1/chat/completions /v1/responses
Модели Shannon Подмножината клучни зборови подолу, применета како strict. Schema каква што ја испраќате, применета како strict.
Хостирани open-weight модели Schema каква што ја испраќате. strict е true освен ако не го испратите. Schema каква што ја испраќате. strict е true освен ако не го испратите.

Подмножината клучни зборови на моделите Shannon на /v1/chat/completions:

Клучен збор Како се чита
Прочитани клучни зборови type, format, title, description, nullable, enum, items, properties, required, minItems, maxItems, minimum, maximum, minLength, maxLength, pattern, anyOf, default
$ref Се разрешува од $defs или definitions на највисокото ниво на schema. Клучните зборови напишани покрај $ref, како description, се задржуваат. Референца без соодветна дефиниција се чита како {"type": "object"}.
allOf Членовите се спојуваат во една schema. Каде што два члена го поставуваат истиот клучен збор, важи подоцнежниот.
oneOf Се чита како anyOf.
Schema што упатуваат на себе Се проширува до 24 нивоа. Подлабоко ниво се чита како {"type": "object"}.
Надвор од подмножината Секој друг клучен збор, на пример additionalProperties, const, multipleOf, uniqueItems, exclusiveMinimum, exclusiveMaximum, patternProperties, prefixItems, minProperties, maxProperties, not и if / then / else. Тие не се дел од schema што ја добива моделот.

Кај /v1/responses: полето text.format

/v1/responses го запишува истото барање како text.format. Schema е директно во format, покрај name и strict, а не под клуч json_schema. За режимот JSON објект испратете {"format": {"type": "json_object"}}.

Тело на барање
{
  "model": "Kimi-K3-3BIT-REAP",
  "input": "Extract the person: John Doe, 30 years old, engineer.",
  "text": {
    "format": {
      "type": "json_schema",
      "name": "person",
      "strict": true,
      "schema": {
        "type": "object",
        "properties": {
          "name": {"type": "string"},
          "age": {"type": "integer"},
          "occupation": {"type": "string"}
        },
        "required": ["name", "age", "occupation"]
      }
    }
  }
}

JSON-от е text на делот output_text од ставката message:

200 JSON
{
  "output": [
    {
      "id": "msg_7e1d3c5b9a2f4d6e8c0b1a3f5e7d9c2b",
      "type": "message",
      "role": "assistant",
      "status": "completed",
      "content": [
        {
          "type": "output_text",
          "text": "{\"name\":\"John Doe\",\"age\":30,\"occupation\":\"engineer\"}",
          "annotations": []
        }
      ]
    }
  ]
}

Поддршката по модел и грешките се исти како на /v1/chat/completions. Responses API

На /v1/messages: алатка како schema

Форматот Messages нема поле за структуриран излез. За JSON од истите модели, повикајте /v1/chat/completions или /v1/responses со истиот клуч.

За да останете на /v1/messages, опишете го објектот како алатка: ставете ја вашата schema во input_schema и именувајте ја алатката во tool_choice. input на блокот tool_use тогаш е вашиот објект, веќе парсиран. Именуван tool_choice го применуваат хостираните open-weight модели.

Тело на барање
{
  "model": "Kimi-K3-3BIT-REAP",
  "max_tokens": 1024,
  "messages": [
    {
      "role": "user",
      "content": "Extract the person: John Doe, 30 years old, engineer."
    }
  ],
  "tools": [
    {
      "name": "record_person",
      "description": "Record the extracted person.",
      "input_schema": {
        "type": "object",
        "properties": {
          "name": {"type": "string"},
          "age": {"type": "integer"},
          "occupation": {"type": "string"}
        },
        "required": ["name", "age", "occupation"]
      }
    }
  ],
  "tool_choice": {"type": "tool", "name": "record_person"}
}
200 JSON
{
  "stop_reason": "tool_use",
  "content": [
    {
      "type": "tool_use",
      "id": "toolu_4b8d2f6a1c3e4a5b9d7f0e2c4a6b8d1f",
      "name": "record_person",
      "input": {"name": "John Doe", "age": 30, "occupation": "engineer"}
    }
  ]
}

Проверете дали stop_reason е tool_use пред да го прочитате блокот. Повик на функции

Како пристигнува JSON-от

  • JSON-от е стринг. Покрај одговорот нема парсиран објект: пуштете го вашиот JSON парсер врз message.content.
  • Со stream: true JSON-от пристигнува во парчиња delta.content. Спојте ги и парсирајте откако streaming-от ќе заврши; парче само по себе не е валиден JSON.
  • Хостиран open-weight модел го одговара барањето со response_format без текст на reasoning: reasoning_content е null.

Проверете го она што го добивате

Schema го насочува начинот на кој моделот пишува. API-то не го споредува готовиот одговор со вашата schema, па вашиот код ја прави конечната проверка:

  • Парсирајте во ракувач на грешки, како примерот на врвот.
  • Валидирајте го парсираниот објект со истата schema во вашиот код, на пример со библиотека за JSON Schema, Pydantic или Zod.
  • Долг одговор може да заврши пред JSON-от да биде комплетен. Одговор без streaming пријавува finish_reason само како stop или tool_calls, па грешката при парсирање е сигналот. Прашајте повторно, или побарајте помал објект.

Грешки

Статус Тип Порака Кога
400 invalid_request_error <id> does not accept response_format Моделот не прима ниту еден од двата режими.
400 invalid_request_error <id> does not accept response_format json_schema; use json_object Моделот прима json_object, а вие испративте json_schema.
422 invalid_request_error Failed to deserialize the JSON body into the target type: … response_format нема type, или не е JSON објект.

Двата одговори 400 се испраќаат пред да се наплати нешто од вашето салдо. Ракување со грешки