refactor(ai): rename llm package

This commit is contained in:
Dax Raad
2026-07-15 15:11:03 -04:00
parent b6ccb66610
commit bb15b16499
238 changed files with 209 additions and 210 deletions
+1 -1
View File
@@ -2,7 +2,7 @@ import { APICallError } from "ai"
import { STATUS_CODES } from "http"
import { iife } from "@/util/iife"
import type { ProviderV2 } from "@opencode-ai/core/provider"
import { isContextOverflow } from "@opencode-ai/llm"
import { isContextOverflow } from "@opencode-ai/ai"
export class HeaderTimeoutError extends Error {
public override readonly name = "ProviderHeaderTimeoutError"
@@ -3,7 +3,7 @@ import { Provider } from "@/provider/provider"
import { LLM } from "@/session/llm"
import { MessageID, SessionID } from "@/session/schema"
import { Slug } from "@opencode-ai/core/util/slug"
import { LLMEvent } from "@opencode-ai/llm"
import { LLMEvent } from "@opencode-ai/ai"
import { Effect, Stream } from "effect"
import { HttpApiBuilder } from "effect/unstable/httpapi"
import { InstanceHttpApi } from "../api"
+4 -4
View File
@@ -7,9 +7,9 @@ import { serviceUse } from "@opencode-ai/core/effect/service-use"
import { Context, Effect, Layer } from "effect"
import * as Stream from "effect/Stream"
import { streamText, wrapLanguageModel, type ModelMessage, type Tool } from "ai"
import type { LLMEvent } from "@opencode-ai/llm"
import { LLMClient } from "@opencode-ai/llm/route"
import type { LLMClientService } from "@opencode-ai/llm/route"
import type { LLMEvent } from "@opencode-ai/ai"
import { LLMClient } from "@opencode-ai/ai/route"
import type { LLMClientService } from "@opencode-ai/ai/route"
import { GitLabWorkflowLanguageModel } from "gitlab-ai-provider"
import { ProviderTransform } from "@/provider/transform"
import { Config } from "@/config/config"
@@ -221,7 +221,7 @@ const live: Layer.Layer<
})
: undefined
// Runtime seam: native is an opt-in adapter over @opencode-ai/llm. It
// Runtime seam: native is an opt-in adapter over @opencode-ai/ai. It
// either returns a ready LLMEvent stream or a concrete fallback reason.
if (flags.experimentalNativeLlm) {
const native = LLMNativeRuntime.stream({
+8 -8
View File
@@ -4,8 +4,8 @@
This folder contains adapters behind that service boundary:
- `ai-sdk.ts` converts AI SDK `fullStream` parts into `@opencode-ai/llm` `LLMEvent`s. This is the default runtime path.
- `native-request.ts` converts opencode's normalized session input into a native `@opencode-ai/llm` `LLMRequest`. It does not execute requests.
- `ai-sdk.ts` converts AI SDK `fullStream` parts into `@opencode-ai/ai` `LLMEvent`s. This is the default runtime path.
- `native-request.ts` converts opencode's normalized session input into a native `@opencode-ai/ai` `LLMRequest`. It does not execute requests.
- `native-runtime.ts` is the opt-in native runtime adapter. It decides whether a selected model is supported, builds the native request, bridges opencode tools into native executable tools, and delegates transport to `LLMClient` / `RequestExecutor`.
## File Structure
@@ -15,19 +15,19 @@ src/session/
llm.ts session-owned orchestration and runtime selection
llm/
AGENTS.md boundary notes for the adapter layer
ai-sdk.ts AI SDK fullStream -> @opencode-ai/llm LLMEvent adapter
native-request.ts opencode/AI SDK-shaped input -> @opencode-ai/llm LLMRequest
ai-sdk.ts AI SDK fullStream -> @opencode-ai/ai LLMEvent adapter
native-request.ts opencode/AI SDK-shaped input -> @opencode-ai/ai LLMRequest
native-runtime.ts native runtime gate, tool bridge, and LLMClient handoff
```
Integration points:
- `../llm.ts` imports `LLMClient` from `@opencode-ai/llm/route`; native execution is the only path that calls it directly.
- `../llm.ts` imports `LLMClient` from `@opencode-ai/ai/route`; native execution is the only path that calls it directly.
- `../llm.ts` imports `LLMAISDK` from `./llm/ai-sdk`; the AI SDK path still calls `streamText(...)` locally, then adapts `result.fullStream` into shared `LLMEvent`s.
- `../llm.ts` imports `LLMNativeRuntime` from `./llm/native-runtime`; this is the runtime-selection seam. Unsupported native requests return a reason and fall back to AI SDK.
- `native-runtime.ts` imports `LLMNative` from `./native-request`; this keeps request lowering separate from transport and tool execution.
- `native-request.ts` is the only adapter file that should construct `LLM.request(...)`, `LLM.model(...)`, `Message.*`, `SystemPart`, `ToolCallPart`, `ToolResultPart`, or `ToolDefinition` values from `@opencode-ai/llm`.
- `ai-sdk.ts` and `native-runtime.ts` both emit `@opencode-ai/llm` `LLMEvent`s so downstream session processing does not care which runtime handled the request.
- `native-request.ts` is the only adapter file that should construct `LLM.request(...)`, `LLM.model(...)`, `Message.*`, `SystemPart`, `ToolCallPart`, `ToolResultPart`, or `ToolDefinition` values from `@opencode-ai/ai`.
- `ai-sdk.ts` and `native-runtime.ts` both emit `@opencode-ai/ai` `LLMEvent`s so downstream session processing does not care which runtime handled the request.
Keep new integration code on one of these seams. Avoid importing session services into `native-request.ts`; pass normalized data through `RequestInput` instead.
@@ -80,7 +80,7 @@ Both runtimes converge on the same `LLMEvent` stream consumed by the session pro
╰─────────────────╯ ╰─────────────────────────────╯
```
`native-runtime.ts` evaluates the gate and either bridges into `@opencode-ai/llm` or returns control so `llm.ts` can take the AI SDK path. Tool execution stays opencode-owned in both branches; only request lowering and transport differ.
`native-runtime.ts` evaluates the gate and either bridges into `@opencode-ai/ai` or returns control so `llm.ts` can take the AI SDK path. Tool execution stays opencode-owned in both branches; only request lowering and transport differ.
Safety boundary:
+2 -2
View File
@@ -1,4 +1,4 @@
import { FinishReason, LLMEvent, ProviderMetadata, ToolResultValue } from "@opencode-ai/llm"
import { FinishReason, LLMEvent, ProviderMetadata, ToolResultValue } from "@opencode-ai/ai"
import { Effect, Schema } from "effect"
import { type streamText } from "ai"
import { errorMessage } from "@/util/error"
@@ -28,7 +28,7 @@ function providerMetadata(value: unknown): ProviderMetadata | undefined {
}
// Temporary AI SDK bridge: Copilot billing survives only in raw provider chunks here.
// Move this extraction into @opencode-ai/llm when Copilot is handled by the native runtime.
// Move this extraction into @opencode-ai/ai when Copilot is handled by the native runtime.
function copilotTotalNanoAiu(value: unknown) {
if (!value || typeof value !== "object") return
const raw = value as Record<string, unknown>
@@ -1,5 +1,5 @@
import type { JsonSchema, LLMRequest, ProviderMetadata } from "@opencode-ai/llm"
import { LLM, Message, SystemPart, ToolCallPart, ToolDefinition, ToolResultPart } from "@opencode-ai/llm"
import type { JsonSchema, LLMRequest, ProviderMetadata } from "@opencode-ai/ai"
import { LLM, Message, SystemPart, ToolCallPart, ToolDefinition, ToolResultPart } from "@opencode-ai/ai"
import {
AmazonBedrock,
Anthropic,
@@ -8,7 +8,7 @@ import {
OpenAI,
OpenAICompatible,
OpenRouter,
} from "@opencode-ai/llm/providers"
} from "@opencode-ai/ai/providers"
import type { ModelMessage } from "ai"
import type { Provider } from "@/provider/provider"
import { isRecord } from "@/util/record"
@@ -181,7 +181,7 @@ export const model = (input: Provider.Model | RequestInput, headers?: Record<str
export const request = (input: RequestInput) => {
const converted = messages(input.messages)
// This is the only native adapter boundary that should construct canonical
// @opencode-ai/llm request objects from opencode's session/AI SDK-shaped data.
// @opencode-ai/ai request objects from opencode's session/AI SDK-shaped data.
return LLM.request({
model: model(input, input.headers),
system: [...(input.system ?? []).map(SystemPart.make), ...converted.system],
@@ -15,8 +15,8 @@ import {
toDefinitions,
type JsonSchema,
type LLMEvent,
} from "@opencode-ai/llm"
import type { LLMClientShape } from "@opencode-ai/llm/route"
} from "@opencode-ai/ai"
import type { LLMClientShape } from "@opencode-ai/ai/route"
import { LLMNative } from "./native-request"
export type RuntimeStatus =
@@ -76,7 +76,7 @@ export function stream(input: StreamInput): StreamResult {
const current = statusWithFetch(input, fetch)
if (current.type === "unsupported") return current
// Integration point with @opencode-ai/llm: native-request lowers session data
// Integration point with @opencode-ai/ai: native-request lowers session data
// into an LLMRequest, then LLMClient handles route selection and transport.
//
// ProviderTransform.providerOptions builds AI-SDK-shaped options for the
@@ -171,7 +171,7 @@ export function nativeTools(tools: Record<string, Tool>, input: Pick<StreamInput
Object.entries(tools).map(([name, item]) => [
name,
// Tool execution remains opencode-owned. The native runtime only adapts
// the @opencode-ai/llm tool call back into the AI SDK Tool.execute shape.
// the @opencode-ai/ai tool call back into the AI SDK Tool.execute shape.
NativeTool.make({
description: item.description ?? "",
jsonSchema: nativeSchema(item.inputSchema),
+1 -1
View File
@@ -24,7 +24,7 @@ import { errorMessage } from "@/util/error"
import { isRecord } from "@/util/record"
import { EventV2Bridge } from "@/event-v2-bridge"
import { Database } from "@opencode-ai/core/database/database"
import { Usage, type LLMEvent } from "@opencode-ai/llm"
import { Usage, type LLMEvent } from "@opencode-ai/ai"
const DOOM_LOOP_THRESHOLD = 3
export type Result = "compact" | "stop" | "continue"
+1 -1
View File
@@ -55,7 +55,7 @@ import { eq } from "drizzle-orm"
import { SessionTable } from "@opencode-ai/core/session/sql"
import { SessionReminders } from "./reminders"
import { SessionTools } from "./tools"
import { LLMEvent } from "@opencode-ai/llm"
import { LLMEvent } from "@opencode-ai/ai"
// @ts-ignore
globalThis.AI_SDK_LOG_WARNINGS = false
+1 -1
View File
@@ -9,7 +9,7 @@ import { serviceUse } from "@opencode-ai/core/effect/service-use"
import path from "path"
import { Job } from "@/job"
import { Decimal } from "decimal.js"
import type { ProviderMetadata, Usage } from "@opencode-ai/llm"
import type { ProviderMetadata, Usage } from "@opencode-ai/ai"
import { InstallationVersion } from "@opencode-ai/core/installation/version"
import { Database } from "@opencode-ai/core/database/database"
import { EventV2Bridge } from "@/event-v2-bridge"