diff --git a/packages/opencode/script/seed-e2e.ts b/packages/opencode/script/seed-e2e.ts index ba2155cb692..d2333414488 100644 --- a/packages/opencode/script/seed-e2e.ts +++ b/packages/opencode/script/seed-e2e.ts @@ -12,6 +12,7 @@ const seed = async () => { const { InstanceBootstrap } = await import("../src/project/bootstrap") const { Session } = await import("../src/session") const { Identifier } = await import("../src/id/id") + const { MessageID } = await import("../src/session/schema") const { Project } = await import("../src/project/project") await Instance.provide({ @@ -19,7 +20,7 @@ const seed = async () => { init: InstanceBootstrap, fn: async () => { const session = await Session.create({ title }) - const messageID = Identifier.descending("message") + const messageID = MessageID.ascending() const partID = Identifier.descending("part") const message = { id: messageID, diff --git a/packages/opencode/src/cli/cmd/debug/agent.ts b/packages/opencode/src/cli/cmd/debug/agent.ts index fe300348597..47e1d36373f 100644 --- a/packages/opencode/src/cli/cmd/debug/agent.ts +++ b/packages/opencode/src/cli/cmd/debug/agent.ts @@ -5,6 +5,7 @@ import { Provider } from "../../../provider/provider" import { Session } from "../../../session" import type { MessageV2 } from "../../../session/message-v2" import { Identifier } from "../../../id/id" +import { MessageID } from "../../../session/schema" import { ToolRegistry } from "../../../tool/registry" import { Instance } from "../../../project/instance" import { PermissionNext } from "../../../permission/next" @@ -113,7 +114,7 @@ function parseToolParams(input?: string) { async function createToolContext(agent: Agent.Info) { const session = await Session.create({ title: `Debug tool run (${agent.name})` }) - const messageID = Identifier.ascending("message") + const messageID = MessageID.ascending() const model = agent.model ?? (await Provider.defaultModel()) const now = Date.now() const message: MessageV2.Assistant = { diff --git a/packages/opencode/src/cli/cmd/github.ts b/packages/opencode/src/cli/cmd/github.ts index ad893ce4f3e..af9ff4a4289 100644 --- a/packages/opencode/src/cli/cmd/github.ts +++ b/packages/opencode/src/cli/cmd/github.ts @@ -24,6 +24,7 @@ import { bootstrap } from "../bootstrap" import { Session } from "../../session" import type { SessionID } from "../../session/schema" import { Identifier } from "../../id/id" +import { MessageID } from "../../session/schema" import { Provider } from "../../provider/provider" import { Bus } from "../../bus" import { MessageV2 } from "../../session/message-v2" @@ -935,7 +936,7 @@ export const GithubRunCommand = cmd({ const result = await SessionPrompt.prompt({ sessionID: session.id, - messageID: Identifier.ascending("message"), + messageID: MessageID.ascending(), variant, model: { providerID, @@ -989,7 +990,7 @@ export const GithubRunCommand = cmd({ console.log("Requesting summary from agent...") const summary = await SessionPrompt.prompt({ sessionID: session.id, - messageID: Identifier.ascending("message"), + messageID: MessageID.ascending(), variant, model: { providerID, diff --git a/packages/opencode/src/cli/cmd/import.ts b/packages/opencode/src/cli/cmd/import.ts index f06b8f39fe0..12beafef11c 100644 --- a/packages/opencode/src/cli/cmd/import.ts +++ b/packages/opencode/src/cli/cmd/import.ts @@ -1,7 +1,7 @@ import type { Argv } from "yargs" import type { Session as SDKSession, Message, Part } from "@opencode-ai/sdk/v2" import { Session } from "../../session" -import { SessionID } from "../../session/schema" +import { SessionID, MessageID } from "../../session/schema" import { cmd } from "./cmd" import { bootstrap } from "../bootstrap" import { Database } from "../../storage/db" @@ -158,6 +158,9 @@ export const ImportCommand = cmd({ id: SessionID.make(exportData.info.id), parentID: exportData.info.parentID ? SessionID.make(exportData.info.parentID) : undefined, projectID: Instance.project.id, + revert: exportData.info.revert + ? { ...exportData.info.revert, messageID: MessageID.make(exportData.info.revert.messageID) } + : undefined, }) Database.use((db) => db @@ -168,28 +171,30 @@ export const ImportCommand = cmd({ ) for (const msg of exportData.messages) { + const { id: _mid, sessionID: _msid, ...msgData } = msg.info Database.use((db) => db .insert(MessageTable) .values({ - id: msg.info.id, + id: MessageID.make(msg.info.id), session_id: row.id, time_created: msg.info.time?.created ?? Date.now(), - data: msg.info, + data: msgData, }) .onConflictDoNothing() .run(), ) for (const part of msg.parts) { + const { id: _pid, sessionID: _psid, messageID: _pmid, ...partData } = part Database.use((db) => db .insert(PartTable) .values({ id: part.id, - message_id: msg.info.id, + message_id: MessageID.make(msg.info.id), session_id: row.id, - data: part, + data: partData, }) .onConflictDoNothing() .run(), diff --git a/packages/opencode/src/cli/cmd/tui/component/prompt/index.tsx b/packages/opencode/src/cli/cmd/tui/component/prompt/index.tsx index 2d99051fb97..9923cd3fabb 100644 --- a/packages/opencode/src/cli/cmd/tui/component/prompt/index.tsx +++ b/packages/opencode/src/cli/cmd/tui/component/prompt/index.tsx @@ -10,6 +10,7 @@ import { useSDK } from "@tui/context/sdk" import { useRoute } from "@tui/context/route" import { useSync } from "@tui/context/sync" import { Identifier } from "@/id/id" +import { MessageID } from "@/session/schema" import { createStore, produce } from "solid-js/store" import { useKeybind } from "@tui/context/keybind" import { usePromptHistory, type PromptInfo } from "./history" @@ -561,7 +562,7 @@ export function Prompt(props: PromptProps) { sessionID = res.data.id } - const messageID = Identifier.ascending("message") + const messageID = MessageID.ascending() let inputText = store.prompt.input // Expand pasted text inline before submitting diff --git a/packages/opencode/src/command/index.ts b/packages/opencode/src/command/index.ts index 3f9f25e1dc4..2c47984fdd8 100644 --- a/packages/opencode/src/command/index.ts +++ b/packages/opencode/src/command/index.ts @@ -1,5 +1,5 @@ import { BusEvent } from "@/bus/bus-event" -import { SessionID } from "@/session/schema" +import { SessionID, MessageID } from "@/session/schema" import z from "zod" import { Config } from "../config/config" import { Instance } from "../project/instance" @@ -17,7 +17,7 @@ export namespace Command { name: z.string(), sessionID: SessionID.zod, arguments: z.string(), - messageID: Identifier.schema("message"), + messageID: MessageID.zod, }), ), } diff --git a/packages/opencode/src/permission/index.ts b/packages/opencode/src/permission/index.ts index 16a94ec54d8..8a2ba64e117 100644 --- a/packages/opencode/src/permission/index.ts +++ b/packages/opencode/src/permission/index.ts @@ -1,6 +1,6 @@ import { BusEvent } from "@/bus/bus-event" import { Bus } from "@/bus" -import { SessionID } from "@/session/schema" +import { SessionID, MessageID } from "@/session/schema" import z from "zod" import { Log } from "../util/log" import { Identifier } from "../id/id" @@ -26,7 +26,7 @@ export namespace Permission { type: z.string(), pattern: z.union([z.string(), z.array(z.string())]).optional(), sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, callID: z.string().optional(), message: z.string(), metadata: z.record(z.string(), z.any()), diff --git a/packages/opencode/src/permission/next.ts b/packages/opencode/src/permission/next.ts index 6bfe0035ba8..2d665a832a4 100644 --- a/packages/opencode/src/permission/next.ts +++ b/packages/opencode/src/permission/next.ts @@ -2,7 +2,7 @@ import { Bus } from "@/bus" import { BusEvent } from "@/bus/bus-event" import { Config } from "@/config/config" import { Identifier } from "@/id/id" -import { SessionID } from "@/session/schema" +import { SessionID, MessageID } from "@/session/schema" import { Instance } from "@/project/instance" import { Database, eq } from "@/storage/db" import { PermissionTable } from "@/session/session.sql" @@ -77,7 +77,7 @@ export namespace PermissionNext { always: z.string().array(), tool: z .object({ - messageID: z.string(), + messageID: MessageID.zod, callID: z.string(), }) .optional(), diff --git a/packages/opencode/src/question/index.ts b/packages/opencode/src/question/index.ts index ba1fc66506b..2142fe183fc 100644 --- a/packages/opencode/src/question/index.ts +++ b/packages/opencode/src/question/index.ts @@ -1,7 +1,7 @@ import { Bus } from "@/bus" import { BusEvent } from "@/bus/bus-event" import { Identifier } from "@/id/id" -import { SessionID } from "@/session/schema" +import { SessionID, MessageID } from "@/session/schema" import { Instance } from "@/project/instance" import { Log } from "@/util/log" import z from "zod" @@ -39,7 +39,7 @@ export namespace Question { questions: z.array(Info).describe("Questions to ask"), tool: z .object({ - messageID: z.string(), + messageID: MessageID.zod, callID: z.string(), }) .optional(), @@ -98,7 +98,7 @@ export namespace Question { export async function ask(input: { sessionID: SessionID questions: Info[] - tool?: { messageID: string; callID: string } + tool?: { messageID: MessageID; callID: string } }): Promise { const s = await state() const id = Identifier.ascending("question") diff --git a/packages/opencode/src/server/routes/session.ts b/packages/opencode/src/server/routes/session.ts index 8e465d7ec23..26468c52c51 100644 --- a/packages/opencode/src/server/routes/session.ts +++ b/packages/opencode/src/server/routes/session.ts @@ -1,7 +1,7 @@ import { Hono } from "hono" import { stream } from "hono/streaming" import { describeRoute, validator, resolver } from "hono-openapi" -import { SessionID } from "@/session/schema" +import { SessionID, MessageID } from "@/session/schema" import z from "zod" import { Session } from "../../session" import { MessageV2 } from "../../session/message-v2" @@ -607,7 +607,7 @@ export const SessionRoutes = lazy(() => "param", z.object({ sessionID: SessionID.zod, - messageID: z.string().meta({ description: "Message ID" }), + messageID: MessageID.zod, }), ), async (c) => { @@ -642,7 +642,7 @@ export const SessionRoutes = lazy(() => "param", z.object({ sessionID: SessionID.zod, - messageID: z.string().meta({ description: "Message ID" }), + messageID: MessageID.zod, }), ), async (c) => { @@ -676,8 +676,8 @@ export const SessionRoutes = lazy(() => "param", z.object({ sessionID: SessionID.zod, - messageID: z.string().meta({ description: "Message ID" }), - partID: z.string().meta({ description: "Part ID" }), + messageID: MessageID.zod, + partID: z.string(), }), ), async (c) => { @@ -711,8 +711,8 @@ export const SessionRoutes = lazy(() => "param", z.object({ sessionID: SessionID.zod, - messageID: z.string().meta({ description: "Message ID" }), - partID: z.string().meta({ description: "Part ID" }), + messageID: MessageID.zod, + partID: z.string(), }), ), validator("json", MessageV2.Part), diff --git a/packages/opencode/src/session/compaction.ts b/packages/opencode/src/session/compaction.ts index d26c3bb6b9f..37a7cad84da 100644 --- a/packages/opencode/src/session/compaction.ts +++ b/packages/opencode/src/session/compaction.ts @@ -2,7 +2,7 @@ import { BusEvent } from "@/bus/bus-event" import { Bus } from "@/bus" import { Session } from "." import { Identifier } from "../id/id" -import { SessionID } from "./schema" +import { SessionID, MessageID } from "./schema" import { Instance } from "../project/instance" import { Provider } from "../provider/provider" import { MessageV2 } from "./message-v2" @@ -100,7 +100,7 @@ export namespace SessionCompaction { } export async function process(input: { - parentID: string + parentID: MessageID messages: MessageV2.WithParts[] sessionID: SessionID abort: AbortSignal @@ -134,7 +134,7 @@ export namespace SessionCompaction { ? await Provider.getModel(agent.model.providerID, agent.model.modelID) : await Provider.getModel(userMessage.model.providerID, userMessage.model.modelID) const msg = (await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "assistant", parentID: input.parentID, sessionID: input.sessionID, @@ -237,7 +237,7 @@ When constructing the summary, try to stick to this template: if (replay) { const original = replay.info as MessageV2.User const replayMsg = await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", sessionID: input.sessionID, time: { created: Date.now() }, @@ -263,7 +263,7 @@ When constructing the summary, try to stick to this template: } } else { const continueMsg = await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", sessionID: input.sessionID, time: { created: Date.now() }, @@ -307,7 +307,7 @@ When constructing the summary, try to stick to this template: }), async (input) => { const msg = await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", model: input.model, sessionID: input.sessionID, diff --git a/packages/opencode/src/session/index.ts b/packages/opencode/src/session/index.ts index 76b550d3098..2f485508241 100644 --- a/packages/opencode/src/session/index.ts +++ b/packages/opencode/src/session/index.ts @@ -24,7 +24,7 @@ import { Command } from "../command" import { Snapshot } from "@/snapshot" import { WorkspaceContext } from "../control-plane/workspace-context" import { ProjectID } from "../project/schema" -import { SessionID } from "./schema" +import { SessionID, MessageID } from "./schema" import type { Provider } from "@/provider/provider" import { PermissionNext } from "@/permission/next" @@ -150,7 +150,7 @@ export namespace Session { permission: PermissionNext.Ruleset.optional(), revert: z .object({ - messageID: z.string(), + messageID: MessageID.zod, partID: z.string().optional(), snapshot: z.string().optional(), diff: z.string().optional(), @@ -238,7 +238,7 @@ export namespace Session { export const fork = fn( z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message").optional(), + messageID: MessageID.zod.optional(), }), async (input) => { const original = await get(input.sessionID) @@ -250,11 +250,11 @@ export namespace Session { title, }) const msgs = await messages({ sessionID: input.sessionID }) - const idMap = new Map() + const idMap = new Map() for (const msg of msgs) { if (input.messageID && msg.info.id >= input.messageID) break - const newID = Identifier.ascending("message") + const newID = MessageID.ascending() idMap.set(msg.info.id, newID) const parentID = msg.info.role === "assistant" && msg.info.parentID ? idMap.get(msg.info.parentID) : undefined @@ -707,7 +707,7 @@ export namespace Session { export const removeMessage = fn( z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message"), + messageID: MessageID.zod, }), async (input) => { // CASCADE delete handles parts automatically @@ -729,7 +729,7 @@ export namespace Session { export const removePart = fn( z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message"), + messageID: MessageID.zod, partID: Identifier.schema("part"), }), async (input) => { @@ -777,7 +777,7 @@ export namespace Session { export const updatePartDelta = fn( z.object({ sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, partID: z.string(), field: z.string(), delta: z.string(), @@ -877,7 +877,7 @@ export namespace Session { sessionID: SessionID.zod, modelID: z.string(), providerID: z.string(), - messageID: Identifier.schema("message"), + messageID: MessageID.zod, }), async (input) => { await SessionPrompt.command({ diff --git a/packages/opencode/src/session/message-v2.ts b/packages/opencode/src/session/message-v2.ts index 43d735e4bdb..0fa842b2999 100644 --- a/packages/opencode/src/session/message-v2.ts +++ b/packages/opencode/src/session/message-v2.ts @@ -1,9 +1,8 @@ import { BusEvent } from "@/bus/bus-event" -import { SessionID } from "./schema" +import { SessionID, MessageID } from "./schema" import z from "zod" import { NamedError } from "@opencode-ai/util/error" import { APICallError, convertToModelMessages, LoadAPIKeyError, type ModelMessage, type UIMessage } from "ai" -import { Identifier } from "../id/id" import { LSP } from "../lsp" import { Snapshot } from "@/snapshot" import { fn } from "@/util/fn" @@ -81,7 +80,7 @@ export namespace MessageV2 { const PartBase = z.object({ id: z.string(), sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, }) export const SnapshotPart = PartBase.extend({ @@ -344,7 +343,7 @@ export namespace MessageV2 { export type ToolPart = z.infer const Base = z.object({ - id: z.string(), + id: MessageID.zod, sessionID: SessionID.zod, }) @@ -411,7 +410,7 @@ export namespace MessageV2 { APIError.Schema, ]) .optional(), - parentID: z.string(), + parentID: MessageID.zod, modelID: z.string(), providerID: z.string(), /** @@ -459,7 +458,7 @@ export namespace MessageV2 { "message.removed", z.object({ sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, }), ), PartUpdated: BusEvent.define( @@ -472,7 +471,7 @@ export namespace MessageV2 { "message.part.delta", z.object({ sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, partID: z.string(), field: z.string(), delta: z.string(), @@ -482,7 +481,7 @@ export namespace MessageV2 { "message.part.removed", z.object({ sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, partID: z.string(), }), ), @@ -699,7 +698,7 @@ export namespace MessageV2 { // media (images, PDFs) in tool results if (media.length > 0) { result.push({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", parts: [ { @@ -782,7 +781,7 @@ export namespace MessageV2 { } }) - export const parts = fn(Identifier.schema("message"), async (message_id) => { + export const parts = fn(MessageID.zod, async (message_id) => { const rows = Database.use((db) => db.select().from(PartTable).where(eq(PartTable.message_id, message_id)).orderBy(PartTable.id).all(), ) @@ -794,7 +793,7 @@ export namespace MessageV2 { export const get = fn( z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message"), + messageID: MessageID.zod, }), async (input): Promise => { const row = Database.use((db) => db.select().from(MessageTable).where(eq(MessageTable.id, input.messageID)).get()) diff --git a/packages/opencode/src/session/processor.ts b/packages/opencode/src/session/processor.ts index 33c6c9e4270..c208663ca25 100644 --- a/packages/opencode/src/session/processor.ts +++ b/packages/opencode/src/session/processor.ts @@ -15,7 +15,7 @@ import { Config } from "@/config/config" import { SessionCompaction } from "./compaction" import { PermissionNext } from "@/permission/next" import { Question } from "@/question" -import type { SessionID } from "./schema" +import type { SessionID, MessageID } from "./schema" export namespace SessionProcessor { const DOOM_LOOP_THRESHOLD = 3 diff --git a/packages/opencode/src/session/prompt.ts b/packages/opencode/src/session/prompt.ts index be28f158a53..2a0a05a7a05 100644 --- a/packages/opencode/src/session/prompt.ts +++ b/packages/opencode/src/session/prompt.ts @@ -4,7 +4,7 @@ import fs from "fs/promises" import z from "zod" import { Filesystem } from "../util/filesystem" import { Identifier } from "../id/id" -import { SessionID } from "./schema" +import { SessionID, MessageID } from "./schema" import { MessageV2 } from "./message-v2" import { Log } from "../util/log" import { SessionRevert } from "./revert" @@ -92,7 +92,7 @@ export namespace SessionPrompt { export const PromptInput = z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message").optional(), + messageID: MessageID.zod.optional(), model: z .object({ providerID: z.string(), @@ -355,7 +355,7 @@ export namespace SessionPrompt { const taskTool = await TaskTool.init() const taskModel = task.model ? await Provider.getModel(task.model.providerID, task.model.modelID) : model const assistantMessage = (await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "assistant", parentID: lastUser.id, sessionID, @@ -504,7 +504,7 @@ export namespace SessionPrompt { // If we create assistant messages w/ out user ones following mid loop thinking signatures // will be missing and it can cause errors for models like gemini for example const summaryUserMsg: MessageV2.User = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), sessionID, role: "user", time: { @@ -568,7 +568,7 @@ export namespace SessionPrompt { const processor = SessionProcessor.create({ assistantMessage: (await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), parentID: lastUser.id, role: "assistant", mode: agent.name, @@ -966,7 +966,7 @@ export namespace SessionPrompt { const variant = input.variant ?? (agent.variant && full?.variants?.[agent.variant] ? agent.variant : undefined) const info: MessageV2.Info = { - id: input.messageID ?? Identifier.ascending("message"), + id: input.messageID ?? MessageID.ascending(), role: "user", sessionID: input.sessionID, time: { @@ -1500,7 +1500,7 @@ NOTE: At any point in time through this workflow you should feel free to ask the const agent = await Agent.get(input.agent) const model = input.model ?? agent.model ?? (await lastModel(input.sessionID)) const userMsg: MessageV2.User = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), sessionID: input.sessionID, time: { created: Date.now(), @@ -1524,7 +1524,7 @@ NOTE: At any point in time through this workflow you should feel free to ask the await Session.updatePart(userPart) const msg: MessageV2.Assistant = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), sessionID: input.sessionID, parentID: userMsg.id, mode: input.agent, @@ -1713,7 +1713,7 @@ NOTE: At any point in time through this workflow you should feel free to ask the } export const CommandInput = z.object({ - messageID: Identifier.schema("message").optional(), + messageID: MessageID.zod.optional(), sessionID: SessionID.zod, agent: z.string().optional(), model: z.string().optional(), diff --git a/packages/opencode/src/session/revert.ts b/packages/opencode/src/session/revert.ts index 9b42ab350af..2f25bdfed95 100644 --- a/packages/opencode/src/session/revert.ts +++ b/packages/opencode/src/session/revert.ts @@ -1,6 +1,6 @@ import z from "zod" import { Identifier } from "../id/id" -import { SessionID } from "./schema" +import { SessionID, MessageID } from "./schema" import { Snapshot } from "../snapshot" import { MessageV2 } from "./message-v2" import { Session } from "." @@ -17,7 +17,7 @@ export namespace SessionRevert { export const RevertInput = z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message"), + messageID: MessageID.zod, partID: Identifier.schema("part").optional(), }) export type RevertInput = z.infer diff --git a/packages/opencode/src/session/schema.ts b/packages/opencode/src/session/schema.ts index 5277f5e0b60..78a0b35ec14 100644 --- a/packages/opencode/src/session/schema.ts +++ b/packages/opencode/src/session/schema.ts @@ -15,3 +15,15 @@ export const SessionID = sessionIdSchema.pipe( zod: z.string().startsWith("ses").pipe(z.custom()), })), ) + +const messageIdSchema = Schema.String.pipe(Schema.brand("MessageId")) + +export type MessageID = typeof messageIdSchema.Type + +export const MessageID = messageIdSchema.pipe( + withStatics((schema: typeof messageIdSchema) => ({ + make: (id: string) => schema.makeUnsafe(id), + ascending: (id?: string) => schema.makeUnsafe(Identifier.ascending("message", id)), + zod: z.string().startsWith("msg").pipe(z.custom()), + })), +) diff --git a/packages/opencode/src/session/session.sql.ts b/packages/opencode/src/session/session.sql.ts index 309b623b864..73e989cfbd4 100644 --- a/packages/opencode/src/session/session.sql.ts +++ b/packages/opencode/src/session/session.sql.ts @@ -4,7 +4,7 @@ import type { MessageV2 } from "./message-v2" import type { Snapshot } from "../snapshot" import type { PermissionNext } from "../permission/next" import type { ProjectID } from "../project/schema" -import type { SessionID } from "./schema" +import type { SessionID, MessageID } from "./schema" import { Timestamps } from "../storage/schema.sql" type PartData = Omit @@ -29,7 +29,7 @@ export const SessionTable = sqliteTable( summary_deletions: integer(), summary_files: integer(), summary_diffs: text({ mode: "json" }).$type(), - revert: text({ mode: "json" }).$type<{ messageID: string; partID?: string; snapshot?: string; diff?: string }>(), + revert: text({ mode: "json" }).$type<{ messageID: MessageID; partID?: string; snapshot?: string; diff?: string }>(), permission: text({ mode: "json" }).$type(), ...Timestamps, time_compacting: integer(), @@ -45,7 +45,7 @@ export const SessionTable = sqliteTable( export const MessageTable = sqliteTable( "message", { - id: text().primaryKey(), + id: text().$type().primaryKey(), session_id: text() .$type() .notNull() @@ -61,6 +61,7 @@ export const PartTable = sqliteTable( { id: text().primaryKey(), message_id: text() + .$type() .notNull() .references(() => MessageTable.id, { onDelete: "cascade" }), session_id: text().$type().notNull(), diff --git a/packages/opencode/src/session/summary.ts b/packages/opencode/src/session/summary.ts index f489c9a6288..678a0085181 100644 --- a/packages/opencode/src/session/summary.ts +++ b/packages/opencode/src/session/summary.ts @@ -4,7 +4,7 @@ import { Session } from "." import { MessageV2 } from "./message-v2" import { Identifier } from "@/id/id" -import { SessionID } from "./schema" +import { SessionID, MessageID } from "./schema" import { Snapshot } from "@/snapshot" import { Storage } from "@/storage/storage" @@ -70,7 +70,7 @@ export namespace SessionSummary { export const summarize = fn( z.object({ sessionID: SessionID.zod, - messageID: z.string(), + messageID: MessageID.zod, }), async (input) => { const all = await Session.messages({ sessionID: input.sessionID }) @@ -115,7 +115,7 @@ export namespace SessionSummary { export const diff = fn( z.object({ sessionID: SessionID.zod, - messageID: Identifier.schema("message").optional(), + messageID: MessageID.zod.optional(), }), async (input) => { const diffs = await Storage.read(["session_diff", input.sessionID]).catch(() => []) diff --git a/packages/opencode/src/tool/plan.ts b/packages/opencode/src/tool/plan.ts index 0c25cf3e95e..75ae4f5a50e 100644 --- a/packages/opencode/src/tool/plan.ts +++ b/packages/opencode/src/tool/plan.ts @@ -7,7 +7,7 @@ import { MessageV2 } from "../session/message-v2" import { Identifier } from "../id/id" import { Provider } from "../provider/provider" import { Instance } from "../project/instance" -import type { SessionID } from "../session/schema" +import { type SessionID, MessageID } from "../session/schema" import EXIT_DESCRIPTION from "./plan-exit.txt" async function getLastModel(sessionID: SessionID) { @@ -45,7 +45,7 @@ export const PlanExitTool = Tool.define("plan_exit", { const model = await getLastModel(ctx.sessionID) const userMsg: MessageV2.User = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), sessionID: ctx.sessionID, role: "user", time: { @@ -103,7 +103,7 @@ export const PlanEnterTool = Tool.define("plan_enter", { const model = await getLastModel(ctx.sessionID) const userMsg: MessageV2.User = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), sessionID: ctx.sessionID, role: "user", time: { diff --git a/packages/opencode/src/tool/task.ts b/packages/opencode/src/tool/task.ts index 2304a2e2bf3..68e44eb97e4 100644 --- a/packages/opencode/src/tool/task.ts +++ b/packages/opencode/src/tool/task.ts @@ -2,7 +2,7 @@ import { Tool } from "./tool" import DESCRIPTION from "./task.txt" import z from "zod" import { Session } from "../session" -import { SessionID } from "../session/schema" +import { SessionID, MessageID } from "../session/schema" import { MessageV2 } from "../session/message-v2" import { Identifier } from "../id/id" import { Agent } from "../agent/agent" @@ -117,7 +117,7 @@ export const TaskTool = Tool.define("task", async (ctx) => { }, }) - const messageID = Identifier.ascending("message") + const messageID = MessageID.ascending() function cancel() { SessionPrompt.cancel(session.id) diff --git a/packages/opencode/src/tool/tool.ts b/packages/opencode/src/tool/tool.ts index 7f58520c56d..8cc7b57d854 100644 --- a/packages/opencode/src/tool/tool.ts +++ b/packages/opencode/src/tool/tool.ts @@ -2,7 +2,7 @@ import z from "zod" import type { MessageV2 } from "../session/message-v2" import type { Agent } from "../agent/agent" import type { PermissionNext } from "../permission/next" -import type { SessionID } from "../session/schema" +import type { SessionID, MessageID } from "../session/schema" import { Truncate } from "./truncation" export namespace Tool { @@ -16,7 +16,7 @@ export namespace Tool { export type Context = { sessionID: SessionID - messageID: string + messageID: MessageID agent: string abort: AbortSignal callID?: string diff --git a/packages/opencode/test/cli/github-action.test.ts b/packages/opencode/test/cli/github-action.test.ts index c2bd293d79f..48d7656ee3d 100644 --- a/packages/opencode/test/cli/github-action.test.ts +++ b/packages/opencode/test/cli/github-action.test.ts @@ -1,14 +1,14 @@ import { test, expect, describe } from "bun:test" import { extractResponseText, formatPromptTooLargeError } from "../../src/cli/cmd/github" import type { MessageV2 } from "../../src/session/message-v2" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" // Helper to create minimal valid parts function createTextPart(text: string): MessageV2.Part { return { id: "1", sessionID: SessionID.make("s"), - messageID: "m", + messageID: MessageID.make("m"), type: "text" as const, text, } @@ -18,7 +18,7 @@ function createReasoningPart(text: string): MessageV2.Part { return { id: "1", sessionID: SessionID.make("s"), - messageID: "m", + messageID: MessageID.make("m"), type: "reasoning" as const, text, time: { start: 0 }, @@ -30,7 +30,7 @@ function createToolPart(tool: string, title: string, status: "completed" | "runn return { id: "1", sessionID: SessionID.make("s"), - messageID: "m", + messageID: MessageID.make("m"), type: "tool" as const, callID: "c1", tool, @@ -47,7 +47,7 @@ function createToolPart(tool: string, title: string, status: "completed" | "runn return { id: "1", sessionID: SessionID.make("s"), - messageID: "m", + messageID: MessageID.make("m"), type: "tool" as const, callID: "c1", tool, @@ -63,7 +63,7 @@ function createStepStartPart(): MessageV2.Part { return { id: "1", sessionID: SessionID.make("s"), - messageID: "m", + messageID: MessageID.make("m"), type: "step-start" as const, } } @@ -72,7 +72,7 @@ function createStepFinishPart(): MessageV2.Part { return { id: "1", sessionID: SessionID.make("s"), - messageID: "m", + messageID: MessageID.make("m"), type: "step-finish" as const, reason: "done", cost: 0, diff --git a/packages/opencode/test/memory/abort-leak.test.ts b/packages/opencode/test/memory/abort-leak.test.ts index 68770bf17ac..eebb651a53b 100644 --- a/packages/opencode/test/memory/abort-leak.test.ts +++ b/packages/opencode/test/memory/abort-leak.test.ts @@ -2,13 +2,13 @@ import { describe, test, expect } from "bun:test" import path from "path" import { Instance } from "../../src/project/instance" import { WebFetchTool } from "../../src/tool/webfetch" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const projectRoot = path.join(__dirname, "../..") const ctx = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: new AbortController().signal, diff --git a/packages/opencode/test/session/llm.test.ts b/packages/opencode/test/session/llm.test.ts index 871fd8cb57e..df9dedb356a 100644 --- a/packages/opencode/test/session/llm.test.ts +++ b/packages/opencode/test/session/llm.test.ts @@ -11,7 +11,7 @@ import { Filesystem } from "../../src/util/filesystem" import { tmpdir } from "../fixture/fixture" import type { Agent } from "../../src/agent/agent" import type { MessageV2 } from "../../src/session/message-v2" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" describe("session.llm.hasToolCalls", () => { test("returns false for empty messages array", () => { @@ -277,7 +277,7 @@ describe("session.llm.stream", () => { } satisfies Agent.Info const user = { - id: "user-1", + id: MessageID.make("user-1"), sessionID, role: "user", time: { created: Date.now() }, @@ -406,7 +406,7 @@ describe("session.llm.stream", () => { } satisfies Agent.Info const user = { - id: "user-2", + id: MessageID.make("user-2"), sessionID, role: "user", time: { created: Date.now() }, @@ -529,7 +529,7 @@ describe("session.llm.stream", () => { } satisfies Agent.Info const user = { - id: "user-3", + id: MessageID.make("user-3"), sessionID, role: "user", time: { created: Date.now() }, @@ -630,7 +630,7 @@ describe("session.llm.stream", () => { } satisfies Agent.Info const user = { - id: "user-4", + id: MessageID.make("user-4"), sessionID, role: "user", time: { created: Date.now() }, diff --git a/packages/opencode/test/session/message-v2.test.ts b/packages/opencode/test/session/message-v2.test.ts index 158d341f9eb..af1d0018bcc 100644 --- a/packages/opencode/test/session/message-v2.test.ts +++ b/packages/opencode/test/session/message-v2.test.ts @@ -2,7 +2,7 @@ import { describe, expect, test } from "bun:test" import { APICallError } from "ai" import { MessageV2 } from "../../src/session/message-v2" import type { Provider } from "../../src/provider/provider" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const sessionID = SessionID.make("session") const model: Provider.Model = { @@ -100,7 +100,7 @@ function basePart(messageID: string, id: string) { return { id, sessionID, - messageID, + messageID: MessageID.make(messageID), } } diff --git a/packages/opencode/test/session/revert-compact.test.ts b/packages/opencode/test/session/revert-compact.test.ts index de2b14573f4..37b3e217717 100644 --- a/packages/opencode/test/session/revert-compact.test.ts +++ b/packages/opencode/test/session/revert-compact.test.ts @@ -7,6 +7,7 @@ import { MessageV2 } from "../../src/session/message-v2" import { Log } from "../../src/util/log" import { Instance } from "../../src/project/instance" import { Identifier } from "../../src/id/id" +import { MessageID } from "../../src/session/schema" import { tmpdir } from "../fixture/fixture" const projectRoot = path.join(__dirname, "../..") @@ -24,7 +25,7 @@ describe("revert + compact workflow", () => { // Create a user message const userMsg1 = await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", sessionID, agent: "default", @@ -48,7 +49,7 @@ describe("revert + compact workflow", () => { // Create an assistant response message const assistantMsg1: MessageV2.Assistant = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "assistant", sessionID, mode: "default", @@ -85,7 +86,7 @@ describe("revert + compact workflow", () => { // Create another user message const userMsg2 = await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", sessionID, agent: "default", @@ -108,7 +109,7 @@ describe("revert + compact workflow", () => { // Create another assistant response const assistantMsg2: MessageV2.Assistant = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "assistant", sessionID, mode: "default", @@ -200,7 +201,7 @@ describe("revert + compact workflow", () => { // Create initial messages const userMsg = await Session.updateMessage({ - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "user", sessionID, agent: "default", @@ -222,7 +223,7 @@ describe("revert + compact workflow", () => { }) const assistantMsg: MessageV2.Assistant = { - id: Identifier.ascending("message"), + id: MessageID.ascending(), role: "assistant", sessionID, mode: "default", diff --git a/packages/opencode/test/session/session.test.ts b/packages/opencode/test/session/session.test.ts index aa9ca05d047..f5512f240ef 100644 --- a/packages/opencode/test/session/session.test.ts +++ b/packages/opencode/test/session/session.test.ts @@ -6,6 +6,7 @@ import { Log } from "../../src/util/log" import { Instance } from "../../src/project/instance" import { MessageV2 } from "../../src/session/message-v2" import { Identifier } from "../../src/id/id" +import { MessageID } from "../../src/session/schema" const projectRoot = path.join(__dirname, "../..") Log.init({ print: false }) @@ -81,7 +82,7 @@ describe("step-finish token propagation via Bus event", () => { fn: async () => { const session = await Session.create({}) - const messageID = Identifier.ascending("message") + const messageID = MessageID.ascending() await Session.updateMessage({ id: messageID, sessionID: session.id, diff --git a/packages/opencode/test/session/structured-output.test.ts b/packages/opencode/test/session/structured-output.test.ts index 537df07af6d..f6131b149b5 100644 --- a/packages/opencode/test/session/structured-output.test.ts +++ b/packages/opencode/test/session/structured-output.test.ts @@ -1,7 +1,7 @@ import { describe, expect, test } from "bun:test" import { MessageV2 } from "../../src/session/message-v2" import { SessionPrompt } from "../../src/session/prompt" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" describe("structured-output.OutputFormat", () => { test("parses text format", () => { @@ -96,7 +96,7 @@ describe("structured-output.StructuredOutputError", () => { describe("structured-output.UserMessage", () => { test("user message accepts outputFormat", () => { const result = MessageV2.User.safeParse({ - id: "test-id", + id: MessageID.ascending(), sessionID: SessionID.descending(), role: "user", time: { created: Date.now() }, @@ -112,7 +112,7 @@ describe("structured-output.UserMessage", () => { test("user message works without outputFormat (optional)", () => { const result = MessageV2.User.safeParse({ - id: "test-id", + id: MessageID.ascending(), sessionID: SessionID.descending(), role: "user", time: { created: Date.now() }, @@ -125,10 +125,10 @@ describe("structured-output.UserMessage", () => { describe("structured-output.AssistantMessage", () => { const baseAssistantMessage = { - id: "test-id", + id: MessageID.ascending(), sessionID: SessionID.descending(), role: "assistant" as const, - parentID: "parent-id", + parentID: MessageID.ascending(), modelID: "claude-3", providerID: "anthropic", mode: "default", diff --git a/packages/opencode/test/storage/json-migration.test.ts b/packages/opencode/test/storage/json-migration.test.ts index f5f8cbd5cd0..f436037158b 100644 --- a/packages/opencode/test/storage/json-migration.test.ts +++ b/packages/opencode/test/storage/json-migration.test.ts @@ -11,7 +11,7 @@ import { ProjectTable } from "../../src/project/project.sql" import { ProjectID } from "../../src/project/schema" import { SessionTable, MessageTable, PartTable, TodoTable, PermissionTable } from "../../src/session/session.sql" import { SessionShareTable } from "../../src/share/share.sql" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" // Test fixtures const fixtures = { @@ -255,7 +255,7 @@ describe("JSON to SQLite migration", () => { const db = drizzle({ client: sqlite }) const messages = db.select().from(MessageTable).all() expect(messages.length).toBe(1) - expect(messages[0].id).toBe("msg_test789ghi") + expect(messages[0].id).toBe(MessageID.make("msg_test789ghi")) const parts = db.select().from(PartTable).all() expect(parts.length).toBe(1) @@ -295,7 +295,7 @@ describe("JSON to SQLite migration", () => { const db = drizzle({ client: sqlite }) const messages = db.select().from(MessageTable).all() expect(messages.length).toBe(1) - expect(messages[0].id).toBe("msg_test789ghi") + expect(messages[0].id).toBe(MessageID.make("msg_test789ghi")) expect(messages[0].session_id).toBe(SessionID.make("ses_test456def")) expect(messages[0].data).not.toHaveProperty("id") expect(messages[0].data).not.toHaveProperty("sessionID") @@ -303,7 +303,7 @@ describe("JSON to SQLite migration", () => { const parts = db.select().from(PartTable).all() expect(parts.length).toBe(1) expect(parts[0].id).toBe("prt_testabc123") - expect(parts[0].message_id).toBe("msg_test789ghi") + expect(parts[0].message_id).toBe(MessageID.make("msg_test789ghi")) expect(parts[0].session_id).toBe(SessionID.make("ses_test456def")) expect(parts[0].data).not.toHaveProperty("id") expect(parts[0].data).not.toHaveProperty("messageID") @@ -336,7 +336,7 @@ describe("JSON to SQLite migration", () => { const db = drizzle({ client: sqlite }) const messages = db.select().from(MessageTable).all() expect(messages.length).toBe(1) - expect(messages[0].id).toBe("msg_from_filename") // Uses filename, not JSON id + expect(messages[0].id).toBe(MessageID.make("msg_from_filename")) // Uses filename, not JSON id expect(messages[0].session_id).toBe(SessionID.make("ses_test456def")) }) @@ -375,7 +375,7 @@ describe("JSON to SQLite migration", () => { const parts = db.select().from(PartTable).all() expect(parts.length).toBe(1) expect(parts[0].id).toBe("prt_from_filename") // Uses filename, not JSON id - expect(parts[0].message_id).toBe("msg_realmsgid") // Uses parent dir, not JSON messageID + expect(parts[0].message_id).toBe(MessageID.make("msg_realmsgid")) // Uses parent dir, not JSON messageID }) test("skips orphaned sessions (no parent project)", async () => { diff --git a/packages/opencode/test/tool/apply_patch.test.ts b/packages/opencode/test/tool/apply_patch.test.ts index 008b4fa49c6..4e276517f10 100644 --- a/packages/opencode/test/tool/apply_patch.test.ts +++ b/packages/opencode/test/tool/apply_patch.test.ts @@ -4,11 +4,11 @@ import * as fs from "fs/promises" import { ApplyPatchTool } from "../../src/tool/apply_patch" import { Instance } from "../../src/project/instance" import { tmpdir } from "../fixture/fixture" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const baseCtx = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/bash.test.ts b/packages/opencode/test/tool/bash.test.ts index d4a6c7ccdb5..f947398b37e 100644 --- a/packages/opencode/test/tool/bash.test.ts +++ b/packages/opencode/test/tool/bash.test.ts @@ -7,11 +7,11 @@ import { Filesystem } from "../../src/util/filesystem" import { tmpdir } from "../fixture/fixture" import type { PermissionNext } from "../../src/permission/next" import { Truncate } from "../../src/tool/truncation" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const ctx = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/edit.test.ts b/packages/opencode/test/tool/edit.test.ts index 601995889ed..b0ee95ff6f7 100644 --- a/packages/opencode/test/tool/edit.test.ts +++ b/packages/opencode/test/tool/edit.test.ts @@ -5,11 +5,11 @@ import { EditTool } from "../../src/tool/edit" import { Instance } from "../../src/project/instance" import { tmpdir } from "../fixture/fixture" import { FileTime } from "../../src/file/time" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const ctx = { sessionID: SessionID.make("ses_test-edit-session"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/external-directory.test.ts b/packages/opencode/test/tool/external-directory.test.ts index fe33d69151d..58e53e58395 100644 --- a/packages/opencode/test/tool/external-directory.test.ts +++ b/packages/opencode/test/tool/external-directory.test.ts @@ -4,11 +4,11 @@ import type { Tool } from "../../src/tool/tool" import { Instance } from "../../src/project/instance" import { assertExternalDirectory } from "../../src/tool/external-directory" import type { PermissionNext } from "../../src/permission/next" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const baseCtx: Omit = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/grep.test.ts b/packages/opencode/test/tool/grep.test.ts index 5823553722e..e03b1752ec0 100644 --- a/packages/opencode/test/tool/grep.test.ts +++ b/packages/opencode/test/tool/grep.test.ts @@ -3,11 +3,11 @@ import path from "path" import { GrepTool } from "../../src/tool/grep" import { Instance } from "../../src/project/instance" import { tmpdir } from "../fixture/fixture" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const ctx = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/question.test.ts b/packages/opencode/test/tool/question.test.ts index 69e211abdd5..9157aaa9a48 100644 --- a/packages/opencode/test/tool/question.test.ts +++ b/packages/opencode/test/tool/question.test.ts @@ -2,11 +2,11 @@ import { describe, expect, test, spyOn, beforeEach, afterEach } from "bun:test" import { z } from "zod" import { QuestionTool } from "../../src/tool/question" import * as QuestionModule from "../../src/question" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const ctx = { sessionID: SessionID.make("ses_test-session"), - messageID: "test-message", + messageID: MessageID.make("test-message"), callID: "test-call", agent: "test-agent", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/read.test.ts b/packages/opencode/test/tool/read.test.ts index 45f3c1b32e8..7659d690c3a 100644 --- a/packages/opencode/test/tool/read.test.ts +++ b/packages/opencode/test/tool/read.test.ts @@ -6,13 +6,13 @@ import { Filesystem } from "../../src/util/filesystem" import { tmpdir } from "../fixture/fixture" import { PermissionNext } from "../../src/permission/next" import { Agent } from "../../src/agent/agent" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const FIXTURES_DIR = path.join(import.meta.dir, "fixtures") const ctx = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/skill.test.ts b/packages/opencode/test/tool/skill.test.ts index 3db08414edb..8c4e8683508 100644 --- a/packages/opencode/test/tool/skill.test.ts +++ b/packages/opencode/test/tool/skill.test.ts @@ -6,11 +6,11 @@ import type { Tool } from "../../src/tool/tool" import { Instance } from "../../src/project/instance" import { SkillTool } from "../../src/tool/skill" import { tmpdir } from "../fixture/fixture" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const baseCtx: Omit = { sessionID: SessionID.make("ses_test"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/webfetch.test.ts b/packages/opencode/test/tool/webfetch.test.ts index 769a61e1656..088f3dd16da 100644 --- a/packages/opencode/test/tool/webfetch.test.ts +++ b/packages/opencode/test/tool/webfetch.test.ts @@ -2,13 +2,13 @@ import { describe, expect, test } from "bun:test" import path from "path" import { Instance } from "../../src/project/instance" import { WebFetchTool } from "../../src/tool/webfetch" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const projectRoot = path.join(import.meta.dir, "../..") const ctx = { sessionID: SessionID.make("ses_test"), - messageID: "message", + messageID: MessageID.make("message"), callID: "", agent: "build", abort: AbortSignal.any([]), diff --git a/packages/opencode/test/tool/write.test.ts b/packages/opencode/test/tool/write.test.ts index 62279057a99..b93ab4e853e 100644 --- a/packages/opencode/test/tool/write.test.ts +++ b/packages/opencode/test/tool/write.test.ts @@ -4,11 +4,11 @@ import fs from "fs/promises" import { WriteTool } from "../../src/tool/write" import { Instance } from "../../src/project/instance" import { tmpdir } from "../fixture/fixture" -import { SessionID } from "../../src/session/schema" +import { SessionID, MessageID } from "../../src/session/schema" const ctx = { sessionID: SessionID.make("ses_test-write-session"), - messageID: "", + messageID: MessageID.make(""), callID: "", agent: "build", abort: AbortSignal.any([]),