@tyvm/knowhow 0.0.109 → 0.0.111

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (108) hide show
  1. package/autodoc/README.md +324 -0
  2. package/autodoc/chat-guide.md +268 -365
  3. package/autodoc/cli-reference.md +399 -473
  4. package/autodoc/config-reference.md +431 -330
  5. package/autodoc/embeddings-guide.md +223 -322
  6. package/autodoc/generate-guide.md +261 -301
  7. package/autodoc/language-plugin-guide.md +221 -247
  8. package/autodoc/modules-guide.md +242 -215
  9. package/autodoc/plugins-guide.md +470 -469
  10. package/autodoc/quickstart-guide.md +67 -70
  11. package/autodoc/skills-guide.md +455 -339
  12. package/autodoc/worker-guide.md +301 -308
  13. package/package.json +1 -1
  14. package/scripts/build-for-node.sh +10 -24
  15. package/src/agents/tools/list.ts +2 -2
  16. package/src/ai.ts +81 -37
  17. package/src/auth/browserLogin.ts +129 -3
  18. package/src/chat/CliChatService.ts +1 -1
  19. package/src/chat/modules/AgentModule.ts +7 -2
  20. package/src/chat/modules/SessionsModule.ts +40 -1
  21. package/src/chat/modules/SystemModule.ts +2 -2
  22. package/src/clients/anthropic.ts +1 -1
  23. package/src/clients/index.ts +25 -6
  24. package/src/clients/openai.ts +8 -5
  25. package/src/clients/types.ts +29 -6
  26. package/src/clients/withRetry.ts +89 -0
  27. package/src/commands/agent.ts +30 -0
  28. package/src/commands/modules.ts +417 -47
  29. package/src/config.ts +1 -1
  30. package/src/fileSync.ts +20 -12
  31. package/src/hashes.ts +43 -22
  32. package/src/index.ts +4 -2
  33. package/src/login.ts +3 -2
  34. package/src/processors/Base64ImageDetector.ts +73 -0
  35. package/src/services/Mcp.ts +14 -1
  36. package/src/services/MediaProcessorService.ts +79 -10
  37. package/src/services/modules/index.ts +47 -18
  38. package/src/utils/http.ts +9 -2
  39. package/tests/processors/Base64ImageDetector.test.ts +160 -0
  40. package/tests/unit/clients/AIClient.test.ts +446 -0
  41. package/tests/unit/clients/withRetry.test.ts +319 -0
  42. package/tests/unit/commands/github-credentials.test.ts +1 -2
  43. package/ts_build/package.json +1 -1
  44. package/ts_build/src/agents/tools/list.js +2 -2
  45. package/ts_build/src/agents/tools/list.js.map +1 -1
  46. package/ts_build/src/ai.d.ts +3 -3
  47. package/ts_build/src/ai.js +51 -23
  48. package/ts_build/src/ai.js.map +1 -1
  49. package/ts_build/src/auth/browserLogin.d.ts +2 -0
  50. package/ts_build/src/auth/browserLogin.js +91 -3
  51. package/ts_build/src/auth/browserLogin.js.map +1 -1
  52. package/ts_build/src/chat/CliChatService.js +1 -1
  53. package/ts_build/src/chat/CliChatService.js.map +1 -1
  54. package/ts_build/src/chat/modules/AgentModule.js +5 -2
  55. package/ts_build/src/chat/modules/AgentModule.js.map +1 -1
  56. package/ts_build/src/chat/modules/SessionsModule.js +30 -1
  57. package/ts_build/src/chat/modules/SessionsModule.js.map +1 -1
  58. package/ts_build/src/chat/modules/SystemModule.js +2 -2
  59. package/ts_build/src/chat/modules/SystemModule.js.map +1 -1
  60. package/ts_build/src/clients/anthropic.js +1 -1
  61. package/ts_build/src/clients/anthropic.js.map +1 -1
  62. package/ts_build/src/clients/index.js +7 -6
  63. package/ts_build/src/clients/index.js.map +1 -1
  64. package/ts_build/src/clients/openai.js +4 -4
  65. package/ts_build/src/clients/openai.js.map +1 -1
  66. package/ts_build/src/clients/types.d.ts +12 -6
  67. package/ts_build/src/clients/withRetry.d.ts +2 -0
  68. package/ts_build/src/clients/withRetry.js +60 -0
  69. package/ts_build/src/clients/withRetry.js.map +1 -0
  70. package/ts_build/src/commands/agent.js +25 -0
  71. package/ts_build/src/commands/agent.js.map +1 -1
  72. package/ts_build/src/commands/modules.js +359 -32
  73. package/ts_build/src/commands/modules.js.map +1 -1
  74. package/ts_build/src/config.js +1 -1
  75. package/ts_build/src/config.js.map +1 -1
  76. package/ts_build/src/fileSync.d.ts +2 -2
  77. package/ts_build/src/fileSync.js +13 -11
  78. package/ts_build/src/fileSync.js.map +1 -1
  79. package/ts_build/src/hashes.d.ts +2 -2
  80. package/ts_build/src/hashes.js +40 -16
  81. package/ts_build/src/hashes.js.map +1 -1
  82. package/ts_build/src/index.js +1 -1
  83. package/ts_build/src/index.js.map +1 -1
  84. package/ts_build/src/login.js +2 -2
  85. package/ts_build/src/login.js.map +1 -1
  86. package/ts_build/src/processors/Base64ImageDetector.d.ts +3 -0
  87. package/ts_build/src/processors/Base64ImageDetector.js +42 -0
  88. package/ts_build/src/processors/Base64ImageDetector.js.map +1 -1
  89. package/ts_build/src/services/Mcp.js +9 -1
  90. package/ts_build/src/services/Mcp.js.map +1 -1
  91. package/ts_build/src/services/MediaProcessorService.d.ts +5 -4
  92. package/ts_build/src/services/MediaProcessorService.js +53 -8
  93. package/ts_build/src/services/MediaProcessorService.js.map +1 -1
  94. package/ts_build/src/services/modules/index.js +35 -12
  95. package/ts_build/src/services/modules/index.js.map +1 -1
  96. package/ts_build/src/utils/http.d.ts +2 -1
  97. package/ts_build/src/utils/http.js +11 -2
  98. package/ts_build/src/utils/http.js.map +1 -1
  99. package/ts_build/tests/processors/Base64ImageDetector.test.js +111 -0
  100. package/ts_build/tests/processors/Base64ImageDetector.test.js.map +1 -1
  101. package/ts_build/tests/unit/clients/AIClient.test.d.ts +1 -0
  102. package/ts_build/tests/unit/clients/AIClient.test.js +339 -0
  103. package/ts_build/tests/unit/clients/AIClient.test.js.map +1 -0
  104. package/ts_build/tests/unit/clients/withRetry.test.d.ts +1 -0
  105. package/ts_build/tests/unit/clients/withRetry.test.js +225 -0
  106. package/ts_build/tests/unit/clients/withRetry.test.js.map +1 -0
  107. package/ts_build/tests/unit/commands/github-credentials.test.js +1 -2
  108. package/ts_build/tests/unit/commands/github-credentials.test.js.map +1 -1
