@kernel.chat/kbot 3.8.2 → 3.10.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/dist/spec.js ADDED
@@ -0,0 +1,177 @@
1
+ // kbot Spec — Spec-Driven Development
2
+ //
3
+ // Generates formal requirements + acceptance criteria before coding.
4
+ // Uses the architect agent to produce a structured specification document.
5
+ //
6
+ // Usage:
7
+ // $ kbot spec "build a user authentication system"
8
+ // $ kbot spec "add rate limiting" --implement
9
+ // $ kbot spec "refactor the database layer" --agent researcher
10
+ // $ kbot spec "notification service" --output ./specs/notifications.md
11
+ import { runAgent } from './agent.js';
12
+ import { gatherContext, formatContextForPrompt } from './context.js';
13
+ import { getRepoMapForContext } from './repo-map.js';
14
+ import { printInfo, printSuccess, createSpinner } from './ui.js';
15
+ import { mkdirSync, writeFileSync, existsSync } from 'node:fs';
16
+ import { join, dirname } from 'node:path';
17
+ import chalk from 'chalk';
18
+ const AMETHYST = chalk.hex('#6B5B95');
19
+ // ── System Prompt ──
20
+ const SPEC_SYSTEM_PROMPT = `You are a systems architect producing a formal specification document. Your output will be saved directly as a markdown file and used as the source of truth for implementation.
21
+
22
+ You MUST output a specification in EXACTLY this markdown format. Do not deviate from the structure. Do not add preamble or commentary outside the spec. Output ONLY the spec document:
23
+
24
+ \`\`\`
25
+ # Specification: [descriptive title derived from the task]
26
+
27
+ ## Requirements
28
+ 1. [REQ-001] [requirement written in EARS notation (Easy Approach to Requirements Syntax)]
29
+ 2. [REQ-002] ...
30
+ (continue numbering sequentially)
31
+
32
+ ## Acceptance Criteria
33
+ - [ ] [AC-001] [specific, testable criterion — must be verifiable by a human or automated test]
34
+ - [ ] [AC-002] ...
35
+ (continue numbering sequentially)
36
+
37
+ ## Technical Design
38
+ - Architecture: [brief architectural approach — patterns, layers, data flow]
39
+ - Key files: [list of files to create or modify, with brief purpose]
40
+ - Dependencies: [external packages, internal modules, APIs needed]
41
+
42
+ ## Implementation Plan
43
+ 1. [concrete implementation step — ordered by dependency]
44
+ 2. [next step]
45
+ ...
46
+
47
+ ## Risks
48
+ - [risk description] — Mitigation: [concrete mitigation strategy]
49
+ - ...
50
+ \`\`\`
51
+
52
+ Rules for writing specs:
53
+ 1. Requirements MUST use EARS notation. Examples:
54
+ - Ubiquitous: "The system shall [action]"
55
+ - Event-driven: "When [trigger], the system shall [response]"
56
+ - State-driven: "While [state], the system shall [behavior]"
57
+ - Unwanted: "If [condition], then the system shall [reaction]"
58
+ - Optional: "Where [feature is supported], the system shall [behavior]"
59
+ 2. Each acceptance criterion MUST be independently testable — a developer should be able to write a test for it.
60
+ 3. Requirements should be atomic — one concern per requirement.
61
+ 4. The implementation plan should be ordered so each step builds on the previous.
62
+ 5. Identify at least 2 risks and their mitigations.
63
+ 6. Use the project context and repository structure to inform your technical design — reference real files and patterns in the codebase.
64
+ 7. Do NOT wrap the spec in code fences. Output raw markdown directly.`;
65
+ // ── Slug Generation ──
66
+ function slugify(description) {
67
+ return description
68
+ .toLowerCase()
69
+ .replace(/[^a-z0-9\s-]/g, '')
70
+ .replace(/\s+/g, '-')
71
+ .replace(/-+/g, '-')
72
+ .replace(/^-|-$/g, '')
73
+ .slice(0, 60);
74
+ }
75
+ export async function generateSpec(description, options = {}) {
76
+ const agent = options.agent || 'architect';
77
+ const agentOpts = options.agentOpts || {};
78
+ // Gather project context for informed spec generation
79
+ let contextStr = '';
80
+ try {
81
+ const context = gatherContext();
82
+ contextStr = formatContextForPrompt(context);
83
+ }
84
+ catch { /* context is non-critical */ }
85
+ let repoMap = '';
86
+ try {
87
+ repoMap = await getRepoMapForContext();
88
+ }
89
+ catch { /* repo map is non-critical */ }
90
+ // Build the prompt — system instructions prepended, then the task
91
+ const userMessage = [
92
+ SPEC_SYSTEM_PROMPT,
93
+ '',
94
+ '---',
95
+ '',
96
+ contextStr ? `Project context:\n${contextStr}\n` : '',
97
+ repoMap ? `Repository structure:\n${repoMap}\n` : '',
98
+ `Task: ${description}`,
99
+ '',
100
+ 'Generate the specification now:',
101
+ ].filter(Boolean).join('\n');
102
+ const spinner = createSpinner('Generating specification...');
103
+ spinner.start();
104
+ let response;
105
+ try {
106
+ response = await runAgent(userMessage, {
107
+ ...agentOpts,
108
+ agent,
109
+ stream: false, // Don't stream — we need the full content for file saving
110
+ });
111
+ spinner.stop();
112
+ }
113
+ catch (err) {
114
+ spinner.stop();
115
+ throw err;
116
+ }
117
+ let spec = response.content;
118
+ // Clean up: if the AI wrapped output in code fences, strip them
119
+ const fenceMatch = spec.match(/^```(?:markdown|md)?\s*\n([\s\S]*?)\n```\s*$/m);
120
+ if (fenceMatch) {
121
+ spec = fenceMatch[1];
122
+ }
123
+ // Determine output path
124
+ const slug = slugify(description);
125
+ const outputPath = options.output || join(process.cwd(), '.kbot', 'specs', `${slug}.md`);
126
+ // Ensure directory exists
127
+ const dir = dirname(outputPath);
128
+ if (!existsSync(dir)) {
129
+ mkdirSync(dir, { recursive: true });
130
+ }
131
+ // Save the spec
132
+ writeFileSync(outputPath, spec, 'utf-8');
133
+ const result = {
134
+ spec,
135
+ path: outputPath,
136
+ agent,
137
+ };
138
+ // Print the spec to stdout
139
+ console.log();
140
+ console.log(` ${AMETHYST('Specification generated')}`);
141
+ console.log(` ${chalk.dim('─'.repeat(60))}`);
142
+ console.log();
143
+ console.log(spec);
144
+ console.log();
145
+ console.log(` ${chalk.dim('─'.repeat(60))}`);
146
+ printSuccess(`Saved to ${outputPath}`);
147
+ console.log();
148
+ // If --implement, pass the spec to the coder agent
149
+ if (options.implement) {
150
+ printInfo('Passing spec to coder agent for implementation...');
151
+ console.log();
152
+ const implementMessage = [
153
+ 'Implement the following specification. Follow the implementation plan exactly.',
154
+ 'Check off each acceptance criterion as you complete it.',
155
+ 'After implementation, run verification to confirm everything works.',
156
+ '',
157
+ '---',
158
+ '',
159
+ spec,
160
+ ].join('\n');
161
+ const implResponse = await runAgent(implementMessage, {
162
+ ...agentOpts,
163
+ agent: 'coder',
164
+ stream: agentOpts.stream ?? true,
165
+ });
166
+ result.implementation = implResponse;
167
+ // Print implementation result if it wasn't streamed
168
+ if (!implResponse.streamed) {
169
+ console.log();
170
+ console.log(implResponse.content);
171
+ }
172
+ console.log();
173
+ printSuccess(`Implementation complete (${implResponse.toolCalls} tool calls)`);
174
+ }
175
+ return result;
176
+ }
177
+ //# sourceMappingURL=spec.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"spec.js","sourceRoot":"","sources":["../src/spec.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@kernel.chat/kbot",
3
- "version": "3.8.2",
3
+ "version": "3.10.0",
4
4
  "description": "The only AI agent that builds its own tools. Self-evolving terminal AI: 290 tools, 23 agents, 20 providers. Runtime tool forging via forge_tool, Forge Registry for community tools, autopoietic health monitoring, immune self-audit agent. Cost-aware model routing, fallback chains, Bayesian skill routing. Embedded llama.cpp, MCP server, programmatic SDK. MIT.",
5
5
  "type": "module",
6
6
  "repository": {