index.ts 3.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136
  1. import type {
  2. Event,
  3. createOpencodeClient,
  4. Project,
  5. Model,
  6. Provider,
  7. Permission,
  8. UserMessage,
  9. Part,
  10. Auth,
  11. Config,
  12. } from "@opencode-ai/sdk"
  13. import type { BunShell } from "./shell"
  14. export type PluginInput = {
  15. client: ReturnType<typeof createOpencodeClient>
  16. project: Project
  17. directory: string
  18. worktree: string
  19. $: BunShell
  20. Tool: {
  21. define(id: string, init: any | (() => Promise<any>)): any
  22. }
  23. z: any // Zod instance for creating schemas
  24. }
  25. export type Plugin = (input: PluginInput) => Promise<Hooks>
  26. // Lightweight schema spec for HTTP-registered tools
  27. export type HttpParamSpec = {
  28. type: "string" | "number" | "boolean" | "array"
  29. description?: string
  30. optional?: boolean
  31. items?: "string" | "number" | "boolean"
  32. }
  33. export type HttpToolRegistration = {
  34. id: string
  35. description: string
  36. parameters: {
  37. type: "object"
  38. properties: Record<string, HttpParamSpec>
  39. }
  40. callbackUrl: string
  41. headers?: Record<string, string>
  42. }
  43. export interface Hooks {
  44. event?: (input: { event: Event }) => Promise<void>
  45. config?: (input: Config) => Promise<void>
  46. auth?: {
  47. provider: string
  48. loader?: (auth: () => Promise<Auth>, provider: Provider) => Promise<Record<string, any>>
  49. methods: (
  50. | {
  51. type: "oauth"
  52. label: string
  53. authorize(): Promise<
  54. { url: string; instructions: string } & (
  55. | {
  56. method: "auto"
  57. callback(): Promise<
  58. | ({
  59. type: "success"
  60. } & (
  61. | {
  62. refresh: string
  63. access: string
  64. expires: number
  65. }
  66. | { key: string }
  67. ))
  68. | {
  69. type: "failed"
  70. }
  71. >
  72. }
  73. | {
  74. method: "code"
  75. callback(code: string): Promise<
  76. | ({
  77. type: "success"
  78. } & (
  79. | {
  80. refresh: string
  81. access: string
  82. expires: number
  83. }
  84. | { key: string }
  85. ))
  86. | {
  87. type: "failed"
  88. }
  89. >
  90. }
  91. )
  92. >
  93. }
  94. | { type: "api"; label: string }
  95. )[]
  96. }
  97. /**
  98. * Called when a new message is received
  99. */
  100. "chat.message"?: (input: {}, output: { message: UserMessage; parts: Part[] }) => Promise<void>
  101. /**
  102. * Modify parameters sent to LLM
  103. */
  104. "chat.params"?: (
  105. input: { model: Model; provider: Provider; message: UserMessage },
  106. output: { temperature: number; topP: number; options: Record<string, any> },
  107. ) => Promise<void>
  108. "permission.ask"?: (input: Permission, output: { status: "ask" | "deny" | "allow" }) => Promise<void>
  109. "tool.execute.before"?: (
  110. input: { tool: string; sessionID: string; callID: string },
  111. output: { args: any },
  112. ) => Promise<void>
  113. "tool.execute.after"?: (
  114. input: { tool: string; sessionID: string; callID: string },
  115. output: {
  116. title: string
  117. output: string
  118. metadata: any
  119. },
  120. ) => Promise<void>
  121. /**
  122. * Allow plugins to register additional tools with the server.
  123. * Use registerHTTP to add a tool that calls back to your plugin/service.
  124. * Use register to add a native/local tool with direct function execution.
  125. */
  126. "tool.register"?: (
  127. input: {},
  128. output: {
  129. registerHTTP: (tool: HttpToolRegistration) => void | Promise<void>
  130. register: (tool: any) => void | Promise<void> // Tool.Info type from opencode
  131. },
  132. ) => Promise<void>
  133. }