@@ -1,352 +1,379 @@
1
- # Knowhow Custom Modules Guide
1
+ # Custom Modules Guide (Knowhow CLI)
2
2
 
3
- Knowhow **modules** are the primary extension mechanism for adding new capabilities to the Knowhow CLI/runtime. A module is a dynamically loaded package (an npm package or a local file) that can register **tools**, **agents**, **plugins**, **AI clients**, and **chat commands**.
3
+ Knowhow **modules** are the primary extension mechanism for adding new capabilitiestools, agents, plugins, AI clients, and even chat commands—without modifying the Knowhow core.
4
+
5
+ This guide explains how modules are loaded and how to write your own.
4
6
 
5
7
  ---
6
8
 
7
9
  ## 1) What modules are
8
10
 
9
- When Knowhow starts, it reads configuration and **dynamically loads** each configured module. A module can extend Knowhow by contributing any of the following:
11
+ A **module** is a dynamically loaded JavaScript/TypeScript export (usually an **npm package**, sometimes a **local file**) that can extend Knowhow at runtime by providing:
12
+
13
+ - **Tools**: callable functions the LLM/agent can invoke
14
+ - **Agents**: additional agent definitions that can use tools
15
+ - **Plugins**: plugin instances registered into Knowhow’s plugin system
16
+ - **Clients**: AI clients (providers + model lists) registered into Knowhow
17
+ - **Commands**: chat commands the module can define
10
18
 
