matimo-examples 0.1.0-alpha.7

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.
package/.env.example ADDED
@@ -0,0 +1,36 @@
1
+ # OpenAI API Key (required for LangChain agent to work)
2
+ # Get your key from: https://platform.openai.com/api-keys
3
+ # OPENAI_API_KEY=sk-your-api-key-here
4
+
5
+ # Gmail Example Configuration
6
+ # Get your token from: https://developers.google.com/oauthplayground
7
+ # GMAIL_ACCESS_TOKEN=<your-access-token-here>
8
+ # TEST_EMAIL=<your-email@gmail.com>
9
+
10
+ # Slack Example Configuration
11
+ # Get your token from: https://api.slack.com/apps
12
+ # IMPORTANT: Replace C1234567890 with a REAL channel ID where your bot is added
13
+ # Find channel ID: Right-click channel > Copy link > Extract ID from URL (e.g., C1234567890)
14
+ # IMPORTANT: Replace U1234567890 with a REAL user ID for fallback DMs
15
+ # Find user ID: Right-click user > Copy link > Extract ID from URL (e.g., U1234567890)
16
+ # SLACK_BOT_TOKEN=xoxb-your-token-here
17
+ # SLACK_CHANNEL_ID=C1234567890
18
+ # SLACK_USER_ID=U1234567890
19
+ # Postgres Example Configuration
20
+ # CHOOSE ONE of the two authentication methods below:
21
+
22
+ # METHOD 1: Connection String (Recommended)
23
+ # Uncomment and set your full Postgres connection string
24
+ # MATIMO_POSTGRES_URL=postgresql://user:password@localhost:5432/mydatabase
25
+
26
+ # METHOD 2: Separate Environment Variables
27
+ # Uncomment and set these individually if not using connection string
28
+ # MATIMO_POSTGRES_HOST=localhost
29
+ # MATIMO_POSTGRES_PORT=5432
30
+ # MATIMO_POSTGRES_USER=postgres
31
+ # MATIMO_POSTGRES_PASSWORD=your-password
32
+ # MATIMO_POSTGRES_DB=mydatabase
33
+
34
+ # SQL Auto-Approval (optional)
35
+ # Set to 'true' to auto-approve SQL queries without prompting
36
+ # MATIMO_SQL_AUTO_APPROVE=false
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 tallclub
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,525 @@
1
+ # Matimo + LangChain.js Agent Examples
2
+
3
+ Three complete, production-ready AI agent examples showing how to integrate **Matimo SDK** with **LangChain.js**.
4
+
5
+ ## ๐ŸŽฏ What These Examples Demonstrate
6
+
7
+ โœ… **Framework-Independent Tool Execution:**
8
+
9
+ - Matimo loads and manages tools independently
10
+ - Tools work the same way in any framework (LangChain, CrewAI, etc.)
11
+ - No tool redefinition needed across frameworks
12
+ - Simple adapter layer for LangChain integration
13
+
14
+ โœ… **Three SDK Calling Patterns:**
15
+
16
+ 1. **LangChain Official API** (Recommended): Use `createAgent()` with `tool()` function
17
+ - Simplest, fastest, most maintainable approach
18
+ - LangChain handles tool selection and calling automatically
19
+ - Use when: You want production-ready, framework-native integration
20
+
21
+ 2. **Decorator Pattern**: Use `@tool(toolName)` decorator on methods
22
+ - Decorator intercepts calls โ†’ executes via Matimo
23
+ - Use when: You want method-based calling style
24
+
25
+ 3. **Factory Pattern**: Direct `matimo.execute(toolName, params)` calls
26
+ - Call Matimo directly โ†’ tool executes
27
+ - Use when: You prefer functional style
28
+
29
+ โœ… **Full LangChain Integration:**
30
+
31
+ - Real OpenAI GPT-4 agent with multi-step reasoning
32
+ - Tool orchestration with natural language understanding
33
+ - Matimo stays independent of LangChain's details
34
+
35
+ โœ… **Production Ready:**
36
+
37
+ - Independent npm package setup
38
+ - Environment variable management
39
+ - Proper TypeScript configuration
40
+ - Clean imports from Matimo SDK
41
+
42
+ ## ๐Ÿ“ฆ Quick Start
43
+
44
+ ### 1. Install Dependencies
45
+
46
+ ```bash
47
+ npm install
48
+ ```
49
+
50
+ This installs LangChain, Matimo SDK, and all required dependencies.
51
+
52
+ ### 2. Setup Environment
53
+
54
+ ```bash
55
+ # Copy environment template
56
+ cp .env.example .env
57
+
58
+ # Add your OpenAI API key
59
+ # Get key from: https://platform.openai.com/api-keys
60
+ echo "OPENAI_API_KEY=sk-your-key-here" >> .env
61
+ ```
62
+
63
+ ### 3. Run LangChain Official API Agent (โญ Recommended)
64
+
65
+ ```bash
66
+ npm run agent:langchain
67
+ ```
68
+
69
+ **What it does:**
70
+
71
+ - Loads all tools from YAML using Matimo SDK
72
+ - Converts each tool to LangChain's native tool format
73
+ - Uses `createAgent()` for automatic tool orchestration
74
+ - LLM intelligently selects and executes tools
75
+ - Runs 3 example queries with real Matimo execution
76
+
77
+ **Pattern:**
78
+
79
+ ```
80
+ LLM decides tool needed
81
+ โ†“
82
+ createAgent() invokes tool
83
+ โ†“
84
+ LangChain tool() wrapper executes
85
+ โ†“
86
+ Wrapper calls matimo.execute()
87
+ โ†“
88
+ Matimo executes via CommandExecutor or HttpExecutor
89
+ โ†“
90
+ Result flows back through LangChain
91
+ ```
92
+
93
+ **Why this approach is best:**
94
+
95
+ - โœ… Minimal code (~100 lines)
96
+ - โœ… Pure LangChain API (no workarounds)
97
+ - โœ… Automatic schema generation from Zod
98
+ - โœ… Framework handles all complexity
99
+ - โœ… Matimo tools execute natively
100
+ - โœ… Production-ready out of the box
101
+
102
+ **Example output:**
103
+
104
+ ```
105
+ โ“ User: "๐Ÿงฎ What is 42 plus 8?"
106
+
107
+ ๐Ÿ”Œ [MATIMO] Executing tool via Matimo SDK: calculator
108
+ ๐Ÿ“ฅ [MATIMO] Input parameters: {"operation":"add","a":42,"b":8}
109
+ โœ… [MATIMO] Execution successful
110
+
111
+ โœ… Agent Response:
112
+ 42 plus 8 equals 50.
113
+ ```
114
+
115
+ ### 4. Run Decorator Pattern Agent
116
+
117
+ ```bash
118
+ npm run agent:decorator
119
+ ```
120
+
121
+ **What it does:**
122
+
123
+ - Loads all tools from YAML using Matimo SDK
124
+ - Creates agent with `@tool(toolName)` decorated methods
125
+ - Decorator intercepts method calls โ†’ executes via Matimo
126
+ - Uses **dynamic dispatch** to route tool calls to decorated methods
127
+ - No hardcoded routing - scales to any number of tools
128
+ - Runs 3 example queries
129
+
130
+ **Pattern:**
131
+
132
+ ```
133
+ LLM decides tool name (string)
134
+ โ†“
135
+ executeTool(toolName, params)
136
+ โ†“
137
+ getToolMethodMap() maps name โ†’ method name
138
+ โ†“
139
+ Dynamically call decorated method
140
+ โ†“
141
+ @tool decorator intercepts
142
+ โ†“
143
+ Decorator calls matimo.execute()
144
+ โ†“
145
+ Matimo executes via CommandExecutor or HttpExecutor
146
+ โ†“
147
+ Result returned to agent
148
+ ```
149
+
150
+ **Why this approach is elegant:**
151
+
152
+ - โœ… Decorated methods define agent's API clearly
153
+ - โœ… No if-else routing code (scales automatically)
154
+ - โœ… Add 100 tools = just add 100 `@tool()` decorated methods
155
+ - โœ… Full type safety with TypeScript
156
+ - โœ… Decorator pattern working with real magic
157
+ - โœ… Dynamic dispatch handles routing
158
+
159
+ **Example output:**
160
+
161
+ ```
162
+ โ“ Prompt: "๐Ÿงฎ What is 42 plus 8?"
163
+
164
+ ๐Ÿ”ง Using tool: calculator
165
+ Parameters: {"operation":"add","a":42,"b":8}
166
+
167
+ โœ… Result: { result: 50 }
168
+ ```
169
+
170
+ ### 5. Run Factory Pattern Agent
171
+
172
+ ```bash
173
+ npm run agent:factory
174
+ ```
175
+
176
+ **What it does:**
177
+
178
+ - Loads all tools from YAML (only those that actually exist)
179
+ - Directly calls `matimo.execute(toolName, params)`
180
+ - Simple, straightforward execution model
181
+ - Adapts to LangChain for agent orchestration
182
+ - Runs 3 example queries
183
+
184
+ **Pattern:**
185
+
186
+ ```
187
+ Direct Matimo Call
188
+ โ†“
189
+ matimo.execute(toolName, params)
190
+ โ†“
191
+ Registry lookup & execution
192
+ โ†“
193
+ Result returned to LangChain
194
+ ```
195
+
196
+ ## ๐Ÿ”€ Patterns Compared
197
+
198
+ | Aspect | LangChain Official | Decorator | Factory |
199
+ | -------------------- | -------------------------- | ----------------------------------- | ------------------------ |
200
+ | **Call Style** | `createAgent()` + `tool()` | `await agent.method()` | `await matimo.execute()` |
201
+ | **Complexity** | ~100 lines | ~200 lines (with dynamic dispatch) | ~150 lines |
202
+ | **Schema** | Automatic from Zod | Inferred from method signature | Manual mapping |
203
+ | **Tool Binding** | Native LangChain | Decorator intercept with reflection | Direct call |
204
+ | **Scalability** | โœ… Great | โœ… Excellent (no routing code) | โœ… Great |
205
+ | **Type Safety** | โœ… Yes | โœ… Yes (full TS support) | โœ… Yes |
206
+ | **Recommended** | โญ **For frameworks** | โญ **For class-based agents** | For functional style |
207
+ | **Production Ready** | โœ… Yes | โœ… Yes | โœ… Yes |
208
+
209
+ ## ๐Ÿ“ Project Structure
210
+
211
+ ````
212
+ examples/tools/
213
+ โ”œโ”€โ”€ agents/
214
+ โ”‚ โ”œโ”€โ”€ langchain-agent.ts # โญ LangChain Official API (recommended)
215
+ โ”‚ โ”œโ”€โ”€ decorator-pattern-agent.ts # Uses @tool decorator with MatimoInstance
216
+ โ”‚ โ””โ”€โ”€ factory-pattern-agent.ts # Uses matimo.execute() with MatimoInstance
217
+ โ”œโ”€โ”€ package.json # Standalone dependencies (LangChain, Matimo, etc.)
218
+ โ”œโ”€โ”€ tsconfig.json # TypeScript configuration
219
+ โ”œโ”€โ”€ .env.example # Environment template (OPENAI_API_KEY)
220
+ โ”œโ”€โ”€ test-agents.ts # Testing script for tool verification
221
+ โ””โ”€โ”€ README.md # This file
222
+
223
+ All agents load tools from: `../../tools/` (parent project's tool definitions)
224
+
225
+ ## ๐Ÿ”„ SDK Patterns Explained
226
+
227
+ ## ๐Ÿ› ๏ธ Converting Matimo Tools to LangChain
228
+
229
+ ### Approach 1: Official LangChain API (โญ Recommended)
230
+
231
+ Use LangChain's native `tool()` function with Zod schemas:
232
+
233
+ ```typescript
234
+ import { tool } from 'langchain';
235
+ import { z } from 'zod';
236
+ import { MatimoInstance } from 'matimo';
237
+
238
+ // 1. Load Matimo tools
239
+ const matimo = await MatimoInstance.init('./tools');
240
+
241
+ // 2. Convert each Matimo tool to LangChain tool
242
+ function convertMatimoTool(matimo: MatimoInstance, toolName: string) {
243
+ const matimoTool = matimo.getTool(toolName);
244
+
245
+ // Build Zod schema from Matimo parameters
246
+ const schemaShape = {};
247
+ Object.entries(matimoTool.parameters).forEach(([paramName, param]) => {
248
+ let fieldSchema = z.string(); // Map Matimo types to Zod
249
+ if (!param.required) fieldSchema = fieldSchema.optional();
250
+ schemaShape[paramName] = fieldSchema;
251
+ });
252
+
253
+ // Create LangChain tool
254
+ return tool(
255
+ async (input) => {
256
+ // Execute via Matimo (the real tool execution)
257
+ const result = await matimo.execute(toolName, input);
258
+ return JSON.stringify(result);
259
+ },
260
+ {
261
+ name: matimoTool.name,
262
+ description: matimoTool.description,
263
+ schema: z.object(schemaShape),
264
+ }
265
+ );
266
+ }
267
+
268
+ // 3. Create agent with tools
269
+ const agent = await createAgent({
270
+ model: 'gpt-4o-mini',
271
+ tools: matimoTools.map(t => convertMatimoTool(matimo, t.name)),
272
+ });
273
+
274
+ // 4. Invoke agent
275
+ await agent.invoke({
276
+ messages: [{ role: 'user', content: 'What is 42 plus 8?' }],
277
+ });
278
+ ````
279
+
280
+ **Why this works:**
281
+
282
+ - โœ… LangChain handles all schema management
283
+ - โœ… Automatic parameter validation
284
+ - โœ… Native function calling with OpenAI
285
+ - โœ… Zero manual schema binding
286
+ - โœ… ~10 lines of tool conversion code
287
+ - โœ… All Matimo features preserved
288
+
289
+ ### Approach 2: Decorator Pattern
290
+
291
+ Use Matimo's `@tool()` decorator for method-based calling:
292
+
293
+ ```typescript
294
+ import { tool, setGlobalMatimoInstance, MatimoInstance } from 'matimo';
295
+
296
+ // 1. Load tools from YAML
297
+ const matimo = await MatimoInstance.init('./tools');
298
+ setGlobalMatimoInstance(matimo);
299
+
300
+ // 2. Define agent class with decorated methods
301
+ class MyAgent {
302
+ // @tool decorator intercepts call and executes via Matimo
303
+ @tool('calculator')
304
+ async calculator(operation: string, a: number, b: number) {
305
+ throw new Error('Decorator handles execution');
306
+ }
307
+ }
308
+
309
+ // 3. Call decorated method
310
+ const agent = new MyAgent();
311
+ const result = await agent.calculator('add', 5, 3); // Decorator intercepts โ†’ Matimo executes
312
+ ```
313
+
314
+ ### Approach 3: Factory Pattern
315
+
316
+ Use `MatimoInstance.init()` then direct `execute()` calls:
317
+
318
+ ```typescript
319
+ import { MatimoInstance } from 'matimo';
320
+
321
+ // 1. Initialize Matimo with tools directory
322
+ const matimo = await MatimoInstance.init('./tools');
323
+
324
+ // 2. List all available tools
325
+ const tools = matimo.listTools();
326
+
327
+ // 3. Execute tools directly
328
+ const result = await matimo.execute('calculator', {
329
+ operation: 'add',
330
+ a: 5,
331
+ b: 3,
332
+ });
333
+ ```
334
+
335
+ ## ๐Ÿ”„ How It Works: Matimo + LangChain Integration
336
+
337
+ The beauty of Matimo is that it stays **completely independent**:
338
+
339
+ ```
340
+ โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”
341
+ โ”‚ LangChain Agent (framework orchestration) โ”‚
342
+ โ”‚ โ”‚
343
+ โ”‚ LLM decides: "I need to use calculator tool" โ”‚
344
+ โ”‚ โ†“ โ”‚
345
+ โ”‚ createAgent() invokes tool with user's params โ”‚
346
+ โ”‚ โ†“ โ”‚
347
+ โ”‚ LangChain tool() wrapper receives params โ”‚
348
+ โ”‚ โ†“ โ”‚
349
+ โ”‚ โ”Œโ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ” โ”‚
350
+ โ”‚ โ”‚ Matimo Wrapper Function โ”‚ โ”‚
351
+ โ”‚ โ”‚ โ”‚ โ”‚
352
+ โ”‚ โ”‚ const result = await matimo.execute( โ”‚ โ”‚
353
+ โ”‚ โ”‚ 'calculator', โ”‚ โ”‚
354
+ โ”‚ โ”‚ { operation: 'add', a: 42, b: 8 } โ”‚ โ”‚
355
+ โ”‚ โ”‚ ); โ”‚ โ”‚
356
+ โ”‚ โ”‚ โ†“ โ”‚ โ”‚
357
+ โ”‚ โ”‚ Matimo loads: tools/calculator.yaml โ”‚ โ”‚
358
+ โ”‚ โ”‚ Validates params against schema โ”‚ โ”‚
359
+ โ”‚ โ”‚ Executes: node calculator.js --op add 42 8 โ”‚ โ”‚
360
+ โ”‚ โ”‚ Parses output โ”‚ โ”‚
361
+ โ”‚ โ”‚ โ†“ โ”‚ โ”‚
362
+ โ”‚ โ”‚ Returns: { result: 50 } โ”‚ โ”‚
363
+ โ”‚ โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜ โ”‚
364
+ โ”‚ โ†“ โ”‚
365
+ โ”‚ Wrapper returns JSON to LangChain โ”‚
366
+ โ”‚ โ†“ โ”‚
367
+ โ”‚ LLM processes result: "42 + 8 = 50" โ”‚
368
+ โ””โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”€โ”˜
369
+ ```
370
+
371
+ **Key insight:** LangChain orchestrates tool selection, Matimo executes the tool.
372
+
373
+ - โœ… Matimo tools work the same in any framework
374
+ - โœ… No framework-specific tool reimplementation
375
+ - โœ… Add tool to `tools/*.yaml`, it appears everywhere
376
+ - โœ… Changes to tool YAML automatically reflect in all frameworks
377
+
378
+ ## โœ… Verification: Matimo Executes, Not LangChain
379
+
380
+ When you run `npm run agent:langchain`, you'll see debug output confirming **Matimo is executing**:
381
+
382
+ ```
383
+ โ“ User: "๐Ÿงฎ What is 42 plus 8?"
384
+
385
+ ๐Ÿ”Œ [MATIMO] Executing tool via Matimo SDK: calculator
386
+ ๐Ÿ“ฅ [MATIMO] Input parameters: {"operation":"add","a":42,"b":8}
387
+ โœ… [MATIMO] Execution successful
388
+
389
+ โœ… Agent Response:
390
+ 42 plus 8 equals 50.
391
+ ```
392
+
393
+ This proves:
394
+
395
+ 1. โœ… LangChain selected the `calculator` tool
396
+ 2. โœ… LangChain called the tool wrapper
397
+ 3. โœ… **Matimo executed the actual tool** (via CommandExecutor)
398
+ 4. โœ… Result flowed back through both frameworks
399
+
400
+ Not a LangChain toolโ€”a **Matimo tool executed through LangChain's orchestration**.
401
+
402
+ ## ๐Ÿ”‘ Key Principles
403
+
404
+ ### "Define Tools ONCE, Use EVERYWHERE" - The Matimo Philosophy
405
+
406
+ Tools are defined in `../../tools/*.yaml` **ONCE**:
407
+
408
+ ```yaml
409
+ # tools/calculator.yaml
410
+ name: calculator
411
+ description: Perform math operations
412
+ parameters:
413
+ operation:
414
+ type: string
415
+ enum: [add, subtract, multiply, divide]
416
+ a:
417
+ type: number
418
+ b:
419
+ type: number
420
+ execution:
421
+ type: command
422
+ command: node calculator.js
423
+ args: ['--op', '{operation}', '{a}', '{b}']
424
+ ```
425
+
426
+ These same tools are used in:
427
+
428
+ - โœ… This example: **LangChain agents** (via both patterns)
429
+ - โœ… **Matimo SDK direct**: `await matimo.execute('calculator', params)`
430
+ - โœ… **MCP Server**: Claude can call them natively
431
+ - โœ… **REST API**: HTTP endpoints (Phase 2)
432
+ - โœ… **CLI**: Command-line tool runner
433
+ - โœ… **CrewAI, LlamaIndex, etc.**: Framework integration
434
+
435
+ **No duplication. No reimplementation. Pure reusability.**
436
+
437
+ Both this example's agents use the exact same YAML tools - just different calling patterns.
438
+
439
+ ## ๐Ÿš€ Available Tools
440
+
441
+ These examples work with whatever tools are in `../../tools/`:
442
+
443
+ | Tool | Type | Purpose |
444
+ | ------------ | ------- | ------------------------------------------------- |
445
+ | `calculator` | Command | Math operations (add, subtract, multiply, divide) |
446
+ | `echo` | Command | Echo messages back |
447
+ | `http` | HTTP | Make HTTP requests (GET, POST, etc.) |
448
+
449
+ **Framework Independence:** Add any tool to `../../tools/` and it automatically appears in all three agents. No code changes needed.
450
+
451
+ (See parent project's `tools/` directory for all available tools)
452
+
453
+ ## ๐Ÿงช Testing
454
+
455
+ All agents are fully testable. The parent project's test suite validates all tools:
456
+
457
+ ```bash
458
+ # From parent project root
459
+ pnpm test test/integration/
460
+ ```
461
+
462
+ ## ๐Ÿ› Troubleshooting
463
+
464
+ ### "Cannot find module 'matimo'"
465
+
466
+ **Solution:** Make sure parent project is built:
467
+
468
+ ```bash
469
+ cd ../..
470
+ pnpm build
471
+ cd examples/tools
472
+ ### "OPENAI_API_KEY is not set"
473
+
474
+ **Solution:** Create `.env` with your API key:
475
+
476
+ ```bash
477
+ cp .env.example .env
478
+ # Edit .env and add your OpenAI API key
479
+ ```
480
+
481
+ ### LangChain package errors
482
+
483
+ **Solution:** Reinstall all dependencies:
484
+
485
+ ```bash
486
+ rm -rf node_modules package-lock.json
487
+ npm install
488
+ ```
489
+
490
+ ### Tools not executing
491
+
492
+ **Solution:** Ensure parent project tools are compiled:
493
+
494
+ ```bash
495
+ cd ../..
496
+ pnpm build
497
+ cd examples/tools
498
+ npm run agent:langchain # or agent:decorator, agent:factory
499
+ ```
500
+
501
+ ## ๐Ÿ“š Next Steps
502
+
503
+ 1. **Try all three agents** - compare patterns: `npm run agent:langchain`, `agent:decorator`, `agent:factory`
504
+ 2. **Modify agent queries** in `agents/*.ts` - change the example prompts
505
+ 3. **Add custom tools** to `../../tools/` - they auto-appear in all agents
506
+ 4. **Extend the agents** - add memory, streaming, custom system prompts
507
+ 5. **Deploy to production** - use Matimo REST API or MCP server
508
+
509
+ ## ๐Ÿ”— Related Documentation
510
+
511
+ - [Matimo API Reference](../../docs/api-reference/SDK.md)
512
+ - [Tool Specification](../../docs/tool-development/TOOL_SPECIFICATION.md)
513
+ - [Decorator Guide](../../docs/tool-development/DECORATOR_GUIDE.md)
514
+ - [LangChain Documentation](https://docs.langchain.com/)
515
+ - [OpenAI API](https://platform.openai.com/docs/)
516
+
517
+ ## ๐Ÿ’ก Key Takeaway
518
+
519
+ This example proves Matimo's core value proposition:
520
+
521
+ **Define tools ONCE in YAML** โ†“
522
+ **Use them EVERYWHERE**: LangChain (3 patterns), SDK, CrewAI, MCP, REST, CLI โ†“
523
+ **Zero duplication. Pure productivity.**
524
+
525
+ All three agents use the exact same Matimo tools with different SDK patterns. That's the Matimo difference.