message.ts 5.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189
  1. import z from "zod"
  2. import { NamedError } from "@opencode-ai/util/error"
  3. export namespace Message {
  4. export const OutputLengthError = NamedError.create("MessageOutputLengthError", z.object({}))
  5. export const AuthError = NamedError.create(
  6. "ProviderAuthError",
  7. z.object({
  8. providerID: z.string(),
  9. message: z.string(),
  10. }),
  11. )
  12. export const ToolCall = z
  13. .object({
  14. state: z.literal("call"),
  15. step: z.number().optional(),
  16. toolCallId: z.string(),
  17. toolName: z.string(),
  18. args: z.custom<Required<unknown>>(),
  19. })
  20. .meta({
  21. ref: "ToolCall",
  22. })
  23. export type ToolCall = z.infer<typeof ToolCall>
  24. export const ToolPartialCall = z
  25. .object({
  26. state: z.literal("partial-call"),
  27. step: z.number().optional(),
  28. toolCallId: z.string(),
  29. toolName: z.string(),
  30. args: z.custom<Required<unknown>>(),
  31. })
  32. .meta({
  33. ref: "ToolPartialCall",
  34. })
  35. export type ToolPartialCall = z.infer<typeof ToolPartialCall>
  36. export const ToolResult = z
  37. .object({
  38. state: z.literal("result"),
  39. step: z.number().optional(),
  40. toolCallId: z.string(),
  41. toolName: z.string(),
  42. args: z.custom<Required<unknown>>(),
  43. result: z.string(),
  44. })
  45. .meta({
  46. ref: "ToolResult",
  47. })
  48. export type ToolResult = z.infer<typeof ToolResult>
  49. export const ToolInvocation = z.discriminatedUnion("state", [ToolCall, ToolPartialCall, ToolResult]).meta({
  50. ref: "ToolInvocation",
  51. })
  52. export type ToolInvocation = z.infer<typeof ToolInvocation>
  53. export const TextPart = z
  54. .object({
  55. type: z.literal("text"),
  56. text: z.string(),
  57. })
  58. .meta({
  59. ref: "TextPart",
  60. })
  61. export type TextPart = z.infer<typeof TextPart>
  62. export const ReasoningPart = z
  63. .object({
  64. type: z.literal("reasoning"),
  65. text: z.string(),
  66. providerMetadata: z.record(z.string(), z.any()).optional(),
  67. })
  68. .meta({
  69. ref: "ReasoningPart",
  70. })
  71. export type ReasoningPart = z.infer<typeof ReasoningPart>
  72. export const ToolInvocationPart = z
  73. .object({
  74. type: z.literal("tool-invocation"),
  75. toolInvocation: ToolInvocation,
  76. })
  77. .meta({
  78. ref: "ToolInvocationPart",
  79. })
  80. export type ToolInvocationPart = z.infer<typeof ToolInvocationPart>
  81. export const SourceUrlPart = z
  82. .object({
  83. type: z.literal("source-url"),
  84. sourceId: z.string(),
  85. url: z.string(),
  86. title: z.string().optional(),
  87. providerMetadata: z.record(z.string(), z.any()).optional(),
  88. })
  89. .meta({
  90. ref: "SourceUrlPart",
  91. })
  92. export type SourceUrlPart = z.infer<typeof SourceUrlPart>
  93. export const FilePart = z
  94. .object({
  95. type: z.literal("file"),
  96. mediaType: z.string(),
  97. filename: z.string().optional(),
  98. url: z.string(),
  99. })
  100. .meta({
  101. ref: "FilePart",
  102. })
  103. export type FilePart = z.infer<typeof FilePart>
  104. export const StepStartPart = z
  105. .object({
  106. type: z.literal("step-start"),
  107. })
  108. .meta({
  109. ref: "StepStartPart",
  110. })
  111. export type StepStartPart = z.infer<typeof StepStartPart>
  112. export const MessagePart = z
  113. .discriminatedUnion("type", [TextPart, ReasoningPart, ToolInvocationPart, SourceUrlPart, FilePart, StepStartPart])
  114. .meta({
  115. ref: "MessagePart",
  116. })
  117. export type MessagePart = z.infer<typeof MessagePart>
  118. export const Info = z
  119. .object({
  120. id: z.string(),
  121. role: z.enum(["user", "assistant"]),
  122. parts: z.array(MessagePart),
  123. metadata: z
  124. .object({
  125. time: z.object({
  126. created: z.number(),
  127. completed: z.number().optional(),
  128. }),
  129. error: z
  130. .discriminatedUnion("name", [AuthError.Schema, NamedError.Unknown.Schema, OutputLengthError.Schema])
  131. .optional(),
  132. sessionID: z.string(),
  133. tool: z.record(
  134. z.string(),
  135. z
  136. .object({
  137. title: z.string(),
  138. snapshot: z.string().optional(),
  139. time: z.object({
  140. start: z.number(),
  141. end: z.number(),
  142. }),
  143. })
  144. .catchall(z.any()),
  145. ),
  146. assistant: z
  147. .object({
  148. system: z.string().array(),
  149. modelID: z.string(),
  150. providerID: z.string(),
  151. path: z.object({
  152. cwd: z.string(),
  153. root: z.string(),
  154. }),
  155. cost: z.number(),
  156. summary: z.boolean().optional(),
  157. tokens: z.object({
  158. input: z.number(),
  159. output: z.number(),
  160. reasoning: z.number(),
  161. cache: z.object({
  162. read: z.number(),
  163. write: z.number(),
  164. }),
  165. }),
  166. })
  167. .optional(),
  168. snapshot: z.string().optional(),
  169. })
  170. .meta({ ref: "MessageMetadata" }),
  171. })
  172. .meta({
  173. ref: "Message",
  174. })
  175. export type Info = z.infer<typeof Info>
  176. }