11
- - **Tools**: functions that Knowhow/agents can call (tool calling)
12
- - **Agents**: preconfigured agent definitions (prompts, tool access, etc.)
13
- - **Plugins**: plugin objects registered under a module-provided name
14
- - **AI clients**: provider/client/model registrations for model routing
15
- - **Commands**: additional chat commands supported by the module
16
- - **Initialization hook (`init`)**: async setup work before registration
19
+ Knowhow loads modules listed in your config and then registers their contributions into the relevant services (Tools, Agents, Plugins, Clients).
17
20
 
18
21
  ---
19
22
 
20
- ## 2) Configuring modules (`knowhow.json`)
23
+ ## 2) Configuring modules (`modules` array in `knowhow.json`)
24
+
25
+ Add module package names and/or local paths to the `modules` array in `knowhow.json`.
21
26
 
22
- In your project’s `knowhow.json`, add a `modules` array.
27
+ ### Local `knowhow.json` example
23
28
 
24
29
  ```jsonc
25
30
  {
26
31
  "modules": [
27
- "@acme/knowhow-module-internal-api",
28
- "./modules/local-module.js"
32
+ "@tyvm/knowhow-module-script",
33
+ "./modules/my-company-module",
34
+ "../../packages/knowhow-module-load-webpage"
29
35
  ]
30
36
  }
31
37
  ```
32
38
 
33
- ### Supported module entries
34
- Each entry supports both:
39
+ ### Supported module specifiers
35
40
 
36
- - **npm package names** (e.g. `@acme/knowhow-module-internal-api`)
37
- - **local file paths** (e.g. `./modules/local-module.js`)
41
+ From the loader behavior, `modules` entries can be:
38
42
 
39
- > Tip: Use the correct extension/format for your runtime (often compiled `.js`). If you author in TypeScript, compile to a Node-loadable format first.
43
+ - **npm package names** (e.g. `@scope/name`, `name`)
44
+ - **local file paths** that start with `"."` (relative to `process.cwd()`), e.g. `./modules/x`
45
+
46
+ **Resolution behavior highlights**
47
+ - Relative entries starting with `"."` are resolved with `path.resolve(process.cwd(), modulePath)`.
48
+ - Package names are resolved using `require.resolve()` with special search paths (see “Global vs local modules” below).
40
49
 
41
50
  ---
42
51
 
43
- ## 3) Global vs local modules
52
+ ## 3) Global vs local modules (load order)
44
53
 
45
- Knowhow supports both a global and local configuration:
54
+ Knowhow supports:
46
55
 
47
- 1. **Global config**: `~/.knowhow/knowhow.json`
48
- 2. **Local config**: your project’s `knowhow.json`
56
+ - **Global modules**: `~/.knowhow/knowhow.json`
57
+ - **Local modules**: `./.knowhow/knowhow.json`
49
58
 
50
59
  ### Load order
51
- Modules load in this order:
52
60
 
