atabey 0.0.13 → 0.0.15
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/ATABEY.md +1 -1
- package/PRIVACY.md +8 -14
- package/README.md +405 -56
- package/bin/cli.js +72 -5
- package/dist/framework-mcp/src/index.js +988 -63
- package/dist/framework-mcp/src/index.js.map +1 -1
- package/dist/framework-mcp/src/tools/compliance/mask_pii.d.ts +17 -0
- package/dist/framework-mcp/src/tools/compliance/mask_pii.js +56 -0
- package/dist/framework-mcp/src/tools/compliance/mask_pii.js.map +1 -0
- package/dist/framework-mcp/src/tools/definitions.js +10 -9
- package/dist/framework-mcp/src/tools/definitions.js.map +1 -1
- package/dist/framework-mcp/src/tools/framework/run_tests.js +25 -0
- package/dist/framework-mcp/src/tools/framework/run_tests.js.map +1 -1
- package/dist/framework-mcp/src/tools/index.js +7 -8
- package/dist/framework-mcp/src/tools/index.js.map +1 -1
- package/dist/framework-mcp/src/tools/messaging/approve_operation.d.ts +22 -0
- package/dist/framework-mcp/src/tools/messaging/approve_operation.js +81 -0
- package/dist/framework-mcp/src/tools/messaging/approve_operation.js.map +1 -0
- package/dist/framework-mcp/src/tools/messaging/ask_human.d.ts +15 -0
- package/dist/framework-mcp/src/tools/messaging/ask_human.js +89 -20
- package/dist/framework-mcp/src/tools/messaging/ask_human.js.map +1 -1
- package/dist/framework-mcp/src/tools/observability/check_ports.d.ts +1 -0
- package/dist/framework-mcp/src/tools/observability/check_ports.js +24 -8
- package/dist/framework-mcp/src/tools/observability/check_ports.js.map +1 -1
- package/dist/framework-mcp/src/tools/quality/analyze_code_quality.js +13 -64
- package/dist/framework-mcp/src/tools/quality/analyze_code_quality.js.map +1 -1
- package/dist/framework-mcp/src/tools/schemas.d.ts +48 -53
- package/dist/framework-mcp/src/tools/schemas.js +18 -22
- package/dist/framework-mcp/src/tools/schemas.js.map +1 -1
- package/dist/framework-mcp/src/tools/shell/run_command.js +146 -90
- package/dist/framework-mcp/src/tools/shell/run_command.js.map +1 -1
- package/dist/framework-mcp/src/tools/types.d.ts +11 -105
- package/dist/framework-mcp/src/tools/types.js +1 -0
- package/dist/framework-mcp/src/tools/types.js.map +1 -1
- package/dist/framework-mcp/src/utils/auth.d.ts +36 -0
- package/dist/framework-mcp/src/utils/auth.js +79 -0
- package/dist/framework-mcp/src/utils/auth.js.map +1 -0
- package/dist/framework-mcp/src/utils/auto-rollback.d.ts +71 -0
- package/dist/framework-mcp/src/utils/auto-rollback.js +266 -0
- package/dist/framework-mcp/src/utils/auto-rollback.js.map +1 -0
- package/dist/framework-mcp/src/utils/compliance.js +12 -4
- package/dist/framework-mcp/src/utils/compliance.js.map +1 -1
- package/dist/framework-mcp/src/utils/context-optimizer.d.ts +69 -0
- package/dist/framework-mcp/src/utils/context-optimizer.js +157 -0
- package/dist/framework-mcp/src/utils/context-optimizer.js.map +1 -0
- package/dist/framework-mcp/src/utils/discipline.d.ts +68 -0
- package/dist/framework-mcp/src/utils/discipline.js +218 -0
- package/dist/framework-mcp/src/utils/discipline.js.map +1 -0
- package/dist/framework-mcp/src/utils/finops.d.ts +143 -0
- package/dist/framework-mcp/src/utils/finops.js +326 -0
- package/dist/framework-mcp/src/utils/finops.js.map +1 -0
- package/dist/framework-mcp/src/utils/human-in-loop.d.ts +95 -0
- package/dist/framework-mcp/src/utils/human-in-loop.js +216 -0
- package/dist/framework-mcp/src/utils/human-in-loop.js.map +1 -0
- package/dist/framework-mcp/src/utils/license-scanner.d.ts +71 -0
- package/dist/framework-mcp/src/utils/license-scanner.js +284 -0
- package/dist/framework-mcp/src/utils/license-scanner.js.map +1 -0
- package/dist/framework-mcp/src/utils/loop-detector.d.ts +105 -0
- package/dist/framework-mcp/src/utils/loop-detector.js +362 -0
- package/dist/framework-mcp/src/utils/loop-detector.js.map +1 -0
- package/dist/framework-mcp/src/utils/quality.d.ts +19 -0
- package/dist/framework-mcp/src/utils/quality.js +125 -0
- package/dist/framework-mcp/src/utils/quality.js.map +1 -0
- package/dist/framework-mcp/src/utils/rules-engine.d.ts +78 -0
- package/dist/framework-mcp/src/utils/rules-engine.js +232 -0
- package/dist/framework-mcp/src/utils/rules-engine.js.map +1 -0
- package/dist/framework-mcp/src/utils/silent-router.d.ts +49 -0
- package/dist/framework-mcp/src/utils/silent-router.js +155 -0
- package/dist/framework-mcp/src/utils/silent-router.js.map +1 -0
- package/dist/framework-mcp/src/utils/storage.d.ts +1 -0
- package/dist/framework-mcp/src/utils/storage.js +2 -2
- package/dist/framework-mcp/src/utils/storage.js.map +1 -1
- package/dist/framework-mcp/src/utils/telemetry-streamer.d.ts +133 -0
- package/dist/framework-mcp/src/utils/telemetry-streamer.js +397 -0
- package/dist/framework-mcp/src/utils/telemetry-streamer.js.map +1 -0
- package/dist/framework-mcp/tests/tools/file_system/file_system_tools.test.js +2 -2
- package/dist/framework-mcp/tests/tools/file_system/file_system_tools.test.js.map +1 -1
- package/dist/framework-mcp/tests/tools/framework/run_tests.test.d.ts +1 -0
- package/dist/framework-mcp/tests/tools/framework/run_tests.test.js +49 -0
- package/dist/framework-mcp/tests/tools/framework/run_tests.test.js.map +1 -0
- package/dist/framework-mcp/tests/tools/messaging/send_message.test.js +14 -5
- package/dist/framework-mcp/tests/tools/messaging/send_message.test.js.map +1 -1
- package/dist/framework-mcp/tests/tools/observability/check_ports.test.d.ts +1 -0
- package/dist/framework-mcp/tests/tools/observability/check_ports.test.js +44 -0
- package/dist/framework-mcp/tests/tools/observability/check_ports.test.js.map +1 -0
- package/dist/framework-mcp/tests/tools/shell/run_command.test.js +44 -14
- package/dist/framework-mcp/tests/tools/shell/run_command.test.js.map +1 -1
- package/dist/framework-mcp/tests/utils/auto-rollback.test.d.ts +7 -0
- package/dist/framework-mcp/tests/utils/auto-rollback.test.js +178 -0
- package/dist/framework-mcp/tests/utils/auto-rollback.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/context-optimizer.test.d.ts +1 -0
- package/dist/framework-mcp/tests/utils/context-optimizer.test.js +62 -0
- package/dist/framework-mcp/tests/utils/context-optimizer.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/finops.test.d.ts +7 -0
- package/dist/framework-mcp/tests/utils/finops.test.js +157 -0
- package/dist/framework-mcp/tests/utils/finops.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/human-in-loop.test.d.ts +1 -0
- package/dist/framework-mcp/tests/utils/human-in-loop.test.js +59 -0
- package/dist/framework-mcp/tests/utils/human-in-loop.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/license-scanner.test.d.ts +7 -0
- package/dist/framework-mcp/tests/utils/license-scanner.test.js +131 -0
- package/dist/framework-mcp/tests/utils/license-scanner.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/loop-detector.test.d.ts +7 -0
- package/dist/framework-mcp/tests/utils/loop-detector.test.js +204 -0
- package/dist/framework-mcp/tests/utils/loop-detector.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/rules-engine.test.d.ts +1 -0
- package/dist/framework-mcp/tests/utils/rules-engine.test.js +106 -0
- package/dist/framework-mcp/tests/utils/rules-engine.test.js.map +1 -0
- package/dist/framework-mcp/tests/utils/telemetry-streamer.test.d.ts +7 -0
- package/dist/framework-mcp/tests/utils/telemetry-streamer.test.js +201 -0
- package/dist/framework-mcp/tests/utils/telemetry-streamer.test.js.map +1 -0
- package/dist/src/cli/commands/check.js +16 -1
- package/dist/src/cli/commands/check.js.map +1 -1
- package/dist/src/cli/commands/dashboard.js +188 -164
- package/dist/src/cli/commands/dashboard.js.map +1 -1
- package/dist/src/cli/commands/gateway.js +2 -2
- package/dist/src/cli/commands/gateway.js.map +1 -1
- package/dist/src/cli/commands/init/scaffold-core.d.ts +2 -0
- package/dist/src/cli/commands/init/scaffold-core.js +16 -1
- package/dist/src/cli/commands/init/scaffold-core.js.map +1 -1
- package/dist/src/cli/commands/init/scaffold-ops.js +2 -2
- package/dist/src/cli/commands/init/scaffold-ops.js.map +1 -1
- package/dist/src/cli/commands/init/scaffold-standards.js +13 -1
- package/dist/src/cli/commands/init/scaffold-standards.js.map +1 -1
- package/dist/src/cli/commands/init.d.ts +4 -0
- package/dist/src/cli/commands/init.js +94 -31
- package/dist/src/cli/commands/init.js.map +1 -1
- package/dist/src/cli/commands/mcp.js +3 -1
- package/dist/src/cli/commands/mcp.js.map +1 -1
- package/dist/src/cli/commands/quickstart.d.ts +1 -1
- package/dist/src/cli/commands/quickstart.js +12 -24
- package/dist/src/cli/commands/quickstart.js.map +1 -1
- package/dist/src/cli/commands/script.js +8 -1
- package/dist/src/cli/commands/script.js.map +1 -1
- package/dist/src/cli/index.js +24 -23
- package/dist/src/cli/index.js.map +1 -1
- package/dist/src/cli/shims.js +7 -7
- package/dist/src/cli/utils/pkg.js +2 -3
- package/dist/src/cli/utils/pkg.js.map +1 -1
- package/dist/src/cli/utils/quality.d.ts +10 -0
- package/dist/src/cli/utils/quality.js +10 -0
- package/dist/src/cli/utils/quality.js.map +1 -0
- package/dist/src/modules/agents/definitions.js +45 -40
- package/dist/src/modules/agents/definitions.js.map +1 -1
- package/dist/src/modules/agents/registry/manager.js +6 -1
- package/dist/src/modules/agents/registry/manager.js.map +1 -1
- package/dist/src/modules/engines/agent-executor.d.ts +6 -10
- package/dist/src/modules/engines/agent-executor.js +63 -21
- package/dist/src/modules/engines/agent-executor.js.map +1 -1
- package/dist/src/modules/engines/agent-loop.d.ts +34 -0
- package/dist/src/modules/engines/agent-loop.js +102 -0
- package/dist/src/modules/engines/agent-loop.js.map +1 -0
- package/dist/src/modules/engines/evaluation-engine.d.ts +12 -2
- package/dist/src/modules/engines/evaluation-engine.js +78 -11
- package/dist/src/modules/engines/evaluation-engine.js.map +1 -1
- package/dist/src/modules/engines/quality-gate.d.ts +13 -5
- package/dist/src/modules/engines/quality-gate.js +39 -31
- package/dist/src/modules/engines/quality-gate.js.map +1 -1
- package/dist/src/modules/engines/routing-engine.d.ts +5 -3
- package/dist/src/modules/engines/routing-engine.js +16 -9
- package/dist/src/modules/engines/routing-engine.js.map +1 -1
- package/dist/src/modules/gateway/cost-tracker.d.ts +5 -0
- package/dist/src/modules/gateway/cost-tracker.js +71 -0
- package/dist/src/modules/gateway/cost-tracker.js.map +1 -1
- package/dist/src/modules/gateway/gateway.d.ts +4 -0
- package/dist/src/modules/gateway/gateway.js +8 -0
- package/dist/src/modules/gateway/gateway.js.map +1 -1
- package/dist/src/shared/audit.js +3 -2
- package/dist/src/shared/audit.js.map +1 -1
- package/dist/src/shared/pii.d.ts +41 -9
- package/dist/src/shared/pii.js +122 -31
- package/dist/src/shared/pii.js.map +1 -1
- package/dist/src/shared/storage.d.ts +62 -0
- package/dist/src/shared/storage.js +47 -7
- package/dist/src/shared/storage.js.map +1 -1
- package/dist/tests/embedding.test.d.ts +1 -0
- package/dist/tests/embedding.test.js +82 -0
- package/dist/tests/embedding.test.js.map +1 -0
- package/dist/tests/engines/evaluation-engine.test.d.ts +1 -0
- package/dist/tests/engines/evaluation-engine.test.js +71 -0
- package/dist/tests/engines/evaluation-engine.test.js.map +1 -0
- package/dist/tests/engines/planning-engine.test.d.ts +1 -0
- package/dist/tests/engines/planning-engine.test.js +100 -0
- package/dist/tests/engines/planning-engine.test.js.map +1 -0
- package/dist/tests/engines/quality-gate.test.d.ts +1 -0
- package/dist/tests/engines/quality-gate.test.js +59 -0
- package/dist/tests/engines/quality-gate.test.js.map +1 -0
- package/dist/tests/engines/risk-engine.test.d.ts +1 -0
- package/dist/tests/engines/risk-engine.test.js +80 -0
- package/dist/tests/engines/risk-engine.test.js.map +1 -0
- package/dist/tests/engines/routing-engine.test.d.ts +1 -0
- package/dist/tests/engines/routing-engine.test.js +78 -0
- package/dist/tests/engines/routing-engine.test.js.map +1 -0
- package/dist/tests/integration/hermes_locking.test.js +1 -0
- package/dist/tests/integration/hermes_locking.test.js.map +1 -1
- package/dist/tests/modules/engines/agent-executor.test.js +1 -1
- package/dist/tests/modules/engines/agent-executor.test.js.map +1 -1
- package/dist/tests/modules/gateway/cost-tracker.test.js +20 -1
- package/dist/tests/modules/gateway/cost-tracker.test.js.map +1 -1
- package/dist/tests/shared/lock.test.d.ts +1 -0
- package/dist/tests/shared/lock.test.js +95 -0
- package/dist/tests/shared/lock.test.js.map +1 -0
- package/dist/tests/shared/pii.test.d.ts +1 -0
- package/dist/tests/shared/pii.test.js +183 -0
- package/dist/tests/shared/pii.test.js.map +1 -0
- package/framework-mcp/README.md +307 -35
- package/framework-mcp/dist/dashboard/assets/index-B_rK57vi.js +1221 -0
- package/framework-mcp/dist/dashboard/index.html +1 -1
- package/framework-mcp/dist/framework-mcp/src/index.js +988 -63
- package/framework-mcp/dist/framework-mcp/src/tools/compliance/mask_pii.js +55 -0
- package/framework-mcp/dist/framework-mcp/src/tools/definitions.js +10 -9
- package/framework-mcp/dist/framework-mcp/src/tools/framework/run_tests.js +25 -0
- package/framework-mcp/dist/framework-mcp/src/tools/index.js +7 -8
- package/framework-mcp/dist/framework-mcp/src/tools/messaging/approve_operation.js +80 -0
- package/framework-mcp/dist/framework-mcp/src/tools/messaging/ask_human.js +89 -20
- package/framework-mcp/dist/framework-mcp/src/tools/observability/check_ports.js +24 -8
- package/framework-mcp/dist/framework-mcp/src/tools/quality/analyze_code_quality.js +13 -64
- package/framework-mcp/dist/framework-mcp/src/tools/schemas.js +18 -22
- package/framework-mcp/dist/framework-mcp/src/tools/shell/run_command.js +146 -90
- package/framework-mcp/dist/framework-mcp/src/tools/types.js +1 -0
- package/framework-mcp/dist/framework-mcp/src/utils/auth.js +78 -0
- package/framework-mcp/dist/framework-mcp/src/utils/auto-rollback.js +265 -0
- package/framework-mcp/dist/framework-mcp/src/utils/compliance.js +12 -4
- package/framework-mcp/dist/framework-mcp/src/utils/context-optimizer.js +156 -0
- package/framework-mcp/dist/framework-mcp/src/utils/discipline.js +217 -0
- package/framework-mcp/dist/framework-mcp/src/utils/finops.js +325 -0
- package/framework-mcp/dist/framework-mcp/src/utils/human-in-loop.js +215 -0
- package/framework-mcp/dist/framework-mcp/src/utils/license-scanner.js +283 -0
- package/framework-mcp/dist/framework-mcp/src/utils/loop-detector.js +361 -0
- package/framework-mcp/dist/framework-mcp/src/utils/quality.js +124 -0
- package/framework-mcp/dist/framework-mcp/src/utils/rules-engine.js +231 -0
- package/framework-mcp/dist/framework-mcp/src/utils/silent-router.js +154 -0
- package/framework-mcp/dist/framework-mcp/src/utils/storage.js +2 -2
- package/framework-mcp/dist/framework-mcp/src/utils/telemetry-streamer.js +396 -0
- package/framework-mcp/dist/src/cli/platforms/core.js +72 -0
- package/framework-mcp/dist/src/cli/platforms/index.js +5 -0
- package/framework-mcp/dist/src/cli/platforms/paths.js +101 -0
- package/framework-mcp/dist/src/cli/platforms/scaffold.js +72 -0
- package/framework-mcp/dist/src/cli/platforms/utils.js +75 -0
- package/framework-mcp/dist/src/cli/utils/claude.js +57 -0
- package/framework-mcp/dist/src/cli/utils/compliance.js +12 -0
- package/framework-mcp/dist/src/cli/utils/fs.js +138 -0
- package/framework-mcp/dist/src/cli/utils/pkg.js +282 -0
- package/framework-mcp/dist/src/cli/utils/quality.js +9 -0
- package/framework-mcp/dist/src/modules/agents/definitions.js +563 -0
- package/framework-mcp/dist/src/modules/agents/registry/analyst.js +39 -0
- package/framework-mcp/dist/src/modules/agents/registry/architect.js +42 -0
- package/framework-mcp/dist/src/modules/agents/registry/backend.js +50 -0
- package/framework-mcp/dist/src/modules/agents/registry/database.js +45 -0
- package/framework-mcp/dist/src/modules/agents/registry/devops.js +45 -0
- package/framework-mcp/dist/src/modules/agents/registry/explorer.js +37 -0
- package/framework-mcp/dist/src/modules/agents/registry/frontend.js +52 -0
- package/framework-mcp/dist/src/modules/agents/registry/git.js +36 -0
- package/framework-mcp/dist/src/modules/agents/registry/manager.js +64 -0
- package/framework-mcp/dist/src/modules/agents/registry/mobile.js +41 -0
- package/framework-mcp/dist/src/modules/agents/registry/native.js +41 -0
- package/framework-mcp/dist/src/modules/agents/registry/quality.js +43 -0
- package/framework-mcp/dist/src/modules/agents/registry/security.js +42 -0
- package/framework-mcp/dist/src/modules/agents/types.js +1 -0
- package/framework-mcp/dist/src/modules/engines/evaluation-engine.js +169 -0
- package/framework-mcp/dist/src/modules/engines/quality-gate.js +92 -0
- package/framework-mcp/dist/src/modules/engines/risk-engine.js +105 -0
- package/framework-mcp/dist/src/modules/engines/routing-engine.js +408 -0
- package/framework-mcp/dist/src/modules/engines/types.js +1 -0
- package/framework-mcp/dist/src/modules/providers/definitions.js +140 -0
- package/framework-mcp/dist/src/modules/providers/registry.js +18 -0
- package/framework-mcp/dist/src/modules/providers/shared.js +104 -0
- package/framework-mcp/dist/src/modules/providers/types.js +1 -0
- package/framework-mcp/dist/src/modules/skills/adapter-skills.js +449 -0
- package/framework-mcp/dist/src/modules/skills/definitions.js +70 -0
- package/framework-mcp/dist/src/shared/audit.js +220 -0
- package/framework-mcp/dist/src/shared/errors.js +68 -0
- package/framework-mcp/dist/src/shared/lock.js +159 -0
- package/framework-mcp/dist/src/shared/pii.js +122 -31
- package/framework-mcp/dist/src/shared/retention.js +170 -0
- package/framework-mcp/dist/src/shared/storage.js +47 -7
- package/framework-mcp/dist/src/shared/string.js +29 -0
- package/framework-mcp/package.json +8 -2
- package/mcp.json +12 -6
- package/package.json +11 -5
- package/templates/full/ATABEY_FULL.md +1 -1
- package/framework-mcp/dist/dashboard/assets/index-BAPGLiWE.js +0 -267
|
@@ -0,0 +1,408 @@
|
|
|
1
|
+
import fs from "fs";
|
|
2
|
+
import path from "path";
|
|
3
|
+
import { getFrameworkDir } from "../../cli/utils/memory.js";
|
|
4
|
+
import { logger } from "../../shared/logger.js";
|
|
5
|
+
import { AtabeyStorage } from "../../shared/storage.js";
|
|
6
|
+
import { asAgentID, asTraceID } from "../../shared/types.js";
|
|
7
|
+
import { ALL_AGENTS } from "../agents/definitions.js";
|
|
8
|
+
export class RoutingEngine {
|
|
9
|
+
/**
|
|
10
|
+
* Advanced Routing Engine — analyzes task descriptions,
|
|
11
|
+
* selects the most suitable agent, and determines subtasks.
|
|
12
|
+
*
|
|
13
|
+
* Uses real TF-IDF scoring: term frequency in the task weighted by
|
|
14
|
+
* inverse document frequency across the full agent candidate corpus.
|
|
15
|
+
*/
|
|
16
|
+
static resolveAgent(taskDescription) {
|
|
17
|
+
return this.resolveWithDetails(taskDescription).agent;
|
|
18
|
+
}
|
|
19
|
+
/**
|
|
20
|
+
* Returns detailed routing result — score, confidence, reasoning, subTasks
|
|
21
|
+
*/
|
|
22
|
+
static resolveWithDetails(taskDescription) {
|
|
23
|
+
const textLower = taskDescription.toLowerCase();
|
|
24
|
+
const tokens = this.tokenize(textLower);
|
|
25
|
+
const candidates = this.getCandidates();
|
|
26
|
+
let bestAgent = "@backend";
|
|
27
|
+
let bestScore = 0;
|
|
28
|
+
let bestReasoning = "";
|
|
29
|
+
let bestSubTasks = [];
|
|
30
|
+
for (const candidate of candidates) {
|
|
31
|
+
let score = 0;
|
|
32
|
+
const matches = [];
|
|
33
|
+
// 1. Specialty matching (weighted TF-IDF)
|
|
34
|
+
for (const [specialty, weight] of Object.entries(candidate.specialties)) {
|
|
35
|
+
const specTokens = this.tokenize(specialty.toLowerCase());
|
|
36
|
+
for (const token of tokens) {
|
|
37
|
+
if (specTokens.some(st => token.includes(st) || st.includes(token))) {
|
|
38
|
+
score += weight * this.calculateTfIdf(token, tokens, candidates);
|
|
39
|
+
matches.push(specialty);
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
// 2. Role matching
|
|
44
|
+
const roleTokens = this.tokenize(candidate.role.toLowerCase());
|
|
45
|
+
for (const token of tokens) {
|
|
46
|
+
if (roleTokens.some(rt => token.includes(rt) || rt.includes(token))) {
|
|
47
|
+
score += 3; // Role match bonus
|
|
48
|
+
matches.push(`role:${candidate.role}`);
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
// 3. DisplayName matching
|
|
52
|
+
const nameTokens = this.tokenize(candidate.displayName.toLowerCase());
|
|
53
|
+
for (const token of tokens) {
|
|
54
|
+
if (nameTokens.some(nt => token.includes(nt) || nt.includes(token))) {
|
|
55
|
+
score += 2;
|
|
56
|
+
matches.push(`name:${candidate.displayName}`);
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
// Capability bonus (more capable agents get priority)
|
|
60
|
+
score += (candidate.capability - 5) * 0.5;
|
|
61
|
+
if (score > bestScore) {
|
|
62
|
+
bestScore = score;
|
|
63
|
+
bestAgent = candidate.agent;
|
|
64
|
+
bestReasoning = matches.length > 0
|
|
65
|
+
? `Matching fields: ${[...new Set(matches)].join(", ")}`
|
|
66
|
+
: "Selected based on general capability";
|
|
67
|
+
bestSubTasks = this.generateSubTasks(candidate.agent, taskDescription);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
// Static fallback (if nothing matches)
|
|
71
|
+
if (bestScore === 0) {
|
|
72
|
+
const fallback = this.fallbackRouting(tokens);
|
|
73
|
+
bestAgent = fallback.agent;
|
|
74
|
+
bestReasoning = fallback.reasoning;
|
|
75
|
+
bestSubTasks = fallback.subTasks;
|
|
76
|
+
}
|
|
77
|
+
const confidence = bestScore > 15 ? "high"
|
|
78
|
+
: bestScore > 7 ? "medium"
|
|
79
|
+
: "low";
|
|
80
|
+
return {
|
|
81
|
+
agent: bestAgent,
|
|
82
|
+
score: Math.round(bestScore * 10) / 10,
|
|
83
|
+
confidence,
|
|
84
|
+
reasoning: bestReasoning,
|
|
85
|
+
subTasks: bestSubTasks,
|
|
86
|
+
};
|
|
87
|
+
}
|
|
88
|
+
/**
|
|
89
|
+
* Automatically splits the task into subtasks
|
|
90
|
+
*/
|
|
91
|
+
static planTask(taskDescription) {
|
|
92
|
+
const result = this.resolveWithDetails(taskDescription);
|
|
93
|
+
const plan = [
|
|
94
|
+
`>> Task: ${taskDescription}`,
|
|
95
|
+
`>> Assigned to: ${result.agent}`,
|
|
96
|
+
`>> Confidence: ${result.confidence.toUpperCase()} (Score: ${result.score})`,
|
|
97
|
+
`>> Reason: ${result.reasoning}`,
|
|
98
|
+
"",
|
|
99
|
+
">> Subtasks:",
|
|
100
|
+
...result.subTasks.map((t, i) => ` ${i + 1}. ${t}`),
|
|
101
|
+
"",
|
|
102
|
+
">> Quality Check:",
|
|
103
|
+
` - When ${result.agent} completes, @quality will review`,
|
|
104
|
+
` - If @quality rejects, the task returns to ${result.agent}`,
|
|
105
|
+
];
|
|
106
|
+
return plan;
|
|
107
|
+
}
|
|
108
|
+
// ─── Private Helpers ────────────────────────────────────────────────
|
|
109
|
+
static tokenize(text) {
|
|
110
|
+
return text
|
|
111
|
+
.replace(/[^a-z0-9çşıöğü ]/g, " ")
|
|
112
|
+
.split(/\s+/)
|
|
113
|
+
.filter(t => t.length > 1);
|
|
114
|
+
}
|
|
115
|
+
/**
|
|
116
|
+
* Real TF-IDF calculation: term frequency × inverse document frequency.
|
|
117
|
+
* IDF = log(N / (df + 1) + 1) where N = total candidates, df = candidates containing the term.
|
|
118
|
+
*/
|
|
119
|
+
static calculateTfIdf(term, tokens, allCandidates) {
|
|
120
|
+
// TF: normalized term frequency in the task
|
|
121
|
+
const tf = tokens.filter(t => t === term).length / Math.max(tokens.length, 1);
|
|
122
|
+
// IDF: log(N / df + 1) where N = total candidates, df = candidates containing the term
|
|
123
|
+
const N = allCandidates.length;
|
|
124
|
+
const df = allCandidates.filter(c => Object.keys(c.specialties).some(s => s.toLowerCase().includes(term))).length;
|
|
125
|
+
const idf = Math.log(N / (df + 1) + 1);
|
|
126
|
+
return (1 + tf) * idf;
|
|
127
|
+
}
|
|
128
|
+
static fallbackRouting(tokens) {
|
|
129
|
+
const text = tokens.join(" ");
|
|
130
|
+
if (tokens.some(t => ["frontend", "ui", "page", "css", "html", "react", "component", "button", "form", "modal", "table", "interface"].includes(t))) {
|
|
131
|
+
return {
|
|
132
|
+
agent: "@frontend",
|
|
133
|
+
reasoning: "Frontend/UI keywords detected",
|
|
134
|
+
subTasks: this.generateSubTasks("@frontend", text),
|
|
135
|
+
};
|
|
136
|
+
}
|
|
137
|
+
if (tokens.some(t => ["security", "auth", "token", "encrypt", "login"].includes(t))) {
|
|
138
|
+
return {
|
|
139
|
+
agent: "@security",
|
|
140
|
+
reasoning: "Security keywords detected",
|
|
141
|
+
subTasks: this.generateSubTasks("@security", text),
|
|
142
|
+
};
|
|
143
|
+
}
|
|
144
|
+
if (tokens.some(t => ["database", "migration", "sql", "schema", "table", "index", "query"].includes(t))) {
|
|
145
|
+
return {
|
|
146
|
+
agent: "@database",
|
|
147
|
+
reasoning: "Database keywords detected",
|
|
148
|
+
subTasks: this.generateSubTasks("@database", text),
|
|
149
|
+
};
|
|
150
|
+
}
|
|
151
|
+
if (tokens.some(t => ["docker", "ci", "cd", "deploy", "devops", "infra", "server", "nginx"].includes(t))) {
|
|
152
|
+
return {
|
|
153
|
+
agent: "@devops",
|
|
154
|
+
reasoning: "DevOps/Infra keywords detected",
|
|
155
|
+
subTasks: this.generateSubTasks("@devops", text),
|
|
156
|
+
};
|
|
157
|
+
}
|
|
158
|
+
if (tokens.some(t => ["mobile", "react native", "expo", "ios", "android"].includes(t))) {
|
|
159
|
+
return {
|
|
160
|
+
agent: "@mobile",
|
|
161
|
+
reasoning: "Mobile keywords detected",
|
|
162
|
+
subTasks: this.generateSubTasks("@mobile", text),
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
if (tokens.some(t => ["architect", "design", "architecture", "contract", "structure"].includes(t))) {
|
|
166
|
+
return {
|
|
167
|
+
agent: "@architect",
|
|
168
|
+
reasoning: "Architecture/design keywords detected",
|
|
169
|
+
subTasks: this.generateSubTasks("@architect", text),
|
|
170
|
+
};
|
|
171
|
+
}
|
|
172
|
+
if (tokens.some(t => ["analysis", "analyst", "requirement", "contract", "validate"].includes(t))) {
|
|
173
|
+
return {
|
|
174
|
+
agent: "@analyst",
|
|
175
|
+
reasoning: "Analysis/requirement keywords detected",
|
|
176
|
+
subTasks: this.generateSubTasks("@analyst", text),
|
|
177
|
+
};
|
|
178
|
+
}
|
|
179
|
+
return {
|
|
180
|
+
agent: "@backend",
|
|
181
|
+
reasoning: "Default routing to backend (most general capability)",
|
|
182
|
+
subTasks: this.generateSubTasks("@backend", text),
|
|
183
|
+
};
|
|
184
|
+
}
|
|
185
|
+
static generateSubTasks(agent, taskDescription) {
|
|
186
|
+
const base = [
|
|
187
|
+
`[*] ${agent}: Analyze and plan the task`,
|
|
188
|
+
`[>] ${taskDescription}`,
|
|
189
|
+
"[*] Write and run tests",
|
|
190
|
+
"[*] Notify @quality for QA review",
|
|
191
|
+
];
|
|
192
|
+
const agentSpecific = {
|
|
193
|
+
"@manager": [
|
|
194
|
+
"[*] Analyze task and break into subtasks",
|
|
195
|
+
"[*] Identify suitable agents and distribute tasks",
|
|
196
|
+
"[*] Monitor progress and manage quality gate",
|
|
197
|
+
],
|
|
198
|
+
"@backend": [
|
|
199
|
+
"[*] Create Controller-Service-Repository layers",
|
|
200
|
+
"[*] Update API contracts",
|
|
201
|
+
"[*] Integrate database operations",
|
|
202
|
+
],
|
|
203
|
+
"@frontend": [
|
|
204
|
+
"[*] Create UI components in atomic structure",
|
|
205
|
+
"[*] Apply responsive design",
|
|
206
|
+
"[*] Integrate with API",
|
|
207
|
+
],
|
|
208
|
+
"@quality": [
|
|
209
|
+
"[*] Run compliance check (check_compliance)",
|
|
210
|
+
"[*] Run lint check",
|
|
211
|
+
"[*] Verify test coverage",
|
|
212
|
+
"[*] Report approval/rejection to @manager",
|
|
213
|
+
],
|
|
214
|
+
"@database": [
|
|
215
|
+
"[*] Prepare migration file",
|
|
216
|
+
"[*] Optimize queries",
|
|
217
|
+
"[*] Define index strategy",
|
|
218
|
+
],
|
|
219
|
+
"@security": [
|
|
220
|
+
"[*] Run security vulnerability scan",
|
|
221
|
+
"[*] Verify auth/encryption controls",
|
|
222
|
+
"[*] Check secret management",
|
|
223
|
+
],
|
|
224
|
+
"@devops": [
|
|
225
|
+
"[*] Prepare Docker configuration",
|
|
226
|
+
"[*] Update CI/CD pipeline",
|
|
227
|
+
"[*] Check environment variables",
|
|
228
|
+
],
|
|
229
|
+
"@mobile": [
|
|
230
|
+
"[*] Create React Native components",
|
|
231
|
+
"[*] Apply offline-first architecture",
|
|
232
|
+
"[*] Implement SafeArea and responsive controls",
|
|
233
|
+
],
|
|
234
|
+
"@explorer": [
|
|
235
|
+
"[*] Explore and map the codebase",
|
|
236
|
+
"[*] Analyze dependencies",
|
|
237
|
+
"[*] Send report to @manager",
|
|
238
|
+
],
|
|
239
|
+
"@git": [
|
|
240
|
+
"[*] Define branch strategy",
|
|
241
|
+
"[*] Prepare commit messages with Trace ID",
|
|
242
|
+
"[*] Perform rebase/merge operations if needed",
|
|
243
|
+
],
|
|
244
|
+
};
|
|
245
|
+
const specific = agentSpecific[agent] || [];
|
|
246
|
+
return [...specific, ...base];
|
|
247
|
+
}
|
|
248
|
+
/**
|
|
249
|
+
* Quality feedback loop — retries if @quality rejects
|
|
250
|
+
* Uses real MCP calls, not simulations.
|
|
251
|
+
*/
|
|
252
|
+
static async qualityLoop(agent, taskDescription, maxRetries = 3) {
|
|
253
|
+
for (let attempt = 1; attempt <= maxRetries; attempt++) {
|
|
254
|
+
logger.info(`[RETRY] Attempt ${attempt}/${maxRetries}: ${agent} running...`, {
|
|
255
|
+
agent,
|
|
256
|
+
attempt,
|
|
257
|
+
maxRetries,
|
|
258
|
+
task: taskDescription.substring(0, 100),
|
|
259
|
+
});
|
|
260
|
+
// Agent runs via MCP call
|
|
261
|
+
const result = await this.runAgent(agent, taskDescription);
|
|
262
|
+
// Quality check via MCP
|
|
263
|
+
const qualityResult = await this.runQualityCheck(result);
|
|
264
|
+
if (qualityResult.passed) {
|
|
265
|
+
logger.info(`[OK] Quality check PASSED (attempt ${attempt})`, { agent, attempt });
|
|
266
|
+
return { success: true, attempts: attempt };
|
|
267
|
+
}
|
|
268
|
+
logger.warn(`[FAIL] Quality check FAILED: ${qualityResult.reason}`, {
|
|
269
|
+
agent,
|
|
270
|
+
attempt,
|
|
271
|
+
reason: qualityResult.reason,
|
|
272
|
+
});
|
|
273
|
+
logger.info(`[RETRY] ${agent} fixing errors...`, { agent, attempt });
|
|
274
|
+
}
|
|
275
|
+
logger.error(`[FAIL] ${maxRetries} attempts exhausted. Human intervention required.`, {
|
|
276
|
+
agent,
|
|
277
|
+
maxRetries,
|
|
278
|
+
task: taskDescription.substring(0, 100),
|
|
279
|
+
});
|
|
280
|
+
return { success: false, attempts: maxRetries };
|
|
281
|
+
}
|
|
282
|
+
/**
|
|
283
|
+
* Runs the agent through the Hermes messaging system.
|
|
284
|
+
*
|
|
285
|
+
* Flow:
|
|
286
|
+
* 1. Write DELEGATION message to agent's queue (Storage.saveMessage)
|
|
287
|
+
* 2. Wait for agent response (polling, max 30 seconds)
|
|
288
|
+
* 3. Parse response and return as output
|
|
289
|
+
*/
|
|
290
|
+
static async runAgent(agent, task) {
|
|
291
|
+
const agentName = agent.replace("@", "");
|
|
292
|
+
const traceId = `T-${Date.now()}-${Math.random().toString(36).substring(2, 8)}`;
|
|
293
|
+
const messagePayload = JSON.stringify({
|
|
294
|
+
type: "DELEGATION",
|
|
295
|
+
task,
|
|
296
|
+
traceId,
|
|
297
|
+
from: "@manager",
|
|
298
|
+
});
|
|
299
|
+
AtabeyStorage.saveMessage({
|
|
300
|
+
from: asAgentID("@manager"),
|
|
301
|
+
to: asAgentID(agent),
|
|
302
|
+
category: "DELEGATION",
|
|
303
|
+
content: messagePayload,
|
|
304
|
+
traceId: asTraceID(traceId),
|
|
305
|
+
timestamp: new Date().toISOString(),
|
|
306
|
+
status: "PENDING",
|
|
307
|
+
priority: "HIGH",
|
|
308
|
+
requiresApproval: false,
|
|
309
|
+
});
|
|
310
|
+
logger.info(`[HERMES] Delegation sent to ${agent} (trace: ${traceId})`);
|
|
311
|
+
// Poll for response (max 30 seconds)
|
|
312
|
+
const maxAttempts = 60;
|
|
313
|
+
const pollInterval = 500;
|
|
314
|
+
for (let attempt = 0; attempt < maxAttempts; attempt++) {
|
|
315
|
+
const messages = AtabeyStorage.getPendingMessages();
|
|
316
|
+
const response = messages.find(m => m.from.replace("@", "") === agentName
|
|
317
|
+
&& m.category === "RESPONSE"
|
|
318
|
+
&& m.traceId === traceId
|
|
319
|
+
&& m.status === "PENDING");
|
|
320
|
+
if (response) {
|
|
321
|
+
if (response.id !== undefined) {
|
|
322
|
+
AtabeyStorage.updateMessageStatus(response.id, "PROCESSED");
|
|
323
|
+
}
|
|
324
|
+
logger.info(`[HERMES] Response received from ${agent} (trace: ${traceId})`);
|
|
325
|
+
return response.content;
|
|
326
|
+
}
|
|
327
|
+
await new Promise(resolve => setTimeout(resolve, pollInterval));
|
|
328
|
+
}
|
|
329
|
+
const timeoutMsg = `[TIMEOUT] ${agent} did not respond within 30s`;
|
|
330
|
+
logger.warn(`[HERMES] ${timeoutMsg} (trace: ${traceId})`);
|
|
331
|
+
return timeoutMsg;
|
|
332
|
+
}
|
|
333
|
+
/**
|
|
334
|
+
* Runs quality control through the real QualityGate.
|
|
335
|
+
*
|
|
336
|
+
* Flow:
|
|
337
|
+
* 1. QualityGate.check() for compliance + lint + test + content validation
|
|
338
|
+
* 2. Aggregate results
|
|
339
|
+
*/
|
|
340
|
+
static async runQualityCheck(result) {
|
|
341
|
+
const { QualityGate } = await import("./quality-gate.js");
|
|
342
|
+
const qualityResult = await QualityGate.check("@quality", result, "Quality check via routing engine");
|
|
343
|
+
return {
|
|
344
|
+
passed: qualityResult.passed,
|
|
345
|
+
reason: qualityResult.reason,
|
|
346
|
+
};
|
|
347
|
+
}
|
|
348
|
+
static getCandidates() {
|
|
349
|
+
const frameworkDir = getFrameworkDir();
|
|
350
|
+
const registryDir = path.join(frameworkDir, "registry");
|
|
351
|
+
let candidates = [];
|
|
352
|
+
// 1. Control Plane Registry (actively registered agents)
|
|
353
|
+
if (fs.existsSync(registryDir)) {
|
|
354
|
+
const registryFiles = fs.readdirSync(registryDir).filter(f => f.endsWith("_active.json"));
|
|
355
|
+
for (const file of registryFiles) {
|
|
356
|
+
try {
|
|
357
|
+
const data = JSON.parse(fs.readFileSync(path.join(registryDir, file), "utf8"));
|
|
358
|
+
if (data.agent && data.specialties) {
|
|
359
|
+
candidates.push({
|
|
360
|
+
agent: data.agent,
|
|
361
|
+
specialties: data.specialties,
|
|
362
|
+
displayName: data.displayName || data.agent,
|
|
363
|
+
role: data.role || "",
|
|
364
|
+
capability: data.capability || 8,
|
|
365
|
+
tier: data.tier || "core",
|
|
366
|
+
});
|
|
367
|
+
}
|
|
368
|
+
}
|
|
369
|
+
catch (err) {
|
|
370
|
+
logger.debug(`Failed to parse registry file: ${file}`, err);
|
|
371
|
+
}
|
|
372
|
+
}
|
|
373
|
+
}
|
|
374
|
+
// 2. Built-in agent definitions
|
|
375
|
+
if (candidates.length === 0) {
|
|
376
|
+
candidates = ALL_AGENTS.map(ag => ({
|
|
377
|
+
agent: ag.name.startsWith("@") ? ag.name : `@${ag.name}`,
|
|
378
|
+
specialties: ag.specialties ?? this.defaultSpecialties(ag.name),
|
|
379
|
+
displayName: ag.displayName,
|
|
380
|
+
role: ag.role,
|
|
381
|
+
capability: ag.capability,
|
|
382
|
+
tier: ag.tier,
|
|
383
|
+
}));
|
|
384
|
+
}
|
|
385
|
+
return candidates;
|
|
386
|
+
}
|
|
387
|
+
/**
|
|
388
|
+
* Default values for agents without a specialties field
|
|
389
|
+
*/
|
|
390
|
+
static defaultSpecialties(name) {
|
|
391
|
+
const defaults = {
|
|
392
|
+
manager: { orchestration: 10, governance: 10, delegation: 10, audit: 8, planning: 9 },
|
|
393
|
+
architect: { design: 10, contract: 9, architecture: 10, types: 9, planning: 8 },
|
|
394
|
+
backend: { backend: 10, api: 9, logic: 9, service: 8, database: 7, test: 8 },
|
|
395
|
+
frontend: { frontend: 10, ui: 10, css: 9, html: 9, react: 9, responsive: 8 },
|
|
396
|
+
mobile: { mobile: 10, "react native": 9, expo: 8, offline: 8, accessibility: 7 },
|
|
397
|
+
quality: { audit: 10, compliance: 10, lint: 9, test: 9, coverage: 8 },
|
|
398
|
+
database: { database: 10, migration: 9, sql: 9, schema: 8, index: 8 },
|
|
399
|
+
security: { security: 10, auth: 9, encryption: 8, audit: 9, token: 8 },
|
|
400
|
+
devops: { devops: 10, docker: 9, ci: 9, deploy: 9, infra: 8 },
|
|
401
|
+
analyst: { analysis: 10, contract: 9, requirement: 9, validation: 8, documentation: 7 },
|
|
402
|
+
native: { native: 9, desktop: 8, "os-level": 8, security: 8 },
|
|
403
|
+
explorer: { discovery: 10, mapping: 9, dependency: 8, recon: 8 },
|
|
404
|
+
git: { git: 10, version: 9, commit: 8, branching: 8, traceability: 8 },
|
|
405
|
+
};
|
|
406
|
+
return defaults[name] || { general: 5 };
|
|
407
|
+
}
|
|
408
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
import path from "path";
|
|
2
|
+
import { addMcpServerToClaude, findClaudeConfigPath } from "../../cli/utils/claude.js";
|
|
3
|
+
import { writeJsonFile } from "../../shared/fs.js";
|
|
4
|
+
import { registerGlobalAntigravityPlugins } from "./shared.js";
|
|
5
|
+
import { registry } from "./registry.js";
|
|
6
|
+
import { UI } from "../../cli/utils/ui.js";
|
|
7
|
+
// ─── Register Core Adapters ──────────────────────────────────────────────────
|
|
8
|
+
// [GEMINI] Gemini
|
|
9
|
+
registry.register({
|
|
10
|
+
id: "gemini",
|
|
11
|
+
frameworkDir: ".gemini",
|
|
12
|
+
shimFile: "GEMINI.md",
|
|
13
|
+
shimTemplate: "src/cli/shims/gemini.md",
|
|
14
|
+
role: "commander",
|
|
15
|
+
templateDir: ".atabey",
|
|
16
|
+
nestedDirs: ["agents", "rules"],
|
|
17
|
+
agentsDir: ".gemini/agents",
|
|
18
|
+
agentsExt: ".md"
|
|
19
|
+
}, (projectRoot, mcpBlock) => {
|
|
20
|
+
const frameworkDir = ".gemini";
|
|
21
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp.json"), mcpBlock);
|
|
22
|
+
UI.success(`Gemini MCP registered → ${frameworkDir}/mcp.json`);
|
|
23
|
+
registerGlobalAntigravityPlugins(mcpBlock);
|
|
24
|
+
});
|
|
25
|
+
// [START] Claude
|
|
26
|
+
registry.register({
|
|
27
|
+
id: "claude",
|
|
28
|
+
frameworkDir: ".claude",
|
|
29
|
+
shimFile: "CLAUDE.md",
|
|
30
|
+
shimTemplate: "src/cli/shims/claude.md",
|
|
31
|
+
role: "architect",
|
|
32
|
+
templateDir: ".atabey",
|
|
33
|
+
nestedDirs: ["agents", "rules"],
|
|
34
|
+
agentsDir: ".claude/agents",
|
|
35
|
+
agentsExt: ".md"
|
|
36
|
+
}, (projectRoot, mcpBlock) => {
|
|
37
|
+
const configPath = findClaudeConfigPath();
|
|
38
|
+
if (configPath) {
|
|
39
|
+
const block = mcpBlock;
|
|
40
|
+
const mcpEntry = block.mcpServers["atabey"];
|
|
41
|
+
const ok = addMcpServerToClaude(configPath, "atabey", mcpEntry);
|
|
42
|
+
if (ok)
|
|
43
|
+
UI.success(`Claude MCP registered → ${configPath}`);
|
|
44
|
+
}
|
|
45
|
+
const frameworkDir = ".claude";
|
|
46
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp_config.json"), mcpBlock);
|
|
47
|
+
writeJsonFile(path.join(projectRoot, ".mcp.json"), mcpBlock);
|
|
48
|
+
UI.success("Claude Code Project MCP → .mcp.json");
|
|
49
|
+
});
|
|
50
|
+
// [AI] Grok
|
|
51
|
+
registry.register({
|
|
52
|
+
id: "grok",
|
|
53
|
+
frameworkDir: ".grok",
|
|
54
|
+
shimFile: "GROK.md",
|
|
55
|
+
shimTemplate: "src/cli/shims/grok.md",
|
|
56
|
+
role: "researcher",
|
|
57
|
+
templateDir: ".atabey",
|
|
58
|
+
nestedDirs: ["agents", "rules"],
|
|
59
|
+
agentsDir: ".grok/agents",
|
|
60
|
+
agentsExt: ".md"
|
|
61
|
+
}, (projectRoot, mcpBlock) => {
|
|
62
|
+
const frameworkDir = ".grok";
|
|
63
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp_config.json"), mcpBlock);
|
|
64
|
+
UI.success(`Grok MCP → ${frameworkDir}/mcp_config.json`);
|
|
65
|
+
});
|
|
66
|
+
// [CURSOR] Cursor
|
|
67
|
+
registry.register({
|
|
68
|
+
id: "cursor",
|
|
69
|
+
frameworkDir: ".cursor",
|
|
70
|
+
shimFile: "CURSOR.md",
|
|
71
|
+
shimTemplate: "src/cli/shims/cursor.mdc",
|
|
72
|
+
role: "implementer",
|
|
73
|
+
templateDir: ".atabey",
|
|
74
|
+
nestedDirs: ["rules"],
|
|
75
|
+
agentsDir: ".cursor/rules",
|
|
76
|
+
agentsExt: ".mdc"
|
|
77
|
+
}, (projectRoot, mcpBlock) => {
|
|
78
|
+
const frameworkDir = ".cursor";
|
|
79
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp.json"), mcpBlock);
|
|
80
|
+
UI.success(`Cursor IDE Project MCP → ${frameworkDir}/mcp.json`);
|
|
81
|
+
});
|
|
82
|
+
// [TIP] Codex (Copilot)
|
|
83
|
+
registry.register({
|
|
84
|
+
id: "codex",
|
|
85
|
+
frameworkDir: ".agents",
|
|
86
|
+
shimFile: "copilot-instructions.md",
|
|
87
|
+
shimTemplate: "src/cli/shims/codex.md",
|
|
88
|
+
role: "implementer",
|
|
89
|
+
templateDir: ".atabey",
|
|
90
|
+
nestedDirs: ["skills", "rules", "instructions"],
|
|
91
|
+
agentsDir: ".agents/instructions",
|
|
92
|
+
agentsExt: ".md"
|
|
93
|
+
}, (projectRoot, mcpBlock) => {
|
|
94
|
+
const frameworkDir = ".agents";
|
|
95
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp_config.json"), mcpBlock);
|
|
96
|
+
writeJsonFile(path.join(projectRoot, ".vscode/mcp.json"), mcpBlock);
|
|
97
|
+
writeJsonFile(path.join(projectRoot, ".mcp.json"), mcpBlock);
|
|
98
|
+
UI.success("GitHub Copilot Project MCP → .vscode/mcp.json & .mcp.json");
|
|
99
|
+
});
|
|
100
|
+
// [LOCAL] Local LLM (Ollama / Private AI)
|
|
101
|
+
registry.register({
|
|
102
|
+
id: "local",
|
|
103
|
+
frameworkDir: ".atabey",
|
|
104
|
+
shimFile: "LOCAL_AI.md",
|
|
105
|
+
shimTemplate: "src/cli/shims/local.md",
|
|
106
|
+
role: "commander",
|
|
107
|
+
templateDir: ".atabey",
|
|
108
|
+
nestedDirs: ["agents", "rules"],
|
|
109
|
+
agentsDir: ".atabey/agents",
|
|
110
|
+
agentsExt: ".md"
|
|
111
|
+
}, (projectRoot, mcpBlock) => {
|
|
112
|
+
const frameworkDir = ".atabey";
|
|
113
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp_config.json"), mcpBlock);
|
|
114
|
+
UI.success(`Local LLM MCP (Ollama/Private AI) registered → ${frameworkDir}/mcp_config.json`);
|
|
115
|
+
});
|
|
116
|
+
// [ANTIGRAVITY] Antigravity
|
|
117
|
+
registry.register({
|
|
118
|
+
id: "antigravity-cli",
|
|
119
|
+
frameworkDir: ".agents",
|
|
120
|
+
shimFile: "AGENTS.md",
|
|
121
|
+
shimTemplate: "src/cli/shims/antigravity-cli.md",
|
|
122
|
+
role: "general",
|
|
123
|
+
templateDir: ".atabey",
|
|
124
|
+
nestedDirs: ["agents", "plugins", "rules"],
|
|
125
|
+
agentsDir: ".agents/agents",
|
|
126
|
+
agentsExt: ".md"
|
|
127
|
+
}, (projectRoot, mcpBlock) => {
|
|
128
|
+
const frameworkDir = ".agents";
|
|
129
|
+
writeJsonFile(path.join(projectRoot, frameworkDir, "mcp_config.json"), mcpBlock);
|
|
130
|
+
UI.success(`Antigravity CLI MCP → ${frameworkDir}/mcp_config.json`);
|
|
131
|
+
registerGlobalAntigravityPlugins(mcpBlock);
|
|
132
|
+
});
|
|
133
|
+
/**
|
|
134
|
+
* Mapped Adapter Configurations
|
|
135
|
+
*/
|
|
136
|
+
export const ADAPTER_CONFIGS = registry.getConfigs();
|
|
137
|
+
/**
|
|
138
|
+
* Post-Initialization Handlers for specific adapters
|
|
139
|
+
*/
|
|
140
|
+
export const POST_INIT_HANDLERS = registry.getHandlers();
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
class AdapterRegistry {
|
|
2
|
+
configs = new Map();
|
|
3
|
+
handlers = new Map();
|
|
4
|
+
register(config, handler) {
|
|
5
|
+
this.configs.set(config.id, config);
|
|
6
|
+
this.handlers.set(config.id, handler);
|
|
7
|
+
}
|
|
8
|
+
getConfigs() {
|
|
9
|
+
return Object.fromEntries(this.configs);
|
|
10
|
+
}
|
|
11
|
+
getHandlers() {
|
|
12
|
+
return Object.fromEntries(this.handlers);
|
|
13
|
+
}
|
|
14
|
+
getIds() {
|
|
15
|
+
return Array.from(this.configs.keys());
|
|
16
|
+
}
|
|
17
|
+
}
|
|
18
|
+
export const registry = new AdapterRegistry();
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
import path from "path";
|
|
2
|
+
import fs from "fs";
|
|
3
|
+
import os from "os";
|
|
4
|
+
import { execSync } from "child_process";
|
|
5
|
+
import { writeJsonFile, writeTextFile } from "../../shared/fs.js";
|
|
6
|
+
import { ALL_AGENTS, toAntigravityJson } from "../agents/definitions.js";
|
|
7
|
+
import { CORE_SKILLS } from "../skills/definitions.js";
|
|
8
|
+
import { getPackageRoot } from "../../cli/utils/pkg.js";
|
|
9
|
+
import { logger } from "../../shared/logger.js";
|
|
10
|
+
export function registerGlobalAntigravityPlugins(mcpBlock) {
|
|
11
|
+
// Allow overriding via env var for different OS/Gemini CLI versions
|
|
12
|
+
const defaultGlobalDir = path.join(os.homedir(), ".gemini/antigravity-cli");
|
|
13
|
+
const customDir = process.env["ANTIGRAVITY_GLOBAL_DIR"];
|
|
14
|
+
const targets = [customDir ?? defaultGlobalDir];
|
|
15
|
+
const baseKnowledgeDir = path.join(getPackageRoot(), "templates/standards");
|
|
16
|
+
for (const globalDir of targets) {
|
|
17
|
+
try {
|
|
18
|
+
// Write directly under directory
|
|
19
|
+
fs.mkdirSync(globalDir, { recursive: true });
|
|
20
|
+
writeJsonFile(path.join(globalDir, "mcp.json"), mcpBlock);
|
|
21
|
+
writeJsonFile(path.join(globalDir, "mcp_config.json"), mcpBlock);
|
|
22
|
+
logger.info(`Antigravity MCP registered → ${globalDir}/`);
|
|
23
|
+
// Global Plugin configuration under plugins/atabey/
|
|
24
|
+
const globalPluginDir = path.join(globalDir, "plugins/atabey");
|
|
25
|
+
fs.mkdirSync(globalPluginDir, { recursive: true });
|
|
26
|
+
// plugin.json marker
|
|
27
|
+
writeJsonFile(path.join(globalPluginDir, "plugin.json"), {
|
|
28
|
+
name: "atabey",
|
|
29
|
+
version: "1.0.0",
|
|
30
|
+
description: "Agent Atabey AI Orchestration framework"
|
|
31
|
+
});
|
|
32
|
+
// MCP Server configs inside the plugin
|
|
33
|
+
writeJsonFile(path.join(globalPluginDir, "mcp.json"), mcpBlock);
|
|
34
|
+
writeJsonFile(path.join(globalPluginDir, "mcp_config.json"), mcpBlock);
|
|
35
|
+
// Scaffold 13 agents
|
|
36
|
+
const agentsBaseDir = path.join(globalPluginDir, "agents");
|
|
37
|
+
fs.mkdirSync(agentsBaseDir, { recursive: true });
|
|
38
|
+
// Also write directly to ~/.gemini/antigravity-cli/agents/ so the CLI's
|
|
39
|
+
// workspace/global agent discovery finds them without the plugins/ prefix.
|
|
40
|
+
const globalAgentsDir = path.join(globalDir, "agents");
|
|
41
|
+
fs.mkdirSync(globalAgentsDir, { recursive: true });
|
|
42
|
+
for (const ag of ALL_AGENTS) {
|
|
43
|
+
const agentJson = toAntigravityJson(ag, baseKnowledgeDir);
|
|
44
|
+
// 1. Nested format inside plugin: plugins/atabey/agents/{name}/agent.json
|
|
45
|
+
const nestedAgentDir = path.join(agentsBaseDir, ag.name);
|
|
46
|
+
fs.mkdirSync(nestedAgentDir, { recursive: true });
|
|
47
|
+
writeTextFile(path.join(nestedAgentDir, "agent.json"), agentJson);
|
|
48
|
+
// 2. Flat format inside plugin: plugins/atabey/agents/{name}.json
|
|
49
|
+
writeTextFile(path.join(agentsBaseDir, `${ag.name}.json`), agentJson);
|
|
50
|
+
// 3. Direct global agents root — THIS is what Antigravity CLI reads:
|
|
51
|
+
// ~/.gemini/antigravity-cli/agents/{name}/agent.json
|
|
52
|
+
const globalNestedDir = path.join(globalAgentsDir, ag.name);
|
|
53
|
+
fs.mkdirSync(globalNestedDir, { recursive: true });
|
|
54
|
+
writeTextFile(path.join(globalNestedDir, "agent.json"), agentJson);
|
|
55
|
+
// 4. Flat global format as fallback
|
|
56
|
+
writeTextFile(path.join(globalAgentsDir, `${ag.name}.json`), agentJson);
|
|
57
|
+
}
|
|
58
|
+
// Scaffold skills
|
|
59
|
+
const skillsDir = path.join(globalPluginDir, "skills");
|
|
60
|
+
fs.mkdirSync(skillsDir, { recursive: true });
|
|
61
|
+
for (const [key, skill] of Object.entries(CORE_SKILLS)) {
|
|
62
|
+
const skillContent = `# [TOOL] Skill — ${skill.name}\n\n${skill.mandates.join("\n")}\n`;
|
|
63
|
+
writeTextFile(path.join(skillsDir, `${key.toLowerCase()}.md`), skillContent);
|
|
64
|
+
}
|
|
65
|
+
// Scaffold rules
|
|
66
|
+
const rulesDir = path.join(globalPluginDir, "rules");
|
|
67
|
+
fs.mkdirSync(rulesDir, { recursive: true });
|
|
68
|
+
for (const ag of ALL_AGENTS) {
|
|
69
|
+
const ruleContent = `# [ATABEY] Agent Atabey — @${ag.name} (${ag.displayName})
|
|
70
|
+
|
|
71
|
+
You are the **${ag.displayName}** of the Agent Atabey AL.
|
|
72
|
+
|
|
73
|
+
## [AI] Specialist Directive (Role: @${ag.name})
|
|
74
|
+
${ag.instructions.identity}
|
|
75
|
+
|
|
76
|
+
### [GOAL] Mission
|
|
77
|
+
${ag.instructions.mission}
|
|
78
|
+
|
|
79
|
+
### [DOCS] Discipline Rules
|
|
80
|
+
${ag.instructions.rules.map(r => `- ${r}`).join("\n")}
|
|
81
|
+
|
|
82
|
+
## [SECURITY] Core Mandates
|
|
83
|
+
- **Surgical Precision:** Enforce replace_text / replace_file_content for all code modifications.
|
|
84
|
+
- **Traceability:** Inherit and pass the active Trace ID across all delegations.
|
|
85
|
+
- **Approval Signature:** High-risk actions require manager approval signature.
|
|
86
|
+
`;
|
|
87
|
+
writeTextFile(path.join(rulesDir, `${ag.name}.md`), ruleContent);
|
|
88
|
+
}
|
|
89
|
+
// Scaffold optional empty hooks.json
|
|
90
|
+
writeJsonFile(path.join(globalPluginDir, "hooks.json"), {});
|
|
91
|
+
logger.info(`Antigravity Plugin registered → ${globalPluginDir}/`);
|
|
92
|
+
try {
|
|
93
|
+
execSync(`agy plugin install "${globalPluginDir}"`, { stdio: "ignore" });
|
|
94
|
+
logger.info("Antigravity Plugin installed in CLI.");
|
|
95
|
+
}
|
|
96
|
+
catch {
|
|
97
|
+
// Ignore if agy is not in PATH or fails
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
catch (e) {
|
|
101
|
+
logger.warn(`Failed to register plugin/MCP in ${globalDir}`, e);
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export const ADAPTER_IDS = ["gemini", "claude", "grok", "cursor", "codex", "local", "antigravity-cli"];
|