chore(vendor): import pi 1.3.0
Imported as a linear vendor commit so forge rebases do not replay the upstream root tree. git-subtree-dir: third_party/pi git-subtree-split: 71023aec1546d6d677a65669c5665c0927ce0dd0
This commit is contained in:
@@ -3,18 +3,12 @@ import { describe, expect, it } from "vitest";
|
||||
import { streamSimple as streamSimpleGoogle } from "../src/api/google-generative-ai.ts";
|
||||
import { resolveGoogleThinkingLevel } from "../src/api/google-shared.ts";
|
||||
import { streamSimple as streamSimpleVertex } from "../src/api/google-vertex.ts";
|
||||
import type {
|
||||
Context,
|
||||
Model,
|
||||
ModelThinkingLevel,
|
||||
ThinkingBudgets,
|
||||
ThinkingLevel,
|
||||
ThinkingLevelMap,
|
||||
} from "../src/types.ts";
|
||||
import type { Model, ThinkingBudgets, ThinkingLevel, ThinkingLevelMap } from "../src/types.ts";
|
||||
import { normalizeContext } from "../src/utils/transcript.ts";
|
||||
|
||||
const context: Context = {
|
||||
const context = normalizeContext({
|
||||
messages: [{ role: "user", content: "Hello", timestamp: 0 }],
|
||||
};
|
||||
});
|
||||
|
||||
function googleModel(id: string, thinkingLevelMap: ThinkingLevelMap): Model<"google-generative-ai"> {
|
||||
return {
|
||||
@@ -50,7 +44,7 @@ function vertexModel(id: string, thinkingLevelMap: ThinkingLevelMap): Model<"goo
|
||||
|
||||
async function captureGooglePayload(
|
||||
model: Model<"google-generative-ai">,
|
||||
reasoning: ThinkingLevel,
|
||||
reasoning?: ThinkingLevel,
|
||||
thinkingBudgets?: ThinkingBudgets,
|
||||
): Promise<GenerateContentParameters> {
|
||||
let payload: GenerateContentParameters | undefined;
|
||||
@@ -71,7 +65,7 @@ async function captureGooglePayload(
|
||||
|
||||
async function captureVertexPayload(
|
||||
model: Model<"google-vertex">,
|
||||
reasoning: ThinkingLevel,
|
||||
reasoning?: ThinkingLevel,
|
||||
thinkingBudgets?: ThinkingBudgets,
|
||||
): Promise<GenerateContentParameters> {
|
||||
let payload: GenerateContentParameters | undefined;
|
||||
@@ -90,19 +84,29 @@ async function captureVertexPayload(
|
||||
return payload;
|
||||
}
|
||||
|
||||
const googleAdapters = [
|
||||
{
|
||||
name: "Google Generative AI",
|
||||
capture: (id: string, thinkingLevelMap: ThinkingLevelMap, reasoning?: ThinkingLevel) =>
|
||||
captureGooglePayload(googleModel(id, thinkingLevelMap), reasoning),
|
||||
},
|
||||
{
|
||||
name: "Google Vertex",
|
||||
capture: (id: string, thinkingLevelMap: ThinkingLevelMap, reasoning?: ThinkingLevel) =>
|
||||
captureVertexPayload(vertexModel(id, thinkingLevelMap), reasoning),
|
||||
},
|
||||
] as const;
|
||||
|
||||
describe("Google thinking level maps", () => {
|
||||
it("exhaustively resolves supported logical levels and mapping values", () => {
|
||||
const defaultExpectations = {
|
||||
off: "high",
|
||||
minimal: "minimal",
|
||||
low: "low",
|
||||
medium: "medium",
|
||||
high: "high",
|
||||
} as const satisfies Partial<Record<ModelThinkingLevel, ThinkingLevel>>;
|
||||
} as const satisfies Partial<Record<ThinkingLevel, ThinkingLevel>>;
|
||||
for (const [level, expected] of Object.entries(defaultExpectations)) {
|
||||
expect(resolveGoogleThinkingLevel(googleModel("gemini-3.7-flash", {}), level as ModelThinkingLevel)).toBe(
|
||||
expected,
|
||||
);
|
||||
expect(resolveGoogleThinkingLevel(googleModel("gemini-3.7-flash", {}), level as ThinkingLevel)).toBe(expected);
|
||||
}
|
||||
|
||||
const mappedExpectations = {
|
||||
@@ -131,6 +135,44 @@ describe("Google thinking level maps", () => {
|
||||
);
|
||||
});
|
||||
|
||||
// Regression test for https://github.com/earendil-works/pi/issues/9455
|
||||
it.each(googleAdapters)("uses the lowest supported $name level when reasoning is omitted", async ({ capture }) => {
|
||||
const payload = await capture("gemini-3.8-flash", {
|
||||
off: null,
|
||||
minimal: null,
|
||||
low: "low",
|
||||
medium: "medium",
|
||||
high: "high",
|
||||
xhigh: null,
|
||||
max: null,
|
||||
});
|
||||
|
||||
expect(payload.config?.thinkingConfig).toEqual({ thinkingLevel: "LOW" });
|
||||
});
|
||||
|
||||
it.each(googleAdapters)("preserves native medium effort for Gemini 3.1 Pro on $name", async ({ capture }) => {
|
||||
const payload = await capture(
|
||||
"gemini-3.1-pro-preview",
|
||||
{ off: null, minimal: null, low: "low", medium: "medium", high: "high", xhigh: null, max: null },
|
||||
"medium",
|
||||
);
|
||||
|
||||
expect(payload.config?.thinkingConfig).toEqual({ includeThoughts: true, thinkingLevel: "MEDIUM" });
|
||||
});
|
||||
|
||||
it.each(googleAdapters)("disables Gemini 2.5 thinking when reasoning is omitted on $name", async ({ capture }) => {
|
||||
const payload = await capture("gemini-2.5-flash", {});
|
||||
|
||||
expect(payload.config?.thinkingConfig).toEqual({ thinkingBudget: 0 });
|
||||
});
|
||||
|
||||
// Regression test for https://github.com/earendil-works/pi/issues/10890
|
||||
it.each(googleAdapters)("uses thinking levels for Gemini 4 models on $name", async ({ capture }) => {
|
||||
const payload = await capture("gemini-4-argon", {}, "medium");
|
||||
|
||||
expect(payload.config?.thinkingConfig).toEqual({ includeThoughts: true, thinkingLevel: "MEDIUM" });
|
||||
});
|
||||
|
||||
it.each(["xhigh", "max"] as const)("maps Google Generative AI %s to a supported level", async (reasoning) => {
|
||||
const payload = await captureGooglePayload(
|
||||
googleModel("gemini-3.7-flash", { xhigh: "high", max: "high" }),
|
||||
|
||||
Reference in New Issue
Block a user