53
- 1. **Global modules** from `~/.knowhow/knowhow.json` load **first**
54
- 2. **Local modules** from `./knowhow.json` load **after**
61
+ Modules are loaded in this order:
62
+
63
+ 1. **Global** `modules` array
64
+ 2. **Local** `modules` array
65
+
66
+ This is done by concatenating:
67
+ - `...(globalConfig.modules || [])`
68
+ - `...(localConfig.modules || [])`
55
69
 
56
- This means local modules can add additional capabilities or change behavior depending on how Knowhow merges/handles registrations (for example, tool name conflicts).
70
+ and then de-duplicating via `toUniqueArray(...)` (preserving order).
71
+
72
+ ### Where module packages are resolved from
73
+
74
+ When loading module specifiers, Knowhow searches these locations (in order):
75
+
76
+ 1. `./.knowhow/node_modules` (so `knowhow modules install` “just works”)
77
+ 2. `~/.knowhow/node_modules` (global install)
78
+ 3. `./node_modules` (project install)
57
79
 
58
80
  ---
59
81
 
60
- ## 4) The `KnowhowModule` interface
82
+ ## 4) The `KnowhowModule` interface (what a module must export)
61
83
 
62
- A module must export an object compatible with the `KnowhowModule` interface. At minimum, a module must provide:
84
+ A module must export an object that matches this interface:
63
85
 
64
- ### `init(params)` (async initialization)
65
86
  ```ts
66
- async init(params): Promise<void>
87
+ export interface KnowhowModule {
88
+ init: (params: InitParams) => Promise<void>;
89
+ commands: ModuleChatCommand[];
90
+ tools: ModuleTool[];
91
+ agents: ModuleAgent[];
92
+ plugins: ModulePlugin[];
93
+ clients: ModuleClient[];
94
+ }
67
95
  ```
68
96
 
69
- Knowhow calls `init` during module loading so you can perform setup such as:
97
+ ### Required exports / properties
70
98
 
71
- - validate config
72
- - read environment variables/secrets
73
- - initialize API clients
74
- - precompute schemas or caches
99
+ #### `init(params)` (async)
75
100
 
76
- ### `tools`
77
101
  ```ts
78
- tools: Array<{
79
- name: string;
80
- handler: (...args: any[]) => any;
81
- definition: any;
82
- }>
102
+ init: (params: {
103
+ config: Config;
104
+ cwd: string;
105
+ context?: ModuleContext;
106
+ }) => Promise<void>;
83
107
  ```
84
108
 
85
- Your module provides tools as entries with:
86
- - **`name`**: the tool name
87
- - **`handler`**: the implementation function
88
- - **`definition`**: tool metadata/schema
109
+ Knowhow calls `init()` before registering tools/agents/plugins/clients.
110
+
111
+ - `params.config` is your config (local + merged with globals by the caller)
112
+ - `params.cwd` is `process.cwd()`
113
+ - `params.context` may include services like `Tools`, `Agents`, `Plugins`, etc.
114
+ - The loader checks `context.Agents`, `context.Tools`, etc. before registering.
89
115
 
90
- #### Important: tool definition shape
91
- In Knowhow’s tool registration flow, tool metadata is used to register the tool, and the tool handler is bound using the tool definition’s function name. That implies your `definition` must include a function name (commonly via something like `definition.function.name`).
116
+ #### `tools`
92
117
 
93
- A typical definition looks like:
118
+ An array of:
94
119
 
95
120
  ```ts
96
- {
97
- type: "function",
98
- function: {
99
- name: "my_tool",
100
- description: "...",
101
- parameters: { /* JSON-schema-like */ }
102
- }
103
- }
121
+ type ModuleTool = {
122
+ name: string;
123
+ handler: (...args: any[]) => any;
124
+ definition: Tool;
125
+ };
104
126
  ```
105
127
 
