@koi-language/koi 1.0.5 → 1.1.0
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/README.md +4 -125
- package/examples/.build/agent-dialogue.ts +138 -0
- package/examples/.build/agent-dialogue.ts.map +1 -0
- package/examples/.build/chess.ts +77 -0
- package/examples/.build/chess.ts.map +1 -0
- package/examples/.build/delegation-test.ts +140 -0
- package/examples/.build/delegation-test.ts.map +1 -0
- package/examples/.build/dialog-demo.ts +77 -0
- package/examples/.build/dialog-demo.ts.map +1 -0
- package/examples/.build/hello-world.ts +77 -0
- package/examples/.build/hello-world.ts.map +1 -0
- package/examples/.build/lover-dialog-demo.ts +77 -0
- package/examples/.build/lover-dialog-demo.ts.map +1 -0
- package/examples/.build/package.json +3 -0
- package/examples/.build/registry-interactive-demo.ts +202 -0
- package/examples/.build/registry-interactive-demo.ts.map +1 -0
- package/examples/.build/registry-playbook-demo.ts +201 -0
- package/examples/.build/registry-playbook-demo.ts.map +1 -0
- package/examples/.build/tic-tac-toe.ts +77 -0
- package/examples/.build/tic-tac-toe.ts.map +1 -0
- package/examples/actions-demo.koi +8 -9
- package/examples/activists-dialogue.koi +75 -0
- package/examples/agent-dialogue.koi +66 -0
- package/examples/chess.koi +19 -0
- package/examples/counter.koi +20 -69
- package/examples/delegation-test.koi +16 -18
- package/examples/dialog-demo.koi +20 -0
- package/examples/hello-world.koi +7 -43
- package/examples/mcp-stdio-demo.koi +29 -0
- package/examples/memory-test.koi +49 -0
- package/examples/mobile-mcp-demo.koi +32 -0
- package/examples/multi-event-handler-test.koi +16 -18
- package/examples/pipeline.koi +15 -17
- package/examples/prompt-demo.koi +20 -0
- package/examples/{registry-playbook-email-compositor.koi → registry-interactive-demo.koi} +27 -27
- package/examples/registry-playbook-demo.koi +28 -28
- package/examples/skill-import-test.koi +7 -9
- package/examples/skills/.build/math-operations.ts +1656 -0
- package/examples/skills/.build/math-operations.ts.map +1 -0
- package/examples/skills/.build/package.json +3 -0
- package/examples/skills/.build/string-operations.ts +1643 -0
- package/examples/skills/.build/string-operations.ts.map +1 -0
- package/examples/skills/advanced/.build/index.ts +3223 -0
- package/examples/skills/advanced/.build/index.ts.map +1 -0
- package/examples/skills/advanced/.build/package.json +3 -0
- package/examples/skills/advanced/index.koi +3 -5
- package/examples/skills/math-operations.koi +1 -3
- package/examples/skills/string-operations.koi +1 -3
- package/examples/tic-tac-toe.koi +19 -0
- package/examples/utils/echo-mcp-server.js +141 -0
- package/examples/web-delegation-demo.koi +15 -17
- package/package.json +2 -1
- package/src/cli/koi.js +30 -41
- package/src/compiler/build-optimizer.js +204 -289
- package/src/compiler/cache-manager.js +1 -1
- package/src/compiler/import-resolver.js +5 -9
- package/src/compiler/parser.js +6072 -3476
- package/src/compiler/transpiler.js +346 -38
- package/src/grammar/koi.pegjs +302 -62
- package/src/runtime/actions/{format.js → call-llm.js} +37 -44
- package/src/runtime/actions/call-mcp.js +97 -0
- package/src/runtime/actions/if.js +179 -0
- package/src/runtime/actions/print.js +3 -1
- package/src/runtime/actions/prompt-user.js +75 -0
- package/src/runtime/actions/repeat.js +147 -0
- package/src/runtime/actions/shell.js +185 -0
- package/src/runtime/actions/while.js +205 -0
- package/src/runtime/agent.js +592 -178
- package/src/runtime/cli-display.js +26 -0
- package/src/runtime/cli-input.js +421 -0
- package/src/runtime/cli-logger.js +2 -5
- package/src/runtime/cli-markdown.js +61 -0
- package/src/runtime/cli-select.js +106 -0
- package/src/runtime/incremental-json-parser.js +51 -17
- package/src/runtime/index.js +1 -0
- package/src/runtime/llm-provider.js +1083 -572
- package/src/runtime/mcp-registry.js +141 -0
- package/src/runtime/mcp-stdio-client.js +334 -0
- package/src/runtime/planner.js +1 -1
- package/src/runtime/playbook-session.js +259 -0
- package/src/runtime/registry-backends/keyv-sqlite.js +1 -1
- package/src/runtime/registry-backends/local.js +1 -1
- package/src/runtime/router.js +22 -26
- package/src/runtime/runtime.js +7 -1
- package/examples/cache-test.koi +0 -29
- package/examples/calculator.koi +0 -61
- package/examples/clear-registry.js +0 -33
- package/examples/clear-registry.koi +0 -30
- package/examples/code-introspection-test.koi +0 -149
- package/examples/directory-import-test.koi +0 -84
- package/examples/hello-world-claude.koi +0 -52
- package/examples/hello.koi +0 -24
- package/examples/mcp-example.koi +0 -70
- package/examples/new-import-test.koi +0 -89
- package/examples/registry-demo.koi +0 -184
- package/examples/registry-playbook-email-compositor-2.koi +0 -140
- package/examples/sentiment.koi +0 -90
- package/examples/simple.koi +0 -48
- package/examples/task-chaining-demo.koi +0 -244
- package/examples/test-await.koi +0 -22
- package/examples/test-crypto-sha256.koi +0 -196
- package/examples/test-delegation.koi +0 -41
- package/examples/test-multi-team-routing.koi +0 -258
- package/examples/test-no-handler.koi +0 -35
- package/examples/test-npm-import.koi +0 -67
- package/examples/test-parse.koi +0 -10
- package/examples/test-peers-with-team.koi +0 -59
- package/examples/test-permissions-fail.koi +0 -20
- package/examples/test-permissions.koi +0 -36
- package/examples/test-simple-registry.koi +0 -31
- package/examples/test-typescript-import.koi +0 -64
- package/examples/test-uses-team-syntax.koi +0 -25
- package/examples/test-uses-team.koi +0 -31
|
@@ -1,84 +0,0 @@
|
|
|
1
|
-
// ============================================================
|
|
2
|
-
// Directory Import Test
|
|
3
|
-
// Tests importing from directories (looks for index.koi)
|
|
4
|
-
// ============================================================
|
|
5
|
-
|
|
6
|
-
package "demo.koi.directory"
|
|
7
|
-
|
|
8
|
-
// Import from directory - automatically finds index.koi
|
|
9
|
-
import "./skills/advanced"
|
|
10
|
-
|
|
11
|
-
role Worker { can work }
|
|
12
|
-
|
|
13
|
-
// Agent that uses skills from the directory import
|
|
14
|
-
Agent StatisticsProcessor : Worker {
|
|
15
|
-
llm default = { provider: "openai", model: "gpt-4o-mini", temperature: 0.1, max_tokens: 300 }
|
|
16
|
-
uses Skill StatisticalAnalysis
|
|
17
|
-
|
|
18
|
-
on process(args: Json) {
|
|
19
|
-
playbook """
|
|
20
|
-
Process statistical analysis for: ${JSON.stringify(args)}
|
|
21
|
-
|
|
22
|
-
Pass the "numbers" array to the tool and return the result.
|
|
23
|
-
"""
|
|
24
|
-
}
|
|
25
|
-
}
|
|
26
|
-
|
|
27
|
-
Team WorkerTeam {
|
|
28
|
-
processor = StatisticsProcessor
|
|
29
|
-
analyzer = DataAnalyzer // Agent from the imported directory
|
|
30
|
-
}
|
|
31
|
-
|
|
32
|
-
// Demo runner
|
|
33
|
-
Agent DemoRunner : Worker {
|
|
34
|
-
uses Team WorkerTeam
|
|
35
|
-
|
|
36
|
-
on runTest(args: Json) {
|
|
37
|
-
console.log("╔════════════════════════════════════════════╗")
|
|
38
|
-
console.log("║ Directory Import Test ║")
|
|
39
|
-
console.log("║ import \"./skills/advanced\" ║")
|
|
40
|
-
console.log("╚════════════════════════════════════════════╝\n")
|
|
41
|
-
|
|
42
|
-
// Test 1: Calculate mean using skill directly
|
|
43
|
-
console.log("📋 Test 1: Calculate mean of [10, 20, 30, 40, 50]")
|
|
44
|
-
console.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━")
|
|
45
|
-
|
|
46
|
-
const meanResult =
|
|
47
|
-
await send peers.event("process").role(Worker).any()({
|
|
48
|
-
operation: "mean",
|
|
49
|
-
numbers: [10, 20, 30, 40, 50]
|
|
50
|
-
}) timeout 10s
|
|
51
|
-
|
|
52
|
-
console.log("Result:", JSON.stringify(meanResult, null, 2))
|
|
53
|
-
|
|
54
|
-
// Test 2: Calculate median
|
|
55
|
-
console.log("\n📋 Test 2: Calculate median of [1, 3, 5, 7, 9, 11]")
|
|
56
|
-
console.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━")
|
|
57
|
-
|
|
58
|
-
const medianResult =
|
|
59
|
-
await send peers.event("process").role(Worker).any()({
|
|
60
|
-
operation: "median",
|
|
61
|
-
numbers: [1, 3, 5, 7, 9, 11]
|
|
62
|
-
}) timeout 10s
|
|
63
|
-
|
|
64
|
-
console.log("Result:", JSON.stringify(medianResult, null, 2))
|
|
65
|
-
|
|
66
|
-
// Test 3: Use the imported DataAnalyzer agent
|
|
67
|
-
console.log("\n📋 Test 3: Full analysis using DataAnalyzer agent!!!!")
|
|
68
|
-
console.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━")
|
|
69
|
-
|
|
70
|
-
const analysisResult =
|
|
71
|
-
await send peers.event("analyze").role(DataScientist).any()({
|
|
72
|
-
numbers: [15, 25, 35, 45, 55, 65, 75]
|
|
73
|
-
}) timeout 10s
|
|
74
|
-
|
|
75
|
-
console.log("Result:", JSON.stringify(analysisResult, null, 2))
|
|
76
|
-
|
|
77
|
-
return {
|
|
78
|
-
success: true,
|
|
79
|
-
tests_completed: 3
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
run DemoRunner.runTest({})
|
|
@@ -1,52 +0,0 @@
|
|
|
1
|
-
// ============================================================
|
|
2
|
-
// Koi — Hello World with Claude
|
|
3
|
-
// Using Anthropic's Claude instead of OpenAI
|
|
4
|
-
// ============================================================
|
|
5
|
-
|
|
6
|
-
package "demo.koi.helloworld.claude"
|
|
7
|
-
|
|
8
|
-
role Worker { can execute }
|
|
9
|
-
|
|
10
|
-
// Agent with playbook using Claude
|
|
11
|
-
Agent Greeter : Worker {
|
|
12
|
-
llm default = { provider: "anthropic", model: "claude-3-5-haiku-20241022", temperature: 0.7, max_tokens: 200 }
|
|
13
|
-
|
|
14
|
-
on greet(args: Json) {
|
|
15
|
-
playbook """
|
|
16
|
-
You are a friendly greeter. Generate a warm, creative greeting for the person whose name is in args.name.
|
|
17
|
-
|
|
18
|
-
Return a JSON object with this exact structure:
|
|
19
|
-
{
|
|
20
|
-
"greeting": "Your creative greeting here",
|
|
21
|
-
"language": "english",
|
|
22
|
-
"style": "friendly"
|
|
23
|
-
}
|
|
24
|
-
|
|
25
|
-
Make the greeting unique and warm, but keep it under 50 words.
|
|
26
|
-
"""
|
|
27
|
-
}
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
Team HelloTeam {
|
|
31
|
-
greeter = Greeter
|
|
32
|
-
}
|
|
33
|
-
|
|
34
|
-
// Orchestrator with procedural code
|
|
35
|
-
Agent Orchestrator : Worker {
|
|
36
|
-
uses Team HelloTeam
|
|
37
|
-
|
|
38
|
-
on start(args: Json) {
|
|
39
|
-
const name = args.name
|
|
40
|
-
|
|
41
|
-
const result =
|
|
42
|
-
await send peers.event("greet").role(Worker).any()({ name: name }) timeout 30s
|
|
43
|
-
|
|
44
|
-
return {
|
|
45
|
-
success: true,
|
|
46
|
-
name: name,
|
|
47
|
-
response: result
|
|
48
|
-
}
|
|
49
|
-
}
|
|
50
|
-
}
|
|
51
|
-
|
|
52
|
-
run Orchestrator.start({ name: "World" })
|
package/examples/hello.koi
DELETED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
// Minimal test
|
|
2
|
-
package "test"
|
|
3
|
-
|
|
4
|
-
role Worker { can execute }
|
|
5
|
-
|
|
6
|
-
Agent Test : Worker {
|
|
7
|
-
on test(args: Json) {
|
|
8
|
-
return { ok: true }
|
|
9
|
-
}
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
Team T {
|
|
13
|
-
t = Test
|
|
14
|
-
}
|
|
15
|
-
|
|
16
|
-
Agent Orch : Worker {
|
|
17
|
-
uses Team T
|
|
18
|
-
on start(args: Json) {
|
|
19
|
-
const r = await send peers.event("test").role(Worker).any()({}) timeout 2s
|
|
20
|
-
return r
|
|
21
|
-
}
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
run Orch.start({})
|
package/examples/mcp-example.koi
DELETED
|
@@ -1,70 +0,0 @@
|
|
|
1
|
-
// ============================================================
|
|
2
|
-
// Koi — MCP (Model Context Protocol) Example
|
|
3
|
-
// Demonstrates using MCP addresses to reference remote agents
|
|
4
|
-
// ============================================================
|
|
5
|
-
|
|
6
|
-
package "demo.koi.mcp"
|
|
7
|
-
|
|
8
|
-
role Worker { can execute }
|
|
9
|
-
role Lead { can delegate }
|
|
10
|
-
|
|
11
|
-
// Local agent
|
|
12
|
-
Agent LocalProcessor : Worker {
|
|
13
|
-
on process(args: Json) {
|
|
14
|
-
const data = args.data
|
|
15
|
-
const processed = "LOCAL: " + data
|
|
16
|
-
return { result: processed, source: "local" }
|
|
17
|
-
}
|
|
18
|
-
}
|
|
19
|
-
|
|
20
|
-
// Team with both local and remote (MCP) agents
|
|
21
|
-
Team HybridTeam {
|
|
22
|
-
// Regular local agent
|
|
23
|
-
local = LocalProcessor
|
|
24
|
-
|
|
25
|
-
// Remote agents via MCP addresses
|
|
26
|
-
// Format: mcp://server/path
|
|
27
|
-
remote1 = mcp://agent.local/processor
|
|
28
|
-
remote2 = mcp://service.local/analyzer
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
// Orchestrator that uses both local and remote agents
|
|
32
|
-
Agent Orchestrator : Lead {
|
|
33
|
-
uses Team HybridTeam
|
|
34
|
-
|
|
35
|
-
on start(args: Json) {
|
|
36
|
-
const data = args.data
|
|
37
|
-
|
|
38
|
-
// This will try local first, then MCP agents
|
|
39
|
-
const result =
|
|
40
|
-
await send peers.event("process").role(Worker).any()({ data: data }) timeout 10s
|
|
41
|
-
|
|
42
|
-
return {
|
|
43
|
-
success: true,
|
|
44
|
-
result: result
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
on processAll(args: Json) {
|
|
49
|
-
const data = args.data
|
|
50
|
-
|
|
51
|
-
// Process with ALL agents (local + MCP)
|
|
52
|
-
const results =
|
|
53
|
-
await send peers.event("process").role(Worker).all()({ data: data }) timeout 15s
|
|
54
|
-
|
|
55
|
-
return {
|
|
56
|
-
success: true,
|
|
57
|
-
count: 3,
|
|
58
|
-
results: results
|
|
59
|
-
}
|
|
60
|
-
}
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
// Example with MCP skill reference
|
|
64
|
-
Team DistributedTeam {
|
|
65
|
-
orchestrator = Orchestrator
|
|
66
|
-
// Reference a remote skill
|
|
67
|
-
sentiment = mcp://skills.local/sentiment-analysis
|
|
68
|
-
}
|
|
69
|
-
|
|
70
|
-
run Orchestrator.start({ data: "Hello from Koi with MCP support!" })
|
|
@@ -1,89 +0,0 @@
|
|
|
1
|
-
// ============================================================
|
|
2
|
-
// New Import System Test
|
|
3
|
-
// Tests the new simplified import syntax
|
|
4
|
-
// ============================================================
|
|
5
|
-
|
|
6
|
-
package "demo.koi.new.import"
|
|
7
|
-
|
|
8
|
-
// New import syntax - imports everything (Skills, Agents, Roles, Teams)
|
|
9
|
-
import "./skills/math-operations.koi"
|
|
10
|
-
import "@koi-lang/common-skills"
|
|
11
|
-
|
|
12
|
-
role Worker { can work }
|
|
13
|
-
|
|
14
|
-
// Agent that uses imported skills from both local and npm package
|
|
15
|
-
Agent DataProcessor : Worker {
|
|
16
|
-
llm default = { provider: "openai", model: "gpt-4o-mini", temperature: 0.1, max_tokens: 300 }
|
|
17
|
-
// Comma-separated syntax (cleaner!)
|
|
18
|
-
uses Skill MathOperations, DataValidation, DataTransformation
|
|
19
|
-
|
|
20
|
-
on process(args: Json) {
|
|
21
|
-
playbook """
|
|
22
|
-
Process the request: ${JSON.stringify(args)}
|
|
23
|
-
|
|
24
|
-
Use the available tools (math, validation, transformation) to complete the task.
|
|
25
|
-
Return the result as JSON.
|
|
26
|
-
"""
|
|
27
|
-
}
|
|
28
|
-
}
|
|
29
|
-
|
|
30
|
-
Team WorkerTeam {
|
|
31
|
-
processor = DataProcessor
|
|
32
|
-
// Also use the imported EmailValidator agent
|
|
33
|
-
emailValidator = EmailValidator
|
|
34
|
-
}
|
|
35
|
-
|
|
36
|
-
// Demo runner
|
|
37
|
-
Agent DemoRunner : Worker {
|
|
38
|
-
uses Team WorkerTeam
|
|
39
|
-
|
|
40
|
-
on runTest(args: Json) {
|
|
41
|
-
console.log("╔════════════════════════════════════════════╗")
|
|
42
|
-
console.log("║ New Import System Test ║")
|
|
43
|
-
console.log("║ Local files + npm packages ║")
|
|
44
|
-
console.log("╚════════════════════════════════════════════╝\n")
|
|
45
|
-
|
|
46
|
-
// Test 1: Use local skill (math)
|
|
47
|
-
console.log("📋 Test 1: Math operation from local skill")
|
|
48
|
-
console.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━")
|
|
49
|
-
|
|
50
|
-
const mathResult =
|
|
51
|
-
await send peers.event("process").role(Worker).any()({
|
|
52
|
-
operation: "add",
|
|
53
|
-
a: 15,
|
|
54
|
-
b: 27
|
|
55
|
-
}) timeout 10s
|
|
56
|
-
|
|
57
|
-
console.log("Result:", JSON.stringify(mathResult, null, 2))
|
|
58
|
-
|
|
59
|
-
// Test 2: Use npm package skill (validation)
|
|
60
|
-
console.log("\n📋 Test 2: Email validation from npm package")
|
|
61
|
-
console.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━")
|
|
62
|
-
|
|
63
|
-
const validationResult =
|
|
64
|
-
await send peers.event("process").role(Worker).any()({
|
|
65
|
-
operation: "validateEmail",
|
|
66
|
-
email: "test@example.com"
|
|
67
|
-
}) timeout 10s
|
|
68
|
-
|
|
69
|
-
console.log("Result:", JSON.stringify(validationResult, null, 2))
|
|
70
|
-
|
|
71
|
-
// Test 3: Use imported agent directly
|
|
72
|
-
console.log("\n📋 Test 3: Using imported EmailValidator agent")
|
|
73
|
-
console.log("━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━")
|
|
74
|
-
|
|
75
|
-
const agentResult =
|
|
76
|
-
await send peers.event("validate").role(Validator).any()({
|
|
77
|
-
email: "invalid-email"
|
|
78
|
-
}) timeout 10s
|
|
79
|
-
|
|
80
|
-
console.log("Result:", JSON.stringify(agentResult, null, 2))
|
|
81
|
-
|
|
82
|
-
return {
|
|
83
|
-
success: true,
|
|
84
|
-
tests_completed: 3
|
|
85
|
-
}
|
|
86
|
-
}
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
run DemoRunner.runTest({})
|
|
@@ -1,184 +0,0 @@
|
|
|
1
|
-
// Registry Demo - Shared data store between agents
|
|
2
|
-
package "registry.demo"
|
|
3
|
-
|
|
4
|
-
role Worker { can execute }
|
|
5
|
-
|
|
6
|
-
// Agent that writes data to the registry
|
|
7
|
-
Agent Writer : Worker {
|
|
8
|
-
on saveUser(args: Json) {
|
|
9
|
-
const userId = args.id
|
|
10
|
-
const userData = {
|
|
11
|
-
name: args.name,
|
|
12
|
-
age: args.age,
|
|
13
|
-
email: args.email,
|
|
14
|
-
createdAt: Date.now()
|
|
15
|
-
}
|
|
16
|
-
|
|
17
|
-
await registry.set("user:" + userId, userData)
|
|
18
|
-
|
|
19
|
-
console.log("✅ Saved user:", userId)
|
|
20
|
-
return { saved: true, userId: userId }
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
on saveConfig(args: Json) {
|
|
24
|
-
await registry.set("config:app", {
|
|
25
|
-
theme: args.theme || "dark",
|
|
26
|
-
language: args.language || "en",
|
|
27
|
-
notifications: args.notifications !== false
|
|
28
|
-
})
|
|
29
|
-
|
|
30
|
-
console.log("✅ Saved config")
|
|
31
|
-
return { saved: true }
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
// Agent that reads data from the registry
|
|
36
|
-
Agent Reader : Worker {
|
|
37
|
-
on getUser(args: Json) {
|
|
38
|
-
const userId = args.id
|
|
39
|
-
const user = await registry.get("user:" + userId)
|
|
40
|
-
|
|
41
|
-
if (!user) {
|
|
42
|
-
console.log("❌ User not found:", userId)
|
|
43
|
-
return { found: false, userId: userId }
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
console.log("📖 Retrieved user:", user.name)
|
|
47
|
-
return { found: true, user: user }
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
on getConfig(args: Json) {
|
|
51
|
-
const config = await registry.get("config:app")
|
|
52
|
-
|
|
53
|
-
if (!config) {
|
|
54
|
-
console.log("⚙️ No config found, using defaults")
|
|
55
|
-
return { found: false, config: null }
|
|
56
|
-
}
|
|
57
|
-
|
|
58
|
-
console.log("⚙️ Retrieved config:", JSON.stringify(config))
|
|
59
|
-
return { found: true, config: config }
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
on listUsers(args: Json) {
|
|
63
|
-
const userKeys = await registry.keys("user:")
|
|
64
|
-
console.log("📋 Found", userKeys.length, "users")
|
|
65
|
-
|
|
66
|
-
const users = []
|
|
67
|
-
for (const key of userKeys) {
|
|
68
|
-
const user = await registry.get(key)
|
|
69
|
-
users.push({ id: key.replace("user:", ""), ...user })
|
|
70
|
-
}
|
|
71
|
-
|
|
72
|
-
return { count: users.length, users: users }
|
|
73
|
-
}
|
|
74
|
-
}
|
|
75
|
-
|
|
76
|
-
// Agent that searches the registry
|
|
77
|
-
Agent Searcher : Worker {
|
|
78
|
-
on findAdults(args: Json) {
|
|
79
|
-
const results = await registry.search({
|
|
80
|
-
age: { $gte: 18 }
|
|
81
|
-
})
|
|
82
|
-
|
|
83
|
-
console.log("🔍 Found", results.length, "adults")
|
|
84
|
-
|
|
85
|
-
const adults = results.map(r => ({
|
|
86
|
-
id: r.key.replace("user:", ""),
|
|
87
|
-
...r.value
|
|
88
|
-
}))
|
|
89
|
-
|
|
90
|
-
return { count: adults.length, adults: adults }
|
|
91
|
-
}
|
|
92
|
-
|
|
93
|
-
on findByName(args: Json) {
|
|
94
|
-
const results = await registry.search({
|
|
95
|
-
name: { $regex: args.pattern }
|
|
96
|
-
})
|
|
97
|
-
|
|
98
|
-
console.log("🔍 Found", results.length, "matching users")
|
|
99
|
-
|
|
100
|
-
const matches = results.map(r => ({
|
|
101
|
-
id: r.key.replace("user:", ""),
|
|
102
|
-
...r.value
|
|
103
|
-
}))
|
|
104
|
-
|
|
105
|
-
return { count: matches.length, matches: matches }
|
|
106
|
-
}
|
|
107
|
-
}
|
|
108
|
-
|
|
109
|
-
// Orchestrator that coordinates the demo
|
|
110
|
-
Agent Demo : Worker {
|
|
111
|
-
on start(args: Json) {
|
|
112
|
-
console.log("═════════════════════════════════════════════")
|
|
113
|
-
console.log(" Registry Demo - Shared Data Store")
|
|
114
|
-
console.log("═════════════════════════════════════════════")
|
|
115
|
-
console.log("")
|
|
116
|
-
|
|
117
|
-
// 1. Save some users
|
|
118
|
-
console.log("1️⃣ Saving users...")
|
|
119
|
-
await Writer.handle("saveUser", { id: "001", name: "Alice", age: 30, email: "alice@example.com" })
|
|
120
|
-
await Writer.handle("saveUser", { id: "002", name: "Bob", age: 25, email: "bob@example.com" })
|
|
121
|
-
await Writer.handle("saveUser", { id: "003", name: "Charlie", age: 17, email: "charlie@example.com" })
|
|
122
|
-
await Writer.handle("saveUser", { id: "004", name: "Diana", age: 35, email: "diana@example.com" })
|
|
123
|
-
console.log("")
|
|
124
|
-
|
|
125
|
-
// 2. Save config
|
|
126
|
-
console.log("2️⃣ Saving config...")
|
|
127
|
-
await Writer.handle("saveConfig", { theme: "light", language: "es", notifications: true })
|
|
128
|
-
console.log("")
|
|
129
|
-
|
|
130
|
-
// 3. Read individual user
|
|
131
|
-
console.log("3️⃣ Reading user...")
|
|
132
|
-
const userResult = await Reader.handle("getUser", { id: "001" })
|
|
133
|
-
console.log(" User:", JSON.stringify(userResult.user, null, 2))
|
|
134
|
-
console.log("")
|
|
135
|
-
|
|
136
|
-
// 4. Read config
|
|
137
|
-
console.log("4️⃣ Reading config...")
|
|
138
|
-
const configResult = await Reader.handle("getConfig", {})
|
|
139
|
-
console.log(" Config:", JSON.stringify(configResult.config, null, 2))
|
|
140
|
-
console.log("")
|
|
141
|
-
|
|
142
|
-
// 5. List all users
|
|
143
|
-
console.log("5️⃣ Listing all users...")
|
|
144
|
-
const listResult = await Reader.handle("listUsers", {})
|
|
145
|
-
for (const user of listResult.users) {
|
|
146
|
-
console.log(" -", user.name, "(" + user.age + " years old)")
|
|
147
|
-
}
|
|
148
|
-
console.log("")
|
|
149
|
-
|
|
150
|
-
// 6. Search for adults
|
|
151
|
-
console.log("6️⃣ Searching for adults (age >= 18)...")
|
|
152
|
-
const adultsResult = await Searcher.handle("findAdults", {})
|
|
153
|
-
for (const adult of adultsResult.adults) {
|
|
154
|
-
console.log(" -", adult.name, "(" + adult.age + " years old)")
|
|
155
|
-
}
|
|
156
|
-
console.log("")
|
|
157
|
-
|
|
158
|
-
// 7. Search by name pattern
|
|
159
|
-
console.log("7️⃣ Searching for names containing 'a'...")
|
|
160
|
-
const searchResult = await Searcher.handle("findByName", { pattern: "a" })
|
|
161
|
-
for (const match of searchResult.matches) {
|
|
162
|
-
console.log(" -", match.name)
|
|
163
|
-
}
|
|
164
|
-
console.log("")
|
|
165
|
-
|
|
166
|
-
// 8. Show stats
|
|
167
|
-
console.log("8️⃣ Registry stats...")
|
|
168
|
-
const stats = await registry.stats()
|
|
169
|
-
console.log(" Backend:", stats.backend)
|
|
170
|
-
console.log(" Entries:", stats.count)
|
|
171
|
-
console.log(" File:", stats.file)
|
|
172
|
-
console.log(" Size:", stats.size, "bytes")
|
|
173
|
-
console.log("")
|
|
174
|
-
|
|
175
|
-
console.log("═════════════════════════════════════════════")
|
|
176
|
-
console.log(" Demo Complete!")
|
|
177
|
-
console.log(" Data persisted to:", stats.file)
|
|
178
|
-
console.log("═════════════════════════════════════════════")
|
|
179
|
-
|
|
180
|
-
return { success: true }
|
|
181
|
-
}
|
|
182
|
-
}
|
|
183
|
-
|
|
184
|
-
run Demo.start({})
|
|
@@ -1,140 +0,0 @@
|
|
|
1
|
-
// Registry with Natural Language Playbooks Demo
|
|
2
|
-
// Shows how agents can use registry operations naturally in playbooks
|
|
3
|
-
package "registry.playbook.demo"
|
|
4
|
-
|
|
5
|
-
role Worker { can execute, can registry }
|
|
6
|
-
role Manager { can execute, can delegate }
|
|
7
|
-
|
|
8
|
-
// Agent that uses natural language to interact with registry
|
|
9
|
-
Agent UserManager : Worker {
|
|
10
|
-
llm default = { provider: "openai", model: "gpt-4o-mini" }
|
|
11
|
-
|
|
12
|
-
on createUser(args: Json) {
|
|
13
|
-
playbook """
|
|
14
|
-
Create a new user with ALL fields from args:
|
|
15
|
-
- name: ${args.name}
|
|
16
|
-
- age: ${args.age}
|
|
17
|
-
- email: ${args.email}
|
|
18
|
-
- birthdate: ${args.birthdate} (if provided)
|
|
19
|
-
- id: ${args.id}
|
|
20
|
-
|
|
21
|
-
Save to registry with key "user:${args.id}".
|
|
22
|
-
CRITICAL: Include ALL fields from args (name, age, email, birthdate, id) plus a createdAt timestamp.
|
|
23
|
-
Return: { "success": true, "message": "User created" }
|
|
24
|
-
|
|
25
|
-
DO NOT add print actions - just return the data.
|
|
26
|
-
"""
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
on getUser(args: Json) {
|
|
30
|
-
playbook """
|
|
31
|
-
Get user ${args.id} from registry.
|
|
32
|
-
|
|
33
|
-
Use registry_get with key "user:${args.id}".
|
|
34
|
-
Extract the .value field from the registry_get result (which contains the user data).
|
|
35
|
-
Return ONLY the user data object (name, age, email, createdAt) without any wrapper.
|
|
36
|
-
"""
|
|
37
|
-
}
|
|
38
|
-
|
|
39
|
-
on listAllUsers(args: Json) {
|
|
40
|
-
playbook """
|
|
41
|
-
List all users in the registry.
|
|
42
|
-
|
|
43
|
-
EXACT STEPS:
|
|
44
|
-
1. Use registry_search with an empty query {} to get ALL users, store with ID "a1"
|
|
45
|
-
2. Extract just the user data (the .value field) from each result
|
|
46
|
-
3. Return: { "count": <count from a1>, "users": <array of user value objects, NOT the full {key, value} wrappers> }
|
|
47
|
-
|
|
48
|
-
Example: If a1.output.results = [{key: "user:001", value: {name: "Alice", age: 30}}, ...]
|
|
49
|
-
Then return: { "count": 2, "users": [{name: "Alice", age: 30}, ...] }
|
|
50
|
-
|
|
51
|
-
CRITICAL: Extract ONLY the .value objects so caller can access with .users[0].name directly
|
|
52
|
-
DO NOT use format action - return a real array!
|
|
53
|
-
"""
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
on findAdults(args: Json) {
|
|
57
|
-
playbook """
|
|
58
|
-
Find all users aged 18 or older using registry search with query: { "age": { "$gte": 18 } }
|
|
59
|
-
|
|
60
|
-
EXACT STEPS:
|
|
61
|
-
1. Use registry_search with query: { "age": { "$gte": 18 } }
|
|
62
|
-
2. Return: { "count": [count from search], "adults": [results array] }
|
|
63
|
-
|
|
64
|
-
DO NOT add print actions - just return the data!
|
|
65
|
-
"""
|
|
66
|
-
}
|
|
67
|
-
|
|
68
|
-
on updateUserAge(args: Json) {
|
|
69
|
-
playbook """
|
|
70
|
-
Update user ${args.id}'s age to ${args.age}.
|
|
71
|
-
|
|
72
|
-
EXACT STEPS:
|
|
73
|
-
1. Use registry_get with key "user:${args.id}", store with ID "a1"
|
|
74
|
-
2. Take the full user object from \${a1.output.value}
|
|
75
|
-
3. Modify ONLY the age field to ${args.age}, keep all other fields (name, email, createdAt, etc.)
|
|
76
|
-
4. Use registry_set with key "user:${args.id}" and the complete updated object
|
|
77
|
-
5. Return: { "success": true, "message": "Age updated" }
|
|
78
|
-
|
|
79
|
-
CRITICAL: Preserve ALL existing fields when saving!
|
|
80
|
-
"""
|
|
81
|
-
}
|
|
82
|
-
|
|
83
|
-
on deleteUser(args: Json) {
|
|
84
|
-
playbook """
|
|
85
|
-
Borra el usuario del registro con ID ${args.id}.
|
|
86
|
-
|
|
87
|
-
EXACT STEPS:
|
|
88
|
-
1. Use registry_delete with key "user:\${args.id}"
|
|
89
|
-
2. Return: { "success": true, "message": "User deleted" }
|
|
90
|
-
"""
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
|
|
94
|
-
// Team that groups our agents
|
|
95
|
-
Team RegistryTeam {
|
|
96
|
-
userManager = UserManager
|
|
97
|
-
}
|
|
98
|
-
|
|
99
|
-
// Orchestrator - uses playbook, router finds UserManager automatically!
|
|
100
|
-
Agent Demo : Manager {
|
|
101
|
-
llm default = { provider: "openai", model: "gpt-4o-mini" }
|
|
102
|
-
uses Team RegistryTeam
|
|
103
|
-
|
|
104
|
-
on start(args: Json) {
|
|
105
|
-
//SUPER IMPORTANT: DO NOT CHANGE THE FOLLOWING PROMPT AT ALL!!!!!!
|
|
106
|
-
playbook """
|
|
107
|
-
Ejecuta un demo del registro de usuarios.
|
|
108
|
-
|
|
109
|
-
Muestra el header:
|
|
110
|
-
╔══════════════════════════════════════════════════╗
|
|
111
|
-
║ Registry with Playbook Demo ║
|
|
112
|
-
╚══════════════════════════════════════════════════╝
|
|
113
|
-
|
|
114
|
-
1️⃣ Crea estos usuarios:
|
|
115
|
-
- Alice: id=001, birthdate=1985-12-05, email=alice@example.com
|
|
116
|
-
- Bob: id=002, fecha de nacimiento: 12 de abril de 2001, bob@example.com
|
|
117
|
-
- Moema: id=003, birth date: 1992 enero 29, email=charlie@example.com
|
|
118
|
-
- Diana: id=004, birthdate: 12 del 12 del 12, diana@example.com
|
|
119
|
-
Muestra: " ✅ X users created" X es la cantidad de usuarios que se crearon
|
|
120
|
-
|
|
121
|
-
2️⃣ Por cada usuario en la base de datos, escribe este correo:
|
|
122
|
-
|
|
123
|
-
Estimado (o Estimada si es chica, deducelo por el nombre) <nombre persona>,
|
|
124
|
-
|
|
125
|
-
Como sabemos que usted tiene {x} años, le queremos dar la enhorabuena!
|
|
126
|
-
|
|
127
|
-
Atentamente,
|
|
128
|
-
La empresa!!
|
|
129
|
-
|
|
130
|
-
Muestra cada correo que escribieste.
|
|
131
|
-
|
|
132
|
-
Muestra el footer:
|
|
133
|
-
╔══════════════════════════════════════════════════╗
|
|
134
|
-
║ Demo completed successfully! ║
|
|
135
|
-
╚══════════════════════════════════════════════════╝
|
|
136
|
-
"""
|
|
137
|
-
}
|
|
138
|
-
}
|
|
139
|
-
|
|
140
|
-
run Demo.start({})
|