sneakoscope 2.0.2 → 2.0.5
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 +12 -8
- package/crates/sks-core/Cargo.lock +1 -1
- package/crates/sks-core/Cargo.toml +1 -1
- package/crates/sks-core/src/main.rs +1 -1
- package/dist/.sks-build-stamp.json +4 -4
- package/dist/bin/sks.js +1 -1
- package/dist/build-manifest.json +86 -8
- package/dist/commands/doctor.js +14 -0
- package/dist/core/agents/agent-orchestrator.js +70 -4
- package/dist/core/agents/agent-patch-proof.js +5 -0
- package/dist/core/agents/agent-proof-evidence.js +61 -0
- package/dist/core/agents/agent-roster.js +35 -6
- package/dist/core/agents/agent-schema.js +1 -1
- package/dist/core/agents/native-worker-backend-router.js +31 -9
- package/dist/core/agents/ollama-worker-config.js +164 -15
- package/dist/core/codex/codex-0-137-compat.js +119 -0
- package/dist/core/codex-control/codex-control-proof.js +4 -1
- package/dist/core/codex-control/codex-fake-sdk-adapter.js +20 -0
- package/dist/core/codex-control/codex-output-schemas.js +5 -1
- package/dist/core/codex-control/codex-sdk-capability.js +1 -1
- package/dist/core/codex-control/codex-task-runner.js +329 -5
- package/dist/core/codex-control/gpt-final-arbiter.js +160 -0
- package/dist/core/codex-control/gpt-final-context-compressor.js +17 -0
- package/dist/core/codex-control/gpt-final-proof-pack.js +120 -0
- package/dist/core/codex-control/gpt-final-review-schema.js +71 -0
- package/dist/core/codex-control/python-codex-sdk-adapter.js +197 -0
- package/dist/core/codex-control/python-codex-sdk-event-translator.js +14 -0
- package/dist/core/commands/local-model-command.js +79 -18
- package/dist/core/commands/naruto-command.js +195 -12
- package/dist/core/commands/run-command.js +6 -2
- package/dist/core/doctor/doctor-readiness-matrix.js +34 -0
- package/dist/core/feature-fixtures.js +4 -0
- package/dist/core/fsx.js +1 -1
- package/dist/core/git-simple.js +143 -4
- package/dist/core/local-llm/local-collaboration-policy.js +93 -0
- package/dist/core/local-llm/local-llm-backpressure.js +20 -0
- package/dist/core/local-llm/local-llm-capability.js +29 -0
- package/dist/core/local-llm/local-llm-client.js +100 -0
- package/dist/core/local-llm/local-llm-config.js +20 -0
- package/dist/core/local-llm/local-llm-context-cache.js +21 -0
- package/dist/core/local-llm/local-llm-control-adapter.js +101 -0
- package/dist/core/local-llm/local-llm-json-repair.js +52 -0
- package/dist/core/local-llm/local-llm-metrics.js +42 -0
- package/dist/core/local-llm/local-llm-ollama-client.js +67 -0
- package/dist/core/local-llm/local-llm-openai-compatible-client.js +30 -0
- package/dist/core/local-llm/local-llm-prompt-cache.js +12 -0
- package/dist/core/local-llm/local-llm-scheduler.js +29 -0
- package/dist/core/local-llm/local-llm-schema-enforcer.js +15 -0
- package/dist/core/local-llm/local-llm-smoke.js +83 -0
- package/dist/core/local-llm/local-llm-warmup.js +20 -0
- package/dist/core/local-llm/local-worker-eligibility.js +27 -0
- package/dist/core/naruto/hardware-capacity-probe.js +36 -0
- package/dist/core/naruto/naruto-active-pool.js +118 -0
- package/dist/core/naruto/naruto-backpressure.js +13 -0
- package/dist/core/naruto/naruto-concurrency-governor.js +65 -0
- package/dist/core/naruto/naruto-finalizer.js +18 -0
- package/dist/core/naruto/naruto-generation-scheduler.js +18 -0
- package/dist/core/naruto/naruto-gpt-final-pack.js +49 -0
- package/dist/core/naruto/naruto-parallel-patch-apply.js +95 -0
- package/dist/core/naruto/naruto-patch-transaction-batch.js +42 -0
- package/dist/core/naruto/naruto-role-policy.js +107 -0
- package/dist/core/naruto/naruto-verification-dag.js +42 -0
- package/dist/core/naruto/naruto-verification-pool.js +18 -0
- package/dist/core/naruto/naruto-work-graph.js +198 -0
- package/dist/core/naruto/naruto-work-item.js +40 -0
- package/dist/core/naruto/naruto-work-stealing.js +11 -0
- package/dist/core/naruto/resource-pressure-monitor.js +32 -0
- package/dist/core/pipeline/final-gpt-patch-stage.js +31 -0
- package/dist/core/pipeline/final-gpt-review-stage.js +5 -0
- package/dist/core/pipeline/finalize-pipeline-result.js +58 -0
- package/dist/core/pipeline/gpt-final-required.js +12 -0
- package/dist/core/prompt/prompt-placeholder-guard.js +30 -0
- package/dist/core/router/capability-card.js +13 -0
- package/dist/core/router/route-cache.js +3 -0
- package/dist/core/router/ultra-router.js +2 -1
- package/dist/core/routes.js +4 -4
- package/dist/core/safety/mutation-guard.js +2 -0
- package/dist/core/update-check.js +60 -25
- package/dist/core/version.js +1 -1
- package/dist/core/zellij/zellij-lane-runtime.js +2 -2
- package/dist/core/zellij/zellij-naruto-dashboard.js +36 -0
- package/dist/core/zellij/zellij-worker-pane-manager.js +4 -4
- package/dist/scripts/blackbox-command-import-smoke.js +10 -1
- package/dist/scripts/check-package-boundary.js +12 -3
- package/dist/scripts/codex-0-137-compat-check.js +27 -0
- package/dist/scripts/codex-environment-scoped-approvals-check.js +10 -0
- package/dist/scripts/codex-plugin-list-json-check.js +8 -0
- package/dist/scripts/codex-sdk-team-naruto-agent-pipeline-check.js +2 -1
- package/dist/scripts/codex-thread-runtime-choice-check.js +10 -0
- package/dist/scripts/gpt-final-arbiter-check.js +63 -0
- package/dist/scripts/gpt-final-arbiter-performance-check.js +36 -0
- package/dist/scripts/local-collab-all-pipelines-final-gpt-check.js +21 -0
- package/dist/scripts/local-collab-gpt-final-availability-check.js +58 -0
- package/dist/scripts/local-collab-no-local-only-final-check.js +27 -0
- package/dist/scripts/local-collab-policy-check.js +17 -0
- package/dist/scripts/local-llm-all-pipelines-check.js +11 -0
- package/dist/scripts/local-llm-cache-performance-check.js +10 -0
- package/dist/scripts/local-llm-capability-check.js +14 -0
- package/dist/scripts/local-llm-smoke-check.js +23 -0
- package/dist/scripts/local-llm-structured-output-check.js +11 -0
- package/dist/scripts/local-llm-throughput-check.js +10 -0
- package/dist/scripts/local-llm-tool-call-repair-check.js +10 -0
- package/dist/scripts/local-llm-warmup-check.js +11 -0
- package/dist/scripts/naruto-active-pool-check.js +27 -0
- package/dist/scripts/naruto-concurrency-governor-check.js +52 -0
- package/dist/scripts/naruto-gpt-final-pack-check.js +34 -0
- package/dist/scripts/naruto-parallel-patch-apply-check.js +41 -0
- package/dist/scripts/naruto-real-local-gpt-final-smoke.js +16 -0
- package/dist/scripts/naruto-role-distribution-check.js +23 -0
- package/dist/scripts/naruto-shadow-clone-swarm-check.js +6 -0
- package/dist/scripts/naruto-verification-pool-check.js +36 -0
- package/dist/scripts/naruto-work-graph-check.js +24 -0
- package/dist/scripts/naruto-zellij-massive-ui-check.js +23 -0
- package/dist/scripts/prompt-placeholder-guard-check.js +33 -0
- package/dist/scripts/python-codex-sdk-all-pipelines-check.js +47 -0
- package/dist/scripts/python-codex-sdk-capability-check.js +75 -0
- package/dist/scripts/python-codex-sdk-sandbox-policy-check.js +10 -0
- package/dist/scripts/python-codex-sdk-stream-bridge-check.js +12 -0
- package/dist/scripts/release-parallel-check.js +1 -1
- package/dist/scripts/release-real-check.js +5 -0
- package/dist/scripts/zellij-worker-pane-manager-check.js +1 -1
- package/package.json +38 -4
- package/schemas/local-llm/local-collaboration-policy.schema.json +57 -0
- package/schemas/local-llm/local-model-config.schema.json +74 -0
- package/schemas/naruto/naruto-concurrency-governor.schema.json +21 -0
- package/schemas/naruto/naruto-work-graph.schema.json +22 -0
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
export const NARUTO_WRITE_ROLES = new Set([
|
|
2
|
+
'implementer',
|
|
3
|
+
'modifier',
|
|
4
|
+
'test_writer',
|
|
5
|
+
'conflict_resolver',
|
|
6
|
+
'rollback_planner',
|
|
7
|
+
'integrator'
|
|
8
|
+
]);
|
|
9
|
+
export const NARUTO_IMPLEMENTATION_LIKE_ROLES = new Set([
|
|
10
|
+
'implementer',
|
|
11
|
+
'modifier',
|
|
12
|
+
'test_writer',
|
|
13
|
+
'conflict_resolver'
|
|
14
|
+
]);
|
|
15
|
+
export function narutoRoleAllowsWrite(role) {
|
|
16
|
+
return NARUTO_WRITE_ROLES.has(role);
|
|
17
|
+
}
|
|
18
|
+
export function mapWorkKindToNarutoRole(kind) {
|
|
19
|
+
switch (kind) {
|
|
20
|
+
case 'implementation':
|
|
21
|
+
return 'implementer';
|
|
22
|
+
case 'code_modification':
|
|
23
|
+
case 'refactor':
|
|
24
|
+
case 'patch_rebase':
|
|
25
|
+
return 'modifier';
|
|
26
|
+
case 'test_generation':
|
|
27
|
+
return 'test_writer';
|
|
28
|
+
case 'test_execution':
|
|
29
|
+
case 'verification':
|
|
30
|
+
case 'ux_review':
|
|
31
|
+
case 'ppt_review':
|
|
32
|
+
case 'image_review':
|
|
33
|
+
return 'verifier';
|
|
34
|
+
case 'research':
|
|
35
|
+
return 'researcher';
|
|
36
|
+
case 'documentation':
|
|
37
|
+
return 'modifier';
|
|
38
|
+
case 'conflict_resolution':
|
|
39
|
+
return 'conflict_resolver';
|
|
40
|
+
case 'rollback_preparation':
|
|
41
|
+
return 'rollback_planner';
|
|
42
|
+
case 'integration_support':
|
|
43
|
+
return 'integrator';
|
|
44
|
+
case 'final_review_input_pack':
|
|
45
|
+
return 'gpt_final_arbiter';
|
|
46
|
+
}
|
|
47
|
+
}
|
|
48
|
+
export function mapNarutoRoleToAgentRole(role) {
|
|
49
|
+
switch (role) {
|
|
50
|
+
case 'implementer':
|
|
51
|
+
case 'modifier':
|
|
52
|
+
case 'test_writer':
|
|
53
|
+
return 'implementer';
|
|
54
|
+
case 'researcher':
|
|
55
|
+
return 'research';
|
|
56
|
+
case 'conflict_resolver':
|
|
57
|
+
case 'rollback_planner':
|
|
58
|
+
case 'integrator':
|
|
59
|
+
case 'gpt_final_arbiter':
|
|
60
|
+
return 'integrator';
|
|
61
|
+
case 'verifier':
|
|
62
|
+
return 'verifier';
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
export function buildNarutoRoleDistribution(workItems, opts = {}) {
|
|
66
|
+
const readonly = opts.readonly === true;
|
|
67
|
+
const counts = new Map();
|
|
68
|
+
const workItemRoles = workItems.map((item) => {
|
|
69
|
+
const role = mapWorkKindToNarutoRole(item.kind);
|
|
70
|
+
counts.set(role, (counts.get(role) || 0) + 1);
|
|
71
|
+
return {
|
|
72
|
+
work_item_id: item.id,
|
|
73
|
+
kind: item.kind,
|
|
74
|
+
role,
|
|
75
|
+
write_allowed: item.write_allowed && narutoRoleAllowsWrite(role)
|
|
76
|
+
};
|
|
77
|
+
});
|
|
78
|
+
const entries = [...counts.entries()].sort((a, b) => a[0].localeCompare(b[0])).map(([role, count]) => ({
|
|
79
|
+
role,
|
|
80
|
+
count,
|
|
81
|
+
write_allowed: narutoRoleAllowsWrite(role)
|
|
82
|
+
}));
|
|
83
|
+
const implementationLikeWorkers = workItemRoles.filter((row) => NARUTO_IMPLEMENTATION_LIKE_ROLES.has(row.role)).length;
|
|
84
|
+
const totalWorkers = workItems.length;
|
|
85
|
+
const implementationLikeRatio = totalWorkers ? implementationLikeWorkers / totalWorkers : 0;
|
|
86
|
+
const verifierOnly = totalWorkers > 0 && workItemRoles.every((row) => row.role === 'verifier');
|
|
87
|
+
const writeAllowedCount = workItemRoles.filter((row) => row.write_allowed).length;
|
|
88
|
+
const blockers = [
|
|
89
|
+
...(totalWorkers === 0 ? ['naruto_role_distribution_empty'] : []),
|
|
90
|
+
...(!readonly && verifierOnly ? ['naruto_default_must_not_be_verifier_only'] : []),
|
|
91
|
+
...(!readonly && implementationLikeRatio < 0.4 ? ['naruto_write_capable_route_requires_40_percent_implementation_like_roles'] : []),
|
|
92
|
+
...(!readonly && writeAllowedCount === 0 ? ['naruto_write_capable_route_requires_write_roles'] : [])
|
|
93
|
+
];
|
|
94
|
+
return {
|
|
95
|
+
schema: 'sks.naruto-role-distribution.v1',
|
|
96
|
+
readonly,
|
|
97
|
+
total_workers: totalWorkers,
|
|
98
|
+
implementation_like_workers: implementationLikeWorkers,
|
|
99
|
+
implementation_like_ratio: Math.round(implementationLikeRatio * 1000) / 1000,
|
|
100
|
+
verifier_only: verifierOnly,
|
|
101
|
+
entries,
|
|
102
|
+
work_item_roles: workItemRoles,
|
|
103
|
+
ok: blockers.length === 0,
|
|
104
|
+
blockers
|
|
105
|
+
};
|
|
106
|
+
}
|
|
107
|
+
//# sourceMappingURL=naruto-role-policy.js.map
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
import { buildVerificationDag } from '../verification/verification-dag.js';
|
|
2
|
+
const NODE_KIND_CYCLE = [
|
|
3
|
+
'typecheck_shard',
|
|
4
|
+
'unit_test_shard',
|
|
5
|
+
'route_gate_shard',
|
|
6
|
+
'lint_static_scan_shard',
|
|
7
|
+
'schema_validation_shard',
|
|
8
|
+
'patch_specific_test_shard',
|
|
9
|
+
'docs_changelog_check',
|
|
10
|
+
'side_effect_check',
|
|
11
|
+
'mutation_ledger_check',
|
|
12
|
+
'zellij_proof_check',
|
|
13
|
+
'local_llm_structured_output_check'
|
|
14
|
+
];
|
|
15
|
+
export function buildNarutoVerificationDag(graph, input = {}) {
|
|
16
|
+
const command = input.command || 'node -e "process.exit(0)"';
|
|
17
|
+
const verifiableItems = graph.work_items.filter((item) => item.verification_required);
|
|
18
|
+
const taskIdByWorkItemId = new Map(verifiableItems.map((item, index) => [item.id, `NV-${String(index + 1).padStart(6, '0')}`]));
|
|
19
|
+
const tasks = verifiableItems
|
|
20
|
+
.map((item, index) => {
|
|
21
|
+
const kind = NODE_KIND_CYCLE[index % NODE_KIND_CYCLE.length] || 'route_gate_shard';
|
|
22
|
+
const taskId = taskIdByWorkItemId.get(item.id) || `NV-${String(index + 1).padStart(6, '0')}`;
|
|
23
|
+
return {
|
|
24
|
+
id: taskId,
|
|
25
|
+
command,
|
|
26
|
+
...(input.cwd ? { cwd: input.cwd } : {}),
|
|
27
|
+
inputs: [...item.target_paths],
|
|
28
|
+
outputs: [`.sneakoscope/reports/naruto-verification/${item.id}.json`],
|
|
29
|
+
dependencies: item.dependencies.map((dep) => taskIdByWorkItemId.get(dep)).filter((dep) => typeof dep === 'string' && dep !== taskId),
|
|
30
|
+
timeout_ms: 60000,
|
|
31
|
+
read_only: true
|
|
32
|
+
};
|
|
33
|
+
});
|
|
34
|
+
const dag = buildVerificationDag(tasks);
|
|
35
|
+
return {
|
|
36
|
+
...dag,
|
|
37
|
+
naruto_schema: 'sks.naruto-verification-dag.v1',
|
|
38
|
+
node_kinds: NODE_KIND_CYCLE,
|
|
39
|
+
starts_when_dependencies_ready: true
|
|
40
|
+
};
|
|
41
|
+
}
|
|
42
|
+
//# sourceMappingURL=naruto-verification-dag.js.map
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
import { runVerificationDag } from '../verification/verification-worker-pool.js';
|
|
2
|
+
export async function runNarutoVerificationPool(dag, governor, opts = {}) {
|
|
3
|
+
const safeConcurrency = Math.max(1, governor.verification_parallel);
|
|
4
|
+
const result = await runVerificationDag(dag, {
|
|
5
|
+
...(opts.cwd ? { cwd: opts.cwd } : {}),
|
|
6
|
+
...(opts.logDir ? { logDir: opts.logDir } : {}),
|
|
7
|
+
concurrency: safeConcurrency
|
|
8
|
+
});
|
|
9
|
+
return {
|
|
10
|
+
...result,
|
|
11
|
+
naruto_schema: 'sks.naruto-verification-pool.v1',
|
|
12
|
+
safe_concurrency: safeConcurrency,
|
|
13
|
+
cpu_heavy_cap_respected: safeConcurrency <= Math.max(1, governor.hardware.cpu_core_count * 2),
|
|
14
|
+
io_heavy_cap_respected: governor.backpressure !== 'saturated',
|
|
15
|
+
api_rate_cap_respected: safeConcurrency <= Math.max(1, governor.remote_codex_parallel)
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
//# sourceMappingURL=naruto-verification-pool.js.map
|
|
@@ -0,0 +1,198 @@
|
|
|
1
|
+
import { mapWorkKindToNarutoRole } from './naruto-role-policy.js';
|
|
2
|
+
import { isNarutoWriteKind, normalizeNarutoPath } from './naruto-work-item.js';
|
|
3
|
+
const WRITE_CAPABLE_KIND_CYCLE = [
|
|
4
|
+
'implementation',
|
|
5
|
+
'code_modification',
|
|
6
|
+
'test_generation',
|
|
7
|
+
'verification',
|
|
8
|
+
'research',
|
|
9
|
+
'documentation',
|
|
10
|
+
'refactor',
|
|
11
|
+
'test_execution',
|
|
12
|
+
'conflict_resolution',
|
|
13
|
+
'patch_rebase',
|
|
14
|
+
'rollback_preparation',
|
|
15
|
+
'integration_support',
|
|
16
|
+
'final_review_input_pack'
|
|
17
|
+
];
|
|
18
|
+
const READONLY_KIND_CYCLE = [
|
|
19
|
+
'verification',
|
|
20
|
+
'research',
|
|
21
|
+
'test_execution',
|
|
22
|
+
'ux_review',
|
|
23
|
+
'ppt_review',
|
|
24
|
+
'image_review',
|
|
25
|
+
'final_review_input_pack'
|
|
26
|
+
];
|
|
27
|
+
export function buildNarutoWorkGraph(input = {}) {
|
|
28
|
+
const requestedClones = normalizePositiveInt(input.requestedClones, 12);
|
|
29
|
+
const readonly = input.readonly === true;
|
|
30
|
+
const writeCapable = input.writeCapable !== false && !readonly;
|
|
31
|
+
const totalWorkItems = Math.max(requestedClones, normalizePositiveInt(input.totalWorkItems, requestedClones));
|
|
32
|
+
const kindCycle = writeCapable ? WRITE_CAPABLE_KIND_CYCLE : READONLY_KIND_CYCLE;
|
|
33
|
+
const basePath = normalizeNarutoPath(input.leaseBasePath || '.sneakoscope/naruto/patch-envelopes');
|
|
34
|
+
const targetPaths = normalizePaths(input.targetPaths || []);
|
|
35
|
+
const readonlyPaths = normalizePaths(input.readonlyPaths || []);
|
|
36
|
+
const workItems = [];
|
|
37
|
+
for (let index = 0; index < totalWorkItems; index += 1) {
|
|
38
|
+
const id = `NW-${String(index + 1).padStart(6, '0')}`;
|
|
39
|
+
const kind = kindCycle[index % kindCycle.length] || 'verification';
|
|
40
|
+
const kindWrites = writeCapable && isNarutoWriteKind(kind);
|
|
41
|
+
const selectedTarget = targetPaths.length ? targetPaths[index % targetPaths.length] || targetPaths[0] || '' : `${basePath}/${id}.json`;
|
|
42
|
+
const writePaths = kindWrites ? [selectedTarget].filter(Boolean) : [];
|
|
43
|
+
const readPaths = readonlyPaths.length ? readonlyPaths : targetPaths.filter((item) => !writePaths.includes(item));
|
|
44
|
+
const leaseRequirements = [
|
|
45
|
+
...writePaths.map((file) => ({ path: file, kind: 'write' })),
|
|
46
|
+
...readPaths.map((file) => ({ path: file, kind: 'read' }))
|
|
47
|
+
];
|
|
48
|
+
workItems.push({
|
|
49
|
+
id,
|
|
50
|
+
kind,
|
|
51
|
+
title: titleForKind(kind, id),
|
|
52
|
+
target_paths: [...new Set([...(writePaths.length ? writePaths : [selectedTarget].filter(Boolean)), ...readPaths])],
|
|
53
|
+
readonly_paths: readPaths,
|
|
54
|
+
write_paths: writePaths,
|
|
55
|
+
required_role: mapWorkKindToNarutoRole(kind),
|
|
56
|
+
write_allowed: writePaths.length > 0,
|
|
57
|
+
verification_required: kind !== 'research' && kind !== 'final_review_input_pack',
|
|
58
|
+
dependencies: dependenciesForKind(kind, workItems),
|
|
59
|
+
can_run_in_parallel_with: [],
|
|
60
|
+
conflicts_with: [],
|
|
61
|
+
estimated_cost: estimateCost(kind),
|
|
62
|
+
lease_requirements: leaseRequirements,
|
|
63
|
+
acceptance: {
|
|
64
|
+
requires_patch_envelope: writePaths.length > 0,
|
|
65
|
+
requires_verification: kind !== 'research' && kind !== 'final_review_input_pack',
|
|
66
|
+
requires_gpt_final: writePaths.length > 0 || kind === 'final_review_input_pack'
|
|
67
|
+
}
|
|
68
|
+
});
|
|
69
|
+
}
|
|
70
|
+
const activeWaves = planNarutoWorkWaves(workItems, Math.max(1, normalizePositiveInt(input.maxActiveWorkers, requestedClones)));
|
|
71
|
+
annotateParallelCompatibility(workItems, activeWaves);
|
|
72
|
+
const mixedWorkKinds = [...new Set(workItems.map((item) => item.kind))];
|
|
73
|
+
const writeAllowedCount = workItems.filter((item) => item.write_allowed).length;
|
|
74
|
+
const blockers = [
|
|
75
|
+
...(mixedWorkKinds.length < 2 ? ['naruto_work_graph_not_mixed'] : []),
|
|
76
|
+
...(!readonly && writeAllowedCount === 0 ? ['naruto_write_capable_graph_missing_write_items'] : []),
|
|
77
|
+
...(workItems.length < requestedClones ? ['naruto_work_graph_below_requested_clones'] : []),
|
|
78
|
+
...activeWaves.flatMap((wave) => wave.conflict_count > 0 ? [`naruto_wave_write_conflict:${wave.wave_id}`] : [])
|
|
79
|
+
];
|
|
80
|
+
return {
|
|
81
|
+
schema: 'sks.naruto-work-graph.v1',
|
|
82
|
+
route: '$Naruto',
|
|
83
|
+
requested_clones: requestedClones,
|
|
84
|
+
total_work_items: workItems.length,
|
|
85
|
+
readonly,
|
|
86
|
+
write_capable: writeCapable,
|
|
87
|
+
work_items: workItems,
|
|
88
|
+
active_waves: activeWaves,
|
|
89
|
+
mixed_work_kinds: mixedWorkKinds,
|
|
90
|
+
write_allowed_count: writeAllowedCount,
|
|
91
|
+
ok: blockers.length === 0,
|
|
92
|
+
blockers
|
|
93
|
+
};
|
|
94
|
+
}
|
|
95
|
+
export function validateNarutoWorkGraph(graph) {
|
|
96
|
+
const ids = new Set();
|
|
97
|
+
const blockers = [...graph.blockers];
|
|
98
|
+
for (const item of graph.work_items) {
|
|
99
|
+
if (ids.has(item.id))
|
|
100
|
+
blockers.push(`duplicate_work_item:${item.id}`);
|
|
101
|
+
ids.add(item.id);
|
|
102
|
+
for (const dep of item.dependencies) {
|
|
103
|
+
if (!ids.has(dep) && !graph.work_items.some((candidate) => candidate.id === dep))
|
|
104
|
+
blockers.push(`missing_dependency:${item.id}:${dep}`);
|
|
105
|
+
}
|
|
106
|
+
if (item.write_allowed && item.acceptance.requires_patch_envelope !== true)
|
|
107
|
+
blockers.push(`write_item_missing_patch_envelope_acceptance:${item.id}`);
|
|
108
|
+
}
|
|
109
|
+
if (graph.total_work_items !== graph.work_items.length)
|
|
110
|
+
blockers.push('naruto_work_graph_count_mismatch');
|
|
111
|
+
if (!graph.readonly && graph.write_allowed_count === 0)
|
|
112
|
+
blockers.push('naruto_write_capable_graph_missing_write_items');
|
|
113
|
+
return { ok: blockers.length === 0, blockers: [...new Set(blockers)] };
|
|
114
|
+
}
|
|
115
|
+
export function planNarutoWorkWaves(items, maxActiveWorkers) {
|
|
116
|
+
const pending = [...items];
|
|
117
|
+
const waves = [];
|
|
118
|
+
while (pending.length) {
|
|
119
|
+
const waveItems = [];
|
|
120
|
+
const writePaths = new Set();
|
|
121
|
+
for (let index = 0; index < pending.length && waveItems.length < maxActiveWorkers;) {
|
|
122
|
+
const item = pending[index];
|
|
123
|
+
if (!item) {
|
|
124
|
+
index += 1;
|
|
125
|
+
continue;
|
|
126
|
+
}
|
|
127
|
+
const conflicts = item.write_paths.some((file) => writePaths.has(file));
|
|
128
|
+
if (conflicts) {
|
|
129
|
+
index += 1;
|
|
130
|
+
continue;
|
|
131
|
+
}
|
|
132
|
+
waveItems.push(item);
|
|
133
|
+
for (const file of item.write_paths)
|
|
134
|
+
writePaths.add(file);
|
|
135
|
+
pending.splice(index, 1);
|
|
136
|
+
}
|
|
137
|
+
if (!waveItems.length) {
|
|
138
|
+
const item = pending.shift();
|
|
139
|
+
if (item)
|
|
140
|
+
waveItems.push(item);
|
|
141
|
+
}
|
|
142
|
+
const paths = waveItems.flatMap((item) => item.write_paths);
|
|
143
|
+
waves.push({
|
|
144
|
+
wave_id: `NWAVE-${String(waves.length + 1).padStart(4, '0')}`,
|
|
145
|
+
work_item_ids: waveItems.map((item) => item.id),
|
|
146
|
+
write_paths: [...new Set(paths)],
|
|
147
|
+
conflict_count: paths.length - new Set(paths).size
|
|
148
|
+
});
|
|
149
|
+
}
|
|
150
|
+
return waves;
|
|
151
|
+
}
|
|
152
|
+
function annotateParallelCompatibility(items, waves) {
|
|
153
|
+
const byId = new Map(items.map((item) => [item.id, item]));
|
|
154
|
+
for (const wave of waves) {
|
|
155
|
+
for (const id of wave.work_item_ids) {
|
|
156
|
+
const item = byId.get(id);
|
|
157
|
+
if (!item)
|
|
158
|
+
continue;
|
|
159
|
+
item.can_run_in_parallel_with = wave.work_item_ids.filter((other) => other !== id);
|
|
160
|
+
item.conflicts_with = items
|
|
161
|
+
.filter((other) => other.id !== id && other.write_paths.some((file) => item.write_paths.includes(file)))
|
|
162
|
+
.map((other) => other.id);
|
|
163
|
+
}
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
function dependenciesForKind(kind, previous) {
|
|
167
|
+
if (kind === 'verification' || kind === 'test_execution') {
|
|
168
|
+
const candidate = [...previous].reverse().find((item) => item.write_allowed);
|
|
169
|
+
return candidate ? [candidate.id] : [];
|
|
170
|
+
}
|
|
171
|
+
if (kind === 'final_review_input_pack') {
|
|
172
|
+
return previous.slice(-3).map((item) => item.id);
|
|
173
|
+
}
|
|
174
|
+
return [];
|
|
175
|
+
}
|
|
176
|
+
function estimateCost(kind) {
|
|
177
|
+
const heavy = kind === 'implementation' || kind === 'code_modification' || kind === 'refactor' || kind === 'conflict_resolution';
|
|
178
|
+
return {
|
|
179
|
+
tokens: heavy ? 8000 : 3000,
|
|
180
|
+
latency_ms: heavy ? 90000 : 30000,
|
|
181
|
+
cpu_weight: kind === 'test_execution' || kind === 'verification' ? 2 : 1,
|
|
182
|
+
memory_mb: heavy ? 512 : 256,
|
|
183
|
+
gpu_weight: 0
|
|
184
|
+
};
|
|
185
|
+
}
|
|
186
|
+
function titleForKind(kind, id) {
|
|
187
|
+
return `${id} ${kind.replace(/_/g, ' ')}`;
|
|
188
|
+
}
|
|
189
|
+
function normalizePositiveInt(value, fallback) {
|
|
190
|
+
const parsed = Number(value);
|
|
191
|
+
if (!Number.isFinite(parsed) || parsed < 1)
|
|
192
|
+
return Math.max(1, Math.floor(fallback));
|
|
193
|
+
return Math.floor(parsed);
|
|
194
|
+
}
|
|
195
|
+
function normalizePaths(paths) {
|
|
196
|
+
return [...new Set(paths.map(normalizeNarutoPath).filter(Boolean))];
|
|
197
|
+
}
|
|
198
|
+
//# sourceMappingURL=naruto-work-graph.js.map
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
export const NARUTO_WORK_KINDS = [
|
|
2
|
+
'implementation',
|
|
3
|
+
'code_modification',
|
|
4
|
+
'refactor',
|
|
5
|
+
'test_generation',
|
|
6
|
+
'test_execution',
|
|
7
|
+
'verification',
|
|
8
|
+
'research',
|
|
9
|
+
'documentation',
|
|
10
|
+
'ux_review',
|
|
11
|
+
'ppt_review',
|
|
12
|
+
'image_review',
|
|
13
|
+
'conflict_resolution',
|
|
14
|
+
'patch_rebase',
|
|
15
|
+
'rollback_preparation',
|
|
16
|
+
'integration_support',
|
|
17
|
+
'final_review_input_pack'
|
|
18
|
+
];
|
|
19
|
+
export const NARUTO_WRITE_WORK_KINDS = new Set([
|
|
20
|
+
'implementation',
|
|
21
|
+
'code_modification',
|
|
22
|
+
'refactor',
|
|
23
|
+
'test_generation',
|
|
24
|
+
'documentation',
|
|
25
|
+
'conflict_resolution',
|
|
26
|
+
'patch_rebase',
|
|
27
|
+
'rollback_preparation',
|
|
28
|
+
'integration_support'
|
|
29
|
+
]);
|
|
30
|
+
export function isNarutoWriteKind(kind) {
|
|
31
|
+
return NARUTO_WRITE_WORK_KINDS.has(kind);
|
|
32
|
+
}
|
|
33
|
+
export function normalizeNarutoWorkKind(value, fallback = 'verification') {
|
|
34
|
+
const text = String(value || '');
|
|
35
|
+
return NARUTO_WORK_KINDS.includes(text) ? text : fallback;
|
|
36
|
+
}
|
|
37
|
+
export function normalizeNarutoPath(value) {
|
|
38
|
+
return String(value || '').replace(/\\/g, '/').replace(/^\.\/+/, '').split('/').filter((part) => part && part !== '.').join('/');
|
|
39
|
+
}
|
|
40
|
+
//# sourceMappingURL=naruto-work-item.js.map
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
export function stealNarutoWork(queue, input = {}) {
|
|
2
|
+
const item = queue.shift() || null;
|
|
3
|
+
return {
|
|
4
|
+
schema: 'sks.naruto-work-stealing.v1',
|
|
5
|
+
stolen: Boolean(item),
|
|
6
|
+
work_item_id: item?.id || null,
|
|
7
|
+
from_queue: input.fromQueue || 'pending',
|
|
8
|
+
to_slot: input.toSlot || 'idle-slot'
|
|
9
|
+
};
|
|
10
|
+
}
|
|
11
|
+
//# sourceMappingURL=naruto-work-stealing.js.map
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
export function monitorNarutoResourcePressure(probe, input = {}) {
|
|
2
|
+
const activeWorkers = Math.max(1, Math.floor(Number(input.activeWorkers || 1)));
|
|
3
|
+
const zellijCap = Math.max(1, Math.floor(Number(input.zellijVisiblePaneCap || 12)));
|
|
4
|
+
const memoryPressure = 1 - (probe.free_memory_bytes / Math.max(1, probe.total_memory_bytes));
|
|
5
|
+
const cpuPressure = Math.min(1, (probe.current_load_average[0] || 0) / Math.max(1, probe.cpu_core_count));
|
|
6
|
+
const fdPressure = Math.min(1, (activeWorkers * 6 + probe.process_count) / Math.max(1, probe.file_descriptor_limit));
|
|
7
|
+
const zellijPressure = Math.min(1, probe.zellij_pane_count / zellijCap);
|
|
8
|
+
const diskIoPressure = probe.disk_io_pressure;
|
|
9
|
+
const reasons = [
|
|
10
|
+
...(memoryPressure > 0.8 ? ['memory_cap'] : []),
|
|
11
|
+
...(cpuPressure > 0.9 ? ['cpu_load_cap'] : []),
|
|
12
|
+
...(fdPressure > 0.75 ? ['file_descriptor_budget'] : []),
|
|
13
|
+
...(zellijPressure > 0.9 ? ['zellij_ui_pane_budget'] : []),
|
|
14
|
+
...(diskIoPressure > 0.75 ? ['disk_io_pressure'] : [])
|
|
15
|
+
];
|
|
16
|
+
const maxPressure = Math.max(memoryPressure, cpuPressure, fdPressure, zellijPressure, diskIoPressure);
|
|
17
|
+
const state = maxPressure >= 0.92 ? 'saturated' : maxPressure >= 0.72 ? 'throttled' : 'normal';
|
|
18
|
+
return {
|
|
19
|
+
schema: 'sks.naruto-resource-pressure.v1',
|
|
20
|
+
state,
|
|
21
|
+
memory_pressure: round(memoryPressure),
|
|
22
|
+
cpu_pressure: round(cpuPressure),
|
|
23
|
+
fd_pressure: round(fdPressure),
|
|
24
|
+
zellij_pressure: round(zellijPressure),
|
|
25
|
+
disk_io_pressure: round(diskIoPressure),
|
|
26
|
+
reasons
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
function round(value) {
|
|
30
|
+
return Math.round(Math.max(0, Math.min(1, value)) * 1000) / 1000;
|
|
31
|
+
}
|
|
32
|
+
//# sourceMappingURL=resource-pressure-monitor.js.map
|
|
@@ -0,0 +1,31 @@
|
|
|
1
|
+
export function selectFinalGptPatchSource(gptFinal, localPatchEnvelopes = []) {
|
|
2
|
+
const status = String(gptFinal?.result?.status || gptFinal?.status || '');
|
|
3
|
+
if (status === 'modified') {
|
|
4
|
+
return {
|
|
5
|
+
schema: 'sks.final-gpt-patch-stage.v1',
|
|
6
|
+
ok: true,
|
|
7
|
+
final_patch_source: 'gpt_final_arbiter',
|
|
8
|
+
patch_envelopes: Array.isArray(gptFinal?.result?.modified_patch_envelopes) ? gptFinal.result.modified_patch_envelopes : [],
|
|
9
|
+
blockers: []
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
if (status === 'approved') {
|
|
13
|
+
return {
|
|
14
|
+
schema: 'sks.final-gpt-patch-stage.v1',
|
|
15
|
+
ok: true,
|
|
16
|
+
final_patch_source: 'gpt_final_arbiter',
|
|
17
|
+
patch_envelopes: Array.isArray(gptFinal?.result?.accepted_patch_envelopes) && gptFinal.result.accepted_patch_envelopes.length
|
|
18
|
+
? gptFinal.result.accepted_patch_envelopes
|
|
19
|
+
: localPatchEnvelopes,
|
|
20
|
+
blockers: []
|
|
21
|
+
};
|
|
22
|
+
}
|
|
23
|
+
return {
|
|
24
|
+
schema: 'sks.final-gpt-patch-stage.v1',
|
|
25
|
+
ok: false,
|
|
26
|
+
final_patch_source: 'blocked',
|
|
27
|
+
patch_envelopes: [],
|
|
28
|
+
blockers: ['gpt_final_not_approved']
|
|
29
|
+
};
|
|
30
|
+
}
|
|
31
|
+
//# sourceMappingURL=final-gpt-patch-stage.js.map
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
import path from 'node:path';
|
|
2
|
+
import { nowIso, writeJsonAtomic } from '../fsx.js';
|
|
3
|
+
import { runGptFinalArbiter } from '../codex-control/gpt-final-arbiter.js';
|
|
4
|
+
import { gptFinalRequiredForPipeline } from './gpt-final-required.js';
|
|
5
|
+
export async function finalizePipelineResult(input) {
|
|
6
|
+
const cwd = path.resolve(input.cwd || process.cwd());
|
|
7
|
+
const root = path.resolve(input.mutationLedgerRoot || path.join(cwd, '.sneakoscope', 'tmp', 'pipeline-finalize', safeName(input.missionId)));
|
|
8
|
+
const requirement = gptFinalRequiredForPipeline({
|
|
9
|
+
localParticipated: input.localParticipated,
|
|
10
|
+
candidateResults: input.candidateResults
|
|
11
|
+
});
|
|
12
|
+
let arbiter = null;
|
|
13
|
+
let blockers = [];
|
|
14
|
+
if (requirement.gpt_final_required) {
|
|
15
|
+
arbiter = await runGptFinalArbiter({
|
|
16
|
+
schema: 'sks.gpt-final-arbiter-input.v1',
|
|
17
|
+
route: input.route,
|
|
18
|
+
mission_id: input.missionId,
|
|
19
|
+
local_mode: 'local-parallel-gpt-final',
|
|
20
|
+
local_outputs: input.candidateResults,
|
|
21
|
+
candidate_patch_envelopes: input.candidatePatchEnvelopes
|
|
22
|
+
}, {
|
|
23
|
+
cwd,
|
|
24
|
+
mutationLedgerRoot: path.join(root, 'gpt-final-arbiter'),
|
|
25
|
+
...(typeof input.forceGptFinalUnavailable === 'boolean' ? { forceUnavailable: input.forceGptFinalUnavailable } : {})
|
|
26
|
+
});
|
|
27
|
+
blockers = [
|
|
28
|
+
...(arbiter.ok ? [] : ['gpt_final_arbiter_required_not_passed']),
|
|
29
|
+
...(Array.isArray(arbiter.blockers) ? arbiter.blockers.map(String) : [])
|
|
30
|
+
];
|
|
31
|
+
}
|
|
32
|
+
const result = {
|
|
33
|
+
schema: 'sks.pipeline-finalize-result.v1',
|
|
34
|
+
generated_at: nowIso(),
|
|
35
|
+
ok: blockers.length === 0,
|
|
36
|
+
route: input.route,
|
|
37
|
+
mission_id: input.missionId,
|
|
38
|
+
local_participated: requirement.local_participated,
|
|
39
|
+
gpt_final_required: requirement.gpt_final_required,
|
|
40
|
+
gpt_final_arbiter: arbiter,
|
|
41
|
+
final_status: blockers.length ? 'blocked' : 'accepted',
|
|
42
|
+
apply_allowed: blockers.length === 0 && input.applyPatches === true,
|
|
43
|
+
final_patch_source: requirement.gpt_final_required ? 'gpt_final_arbiter' : 'deterministic_finalize',
|
|
44
|
+
candidate_results_count: input.candidateResults.length,
|
|
45
|
+
candidate_patch_envelope_count: input.candidatePatchEnvelopes.length,
|
|
46
|
+
verification_results_count: input.verificationResults.length,
|
|
47
|
+
side_effect_report: input.sideEffectReport,
|
|
48
|
+
mutation_ledger: input.mutationLedger,
|
|
49
|
+
rollback_plan: input.rollbackPlan,
|
|
50
|
+
blockers
|
|
51
|
+
};
|
|
52
|
+
await writeJsonAtomic(path.join(root, 'pipeline-finalize-result.json'), result);
|
|
53
|
+
return result;
|
|
54
|
+
}
|
|
55
|
+
function safeName(value) {
|
|
56
|
+
return String(value || 'unknown').replace(/[^a-zA-Z0-9_.-]+/g, '-').slice(0, 80);
|
|
57
|
+
}
|
|
58
|
+
//# sourceMappingURL=finalize-pipeline-result.js.map
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { localCollaborationParticipated } from '../local-llm/local-collaboration-policy.js';
|
|
2
|
+
export function gptFinalRequiredForPipeline(input) {
|
|
3
|
+
const localParticipated = input.localParticipated === true
|
|
4
|
+
|| localCollaborationParticipated(Array.isArray(input.candidateResults) ? input.candidateResults : []);
|
|
5
|
+
return {
|
|
6
|
+
schema: 'sks.gpt-final-required.v1',
|
|
7
|
+
local_participated: localParticipated,
|
|
8
|
+
gpt_final_required: localParticipated,
|
|
9
|
+
reason: localParticipated ? 'local_llm_outputs_are_drafts' : 'no_local_participation'
|
|
10
|
+
};
|
|
11
|
+
}
|
|
12
|
+
//# sourceMappingURL=gpt-final-required.js.map
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
const PLACEHOLDER_PATTERNS = [
|
|
2
|
+
/@filename\b/i,
|
|
3
|
+
/<file>/i,
|
|
4
|
+
/\bTODO_PATH\b/i,
|
|
5
|
+
/\bINSERT_PATH_HERE\b/i,
|
|
6
|
+
/\/path\/to\/file\b/i
|
|
7
|
+
];
|
|
8
|
+
export function checkPromptPlaceholders(input = {}) {
|
|
9
|
+
const prompt = String(input.prompt || '');
|
|
10
|
+
const writeCapable = input.writeCapable === true;
|
|
11
|
+
const placeholders = PLACEHOLDER_PATTERNS
|
|
12
|
+
.filter((pattern) => pattern.test(prompt))
|
|
13
|
+
.map((pattern) => pattern.source);
|
|
14
|
+
const emptyTargetPaths = writeCapable && (!Array.isArray(input.targetPaths) || input.targetPaths.length === 0);
|
|
15
|
+
const blockers = writeCapable ? [
|
|
16
|
+
...placeholders.map((placeholder) => `unresolved_prompt_placeholder:${placeholder}`),
|
|
17
|
+
...(emptyTargetPaths ? ['write_capable_prompt_target_paths_empty'] : [])
|
|
18
|
+
] : [];
|
|
19
|
+
const warnings = writeCapable ? [] : placeholders.map((placeholder) => `readonly_prompt_placeholder_warning:${placeholder}`);
|
|
20
|
+
return {
|
|
21
|
+
schema: 'sks.prompt-placeholder-guard.v1',
|
|
22
|
+
ok: blockers.length === 0,
|
|
23
|
+
write_capable: writeCapable,
|
|
24
|
+
placeholders,
|
|
25
|
+
empty_target_paths: emptyTargetPaths,
|
|
26
|
+
blockers,
|
|
27
|
+
warnings
|
|
28
|
+
};
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=prompt-placeholder-guard.js.map
|
|
@@ -1,4 +1,17 @@
|
|
|
1
1
|
export const DEFAULT_CAPABILITY_CARDS = [
|
|
2
|
+
{
|
|
3
|
+
id: 'local-llm-worker',
|
|
4
|
+
tier: 'worker',
|
|
5
|
+
supports_images: false,
|
|
6
|
+
supports_write: true,
|
|
7
|
+
supports_research: false,
|
|
8
|
+
reliability: 0.78,
|
|
9
|
+
latency_cost: 1,
|
|
10
|
+
token_cost: 0,
|
|
11
|
+
mutation_risk_cost: 2,
|
|
12
|
+
model_price_cost: 0,
|
|
13
|
+
queue_pressure_cost: 2
|
|
14
|
+
},
|
|
2
15
|
{
|
|
3
16
|
id: 'fast-worker',
|
|
4
17
|
tier: 'worker',
|
|
@@ -8,6 +8,9 @@ export function codexRouteCacheKey(input) {
|
|
|
8
8
|
files: input.inputFiles || [],
|
|
9
9
|
images: (input.inputImages || []).length,
|
|
10
10
|
sandbox: input.sandboxPolicy,
|
|
11
|
+
allow_local_llm: input.allowLocalLlm === true,
|
|
12
|
+
backend_preference: input.backendPreference || [],
|
|
13
|
+
local_llm_policy: input.localLlmPolicy || null,
|
|
11
14
|
write_paths: input.requestedScopeContract?.write_paths || [],
|
|
12
15
|
allowed_paths: input.requestedScopeContract?.allowed_paths || []
|
|
13
16
|
}));
|
|
@@ -8,7 +8,8 @@ export function routeCodexTask(input, cards = DEFAULT_CAPABILITY_CARDS) {
|
|
|
8
8
|
return { ...cached, cache_hit: true };
|
|
9
9
|
const classification = classifyCodexTask(input);
|
|
10
10
|
const hardFilters = [];
|
|
11
|
-
const
|
|
11
|
+
const availableCards = input.allowLocalLlm === true ? cards : cards.filter((card) => card.id !== 'local-llm-worker');
|
|
12
|
+
const scored = availableCards.map((card) => {
|
|
12
13
|
const score = scoreCapabilityCard(card, classification);
|
|
13
14
|
if (score === 0)
|
|
14
15
|
hardFilters.push(card.id);
|
package/dist/core/routes.js
CHANGED
|
@@ -371,16 +371,16 @@ export const ROUTES = [
|
|
|
371
371
|
id: 'Naruto',
|
|
372
372
|
command: '$Naruto',
|
|
373
373
|
mode: 'NARUTO',
|
|
374
|
-
route: '
|
|
375
|
-
description: '
|
|
374
|
+
route: 'hardware-safe massive parallel work swarm',
|
|
375
|
+
description: '$Naruto mode launches a hardware-safe massive parallel work swarm. Clones may implement, modify, verify, test, research, document, and resolve conflicts according to role and lease policy; write-capable output is accepted only through patch envelopes, verification DAG, mutation guard, and GPT final arbiter.',
|
|
376
376
|
requiredSkills: ['team', 'pipeline-runner', 'prompt-pipeline', 'honest-mode'],
|
|
377
377
|
dollarAliases: ['$ShadowClone', '$Kagebunshin'],
|
|
378
378
|
appSkillAliases: ['shadow-clone', 'kage-bunshin'],
|
|
379
|
-
lifecycle: ['clone_roster_build', '
|
|
379
|
+
lifecycle: ['clone_roster_build', 'massive_work_graph', 'hardware_safe_governor', 'dynamic_active_pool', 'lease_based_write_swarm', 'parallel_verification_dag', 'gpt_final_arbiter_pack', 'per_clone_proof', 'session_cleanup', 'honest_mode'],
|
|
380
380
|
context7Policy: 'optional',
|
|
381
381
|
reasoningPolicy: 'high',
|
|
382
382
|
stopGate: 'team-gate.json',
|
|
383
|
-
cliEntrypoint: 'sks naruto run "task" [--clones N] [--backend codex-
|
|
383
|
+
cliEntrypoint: 'sks naruto run "task" [--clones N] [--backend codex-sdk|fake|ollama] [--parallel-write] | sks naruto status',
|
|
384
384
|
examples: ['$Naruto run sweep the codebase for TODO comments with 50 clones', '$ShadowClone --clones 100 fan out and draft tests for every module']
|
|
385
385
|
},
|
|
386
386
|
{
|