106
- ### `agents`
128
+ Knowhow registers each tool by:
129
+ - `context.Tools.addTool(tool.definition)`
130
+ - `context.Tools.setFunction(tool.definition.function.name, tool.handler)`
131
+
132
+ So your `definition` **must include** `definition.function.name`.
133
+
134
+ #### `agents`
135
+
107
136
  ```ts
108
- agents: any[] // array of agent configs (shape depends on Knowhow)
137
+ export type ModuleAgent = IAgent;
109
138
  ```
110
139
 
111
- Agents are module-provided configurations. The exact schema depends on your Knowhow version, but typically includes:
140
+ So `agents` must be an array of `IAgent` objects (not just plain JSON configs), matching Knowhow’s agent interface.
112
141
 
113
- - agent name
114
- - instructions/system prompt
115
- - allowed tools (by tool name)
116
- - model/provider selection (or references to registered clients/models)
142
+ #### `plugins`
117
143
 
118
- ### `plugins`
119
144
  ```ts
120
- plugins: Array<{
121
- name: string;
122
- plugin: any; // plugin instance/object
123
- }>
145
+ type ModulePlugin = { name: string; plugin: PluginConstructor };
124
146
  ```
125
147
 
126
- ### `clients`
148
+ Knowhow registers each plugin with:
149
+
150
+ - `context.Plugins.registerPlugin(plugin.name, new plugin.plugin(context))`
151
+
152
+ So your module should provide a plugin constructor (`class ...`) that takes `PluginContext`.
153
+
154
+ #### `clients`
155
+
127
156
  ```ts
128
- clients: Array<{
157
+ type ModuleClient = {
158
+ client: GenericClient;
129
159
  provider: string;
130
- client: any; // AI client instance/constructor
131
- models: string[]; // supported model IDs
132
- }>
160
+ models: string[];
161
+ };
133
162
  ```
134
163
 
135
- ### `commands`
164
+ Knowhow registers each client with:
165
+
166
+ - `context.Clients.registerClient(client.provider, client.client)`
167
+ - `context.Clients.registerModels(client.provider, client.models)`
168
+
169
+ #### `commands`
170
+
136
171
  ```ts
137
- commands: any[] // chat commands
172
+ type ModuleChatCommand = {
173
+ name: string;
174
+ description: string;
175
+ handler: (ctx: any) => void;
176
+ };
138
177
  ```
139
178
 
140
- Commands are additional chat-loop commands exposed by your module (exact handler signature depends on Knowhow’s command system).
179
+ Your module can define chat commands. (Registration happens elsewhere in the CLI; the interface is provided for modules to declare them.)
141
180
 
142
181
  ---
143
182
 
144
183
  ## 5) Writing a custom module (step-by-step)
145
184
 
146
- Below is a practical workflow with a concrete example at the end.
185
+ Below is a realistic workflow you can follow.
186
+
187
+ ### Step 1: Create the module file
147
188
 
148
- ### Step 1 — Create the module file
149
- Example layout:
189
+ Example local structure:
150
190
 
151
191
  ```
152
192
  your-project/
153
- knowhow.json
193
+ .knowhow/
154
194
  modules/
155
- hello-module.js (or hello-module.ts compiled to js)
195
+ my-company-module.ts
196
+ .knowhow/knowhow.json
197
+ ```
198
+
199
+ In `knowhow.json`, you’ll later point to:
200
+
201
+ ```jsonc
202
+ {
203
+ "modules": ["./modules/my-company-module"]
204
+ }
205
+ ```
206
+
207
+ ---
208
+
209
+ ### Step 2: Implement `init(params)`
210
+
211
+ Typically used to:
212
+ - read config
213
+ - set up clients or API keys
214
+ - do any async initialization (discover endpoints, validate auth, etc.)
215
+
216
+ ```ts
217
+ export async function init(params: InitParams) {
218
+ // do async setup
219
+ }
156
220
  ```
157
221
 
158
- ### Step 2 Implement `init(params)`
159
- Create an async function that performs any setup once at startup.
222
+ In practice, you export the whole module object with `init`.
160
223
 
