Skip to content

Commit f85d30c

Browse files
committed
wip: plugins
1 parent 1bac466 commit f85d30c

7 files changed

Lines changed: 67 additions & 316 deletions

File tree

.opencode/plugin/example.ts

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
import { Plugin } from "./index"
2+
3+
export const ExamplePlugin: Plugin = async ({ app, client, $ }) => {
4+
return {
5+
permission: {},
6+
async "chat.params"(input, output) {
7+
output.topP = 1
8+
},
9+
}
10+
}

opencode.json

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
{
22
"$schema": "https://opencode.ai/config.json",
3-
"plugin": ["./packages/plugin/src/example.ts"],
43
"mcp": {
54
"context7": {
65
"type": "remote",

packages/opencode/src/config/config.ts

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -93,6 +93,14 @@ export namespace Config {
9393
throw new InvalidError({ path: item }, { cause: parsed.error })
9494
}
9595

96+
result.plugin = result.plugin || []
97+
result.plugin.push(
98+
...[
99+
...(await Filesystem.globUp("plugin/*.ts", Global.Path.config, Global.Path.config)),
100+
...(await Filesystem.globUp(".opencode/plugin/*.ts", app.path.cwd, app.path.root)),
101+
].map((x) => "file://" + x),
102+
)
103+
96104
// Handle migration from autoshare to share field
97105
if (result.autoshare === true && !result.share) {
98106
result.share = "auto"

packages/opencode/src/plugin/index.ts

Lines changed: 6 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ import { Bus } from "../bus"
55
import { Log } from "../util/log"
66
import { createOpencodeClient } from "@opencode-ai/sdk"
77
import { Server } from "../server/server"
8-
import { pathOr } from "remeda"
98
import { BunProc } from "../bun"
109

1110
export namespace Plugin {
@@ -40,38 +39,14 @@ export namespace Plugin {
4039
}
4140
})
4241

43-
type Path<T, Prefix extends string = ""> = T extends object
44-
? {
45-
[K in keyof T]: K extends string
46-
? T[K] extends Function | undefined
47-
? `${Prefix}${K}`
48-
: Path<T[K], `${Prefix}${K}.`>
49-
: never
50-
}[keyof T]
51-
: never
52-
53-
export type FunctionFromKey<T, P extends Path<T>> = P extends `${infer K}.${infer R}`
54-
? K extends keyof T
55-
? R extends Path<T[K]>
56-
? FunctionFromKey<T[K], R>
57-
: never
58-
: never
59-
: P extends keyof T
60-
? T[P]
61-
: never
62-
6342
export async function trigger<
64-
Name extends Path<Required<Hooks>>,
65-
Input = Parameters<FunctionFromKey<Required<Hooks>, Name>>[0],
66-
Output = Parameters<FunctionFromKey<Required<Hooks>, Name>>[1],
67-
>(fn: Name, input: Input, output: Output): Promise<Output> {
68-
if (!fn) return output
69-
const path = fn.split(".")
43+
Name extends keyof Required<Hooks>,
44+
Input = Parameters<Required<Hooks>[Name]>[0],
45+
Output = Parameters<Required<Hooks>[Name]>[1],
46+
>(name: Name, input: Input, output: Output): Promise<Output> {
47+
if (!name) return output
7048
for (const hook of await state().then((x) => x.hooks)) {
71-
// @ts-expect-error if you feel adventurous, please fix the typing, make sure to bump the try-counter if you
72-
// give up.
73-
// try-counter: 2
74-
const fn = pathOr(hook, path, undefined)
49+
const fn = hook[name]
7550
if (!fn) continue
7651
// @ts-expect-error if you feel adventurous, please fix the typing, make sure to bump the try-counter if you
7752
// give up.

packages/plugin/src/example.ts

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,8 @@ import { Plugin } from "./index"
33
export const ExamplePlugin: Plugin = async ({ app, client, $ }) => {
44
return {
55
permission: {},
6-
tool: {
7-
execute: {
8-
async before(input, output) {
9-
console.log("before", input, output)
10-
},
11-
},
6+
async "chat.params"(input, output) {
7+
output.topP = 1
128
},
139
}
1410
}

packages/plugin/src/index.ts

Lines changed: 24 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -10,47 +10,28 @@ export type Plugin = (input: PluginInput) => Promise<Hooks>
1010

1111
export interface Hooks {
1212
event?: (input: { event: Event }) => Promise<void>
13-
chat?: {
14-
/**
15-
* Called when a new message is received
16-
*/
17-
message?: (input: {}, output: { message: UserMessage; parts: Part[] }) => Promise<void>
18-
/**
19-
* Modify parameters sent to LLM
20-
*/
21-
params?: (
22-
input: { model: Model; provider: Provider; message: UserMessage },
23-
output: { temperature: number; topP: number },
24-
) => Promise<void>
25-
}
26-
permission?: {
27-
/**
28-
* Called when a permission is asked
29-
*/
30-
ask?: (input: Permission, output: { status: "ask" | "deny" | "allow" }) => Promise<void>
31-
}
32-
tool?: {
33-
execute?: {
34-
/**
35-
* Called before a tool is executed
36-
*/
37-
before?: (
38-
input: { tool: string; sessionID: string; callID: string },
39-
output: {
40-
args: any
41-
},
42-
) => Promise<void>
43-
/**
44-
* Called after a tool is executed
45-
*/
46-
after?: (
47-
input: { tool: string; sessionID: string; callID: string },
48-
output: {
49-
title: string
50-
output: string
51-
metadata: any
52-
},
53-
) => Promise<void>
54-
}
55-
}
13+
/**
14+
* Called when a new message is received
15+
*/
16+
"chat.message"?: (input: {}, output: { message: UserMessage; parts: Part[] }) => Promise<void>
17+
/**
18+
* Modify parameters sent to LLM
19+
*/
20+
"chat.params"?: (
21+
input: { model: Model; provider: Provider; message: UserMessage },
22+
output: { temperature: number; topP: number },
23+
) => Promise<void>
24+
"permission.ask"?: (input: Permission, output: { status: "ask" | "deny" | "allow" }) => Promise<void>
25+
"tool.execute.before"?: (
26+
input: { tool: string; sessionID: string; callID: string },
27+
output: { args: any },
28+
) => Promise<void>
29+
"tool.execute.after"?: (
30+
input: { tool: string; sessionID: string; callID: string },
31+
output: {
32+
title: string
33+
output: string
34+
metadata: any
35+
},
36+
) => Promise<void>
5637
}

0 commit comments

Comments
 (0)