Інтеграція OpenAI Structured Outputs для парсингу відповідей

Проектуємо та впроваджуємо системи штучного інтелекту: від прототипу до production-ready рішення. Наша команда поєднує експертизу в машинному навчанні, дата-інжинірингу та MLOps, щоб AI працював не в лабораторії, а в реальному бізнесі.
Показано 1 з 1Усі 1566 послуг
Інтеграція OpenAI Structured Outputs для парсингу відповідей
Простий
~1 день
Часті запитання

Напрямки AI-розробки

Етапи розробки AI-рішення

Останні роботи

  • image_website-b2b-advance_0.webp
    Розробка сайту компанії B2B ADVANCE
    1284
  • image_web-applications_feedme_466_0.webp
    Розробка веб-додатків для компанії FEEDME
    1196
  • image_websites_belfingroup_462_0.webp
    Розробка веб-сайту для компанії БЕЛФІНГРУП
    901
  • image_ecommerce_furnoro_435_0.webp
    Розробка інтернет магазину для компанії FURNORO
    1119
  • image_logo-advance_0.webp
    Розробка логотипу компанії B2B Advance
    586
  • image_crm_enviok_479_0.webp
    Розробка веб-додатків для компанії Enviok
    853

Інтеграція OpenAI Structured Outputs для парсингу відповідей

Structured Outputs гарантує, що відповідь моделі точно відповідає заданій JSON-схемі. На відміну від response_format: json_object (що просто просить повернути JSON), Structured Outputs забезпечує відповідність конкретній схемі через constrained decoding — модель фізично не може повернути невалідний JSON.

Базова інтеграція з Pydantic

from openai import OpenAI
from pydantic import BaseModel
from typing import Literal, Optional

client = OpenAI()

# Схема для добування даних
class Invoice(BaseModel):
    vendor_name: str
    invoice_number: str
    date: str
    total_amount: float
    currency: str
    line_items: list["InvoiceItem"]
    vat_amount: Optional[float] = None

class InvoiceItem(BaseModel):
    description: str
    quantity: float
    unit_price: float
    total: float

Invoice.model_rebuild()  # Необхідно для forward references

# Парсинг — гарантована відповідність схемі
def extract_invoice(text: str) -> Invoice:
    response = client.beta.chat.completions.parse(
        model="gpt-4o",
        messages=[
            {"role": "system", "content": "Добути дані рахунку з тексту"},
            {"role": "user", "content": text}
        ],
        response_format=Invoice,
    )
    return response.choices[0].message.parsed  # Відразу об'єкт Pydantic

Класифікація з Enum

from enum import Enum

class TicketCategory(str, Enum):
    technical = "technical"
    billing = "billing"
    feature_request = "feature_request"
    complaint = "complaint"
    general = "general"

class TicketClassification(BaseModel):
    category: TicketCategory
    priority: Literal["low", "medium", "high", "critical"]
    sentiment: Literal["positive", "neutral", "negative", "angry"]
    requires_human: bool
    summary: str
    tags: list[str]

def classify_ticket(text: str) -> TicketClassification:
    response = client.beta.chat.completions.parse(
        model="gpt-4o-mini",  # Structured Outputs доступні і в mini
        messages=[{"role": "user", "content": f"Класифікуй тікет: {text}"}],
        response_format=TicketClassification,
        temperature=0,
    )
    return response.choices[0].message.parsed

Structured Outputs через JSON Schema (без Pydantic)

# Для мов без Pydantic або складних схем
response = client.chat.completions.create(
    model="gpt-4o",
    messages=[{"role": "user", "content": "Дані продукту"}],
    response_format={
        "type": "json_schema",
        "json_schema": {
            "name": "product_data",
            "strict": True,
            "schema": {
                "type": "object",
                "properties": {
                    "name": {"type": "string"},
                    "price": {"type": "number"},
                    "in_stock": {"type": "boolean"},
                    "categories": {
                        "type": "array",
                        "items": {"type": "string"}
                    }
                },
                "required": ["name", "price", "in_stock", "categories"],
                "additionalProperties": False,
            }
        }
    }
)
import json
data = json.loads(response.choices[0].message.content)

Обмеження Structured Outputs

  • strict: True вимагає additionalProperties: False на всіх рівнях
  • Не підтримуються: nullable поля через "type": ["string", "null"] (використовуйте anyOf)
  • Максимальна вкладеність: 5 рівнів
  • Для рекурсивних схем — використовувати $ref

Коли використовувати

Сценарій Метод
Добування даних з документів Structured Outputs
Класифікація Structured Outputs
Відповіді з передбачуваною структурою Structured Outputs
Вільний JSON (невідома структура) json_object mode
Прості відповіді Звичайний текст

Строки реалізації

  • Базове добування з Pydantic: 0.5–1 день
  • Комплексні вкладені схеми: 1–2 дні