161
- ### Step 3 — Add a custom tool (with a definition)
162
- Add a tool entry:
163
- - choose a unique tool `name`
164
- - implement `handler`
165
- - provide `definition` with a callable-function name (commonly `definition.function.name`)
224
+ ---
225
+
226
+ ### Step 3: Add a custom tool
227
+
228
+ A tool is the most common extension. Provide:
166
229
 
167
- ### Step 4 Add a custom agent
168
- Add an agent config referencing your tools and setting prompt/model behavior.
230
+ - a unique tool `name`
231
+ - a `handler` function
232
+ - a `definition` object with `definition.function.name`
169
233
 
170
- ### Step 5 Register the module in `knowhow.json`
171
- Add your module path or npm package to the `modules` array.
234
+ Knowhow will connect `definition.function.name` `handler`.
172
235
 
173
236
  ---
174
237
 
175
- ## 6) Plugin packages (`pluginPackages`)
238
+ ### Step 4: Add a custom agent
239
+
240
+ Your module must provide `IAgent` objects. The exact shape depends on `IAgent` implementation in your Knowhow version.
241
+
242
+ **Pattern:** create an agent class/instance using Knowhow’s agent interfaces and add it to `agents`.
176
243
 
177
- In addition to full **modules**, Knowhow can load **plugin-only** npm packages via a configuration map called `pluginPackages`.
244
+ > Note: Since `IAgent` isn’t shown in the provided code, the exact constructor/signature may differ. Use Knowhow’s built-in agent implementations as reference and then export them as module `agents`.
178
245
 
179
- Conceptually, Knowhow will iterate `pluginPackages` entries and load/instantiate them, typically expecting a default export that represents a plugin constructor/class.
246
+ ---
180
247
 
181
- Example (conceptual):
248
+ ### Step 5: Register the module in `knowhow.json`
182
249
 
183
250
  ```jsonc
184
251
  {
185
- "pluginPackages": {
186
- "acme-lint": "@acme/knowhow-plugin-eslint",
187
- "kb": "./plugins/my-kb-plugin.js"
188
- }
252
+ "modules": [
253
+ "./modules/my-company-module"
254
+ ]
189
255
  }
190
256
  ```
191
257
 
192
- **Use `pluginPackages` when** your package is intended to register plugins only and doesn’t need to define tools/agents/clients.
258
+ Then run:
259
+
260
+ ```bash
261
+ knowhow
262
+ ```
263
+
264
+ (or restart the CLI) so the module gets loaded.
265
+
266
+ ---
267
+
268
+ ## 6) Plugin packages (plugin-only npm registrations)
269
+
270
+ Knowhow also supports **plugin-only packages** via a `pluginPackages`-style map (a simpler way to load/register plugins without a full “module” object).
271
+
272
+ Conceptually:
273
+
274
+ - `modules` are full modules (tools + agents + plugins + clients + commands)
275
+ - `pluginPackages` is for registering **plugins only** from npm packages
276
+
277
+ > The exact config schema can vary by Knowhow version. If you use `pluginPackages`, ensure the referenced package exports a plugin constructor compatible with Knowhow’s plugin system.
193
278
 
194
279
  ---
195
280
 
196
281
  ## 7) Use cases
197
282
 
198
- Modules are ideal for connecting Knowhow to your organization’s environment, for example:
283
+ Common reasons teams create custom modules:
199
284
 
200
285
  1. **Connect to internal APIs**
201
- - Build tools like `internal_ticket_create`, `internal_user_lookup`, `internal_doc_search`
202
- - Use `init` to authenticate and construct API clients
286
+ - Add tools that call `https://internal.company/api/...`
287
+ - Add clients for proprietary model providers
288
+ - Add agents that follow company workflows
203
289
 
