Skip to content

Commit

Permalink
fix up structured outputs and add examples
Browse files Browse the repository at this point in the history
  • Loading branch information
EvanBoyle committed Feb 1, 2025
1 parent 5c58650 commit 67521b4
Show file tree
Hide file tree
Showing 2 changed files with 103 additions and 15 deletions.
102 changes: 89 additions & 13 deletions examples/openai-vNext/index.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,9 @@
import { CompositionCompletion, GSXTool, OpenAIProvider } from "@gensx/openai";
import {
CompositionCompletion,
GSXStructuredOutput,
GSXTool,
OpenAIProvider,
} from "@gensx/openai";
import { gsx } from "gensx";
import {
ChatCompletion as ChatCompletionOutput,
Expand Down Expand Up @@ -151,26 +156,97 @@ async function streamingCompletion() {
return results;
}

// async function toolsSync() {}
async function structuredOutput() {
// Define a schema for rating trash bins
const trashRatingSchema = z.object({
bins: z.array(
z.object({
location: z.string().describe("Location of the trash bin"),
rating: z.number().describe("Rating from 1-10"),
review: z.string().describe("A sassy review of the trash bin"),
bestFinds: z
.array(z.string())
.describe("List of the best items found in this bin"),
}),
),
overallVerdict: z
.string()
.describe("Overall verdict on the neighborhood's trash quality"),
});

// async function toolsStreaming() {}
type TrashRating = z.infer<typeof trashRatingSchema>;

async function main() {
// const results = await basicCompletion();
// console.log(results.choices[0].message.content);
// Create a structured output wrapper
const structuredOutput = new GSXStructuredOutput(trashRatingSchema, {
description: "Rate and review different trash bins in a neighborhood",
examples: [
{
bins: [
{
location: "Behind the fancy restaurant",
rating: 9,
review: "Michelin star garbage, simply exquisite!",
bestFinds: ["day-old croissants", "barely touched sushi"],
},
],
overallVerdict:
"High-class neighborhood with refined taste in leftovers",
},
],
});

const results = await gsx.execute<TrashRating>(
<OpenAIProvider apiKey={process.env.OPENAI_API_KEY}>
<CompositionCompletion
messages={[
{
role: "system",
content:
"you are a trash eating infrastructure engineer embodied as a racoon. Be sassy and fun.",
},
{
role: "user",
content:
"Rate and review three different trash bins in the neighborhood. Be creative with the locations!",
},
]}
model="gpt-4o-mini"
temperature={0.7}
structuredOutput={structuredOutput}
/>
</OpenAIProvider>,
);

// const stream = await streamingCompletion();
// for await (const chunk of stream) {
// process.stdout.write(chunk.choices[0].delta.content ?? "");
// }
return results;
}

// const results = await tools();
// console.log(results.choices[0].message.content);
async function main() {
console.log("basic completion 🔥");
const r = await basicCompletion();
console.log(r.choices[0].message.content);

const stream = await toolsStreaming();
console.log("streaming completion 🔥");
const stream = await streamingCompletion();
for await (const chunk of stream) {
process.stdout.write(chunk.choices[0].delta.content ?? "");
}
console.log("\n");

console.log("tools completion 🔥");
const results = await tools();
console.log(results.choices[0].message.content);

console.log("tools streaming completion 🔥");
const s2 = await toolsStreaming();
for await (const chunk of s2) {
process.stdout.write(chunk.choices[0].delta.content ?? "");
}
console.log("\n");

console.log("structured output completion 🔥");
const structured = await structuredOutput();
console.log(structured.overallVerdict);
console.log(structured);
}

main().catch(console.error);
16 changes: 14 additions & 2 deletions packages/gensx-openai/src/composition.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -245,15 +245,27 @@ export const ToolTransform = gsx.Component<
return completion;
}

// Execute tools and get final completion
return gsx.execute<ChatCompletionOutput>(
// Execute tools
const toolResponses = await gsx.execute<ChatCompletionMessageParam[]>(
<ToolExecutor
tools={tools}
toolCalls={toolCalls}
messages={[...rest.messages, completion.choices[0].message]}
model={rest.model}
/>,
);

// Make final completion with tool results
return gsx.execute<ChatCompletionOutput>(
<RawCompletion
{...rest}
messages={[
...rest.messages,
completion.choices[0].message,
...toolResponses,
]}
/>,
);
});

// Structured output transform component
Expand Down

0 comments on commit 67521b4

Please sign in to comment.