Structured Outputs ensure that the model always follows your supplied JSON schema. Portkey supports OpenAI’s Structured Outputs feature out of the box with our SDKs & APIs.
Structured Outputs is different from OpenAI’s JSON Mode as well as Function Calling. Check out this table for a quick comparison.
Portkey SDKs for Python and JavaScript also make it easy to define object schemas using Pydantic and Zod respectively. Below, you can see how to extract information from unstructured text that conforms to a schema defined in code.
Copy
Ask AI
from portkey_ai import Portkeyfrom pydantic import BaseModelclass Step(BaseModel): explanation: str output: strclass MathReasoning(BaseModel): steps: list[Step] final_answer: strportkey = Portkey( api_key="PORTKEY_API_KEY", virtual_key="OPENAI_VIRTUAL_KEY")completion = portkey.beta.chat.completions.parse( model="gpt-4o-2024-08-06", messages=[ {"role": "system", "content": "You are a helpful math tutor. Guide the user through the solution step by step."}, {"role": "user", "content": "how can I solve 8x + 7 = -23"} ], response_format=MathReasoning,)print(completion.choices[0].message)print(completion.choices[0].message.parsed)
Copy
Ask AI
from portkey_ai import Portkeyfrom pydantic import BaseModelclass Step(BaseModel): explanation: str output: strclass MathReasoning(BaseModel): steps: list[Step] final_answer: strportkey = Portkey( api_key="PORTKEY_API_KEY", virtual_key="OPENAI_VIRTUAL_KEY")completion = portkey.beta.chat.completions.parse( model="gpt-4o-2024-08-06", messages=[ {"role": "system", "content": "You are a helpful math tutor. Guide the user through the solution step by step."}, {"role": "user", "content": "how can I solve 8x + 7 = -23"} ], response_format=MathReasoning,)print(completion.choices[0].message)print(completion.choices[0].message.parsed)
Copy
Ask AI
import { Portkey } from 'portkey-ai';import { z } from 'zod';import { zodResponseFormat } from "openai/helpers/zod";const MathReasoning = z.object({ steps: z.array(z.object({ explanation: z.string(), output: z.string() })), final_answer: z.string()});const portkey = new Portkey({ apiKey: "YOUR_API_KEY", virtualKey: "YOUR_VIRTUAL_KEY"});async function runMathTutor() { try { const completion = await portkey.chat.completions.create({ model: "gpt-4o-2024-08-06", messages: [ { role: "system", content: "You are a helpful math tutor." }, { role: "user", content: "Solve 8x + 7 = -23" } ], response_format: zodResponseFormat(MathReasoning, "MathReasoning") }); console.log(completion.choices[0].message.content); } catch (error) { console.error("Error:", error); }}runMathTutor();
The second approach, shown in the subsequent examples, uses a JSON schema directly in the API call. This method is more portable across different languages and doesn’t require additional libraries, but lacks the integrated type checking of the Pydantic/Zod approach. Choose the method that best fits your project’s needs and language ecosystem.