204
- 2. **Custom tools**
205
- - Wrap internal services as LLM-callable tools
206
- - Provide JSON-schema-like definitions so agents can call them safely
290
+ 2. **Company-specific tools**
291
+ - e.g., “Create Jira ticket”, “Search internal docs”, “Trigger deployment”
292
+ - Provide tool definitions with strict JSON schemas and safe handlers
207
293
 
208
294
  3. **Company-specific agents**
209
- - Ship agents tuned for your workflows (support triage, engineering review, compliance checks)
210
- - Restrict agents to only the tools you want them to use
295
+ - Add agents with tailored instructions and model/provider selection
296
+ - Reuse built-in tools and add new company-only tools
211
297
 
212
- 4. **Custom AI clients**
213
- - Register model providers that point to internal gateways or custom hosting
214
- - Limit allowed models to those approved by your org
298
+ 4. **Environment-specific behavior**
299
+ - In `init`, detect environment variables, feature flags, or endpoint availability
300
+ - Register only the tools/clients that are valid for this deployment
215
301
 
216
302
  ---
217
303
 
218
- ## Complete working TypeScript example (minimal module)
304
+ # Complete working TypeScript example (minimal module)
219
305
 
220
- > This is a minimal module that:
221
- > - implements `init`
222
- > - registers one tool with a `definition.function.name`
223
- > - registers one agent
224
- > - leaves plugins/clients empty
225
- > - registers one chat command
226
- >
227
- > **Save as:** `modules/minimal-module.ts`
228
- > **Compile to JS** (CommonJS or runtime-compatible output), then reference the compiled `.js` in `knowhow.json`.
306
+ This minimal module registers **one tool**: `getGreeting({ name })`.
229
307
 
230
- ### `modules/minimal-module.ts`
231
- ```ts
232
- // modules/minimal-module.ts
308
+ It includes:
309
+ - `init()`
310
+ - `tools` with a proper `definition.function.name`
311
+ - everything else left empty
233
312
 
234
- // If you have the exact Knowhow types in your repo, replace `any` with real imports.
235
- // This example is intentionally robust against type mismatches.
313
+ > Save this file as: `./modules/minimal-greeting-module.ts` and reference it in `./.knowhow/knowhow.json`.
236
314
 
237
- type ToolDefinition = {
238
- type: "function";
239
- function: {
240
- name: string;
241
- description?: string;
242
- parameters?: any;
243
- };
244
- };
315
+ ## `modules/minimal-greeting-module.ts`
245
316
 
246
- type KnowhowModule = {
247
- init: (params: { config: any; cwd: string }) => Promise<void> | void;
248
- tools: Array<{
249
- name: string;
250
- handler: (args: any) => Promise<any> | any;
251
- definition: ToolDefinition;
252
- }>;
253
- agents: any[];
254
- plugins: Array<{ name: string; plugin: any }>;
255
- clients: Array<{ provider: string; client: any; models: string[] }>;
256
- commands: any[];
257
- };
258
-
259
- const toolDefinition: ToolDefinition = {
317
+ ```ts
318
+ import type { KnowhowModule, InitParams, ModuleTool } from "../src/services/modules/types";
319
+ import type { Tool } from "../src/clients/types";
320
+
321
+ /**
322
+ * Minimal, working module:
323
+ * - provides 1 tool
324
+ * - no agents/plugins/clients/commands
325
+ */
326
+ const toolDefinition: Tool = {
260
327
  type: "function",
261
328
  function: {
262
- name: "demo_echo",
263
- description: "Echoes input back to the caller.",
329
+ name: "getGreeting",
330
+ description: "Return a friendly greeting for a given name.",
264
331
  parameters: {
265
332
  type: "object",
266
333
  properties: {
267
- text: { type: "string", description: "Text to echo" }
334
+ name: { type: "string", description: "Name to greet" }
268
335
  },
269
- required: ["text"],
270
- additionalProperties: false
336
+ required: ["name"]
271
337
  }
272
338
  }
273
339
  };
