瀏覽代碼

Drop prompt input Zod statics (#26923)

Kit Langton 3 月之前
父節點
當前提交
cc95197d72

+ 4 - 8
packages/opencode/src/session/prompt.ts

@@ -46,8 +46,6 @@ import { Truncate } from "@/tool/truncate"
 import { decodeDataUrl } from "@/util/data-url"
 import { Process } from "@/util/process"
 import { Cause, Effect, Exit, Latch, Layer, Option, Scope, Context, Schema, Types } from "effect"
-import { zod } from "@opencode-ai/core/effect-zod"
-import { withStatics } from "@opencode-ai/core/schema"
 import * as EffectLogger from "@opencode-ai/core/effect/logger"
 import { InstanceState } from "@/effect/instance-state"
 import { TaskTool, type TaskPromptOps } from "@/tool/task"
@@ -2054,14 +2052,12 @@ export const PromptInput = Schema.Struct({
       MessageV2.SubtaskPartInput,
     ]).annotate({ discriminator: "type" }),
   ),
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export type PromptInput = Schema.Schema.Type<typeof PromptInput>
 
 export class LoopInput extends Schema.Class<LoopInput>("SessionPrompt.LoopInput")({
   sessionID: SessionID,
-}) {
-  static readonly zod = zod(this)
-}
+}) {}
 
 export const ShellInput = Schema.Struct({
   sessionID: SessionID,
@@ -2069,7 +2065,7 @@ export const ShellInput = Schema.Struct({
   agent: Schema.String,
   model: Schema.optional(ModelRef),
   command: Schema.String,
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export type ShellInput = Schema.Schema.Type<typeof ShellInput>
 
 export const CommandInput = Schema.Struct({
@@ -2097,7 +2093,7 @@ export const CommandInput = Schema.Struct({
       ]).annotate({ discriminator: "type" }),
     ),
   ),
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export type CommandInput = Schema.Schema.Type<typeof CommandInput>
 
 /** @internal Exported for testing */

+ 11 - 20
packages/opencode/src/session/session.ts

@@ -37,8 +37,7 @@ import type { Provider } from "@/provider/provider"
 import { Permission } from "@/permission"
 import { Global } from "@opencode-ai/core/global"
 import { Effect, Layer, Option, Context, Schema, Types } from "effect"
-import { zod } from "@opencode-ai/core/effect-zod"
-import { NonNegativeInt, optionalOmitUndefined, withStatics } from "@opencode-ai/core/schema"
+import { NonNegativeInt, optionalOmitUndefined } from "@opencode-ai/core/schema"
 
 const log = Log.create({ service: "session" })
 
@@ -193,26 +192,20 @@ export const Info = Schema.Struct({
   time: Time,
   permission: optionalOmitUndefined(Permission.Ruleset),
   revert: optionalOmitUndefined(Revert),
-})
-  .annotate({ identifier: "Session" })
-  .pipe(withStatics((s) => ({ zod: zod(s) })))
+}).annotate({ identifier: "Session" })
 export type Info = Types.DeepMutable<Schema.Schema.Type<typeof Info>>
 
 export const ProjectInfo = Schema.Struct({
   id: ProjectID,
   name: optionalOmitUndefined(Schema.String),
   worktree: Schema.String,
-})
-  .annotate({ identifier: "ProjectSummary" })
-  .pipe(withStatics((s) => ({ zod: zod(s) })))
+}).annotate({ identifier: "ProjectSummary" })
 export type ProjectInfo = Types.DeepMutable<Schema.Schema.Type<typeof ProjectInfo>>
 
 export const GlobalInfo = Schema.Struct({
   ...Info.fields,
   project: Schema.NullOr(ProjectInfo),
-})
-  .annotate({ identifier: "GlobalSession" })
-  .pipe(withStatics((s) => ({ zod: zod(s) })))
+}).annotate({ identifier: "GlobalSession" })
 export type GlobalInfo = Types.DeepMutable<Schema.Schema.Type<typeof GlobalInfo>>
 
 export const CreateInput = Schema.optional(
@@ -224,36 +217,34 @@ export const CreateInput = Schema.optional(
     permission: Schema.optional(Permission.Ruleset),
     workspaceID: Schema.optional(WorkspaceID),
   }),