274
340
 
341
+ const greetingTool: ModuleTool = {
342
+ name: "getGreeting",
343
+ definition: toolDefinition,
344
+ handler: ({ name }: { name: string }) => {
345
+ return `Hello, ${name}! 👋`;
346
+ }
347
+ };
348
+
275
349
  const module: KnowhowModule = {
276
- // 1) Required async initialization hook
277
- async init({ config, cwd }) {
278
- // Example: validate config or prepare resources once at startup
279
- // console.log("[minimal-module] init", { cwd, hasConfig: !!config });
280
- void config;
281
- void cwd;
350
+ async init(_params: InitParams) {
351
+ // Optional initialization.
352
+ // You could validate env vars or configure SDK clients here.
282
353
  },
283
354
 
284
- // 2) Tool registrations
285
- tools: [
286
- {
287
- name: "demo_echo",
288
- definition: toolDefinition,
289
-
290
- // Important: handler is bound to definition.function.name by Knowhow’s loader
291
- handler: async (args: any) => {
292
- const text = typeof args?.text === "string" ? args.text : "";
293
- return { echoed: text };
294
- }
295
- }
296
- ],
297
-
298
- // 3) Agent registrations (shape depends on Knowhow’s IAgent schema)
299
- agents: [
300
- {
301
- name: "demo-echo-agent",
302
- description: "A demo agent that can call demo_echo.",
303
- // Common pattern: restrict the agent to specific tools by name
304
- tools: ["demo_echo"],
305
- // Provide instructions/prompt. (Field names vary by Knowhow version.)
306
- systemPrompt: "You are a demo agent. When asked to echo, call demo_echo."
307
- }
308
- ],
355
+ commands: [],
309
356
 
310
- // 4) Plugin registrations (optional)
311
- plugins: [],
357
+ tools: [greetingTool],
312
358
 
313
- // 5) AI client registrations (optional)
314
- clients: [],
315
-
316
- // 6) Chat commands (optional; exact handler signature depends on Knowhow)
317
- commands: [
318
- {
319
- name: "/echo",
320
- description: "Echo text using the demo_echo tool.",
321
- handler: (ctx: any) => {
322
- // This is a minimal placeholder. Depending on Knowhow’s command system,
323
- // you may need to call a tool runner from ctx.
324
- const raw = typeof ctx?.args === "string" ? ctx.args : ctx?.args?.text;
325
- const text = typeof raw === "string" ? raw : "hello";
326
- ctx?.reply?.({ text: `Echo: ${text}` });
327
- }
328
- }
329
- ]
359
+ agents: [],
360
+ plugins: [],
361
+ clients: []
330
362
  };
331
363
 
332
- // Export strategy:
333
- // - If your Knowhow loader uses require(), CommonJS export can be safest.
334
- // - This `export =` pattern works with CommonJS outputs.
335
- export = module;
364
+ export default module;
336
365
  ```
337
366
 
338
- ### Register it in `knowhow.json`
339
-
340
- After compiling, point to the compiled JS file, for example:
367
+ ## Register it in `./.knowhow/knowhow.json`
341
368
 
342
369
  ```jsonc
343
370
  {
344
- "modules": [
345
- "./modules/dist/minimal-module.js"
346
- ]
371
+ "modules": ["./modules/minimal-greeting-module"]
347
372
  }
348
373
  ```
349
374
 
375
+ Then restart Knowhow.
376
+
350
377
  ---
351
378
 
352
- If you paste (or link) the exact `KnowhowModule`, `Tool` definition, and `IAgent` type shapes from your source tree, I can tailor the example to be **fully type-checked** (no `any`) and ensure your command handler matches the exact runtime signature.
379
+ If you share your Knowhow version and (optionally) the `IAgent` / `Tool` type definitions from your repo, I can provide a fully compiling example that also includes a custom agent and a plugin/client.