-).pipe(withStatics((s) => ({ zod: zod(s) })))
+)
 export type CreateInput = Types.DeepMutable<Schema.Schema.Type<typeof CreateInput>>
 
 export const ForkInput = Schema.Struct({
   sessionID: SessionID,
   messageID: Schema.optional(MessageID),
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export const GetInput = SessionID
 export const ChildrenInput = SessionID
 export const RemoveInput = SessionID
-export const SetTitleInput = Schema.Struct({ sessionID: SessionID, title: Schema.String }).pipe(
-  withStatics((s) => ({ zod: zod(s) })),
-)
+export const SetTitleInput = Schema.Struct({ sessionID: SessionID, title: Schema.String })
 export const SetArchivedInput = Schema.Struct({
   sessionID: SessionID,
   time: Schema.optional(ArchivedTimestamp),
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export const SetPermissionInput = Schema.Struct({
   sessionID: SessionID,
   permission: Permission.Ruleset,
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export const SetRevertInput = Schema.Struct({
   sessionID: SessionID,
   revert: Schema.optional(Revert),
   summary: Schema.optional(Summary),
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export const MessagesInput = Schema.Struct({
   sessionID: SessionID,
   limit: Schema.optional(NonNegativeInt),
-}).pipe(withStatics((s) => ({ zod: zod(s) })))
+})
 export type ListInput = {
   directory?: string
   scope?: "project"

+ 1 - 3
packages/opencode/test/server/global-session-list.test.ts

@@ -1,7 +1,5 @@
 import { describe, expect, test } from "bun:test"
 import { Effect } from "effect"
-import z from "zod"
-import { Instance } from "../../src/project/instance"
 import { WithInstance } from "../../src/project/with-instance"
 import { Project } from "@/project/project"
 import { Session as SessionNs } from "@/session/session"
@@ -19,7 +17,7 @@ const svc = {
   create(input?: SessionNs.CreateInput) {
     return run(SessionNs.Service.use((svc) => svc.create(input)))
   },
-  setArchived(input: z.output<typeof SessionNs.SetArchivedInput.zod>) {
+  setArchived(input: typeof SessionNs.SetArchivedInput.Type) {
     return run(SessionNs.Service.use((svc) => svc.setArchived(input)))
   },
 }

+ 0 - 21
packages/opencode/test/session/schema-decoding.test.ts

@@ -49,7 +49,6 @@ describe("Session.Info", () => {
       time: { created: 1, updated: 2 },
     }
     expect(decode(input)).toEqual(input)
-    expect(Session.Info.zod.parse(input)).toEqual(input)
   })
 
   test("round-trips every optional field", () => {
@@ -80,7 +79,6 @@ describe("Session.Info", () => {
       },
     }
     expect(decode(input)).toEqual(input)
-    expect(Session.Info.zod.parse(input)).toEqual(input)
   })
 
   test("accepts migrated summary diffs without file details", () => {
@@ -100,19 +98,16 @@ describe("Session.Info", () => {
       time: { created: 1, updated: 2 },
     }
     expect(decode(input)).toEqual(input)
-    expect(Session.Info.zod.parse(input)).toEqual(input)
   })
 
   test("rejects unbranded session id", () => {
     const bad = { id: "not-a-session-id" } as unknown
     expect(() => decode(bad)).toThrow()
-    expect(() => Session.Info.zod.parse(bad)).toThrow()
   })
 
   test("rejects missing required fields", () => {
     const bad = { id: sessionID } as unknown
     expect(() => decode(bad)).toThrow()
-    expect(() => Session.Info.zod.parse(bad)).toThrow()
   })
 })
 
@@ -124,8 +119,6 @@ describe("Session.ProjectInfo", () => {
     const withName = { ...noName, name: "alpha" }
     expect(decode(noName)).toEqual(noName)
     expect(decode(withName)).toEqual(withName)
-    expect(Session.ProjectInfo.zod.parse(noName)).toEqual(noName)
-    expect(Session.ProjectInfo.zod.parse(withName)).toEqual(withName)
   })
 })
 
@@ -144,7 +137,6 @@ describe("Session.GlobalInfo", () => {
       project: null,
     }
     expect(decode(input)).toEqual(input)
-    expect(Session.GlobalInfo.zod.parse(input)).toEqual(input)
   })
 
   test("accepts populated project", () => {
@@ -159,7 +151,6 @@ describe("Session.GlobalInfo", () => {
       project: { id: projectID, worktree: "/tmp/wt", name: "alpha" },
     }
     expect(decode(input)).toEqual(input)
-    expect(Session.GlobalInfo.zod.parse(input)).toEqual(input)
   })
 })
 
@@ -167,7 +158,6 @@ describe("Session input schemas", () => {
   test("CreateInput accepts undefined and populated forms", () => {
     const decode = decodeUnknown(Session.CreateInput)
     expect(decode(undefined)).toBeUndefined()
-    expect(Session.CreateInput.zod.parse(undefined)).toBeUndefined()
 
     const populated = {
       parentID: sessionID,
@@ -176,23 +166,19 @@ describe("Session input schemas", () => {
       workspaceID,
     }
     expect(decode(populated)).toEqual(populated)
-    expect(Session.CreateInput.zod.parse(populated)).toEqual(populated)
   })
 
   test("ForkInput round-trips", () => {
     const decode = decodeUnknown(Session.ForkInput)
     const input = { sessionID, messageID }
     expect(decode(input)).toEqual(input)
-    expect(Session.ForkInput.zod.parse(input)).toEqual(input)
     // messageID is optional
     const bare = { sessionID }
     expect(decode(bare)).toEqual(bare)
-    expect(Session.ForkInput.zod.parse(bare)).toEqual(bare)
   })
 
   test("SetTitleInput rejects missing title", () => {
     expect(() => decodeUnknown(Session.SetTitleInput)({ sessionID })).toThrow()
-    expect(() => Session.SetTitleInput.zod.parse({ sessionID })).toThrow()
   })
 
   test("SetArchivedInput accepts both with and without time", () => {
@@ -282,7 +268,6 @@ describe("SessionPrompt input schemas", () => {
   test("LoopInput is just sessionID", () => {
     const decode = decodeUnknown(SessionPrompt.LoopInput)
     expect(decode({ sessionID })).toEqual({ sessionID })
-    expect(SessionPrompt.LoopInput.zod.parse({ sessionID } as unknown)).toEqual({ sessionID })
   })
 
   test("ShellInput requires agent + command", () => {
@@ -290,7 +275,6 @@ describe("SessionPrompt input schemas", () => {
     const expected = { sessionID, agent: "build", command: "echo hi" }
     const input: unknown = expected
     expect(decode(input)).toEqual(expected)
-    expect(SessionPrompt.ShellInput.zod.parse(input as unknown)).toEqual(expected)
     expect(() => decode({ sessionID })).toThrow()
   })
 
@@ -308,9 +292,6 @@ describe("SessionPrompt input schemas", () => {
     expect(decoded.parts).toHaveLength(2)
     expect(decoded.parts[0]).toMatchObject({ type: "text", text: "hello" })
     expect(decoded.parts[1]).toMatchObject({ type: "file", mime: "image/png" })
-
-    const viaZod = SessionPrompt.PromptInput.zod.parse(input)
-    expect(viaZod.parts).toHaveLength(2)
   })
 
   test("PromptInput rejects unknown part type", () => {
@@ -320,7 +301,6 @@ describe("SessionPrompt input schemas", () => {
       parts: [{ type: "nonsense", payload: 42 }],
     }
     expect(() => decode(bad)).toThrow()
-    expect(() => SessionPrompt.PromptInput.zod.parse(bad)).toThrow()
   })
 
   test("CommandInput round-trips core fields", () => {
@@ -332,6 +312,5 @@ describe("SessionPrompt input schemas", () => {
     }
     const input: unknown = expected
     expect(decode(input)).toEqual(expected)
-    expect(SessionPrompt.CommandInput.zod.parse(input)).toEqual(expected)
   })
 })