opencode-swarm 7.73.3 → 7.74.1
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/cli/index.js +478 -196
- package/dist/config/schema.d.ts +14 -0
- package/dist/hooks/knowledge-application.d.ts +1 -0
- package/dist/hooks/knowledge-curator.d.ts +7 -2
- package/dist/hooks/knowledge-events.d.ts +16 -9
- package/dist/hooks/knowledge-injector.d.ts +1 -1
- package/dist/hooks/knowledge-reader.d.ts +1 -0
- package/dist/hooks/knowledge-store.d.ts +3 -0
- package/dist/hooks/knowledge-types.d.ts +5 -0
- package/dist/hooks/knowledge-validator.d.ts +5 -6
- package/dist/hooks/micro-reflector.d.ts +2 -1
- package/dist/hooks/skill-scoring.d.ts +1 -1
- package/dist/hooks/skill-usage-log.d.ts +7 -2
- package/dist/index.js +715 -318
- package/dist/services/external-skill-validator.d.ts +3 -0
- package/dist/services/skill-generator.d.ts +5 -0
- package/dist/services/skill-improver-quota.d.ts +6 -4
- package/dist/services/skill-improver.d.ts +6 -2
- package/dist/services/unactionable-hardening.d.ts +2 -2
- package/package.json +1 -1
- package/dist/skills/index.d.ts +0 -30
package/dist/index.js
CHANGED
|
@@ -69,7 +69,7 @@ var package_default;
|
|
|
69
69
|
var init_package = __esm(() => {
|
|
70
70
|
package_default = {
|
|
71
71
|
name: "opencode-swarm",
|
|
72
|
-
version: "7.
|
|
72
|
+
version: "7.74.1",
|
|
73
73
|
description: "Architect-centric agentic swarm plugin for OpenCode - hub-and-spoke orchestration with SME consultation, code generation, and QA review",
|
|
74
74
|
main: "dist/index.js",
|
|
75
75
|
types: "dist/index.d.ts",
|
|
@@ -648,7 +648,7 @@ var init_tool_metadata = __esm(() => {
|
|
|
648
648
|
agents: ["architect", "coder"]
|
|
649
649
|
},
|
|
650
650
|
knowledge_archive: {
|
|
651
|
-
description: "archive (default), quarantine, or purge a swarm knowledge entry by ID with an immutable audit tombstone; purge requires an admin flag",
|
|
651
|
+
description: "archive (default), quarantine, or purge a swarm or hive knowledge entry by ID with an immutable audit tombstone; purge requires an admin flag",
|
|
652
652
|
agents: ["architect"]
|
|
653
653
|
},
|
|
654
654
|
swarm_memory_recall: {
|
|
@@ -15921,7 +15921,11 @@ var init_schema = __esm(() => {
|
|
|
15921
15921
|
cold_start_max_age_phases: exports_external.number().int().min(0).max(100).default(3),
|
|
15922
15922
|
synonym_min_cooccurrence: exports_external.number().int().min(1).max(100).default(3),
|
|
15923
15923
|
synonym_map_max_pairs: exports_external.number().int().min(1).max(1e4).default(500)
|
|
15924
|
-
}).optional()
|
|
15924
|
+
}).optional(),
|
|
15925
|
+
enrichment: exports_external.object({
|
|
15926
|
+
max_calls_per_day: exports_external.number().int().min(0).max(1000).default(30),
|
|
15927
|
+
quota_window: exports_external.enum(["utc", "local"]).default("utc")
|
|
15928
|
+
}).default({ max_calls_per_day: 30, quota_window: "utc" })
|
|
15925
15929
|
});
|
|
15926
15930
|
MemoryConfigSchema = exports_external.object({
|
|
15927
15931
|
enabled: exports_external.boolean().default(false),
|
|
@@ -15988,7 +15992,7 @@ var init_schema = __esm(() => {
|
|
|
15988
15992
|
llm_timeout_ms: exports_external.number().int().min(5000).max(600000).default(300000),
|
|
15989
15993
|
skill_generation_enabled: exports_external.boolean().default(true),
|
|
15990
15994
|
skill_generation_mode: exports_external.enum(["draft", "active"]).default("draft"),
|
|
15991
|
-
min_skill_confidence: exports_external.number().min(0).max(1).default(0.
|
|
15995
|
+
min_skill_confidence: exports_external.number().min(0).max(1).default(0.7),
|
|
15992
15996
|
min_skill_confirmations: exports_external.number().int().min(1).max(50).default(2)
|
|
15993
15997
|
});
|
|
15994
15998
|
ArchitecturalSupervisionConfigSchema = exports_external.object({
|
|
@@ -16736,7 +16740,7 @@ var init_plan_schema = __esm(() => {
|
|
|
16736
16740
|
init_zod();
|
|
16737
16741
|
ExecutionProfileSchema = exports_external.object({
|
|
16738
16742
|
parallelization_enabled: exports_external.boolean().default(false),
|
|
16739
|
-
max_concurrent_tasks: exports_external.number().int().min(1).max(64).default(
|
|
16743
|
+
max_concurrent_tasks: exports_external.number().int().min(1).max(64).default(10),
|
|
16740
16744
|
council_parallel: exports_external.boolean().default(true),
|
|
16741
16745
|
locked: exports_external.boolean().default(false),
|
|
16742
16746
|
auto_proceed: exports_external.boolean().default(false)
|
|
@@ -42662,8 +42666,30 @@ async function buildParallelExecutionGuidance(directory, sessionID, session) {
|
|
|
42662
42666
|
}
|
|
42663
42667
|
const profile = plan.execution_profile;
|
|
42664
42668
|
const enabled = profile?.parallelization_enabled === true;
|
|
42665
|
-
const maxConcurrent = profile?.max_concurrent_tasks ??
|
|
42666
|
-
|
|
42669
|
+
const maxConcurrent = profile?.max_concurrent_tasks ?? 10;
|
|
42670
|
+
let effectiveMaxConcurrent = session?.maxConcurrencyOverride ?? maxConcurrent;
|
|
42671
|
+
const allTasks = plan.phases.flatMap((phase) => phase.tasks);
|
|
42672
|
+
const blockedTasks = allTasks.filter((task) => {
|
|
42673
|
+
if (task.status !== "blocked")
|
|
42674
|
+
return false;
|
|
42675
|
+
const reason = (task.blocked_reason ?? "").toLowerCase();
|
|
42676
|
+
return reason.includes("fail") || reason.includes("error") || reason.includes("exception");
|
|
42677
|
+
});
|
|
42678
|
+
const totalTasks = allTasks.length;
|
|
42679
|
+
let backoffTriggered = false;
|
|
42680
|
+
if (totalTasks > 0 && blockedTasks.length > 0) {
|
|
42681
|
+
const failureRate = blockedTasks.length / totalTasks;
|
|
42682
|
+
const FAILURE_RATE_THRESHOLD = 0.2;
|
|
42683
|
+
const BACKOFF_MULTIPLIER = 0.5;
|
|
42684
|
+
if (failureRate > FAILURE_RATE_THRESHOLD && blockedTasks.length >= 2) {
|
|
42685
|
+
const newConcurrency = Math.max(1, Math.floor(effectiveMaxConcurrent * BACKOFF_MULTIPLIER));
|
|
42686
|
+
if (newConcurrency < effectiveMaxConcurrent) {
|
|
42687
|
+
effectiveMaxConcurrent = newConcurrency;
|
|
42688
|
+
session.maxConcurrencyOverride = newConcurrency;
|
|
42689
|
+
backoffTriggered = true;
|
|
42690
|
+
}
|
|
42691
|
+
}
|
|
42692
|
+
}
|
|
42667
42693
|
if (!enabled || effectiveMaxConcurrent <= 1)
|
|
42668
42694
|
return null;
|
|
42669
42695
|
if (hasActiveLeanTurbo(sessionID)) {
|
|
@@ -42675,7 +42701,6 @@ async function buildParallelExecutionGuidance(directory, sessionID, session) {
|
|
|
42675
42701
|
const tasks = currentPhase.tasks;
|
|
42676
42702
|
if (tasks.length === 0)
|
|
42677
42703
|
return null;
|
|
42678
|
-
const allTasks = plan.phases.flatMap((phase) => phase.tasks);
|
|
42679
42704
|
const completed = new Set;
|
|
42680
42705
|
for (const task of allTasks) {
|
|
42681
42706
|
const taskId = task.id;
|
|
@@ -42709,7 +42734,8 @@ async function buildParallelExecutionGuidance(directory, sessionID, session) {
|
|
|
42709
42734
|
if (eligible.length === 0) {
|
|
42710
42735
|
return `[PARALLEL EXECUTION PROFILE] parallelization_enabled=true max_concurrent_tasks=${effectiveMaxConcurrent}; no dependency-ready pending tasks are available for a new coder slot. Continue the current task/gate.`;
|
|
42711
42736
|
}
|
|
42712
|
-
|
|
42737
|
+
const failureWarning = backoffTriggered ? ` (${blockedTasks.length} blocked task(s) detected — concurrency auto-reduced due to failures)` : "";
|
|
42738
|
+
return `[PARALLEL EXECUTION PROFILE] parallelization_enabled=true max_concurrent_tasks=${effectiveMaxConcurrent}; ${occupied.size} slot(s) occupied. Eligible now: ${eligible.join(", ")}. [NEXT] dispatch up to ${availableSlots} eligible coder task(s) before waiting; preserve ONE task per coder call and call declare_scope for each task.${failureWarning}`;
|
|
42713
42739
|
}
|
|
42714
42740
|
function isParallelGuidancePhaseComplete(phase) {
|
|
42715
42741
|
return phase.status === "complete" || phase.status === "completed" || phase.status === "closed";
|
|
@@ -42873,7 +42899,7 @@ function createDelegationGateHook(config2, directory) {
|
|
|
42873
42899
|
return;
|
|
42874
42900
|
const profile = plan.execution_profile;
|
|
42875
42901
|
const parallelEnabled = profile?.parallelization_enabled === true;
|
|
42876
|
-
const maxConcurrent = profile?.max_concurrent_tasks ??
|
|
42902
|
+
const maxConcurrent = profile?.max_concurrent_tasks ?? 10;
|
|
42877
42903
|
const effectiveMaxConcurrent = session.maxConcurrencyOverride ?? maxConcurrent;
|
|
42878
42904
|
if (!parallelEnabled || effectiveMaxConcurrent <= 1)
|
|
42879
42905
|
return;
|
|
@@ -59501,7 +59527,7 @@ async function appendKnowledgeWithCapEnforcement(filePath, entry, maxEntries) {
|
|
|
59501
59527
|
return transactKnowledge(filePath, (entries) => {
|
|
59502
59528
|
const updated = [...entries, entry];
|
|
59503
59529
|
if (updated.length > maxEntries) {
|
|
59504
|
-
return
|
|
59530
|
+
return selectKnowledgeCapSurvivors(updated, maxEntries);
|
|
59505
59531
|
}
|
|
59506
59532
|
return updated;
|
|
59507
59533
|
});
|
|
@@ -59510,8 +59536,45 @@ async function enforceKnowledgeCap(filePath, maxEntries) {
|
|
|
59510
59536
|
await transactKnowledge(filePath, (entries) => {
|
|
59511
59537
|
if (entries.length <= maxEntries)
|
|
59512
59538
|
return null;
|
|
59513
|
-
return
|
|
59539
|
+
return selectKnowledgeCapSurvivors(entries, maxEntries);
|
|
59540
|
+
});
|
|
59541
|
+
}
|
|
59542
|
+
function selectKnowledgeCapSurvivors(entries, maxEntries) {
|
|
59543
|
+
if (entries.length <= maxEntries)
|
|
59544
|
+
return entries;
|
|
59545
|
+
if (maxEntries <= 0)
|
|
59546
|
+
return [];
|
|
59547
|
+
const candidates = entries.map((entry, index) => {
|
|
59548
|
+
const maybeKnowledge = entry;
|
|
59549
|
+
return {
|
|
59550
|
+
entry,
|
|
59551
|
+
index,
|
|
59552
|
+
status: maybeKnowledge.status,
|
|
59553
|
+
outcomeSignal: computeOutcomeSignal(maybeKnowledge.retrieval_outcomes)
|
|
59554
|
+
};
|
|
59514
59555
|
});
|
|
59556
|
+
const allPromoted = candidates.every((c) => c.status === "promoted");
|
|
59557
|
+
const evictable = allPromoted ? candidates : candidates.filter((c) => c.status !== "promoted");
|
|
59558
|
+
const targetDropCount = entries.length - maxEntries;
|
|
59559
|
+
const dropCount = Math.min(targetDropCount, evictable.length);
|
|
59560
|
+
if (dropCount <= 0)
|
|
59561
|
+
return entries;
|
|
59562
|
+
const drop = new Set([...evictable].sort((a, b) => {
|
|
59563
|
+
const inactiveDelta = getKnowledgeCapStatusPriority(a.status) - getKnowledgeCapStatusPriority(b.status);
|
|
59564
|
+
if (inactiveDelta !== 0)
|
|
59565
|
+
return inactiveDelta;
|
|
59566
|
+
const signalDelta = a.outcomeSignal - b.outcomeSignal;
|
|
59567
|
+
if (signalDelta !== 0)
|
|
59568
|
+
return signalDelta;
|
|
59569
|
+
return a.index - b.index;
|
|
59570
|
+
}).slice(0, dropCount).map((c) => c.index));
|
|
59571
|
+
return candidates.filter((c) => !drop.has(c.index)).map((c) => c.entry);
|
|
59572
|
+
}
|
|
59573
|
+
function getKnowledgeCapStatusPriority(status) {
|
|
59574
|
+
if (status === "archived" || status === "quarantined" || status === "quarantined_unactionable") {
|
|
59575
|
+
return 0;
|
|
59576
|
+
}
|
|
59577
|
+
return 1;
|
|
59515
59578
|
}
|
|
59516
59579
|
async function sweepAgedEntries(filePath, defaultMaxPhases) {
|
|
59517
59580
|
const result = {
|
|
@@ -59748,6 +59811,7 @@ var init_knowledge_store = __esm(() => {
|
|
|
59748
59811
|
findNearDuplicate,
|
|
59749
59812
|
computeConfidence,
|
|
59750
59813
|
computeOutcomeSignal,
|
|
59814
|
+
selectKnowledgeCapSurvivors,
|
|
59751
59815
|
inferTags,
|
|
59752
59816
|
bumpKnowledgeConfidenceBatch
|
|
59753
59817
|
};
|
|
@@ -59758,6 +59822,7 @@ var exports_knowledge_events = {};
|
|
|
59758
59822
|
__export(exports_knowledge_events, {
|
|
59759
59823
|
resolveLegacyApplicationLogPath: () => resolveLegacyApplicationLogPath,
|
|
59760
59824
|
resolveKnowledgeEventsPath: () => resolveKnowledgeEventsPath,
|
|
59825
|
+
resolveKnowledgeCounterBaselinePath: () => resolveKnowledgeCounterBaselinePath,
|
|
59761
59826
|
recordKnowledgeEvent: () => recordKnowledgeEvent,
|
|
59762
59827
|
recomputeCounters: () => recomputeCounters,
|
|
59763
59828
|
readLegacyApplicationRecords: () => readLegacyApplicationRecords,
|
|
@@ -59778,11 +59843,14 @@ __export(exports_knowledge_events, {
|
|
|
59778
59843
|
});
|
|
59779
59844
|
import { randomUUID as randomUUID2 } from "node:crypto";
|
|
59780
59845
|
import { existsSync as existsSync15 } from "node:fs";
|
|
59781
|
-
import { appendFile as appendFile4, mkdir as mkdir4, readFile as readFile5,
|
|
59846
|
+
import { appendFile as appendFile4, mkdir as mkdir4, readFile as readFile5, stat as stat3 } from "node:fs/promises";
|
|
59782
59847
|
import * as path32 from "node:path";
|
|
59783
59848
|
function resolveKnowledgeEventsPath(directory) {
|
|
59784
59849
|
return path32.join(directory, ".swarm", "knowledge-events.jsonl");
|
|
59785
59850
|
}
|
|
59851
|
+
function resolveKnowledgeCounterBaselinePath(directory) {
|
|
59852
|
+
return path32.join(directory, ".swarm", "knowledge-counter-baseline.json");
|
|
59853
|
+
}
|
|
59786
59854
|
function resolveLegacyApplicationLogPath(directory) {
|
|
59787
59855
|
return path32.join(directory, ".swarm", "knowledge-application.jsonl");
|
|
59788
59856
|
}
|
|
@@ -59817,10 +59885,12 @@ async function appendKnowledgeEvent(directory, event) {
|
|
|
59817
59885
|
const lines = content.split(`
|
|
59818
59886
|
`).filter((line) => line.trim().length > 0);
|
|
59819
59887
|
if (lines.length > MAX_EVENT_LOG_ENTRIES) {
|
|
59888
|
+
const evicted = lines.slice(0, lines.length - MAX_EVENT_LOG_ENTRIES);
|
|
59820
59889
|
const trimmed = lines.slice(lines.length - MAX_EVENT_LOG_ENTRIES);
|
|
59821
|
-
await
|
|
59890
|
+
await foldEvictedEventsIntoBaseline(directory, evicted, filePath);
|
|
59891
|
+
await atomicWriteFile(filePath, `${trimmed.join(`
|
|
59822
59892
|
`)}
|
|
59823
|
-
|
|
59893
|
+
`);
|
|
59824
59894
|
}
|
|
59825
59895
|
} catch (err2) {
|
|
59826
59896
|
warn(`[knowledge-events] local cap trim failed (non-fatal): ${err2 instanceof Error ? err2.message : String(err2)}`);
|
|
@@ -59844,19 +59914,8 @@ async function readKnowledgeEvents(directory) {
|
|
|
59844
59914
|
if (!existsSync15(filePath))
|
|
59845
59915
|
return [];
|
|
59846
59916
|
const content = await readFile5(filePath, "utf-8");
|
|
59847
|
-
|
|
59848
|
-
|
|
59849
|
-
`)) {
|
|
59850
|
-
const trimmed = line.trim();
|
|
59851
|
-
if (!trimmed)
|
|
59852
|
-
continue;
|
|
59853
|
-
try {
|
|
59854
|
-
out2.push(JSON.parse(trimmed));
|
|
59855
|
-
} catch {
|
|
59856
|
-
warn(`[knowledge-events] Skipping corrupted JSONL line in ${filePath}: ${trimmed.slice(0, 80)}`);
|
|
59857
|
-
}
|
|
59858
|
-
}
|
|
59859
|
-
return out2;
|
|
59917
|
+
return parseEventLines(content.split(`
|
|
59918
|
+
`), filePath);
|
|
59860
59919
|
}
|
|
59861
59920
|
async function readLegacyApplicationRecords(directory) {
|
|
59862
59921
|
const filePath = resolveLegacyApplicationLogPath(directory);
|
|
@@ -59892,6 +59951,49 @@ function emptyRollup() {
|
|
|
59892
59951
|
violation_timestamps: []
|
|
59893
59952
|
};
|
|
59894
59953
|
}
|
|
59954
|
+
function cloneRollup(input) {
|
|
59955
|
+
return {
|
|
59956
|
+
...emptyRollup(),
|
|
59957
|
+
...input,
|
|
59958
|
+
violation_timestamps: [...input.violation_timestamps ?? []]
|
|
59959
|
+
};
|
|
59960
|
+
}
|
|
59961
|
+
function cloneRollupMap(input) {
|
|
59962
|
+
const out2 = new Map;
|
|
59963
|
+
for (const [id, rollup] of input) {
|
|
59964
|
+
out2.set(id, cloneRollup(rollup));
|
|
59965
|
+
}
|
|
59966
|
+
return out2;
|
|
59967
|
+
}
|
|
59968
|
+
function normalizeRollupTimestamps(rollup) {
|
|
59969
|
+
if (rollup.violation_timestamps.length > 1) {
|
|
59970
|
+
rollup.violation_timestamps.sort((a, b) => a < b ? 1 : a > b ? -1 : 0);
|
|
59971
|
+
}
|
|
59972
|
+
if (rollup.violation_timestamps.length > MAX_VIOLATION_TIMESTAMPS) {
|
|
59973
|
+
rollup.violation_timestamps = rollup.violation_timestamps.slice(0, MAX_VIOLATION_TIMESTAMPS);
|
|
59974
|
+
}
|
|
59975
|
+
return rollup;
|
|
59976
|
+
}
|
|
59977
|
+
function mergeRollupInto(target, source) {
|
|
59978
|
+
target.shown_count += source.shown_count ?? 0;
|
|
59979
|
+
target.acknowledged_count += source.acknowledged_count ?? 0;
|
|
59980
|
+
target.applied_explicit_count += source.applied_explicit_count ?? 0;
|
|
59981
|
+
target.ignored_count += source.ignored_count ?? 0;
|
|
59982
|
+
target.violated_count += source.violated_count ?? 0;
|
|
59983
|
+
target.contradicted_count += source.contradicted_count ?? 0;
|
|
59984
|
+
target.n_a_count += source.n_a_count ?? 0;
|
|
59985
|
+
target.succeeded_after_shown_count += source.succeeded_after_shown_count ?? 0;
|
|
59986
|
+
target.failed_after_shown_count += source.failed_after_shown_count ?? 0;
|
|
59987
|
+
target.partial_after_shown_count += source.partial_after_shown_count ?? 0;
|
|
59988
|
+
if (source.last_applied_at) {
|
|
59989
|
+
target.last_applied_at = maxIso(target.last_applied_at, source.last_applied_at);
|
|
59990
|
+
}
|
|
59991
|
+
if (source.last_acknowledged_at) {
|
|
59992
|
+
target.last_acknowledged_at = maxIso(target.last_acknowledged_at, source.last_acknowledged_at);
|
|
59993
|
+
}
|
|
59994
|
+
target.violation_timestamps.push(...source.violation_timestamps ?? []);
|
|
59995
|
+
normalizeRollupTimestamps(target);
|
|
59996
|
+
}
|
|
59895
59997
|
function get(map3, id) {
|
|
59896
59998
|
let r = map3.get(id);
|
|
59897
59999
|
if (!r) {
|
|
@@ -59905,9 +60007,91 @@ function maxIso(current, candidate) {
|
|
|
59905
60007
|
return candidate;
|
|
59906
60008
|
return candidate > current ? candidate : current;
|
|
59907
60009
|
}
|
|
59908
|
-
function
|
|
60010
|
+
async function readCounterBaseline(directory) {
|
|
60011
|
+
const filePath = resolveKnowledgeCounterBaselinePath(directory);
|
|
60012
|
+
if (!existsSync15(filePath))
|
|
60013
|
+
return new Map;
|
|
60014
|
+
const raw = JSON.parse(await readFile5(filePath, "utf-8"));
|
|
60015
|
+
const map3 = new Map;
|
|
60016
|
+
for (const [id, rollup] of Object.entries(raw)) {
|
|
60017
|
+
map3.set(id, normalizeRollupTimestamps(cloneRollup(rollup)));
|
|
60018
|
+
}
|
|
60019
|
+
return map3;
|
|
60020
|
+
}
|
|
60021
|
+
async function writeCounterBaseline(directory, baseline) {
|
|
60022
|
+
const filePath = resolveKnowledgeCounterBaselinePath(directory);
|
|
60023
|
+
const out2 = {};
|
|
60024
|
+
for (const [id, rollup] of [...baseline.entries()].sort(([a], [b]) => a.localeCompare(b))) {
|
|
60025
|
+
out2[id] = normalizeRollupTimestamps(cloneRollup(rollup));
|
|
60026
|
+
}
|
|
60027
|
+
await atomicWriteFile(filePath, `${JSON.stringify(out2, null, 2)}
|
|
60028
|
+
`);
|
|
60029
|
+
}
|
|
60030
|
+
async function statCacheKey(filePath) {
|
|
60031
|
+
try {
|
|
60032
|
+
const fileStat = await stat3(filePath);
|
|
60033
|
+
return `${fileStat.mtimeMs}:${fileStat.ctimeMs}:${fileStat.size}`;
|
|
60034
|
+
} catch (err2) {
|
|
60035
|
+
if (err2?.code === "ENOENT")
|
|
60036
|
+
return "missing";
|
|
60037
|
+
throw err2;
|
|
60038
|
+
}
|
|
60039
|
+
}
|
|
60040
|
+
async function buildCounterRollupCacheKey(directory) {
|
|
60041
|
+
const [eventsKey, legacyKey, baselineKey] = await Promise.all([
|
|
60042
|
+
statCacheKey(resolveKnowledgeEventsPath(directory)),
|
|
60043
|
+
statCacheKey(resolveLegacyApplicationLogPath(directory)),
|
|
60044
|
+
statCacheKey(resolveKnowledgeCounterBaselinePath(directory))
|
|
60045
|
+
]);
|
|
60046
|
+
return `${eventsKey}|${legacyKey}|${baselineKey}`;
|
|
60047
|
+
}
|
|
60048
|
+
function setCounterRollupCache(directory, key, rollups) {
|
|
60049
|
+
if (counterRollupCache.has(directory)) {
|
|
60050
|
+
counterRollupCache.delete(directory);
|
|
60051
|
+
}
|
|
60052
|
+
counterRollupCache.set(directory, {
|
|
60053
|
+
key,
|
|
60054
|
+
rollups: cloneRollupMap(rollups)
|
|
60055
|
+
});
|
|
60056
|
+
while (counterRollupCache.size > MAX_COUNTER_ROLLUP_CACHE_DIRS) {
|
|
60057
|
+
const oldestKey = counterRollupCache.keys().next().value;
|
|
60058
|
+
if (oldestKey === undefined)
|
|
60059
|
+
break;
|
|
60060
|
+
counterRollupCache.delete(oldestKey);
|
|
60061
|
+
}
|
|
60062
|
+
}
|
|
60063
|
+
function parseEventLines(lines, filePath) {
|
|
60064
|
+
const out2 = [];
|
|
60065
|
+
for (const line of lines) {
|
|
60066
|
+
const trimmed = line.trim();
|
|
60067
|
+
if (!trimmed)
|
|
60068
|
+
continue;
|
|
60069
|
+
try {
|
|
60070
|
+
out2.push(JSON.parse(trimmed));
|
|
60071
|
+
} catch {
|
|
60072
|
+
warn(`[knowledge-events] Skipping corrupted JSONL line in ${filePath}: ${trimmed.slice(0, 80)}`);
|
|
60073
|
+
}
|
|
60074
|
+
}
|
|
60075
|
+
return out2;
|
|
60076
|
+
}
|
|
60077
|
+
async function foldEvictedEventsIntoBaseline(directory, evictedLines, filePath) {
|
|
60078
|
+
const evictedEvents = parseEventLines(evictedLines, filePath);
|
|
60079
|
+
if (evictedEvents.length === 0)
|
|
60080
|
+
return;
|
|
60081
|
+
const baseline = await readCounterBaseline(directory);
|
|
60082
|
+
for (const [id, rollup] of recomputeCounters(evictedEvents)) {
|
|
60083
|
+
mergeRollupInto(get(baseline, id), rollup);
|
|
60084
|
+
}
|
|
60085
|
+
await writeCounterBaseline(directory, baseline);
|
|
60086
|
+
}
|
|
60087
|
+
function recomputeCounters(events, legacyRecords = [], baseline = new Map) {
|
|
59909
60088
|
const map3 = new Map;
|
|
59910
60089
|
const retrievedIds = new Set;
|
|
60090
|
+
for (const [id, rollup] of baseline) {
|
|
60091
|
+
map3.set(id, cloneRollup(rollup));
|
|
60092
|
+
if ((rollup.shown_count ?? 0) > 0)
|
|
60093
|
+
retrievedIds.add(id);
|
|
60094
|
+
}
|
|
59911
60095
|
for (const e of events) {
|
|
59912
60096
|
switch (e.type) {
|
|
59913
60097
|
case "retrieved": {
|
|
@@ -59983,12 +60167,7 @@ function recomputeCounters(events, legacyRecords = []) {
|
|
|
59983
60167
|
}
|
|
59984
60168
|
}
|
|
59985
60169
|
for (const r of map3.values()) {
|
|
59986
|
-
|
|
59987
|
-
r.violation_timestamps.sort((a, b) => a < b ? 1 : a > b ? -1 : 0);
|
|
59988
|
-
}
|
|
59989
|
-
if (r.violation_timestamps.length > MAX_VIOLATION_TIMESTAMPS) {
|
|
59990
|
-
r.violation_timestamps = r.violation_timestamps.slice(0, MAX_VIOLATION_TIMESTAMPS);
|
|
59991
|
-
}
|
|
60170
|
+
normalizeRollupTimestamps(r);
|
|
59992
60171
|
}
|
|
59993
60172
|
return map3;
|
|
59994
60173
|
}
|
|
@@ -60031,11 +60210,21 @@ async function countEntryViolationsInWindow(directory, entryId, windowDays, now
|
|
|
60031
60210
|
}
|
|
60032
60211
|
async function readKnowledgeCounterRollups(directory) {
|
|
60033
60212
|
try {
|
|
60034
|
-
const
|
|
60213
|
+
const cacheKey = await buildCounterRollupCacheKey(directory);
|
|
60214
|
+
const cached3 = counterRollupCache.get(directory);
|
|
60215
|
+
if (cached3?.key === cacheKey) {
|
|
60216
|
+
counterRollupCache.delete(directory);
|
|
60217
|
+
counterRollupCache.set(directory, cached3);
|
|
60218
|
+
return cloneRollupMap(cached3.rollups);
|
|
60219
|
+
}
|
|
60220
|
+
const [events, legacyRecords, baseline] = await Promise.all([
|
|
60035
60221
|
readKnowledgeEvents(directory),
|
|
60036
|
-
readLegacyApplicationRecords(directory)
|
|
60222
|
+
readLegacyApplicationRecords(directory),
|
|
60223
|
+
readCounterBaseline(directory)
|
|
60037
60224
|
]);
|
|
60038
|
-
|
|
60225
|
+
const rollups = recomputeCounters(events, legacyRecords, baseline);
|
|
60226
|
+
setCounterRollupCache(directory, cacheKey, rollups);
|
|
60227
|
+
return cloneRollupMap(rollups);
|
|
60039
60228
|
} catch (err2) {
|
|
60040
60229
|
warn(`[knowledge-events] readKnowledgeCounterRollups failed: ${err2 instanceof Error ? err2.message : String(err2)}`);
|
|
60041
60230
|
return new Map;
|
|
@@ -60102,10 +60291,12 @@ async function applyKnowledgeVerdictFeedback(directory, options) {
|
|
|
60102
60291
|
return { processed: 0, bumps: 0 };
|
|
60103
60292
|
}
|
|
60104
60293
|
}
|
|
60105
|
-
var import_proper_lockfile4, KNOWLEDGE_EVENT_SCHEMA_VERSION = 1, MAX_EVENT_LOG_ENTRIES = 5000, RECEIPT_EVENT_TYPES, MAX_VIOLATION_TIMESTAMPS = 10, VERDICT_CONFIDENCE_BOOST = 0.03, VERDICT_CONFIDENCE_DECAY = 0.05, _internals23;
|
|
60294
|
+
var import_proper_lockfile4, KNOWLEDGE_EVENT_SCHEMA_VERSION = 1, MAX_EVENT_LOG_ENTRIES = 5000, counterRollupCache, MAX_COUNTER_ROLLUP_CACHE_DIRS = 32, RECEIPT_EVENT_TYPES, MAX_VIOLATION_TIMESTAMPS = 10, VERDICT_CONFIDENCE_BOOST = 0.03, VERDICT_CONFIDENCE_DECAY = 0.05, _internals23;
|
|
60106
60295
|
var init_knowledge_events = __esm(() => {
|
|
60296
|
+
init_task_file();
|
|
60107
60297
|
init_logger();
|
|
60108
60298
|
import_proper_lockfile4 = __toESM(require_proper_lockfile(), 1);
|
|
60299
|
+
counterRollupCache = new Map;
|
|
60109
60300
|
RECEIPT_EVENT_TYPES = new Set([
|
|
60110
60301
|
"acknowledged",
|
|
60111
60302
|
"applied",
|
|
@@ -60117,9 +60308,11 @@ var init_knowledge_events = __esm(() => {
|
|
|
60117
60308
|
]);
|
|
60118
60309
|
_internals23 = {
|
|
60119
60310
|
resolveKnowledgeEventsPath,
|
|
60311
|
+
resolveKnowledgeCounterBaselinePath,
|
|
60120
60312
|
appendKnowledgeEvent,
|
|
60121
60313
|
recordKnowledgeEvent,
|
|
60122
60314
|
readKnowledgeEvents,
|
|
60315
|
+
readCounterBaseline,
|
|
60123
60316
|
readLegacyApplicationRecords,
|
|
60124
60317
|
readKnowledgeCounterRollups,
|
|
60125
60318
|
effectiveRetrievalOutcomes,
|
|
@@ -60757,7 +60950,7 @@ function validateLesson(candidate, existingLessons, meta3) {
|
|
|
60757
60950
|
};
|
|
60758
60951
|
}
|
|
60759
60952
|
const normalizedCandidate = candidate.normalize("NFKC").replace(INVISIBLE_FORMAT_CHARS, " ").replace(/\s+/g, " ").toLowerCase();
|
|
60760
|
-
for (const pattern of
|
|
60953
|
+
for (const pattern of DANGEROUS_COMMAND_ERROR_PATTERNS) {
|
|
60761
60954
|
if (pattern.test(normalizedCandidate)) {
|
|
60762
60955
|
return {
|
|
60763
60956
|
valid: false,
|
|
@@ -60767,6 +60960,16 @@ function validateLesson(candidate, existingLessons, meta3) {
|
|
|
60767
60960
|
};
|
|
60768
60961
|
}
|
|
60769
60962
|
}
|
|
60963
|
+
for (const pattern of DANGEROUS_COMMAND_WARNING_PATTERNS) {
|
|
60964
|
+
if (pattern.test(normalizedCandidate)) {
|
|
60965
|
+
return {
|
|
60966
|
+
valid: true,
|
|
60967
|
+
layer: 2,
|
|
60968
|
+
reason: "potentially dangerous command pattern queued for review",
|
|
60969
|
+
severity: "warning"
|
|
60970
|
+
};
|
|
60971
|
+
}
|
|
60972
|
+
}
|
|
60770
60973
|
for (const pattern of SECURITY_DEGRADING_PATTERNS) {
|
|
60771
60974
|
if (pattern.test(normalizedCandidate)) {
|
|
60772
60975
|
return {
|
|
@@ -60789,10 +60992,10 @@ function validateLesson(candidate, existingLessons, meta3) {
|
|
|
60789
60992
|
}
|
|
60790
60993
|
if (detectContradiction(candidate, existingLessons)) {
|
|
60791
60994
|
return {
|
|
60792
|
-
valid:
|
|
60995
|
+
valid: true,
|
|
60793
60996
|
layer: 3,
|
|
60794
|
-
reason: "
|
|
60795
|
-
severity: "
|
|
60997
|
+
reason: "possible contradiction with an existing lesson with shared tags",
|
|
60998
|
+
severity: "warning"
|
|
60796
60999
|
};
|
|
60797
61000
|
}
|
|
60798
61001
|
if (isVagueLesson(candidate)) {
|
|
@@ -60932,31 +61135,22 @@ async function appendUnactionable(directory, entry, reason) {
|
|
|
60932
61135
|
const filePath = resolveUnactionablePath(directory);
|
|
60933
61136
|
const dirPath = path33.dirname(filePath);
|
|
60934
61137
|
await mkdir5(dirPath, { recursive: true });
|
|
60935
|
-
|
|
60936
|
-
try {
|
|
60937
|
-
release = await import_proper_lockfile5.default.lock(dirPath, {
|
|
60938
|
-
retries: { retries: 50, minTimeout: 10, maxTimeout: 100 },
|
|
60939
|
-
stale: 5000
|
|
60940
|
-
});
|
|
61138
|
+
await transactKnowledge(filePath, (existing) => {
|
|
60941
61139
|
const record3 = {
|
|
60942
61140
|
...entry,
|
|
60943
61141
|
status: "quarantined_unactionable",
|
|
60944
61142
|
unactionable_reason: reason,
|
|
60945
61143
|
quarantined_at: new Date().toISOString()
|
|
60946
61144
|
};
|
|
60947
|
-
|
|
60948
|
-
|
|
60949
|
-
|
|
60950
|
-
|
|
60951
|
-
|
|
60952
|
-
await atomicWriteFile(filePath, `${trimmed.map((e) => JSON.stringify(e)).join(`
|
|
60953
|
-
`)}
|
|
60954
|
-
`);
|
|
61145
|
+
const duplicate = findNearDuplicate(record3.lesson, existing, 0.6);
|
|
61146
|
+
if (duplicate?.unactionable_reason === reason) {
|
|
61147
|
+
duplicate.quarantined_at = record3.quarantined_at;
|
|
61148
|
+
duplicate.updated_at = record3.updated_at;
|
|
61149
|
+
return existing;
|
|
60955
61150
|
}
|
|
60956
|
-
|
|
60957
|
-
|
|
60958
|
-
|
|
60959
|
-
}
|
|
61151
|
+
const next = [...existing, record3];
|
|
61152
|
+
return next.length > 200 ? next.slice(-200) : next;
|
|
61153
|
+
});
|
|
60960
61154
|
}
|
|
60961
61155
|
async function quarantineEntry(directory, entryId, reason, reportedBy) {
|
|
60962
61156
|
if (!directory || directory.includes("..")) {
|
|
@@ -61090,28 +61284,34 @@ async function restoreEntry(directory, entryId) {
|
|
|
61090
61284
|
}
|
|
61091
61285
|
}
|
|
61092
61286
|
}
|
|
61093
|
-
var import_proper_lockfile5, DANGEROUS_COMMAND_PATTERNS, SECURITY_DEGRADING_PATTERNS, INVISIBLE_FORMAT_CHARS, INJECTION_PATTERNS, VALID_CATEGORIES, TECH_REFERENCE_WORDS, ACTION_VERB_WORDS, NEGATION_PAIRS, ACTIONABLE_STRING_MAX = 200, ACTIONABLE_LIST_MAX = 20, NAME_PATTERN, SOURCE_REF_FORBIDDEN, ALLOWED_SKILL_PATH_PREFIXES, VALID_DIRECTIVE_PRIORITIES;
|
|
61287
|
+
var import_proper_lockfile5, DANGEROUS_COMMAND_ERROR_PATTERNS, DANGEROUS_COMMAND_WARNING_PATTERNS, DANGEROUS_COMMAND_PATTERNS, SECURITY_DEGRADING_PATTERNS, INVISIBLE_FORMAT_CHARS, INJECTION_PATTERNS, VALID_CATEGORIES, TECH_REFERENCE_WORDS, ACTION_VERB_WORDS, NEGATION_PAIRS, ACTIONABLE_STRING_MAX = 200, ACTIONABLE_LIST_MAX = 20, NAME_PATTERN, SOURCE_REF_FORBIDDEN, ALLOWED_SKILL_PATH_PREFIXES, VALID_DIRECTIVE_PRIORITIES;
|
|
61094
61288
|
var init_knowledge_validator = __esm(() => {
|
|
61095
61289
|
init_task_file();
|
|
61096
61290
|
init_logger();
|
|
61097
61291
|
init_knowledge_store();
|
|
61098
61292
|
import_proper_lockfile5 = __toESM(require_proper_lockfile(), 1);
|
|
61099
|
-
|
|
61293
|
+
DANGEROUS_COMMAND_ERROR_PATTERNS = [
|
|
61100
61294
|
/\brm\s+-rf\b/,
|
|
61101
61295
|
/\bsudo\s+rm\b/,
|
|
61102
|
-
/\bformat\b/,
|
|
61103
61296
|
/\bmkfs\b/,
|
|
61104
61297
|
/\bdd\s+if=/,
|
|
61105
61298
|
/:\(\)\s*\{/,
|
|
61106
61299
|
/\bchmod\s+-R\s+777\b/i,
|
|
61107
61300
|
/\bdeltree\b/,
|
|
61108
|
-
/\brmdir\s+\/s\b
|
|
61301
|
+
/\brmdir\s+\/s\b/
|
|
61302
|
+
];
|
|
61303
|
+
DANGEROUS_COMMAND_WARNING_PATTERNS = [
|
|
61304
|
+
/\bformat\b/,
|
|
61109
61305
|
/\bkill\s+-9\b/,
|
|
61110
61306
|
/\bpkill\b/,
|
|
61111
61307
|
/\bkillall\b/,
|
|
61112
61308
|
/`[^`]*`/,
|
|
61113
61309
|
/\$\([^)]*\)/
|
|
61114
61310
|
];
|
|
61311
|
+
DANGEROUS_COMMAND_PATTERNS = [
|
|
61312
|
+
...DANGEROUS_COMMAND_ERROR_PATTERNS,
|
|
61313
|
+
...DANGEROUS_COMMAND_WARNING_PATTERNS
|
|
61314
|
+
];
|
|
61115
61315
|
SECURITY_DEGRADING_PATTERNS = [
|
|
61116
61316
|
/disable\s+.{0,50}firewall/i,
|
|
61117
61317
|
/turn\s+off\s+.{0,50}security/i,
|
|
@@ -61213,7 +61413,7 @@ var init_knowledge_validator = __esm(() => {
|
|
|
61213
61413
|
});
|
|
61214
61414
|
|
|
61215
61415
|
// src/services/skill-changelog.ts
|
|
61216
|
-
import { appendFile as appendFile6, mkdir as mkdir6, readFile as readFile6, writeFile as
|
|
61416
|
+
import { appendFile as appendFile6, mkdir as mkdir6, readFile as readFile6, writeFile as writeFile3 } from "node:fs/promises";
|
|
61217
61417
|
import * as path34 from "node:path";
|
|
61218
61418
|
function resolveSkillChangelogPath(directory, slug) {
|
|
61219
61419
|
if (slug.includes("..") || slug.includes("/") || slug.includes("\\")) {
|
|
@@ -61233,7 +61433,7 @@ async function appendSkillChangelog(directory, slug, entry) {
|
|
|
61233
61433
|
`).filter((line) => line.trim().length > 0);
|
|
61234
61434
|
if (lines.length > MAX_CHANGELOG_ENTRIES_PER_SKILL) {
|
|
61235
61435
|
const trimmed = lines.slice(lines.length - MAX_CHANGELOG_ENTRIES_PER_SKILL);
|
|
61236
|
-
await
|
|
61436
|
+
await writeFile3(filePath, `${trimmed.join(`
|
|
61237
61437
|
`)}
|
|
61238
61438
|
`, "utf-8");
|
|
61239
61439
|
}
|
|
@@ -61258,6 +61458,7 @@ __export(exports_skill_generator, {
|
|
|
61258
61458
|
parseDraftFrontmatter: () => parseDraftFrontmatter,
|
|
61259
61459
|
listSkills: () => listSkills,
|
|
61260
61460
|
isValidSlug: () => isValidSlug,
|
|
61461
|
+
isSkillMaturityEligible: () => isSkillMaturityEligible,
|
|
61261
61462
|
inspectSkill: () => inspectSkill,
|
|
61262
61463
|
generateSkills: () => generateSkills,
|
|
61263
61464
|
clusterEntries: () => clusterEntries,
|
|
@@ -61265,10 +61466,13 @@ __export(exports_skill_generator, {
|
|
|
61265
61466
|
activeRepoRelativePath: () => activeRepoRelativePath,
|
|
61266
61467
|
activePath: () => activePath,
|
|
61267
61468
|
activateProposal: () => activateProposal,
|
|
61268
|
-
_internals: () => _internals24
|
|
61469
|
+
_internals: () => _internals24,
|
|
61470
|
+
STRONG_SKILL_OUTCOME_COUNT: () => STRONG_SKILL_OUTCOME_COUNT,
|
|
61471
|
+
DEFAULT_SKILL_MIN_CONFIRMATIONS: () => DEFAULT_SKILL_MIN_CONFIRMATIONS,
|
|
61472
|
+
DEFAULT_SKILL_MIN_CONFIDENCE: () => DEFAULT_SKILL_MIN_CONFIDENCE
|
|
61269
61473
|
});
|
|
61270
61474
|
import { existsSync as existsSync17, unlinkSync as unlinkSync5 } from "node:fs";
|
|
61271
|
-
import { mkdir as mkdir7, readFile as readFile7, rename as rename3, writeFile as
|
|
61475
|
+
import { mkdir as mkdir7, readFile as readFile7, rename as rename3, writeFile as writeFile4 } from "node:fs/promises";
|
|
61272
61476
|
import * as path35 from "node:path";
|
|
61273
61477
|
function sanitizeSlug(input) {
|
|
61274
61478
|
const lc = input.toLowerCase().trim();
|
|
@@ -61293,18 +61497,35 @@ async function selectCandidateEntries(directory, opts) {
|
|
|
61293
61497
|
const hivePath = resolveHiveKnowledgePath();
|
|
61294
61498
|
const hive = existsSync17(hivePath) ? await readKnowledge(hivePath) : [];
|
|
61295
61499
|
const all = [...swarm, ...hive];
|
|
61296
|
-
|
|
61500
|
+
const counterRollups = await readKnowledgeCounterRollups(directory);
|
|
61501
|
+
const selected = [];
|
|
61502
|
+
for (const e of all) {
|
|
61297
61503
|
if (e.status === "archived")
|
|
61298
|
-
|
|
61299
|
-
if (e.confidence < opts.minConfidence)
|
|
61300
|
-
return false;
|
|
61301
|
-
const confirmations = (e.confirmed_by ?? []).length;
|
|
61302
|
-
if (confirmations < opts.minConfirmations)
|
|
61303
|
-
return false;
|
|
61504
|
+
continue;
|
|
61304
61505
|
if (e.generated_skill_slug)
|
|
61305
|
-
|
|
61306
|
-
|
|
61307
|
-
|
|
61506
|
+
continue;
|
|
61507
|
+
const outcomes = effectiveRetrievalOutcomes(e.retrieval_outcomes, counterRollups.get(e.id));
|
|
61508
|
+
if (!isSkillMaturityEligible(e, opts, outcomes))
|
|
61509
|
+
continue;
|
|
61510
|
+
selected.push({ ...e, retrieval_outcomes: outcomes });
|
|
61511
|
+
}
|
|
61512
|
+
return selected;
|
|
61513
|
+
}
|
|
61514
|
+
function hasStrongSkillOutcomeRecord(outcomes) {
|
|
61515
|
+
return (outcomes?.applied_explicit_count ?? 0) >= STRONG_SKILL_OUTCOME_COUNT || (outcomes?.succeeded_after_shown_count ?? 0) >= STRONG_SKILL_OUTCOME_COUNT;
|
|
61516
|
+
}
|
|
61517
|
+
function isHighPriorityDirective(entry) {
|
|
61518
|
+
return entry.directive_priority === "critical" || entry.directive_priority === "high";
|
|
61519
|
+
}
|
|
61520
|
+
function isSkillMaturityEligible(entry, opts, outcomes = entry.retrieval_outcomes) {
|
|
61521
|
+
const outcomeSignal = computeOutcomeSignal(outcomes);
|
|
61522
|
+
if (outcomeSignal < 0)
|
|
61523
|
+
return false;
|
|
61524
|
+
const strongOutcomes = hasStrongSkillOutcomeRecord(outcomes);
|
|
61525
|
+
if (entry.confidence < opts.minConfidence && !strongOutcomes)
|
|
61526
|
+
return false;
|
|
61527
|
+
const confirmations = (entry.confirmed_by ?? []).length;
|
|
61528
|
+
return confirmations >= opts.minConfirmations || strongOutcomes;
|
|
61308
61529
|
}
|
|
61309
61530
|
function jaccardSimilarity(setA, setB) {
|
|
61310
61531
|
const normA = setA.map((s) => s.toLowerCase());
|
|
@@ -61344,8 +61565,9 @@ function clusterEntries(entries) {
|
|
|
61344
61565
|
}
|
|
61345
61566
|
const result = [];
|
|
61346
61567
|
for (const c of clusters) {
|
|
61347
|
-
if (c.members.length < MIN_CLUSTER_SIZE)
|
|
61568
|
+
if (c.members.length < MIN_CLUSTER_SIZE && !isSkillSingletonEligible(c.members[0])) {
|
|
61348
61569
|
continue;
|
|
61570
|
+
}
|
|
61349
61571
|
const arr = c.members;
|
|
61350
61572
|
const triggers = uniqueStrings(arr.flatMap((e) => e.triggers ?? []));
|
|
61351
61573
|
const required3 = uniqueStrings(arr.flatMap((e) => e.required_actions ?? []));
|
|
@@ -61371,6 +61593,11 @@ function clusterEntries(entries) {
|
|
|
61371
61593
|
result.sort((a, b) => b.entries.length - a.entries.length || b.avgConfidence - a.avgConfidence || a.slug.localeCompare(b.slug));
|
|
61372
61594
|
return result;
|
|
61373
61595
|
}
|
|
61596
|
+
function isSkillSingletonEligible(entry) {
|
|
61597
|
+
if (!entry)
|
|
61598
|
+
return false;
|
|
61599
|
+
return isHighPriorityDirective(entry) || hasStrongSkillOutcomeRecord(entry.retrieval_outcomes);
|
|
61600
|
+
}
|
|
61374
61601
|
function uniqueStrings(arr) {
|
|
61375
61602
|
return [...new Set(arr.filter((s) => typeof s === "string" && s.length > 0))];
|
|
61376
61603
|
}
|
|
@@ -61471,12 +61698,12 @@ function escapeMarkdown(s) {
|
|
|
61471
61698
|
async function atomicWrite2(p, content) {
|
|
61472
61699
|
await mkdir7(path35.dirname(p), { recursive: true });
|
|
61473
61700
|
const tmp = `${p}.tmp-${process.pid}-${Date.now()}`;
|
|
61474
|
-
await
|
|
61701
|
+
await writeFile4(tmp, content, "utf-8");
|
|
61475
61702
|
await rename3(tmp, p);
|
|
61476
61703
|
}
|
|
61477
61704
|
async function generateSkills(req) {
|
|
61478
|
-
const minConfidence = req.minConfidence ??
|
|
61479
|
-
const minConfirmations = req.minConfirmations ??
|
|
61705
|
+
const minConfidence = req.minConfidence ?? DEFAULT_SKILL_MIN_CONFIDENCE;
|
|
61706
|
+
const minConfirmations = req.minConfirmations ?? DEFAULT_SKILL_MIN_CONFIRMATIONS;
|
|
61480
61707
|
const candidates = await selectCandidateEntries(req.directory, {
|
|
61481
61708
|
minConfidence,
|
|
61482
61709
|
minConfirmations
|
|
@@ -61871,7 +62098,7 @@ async function retireSkill(directory, slug, reason) {
|
|
|
61871
62098
|
reason: reason ?? "manual_retire"
|
|
61872
62099
|
});
|
|
61873
62100
|
await mkdir7(markerDir, { recursive: true });
|
|
61874
|
-
await
|
|
62101
|
+
await writeFile4(markerPath, markerContent, "utf-8");
|
|
61875
62102
|
return {
|
|
61876
62103
|
retired: true,
|
|
61877
62104
|
path: skillPath,
|
|
@@ -62034,8 +62261,9 @@ async function regenerateSkill(directory, slug) {
|
|
|
62034
62261
|
entryCount: matchedEntries.length
|
|
62035
62262
|
};
|
|
62036
62263
|
}
|
|
62037
|
-
var SLUG_PATTERN, MIN_CLUSTER_SIZE = 2, JACCARD_THRESHOLD = 0.5, AUTO_APPLY_BATCH_LIMIT = 5, _internals24;
|
|
62264
|
+
var SLUG_PATTERN, DEFAULT_SKILL_MIN_CONFIDENCE = 0.7, DEFAULT_SKILL_MIN_CONFIRMATIONS = 2, STRONG_SKILL_OUTCOME_COUNT = 3, MIN_CLUSTER_SIZE = 2, JACCARD_THRESHOLD = 0.5, AUTO_APPLY_BATCH_LIMIT = 5, _internals24;
|
|
62038
62265
|
var init_skill_generator = __esm(() => {
|
|
62266
|
+
init_knowledge_events();
|
|
62039
62267
|
init_knowledge_store();
|
|
62040
62268
|
init_knowledge_validator();
|
|
62041
62269
|
init_logger();
|
|
@@ -62045,6 +62273,7 @@ var init_skill_generator = __esm(() => {
|
|
|
62045
62273
|
sanitizeSlug,
|
|
62046
62274
|
isValidSlug,
|
|
62047
62275
|
selectCandidateEntries,
|
|
62276
|
+
isSkillMaturityEligible,
|
|
62048
62277
|
clusterEntries,
|
|
62049
62278
|
jaccardSimilarity,
|
|
62050
62279
|
renderSkillMarkdown,
|
|
@@ -62063,7 +62292,7 @@ var init_skill_generator = __esm(() => {
|
|
|
62063
62292
|
|
|
62064
62293
|
// src/services/skill-improver-quota.ts
|
|
62065
62294
|
import { existsSync as existsSync18 } from "node:fs";
|
|
62066
|
-
import { mkdir as mkdir8, readFile as readFile8, rename as rename4, writeFile as
|
|
62295
|
+
import { mkdir as mkdir8, readFile as readFile8, rename as rename4, writeFile as writeFile5 } from "node:fs/promises";
|
|
62067
62296
|
import * as path36 from "node:path";
|
|
62068
62297
|
async function acquireLock(dir) {
|
|
62069
62298
|
const acquire = import_proper_lockfile6.default.lock(dir, LOCK_RETRY_OPTS);
|
|
@@ -62081,8 +62310,9 @@ async function acquireLock(dir) {
|
|
|
62081
62310
|
clearTimeout(timer);
|
|
62082
62311
|
}
|
|
62083
62312
|
}
|
|
62084
|
-
function resolveQuotaPath(directory) {
|
|
62085
|
-
|
|
62313
|
+
function resolveQuotaPath(directory, scope = "skill-improver") {
|
|
62314
|
+
const fileName = scope === "knowledge-enrichment" ? "knowledge-enrichment-quota.json" : "skill-improver-quota.json";
|
|
62315
|
+
return path36.join(directory, ".swarm", fileName);
|
|
62086
62316
|
}
|
|
62087
62317
|
function todayKey(window2, now = new Date) {
|
|
62088
62318
|
if (window2 === "utc") {
|
|
@@ -62110,11 +62340,11 @@ async function readState(filePath) {
|
|
|
62110
62340
|
async function writeState(filePath, state) {
|
|
62111
62341
|
await mkdir8(path36.dirname(filePath), { recursive: true });
|
|
62112
62342
|
const tmp = `${filePath}.tmp-${process.pid}`;
|
|
62113
|
-
await
|
|
62343
|
+
await writeFile5(tmp, JSON.stringify(state, null, 2), "utf-8");
|
|
62114
62344
|
await rename4(tmp, filePath);
|
|
62115
62345
|
}
|
|
62116
62346
|
async function getQuotaState(directory, opts) {
|
|
62117
|
-
const filePath = resolveQuotaPath(directory);
|
|
62347
|
+
const filePath = resolveQuotaPath(directory, opts.scope);
|
|
62118
62348
|
const today = todayKey(opts.window, opts.now);
|
|
62119
62349
|
const existing = await readState(filePath);
|
|
62120
62350
|
if (!existing || existing.date !== today || existing.window !== opts.window) {
|
|
@@ -62130,7 +62360,7 @@ async function getQuotaState(directory, opts) {
|
|
|
62130
62360
|
return { ...existing, max_calls: opts.maxCalls };
|
|
62131
62361
|
}
|
|
62132
62362
|
async function reserveQuota(directory, opts) {
|
|
62133
|
-
const filePath = resolveQuotaPath(directory);
|
|
62363
|
+
const filePath = resolveQuotaPath(directory, opts.scope);
|
|
62134
62364
|
await mkdir8(path36.dirname(filePath), { recursive: true });
|
|
62135
62365
|
let release = null;
|
|
62136
62366
|
try {
|
|
@@ -62160,7 +62390,7 @@ async function reserveQuota(directory, opts) {
|
|
|
62160
62390
|
}
|
|
62161
62391
|
}
|
|
62162
62392
|
async function releaseQuota(directory, opts) {
|
|
62163
|
-
const filePath = resolveQuotaPath(directory);
|
|
62393
|
+
const filePath = resolveQuotaPath(directory, opts.scope);
|
|
62164
62394
|
await mkdir8(path36.dirname(filePath), { recursive: true });
|
|
62165
62395
|
let release = null;
|
|
62166
62396
|
try {
|
|
@@ -62196,7 +62426,7 @@ var init_skill_improver_quota = __esm(() => {
|
|
|
62196
62426
|
});
|
|
62197
62427
|
|
|
62198
62428
|
// src/services/skill-reviser.ts
|
|
62199
|
-
import { readFile as readFile9, rename as rename5, writeFile as
|
|
62429
|
+
import { readFile as readFile9, rename as rename5, writeFile as writeFile6 } from "node:fs/promises";
|
|
62200
62430
|
async function getSkillVersion(skillPath) {
|
|
62201
62431
|
try {
|
|
62202
62432
|
const content = await readFile9(skillPath, "utf-8");
|
|
@@ -62302,7 +62532,7 @@ async function reviseSkill(params) {
|
|
|
62302
62532
|
try {
|
|
62303
62533
|
const revised = _internals25.buildDeterministicRevision(params.currentContent, params.currentVersion, params.violationContexts);
|
|
62304
62534
|
const tmpPath = `${params.skillPath}.tmp-${process.pid}-${Date.now()}`;
|
|
62305
|
-
await
|
|
62535
|
+
await writeFile6(tmpPath, revised, "utf-8");
|
|
62306
62536
|
await rename5(tmpPath, params.skillPath);
|
|
62307
62537
|
const newVersion = params.currentVersion + 1;
|
|
62308
62538
|
const entry = {
|
|
@@ -62370,7 +62600,7 @@ async function reviseSkill(params) {
|
|
|
62370
62600
|
finalOutput = finalOutput.replace(/^version:\s*\d+\s*$/m, `version: ${expectedVersion}`);
|
|
62371
62601
|
}
|
|
62372
62602
|
const tmpPath = `${params.skillPath}.tmp-${process.pid}-${Date.now()}`;
|
|
62373
|
-
await
|
|
62603
|
+
await writeFile6(tmpPath, `${finalOutput}
|
|
62374
62604
|
`, "utf-8");
|
|
62375
62605
|
await rename5(tmpPath, params.skillPath);
|
|
62376
62606
|
const newVersion = expectedVersion;
|
|
@@ -62436,6 +62666,89 @@ function resolveLogPath(directory) {
|
|
|
62436
62666
|
function normalizeComplianceVerdict(verdict) {
|
|
62437
62667
|
return verdict === "violation" ? "violated" : verdict;
|
|
62438
62668
|
}
|
|
62669
|
+
function normalizeSkillUsageEntry(raw) {
|
|
62670
|
+
const entry = raw;
|
|
62671
|
+
return {
|
|
62672
|
+
...entry,
|
|
62673
|
+
complianceVerdict: normalizeComplianceVerdict(entry.complianceVerdict)
|
|
62674
|
+
};
|
|
62675
|
+
}
|
|
62676
|
+
function legacySkillUsageId(entry) {
|
|
62677
|
+
const stable = JSON.stringify({
|
|
62678
|
+
skillPath: entry.skillPath,
|
|
62679
|
+
agentName: entry.agentName,
|
|
62680
|
+
taskID: entry.taskID,
|
|
62681
|
+
timestamp: entry.timestamp,
|
|
62682
|
+
complianceVerdict: entry.complianceVerdict,
|
|
62683
|
+
sessionID: entry.sessionID,
|
|
62684
|
+
skillVersion: entry.skillVersion
|
|
62685
|
+
});
|
|
62686
|
+
return `legacy:${crypto4.createHash("sha256").update(stable).digest("hex")}`;
|
|
62687
|
+
}
|
|
62688
|
+
function parseSkillUsageEntry(raw) {
|
|
62689
|
+
const entry = raw;
|
|
62690
|
+
if (entry.type === "feedback_applied")
|
|
62691
|
+
return null;
|
|
62692
|
+
if (typeof entry.skillPath !== "string" || typeof entry.agentName !== "string" || typeof entry.taskID !== "string" || typeof entry.timestamp !== "string" || typeof entry.complianceVerdict !== "string" || typeof entry.sessionID !== "string") {
|
|
62693
|
+
return null;
|
|
62694
|
+
}
|
|
62695
|
+
return normalizeSkillUsageEntry({
|
|
62696
|
+
...entry,
|
|
62697
|
+
id: typeof entry.id === "string" ? entry.id : legacySkillUsageId(entry)
|
|
62698
|
+
});
|
|
62699
|
+
}
|
|
62700
|
+
function parseFeedbackMarker(raw) {
|
|
62701
|
+
const marker = raw;
|
|
62702
|
+
if (marker.type !== "feedback_applied")
|
|
62703
|
+
return null;
|
|
62704
|
+
if (typeof marker.timestamp !== "string")
|
|
62705
|
+
return null;
|
|
62706
|
+
if (!Array.isArray(marker.processedEntryIds))
|
|
62707
|
+
return null;
|
|
62708
|
+
const processedEntryIds = marker.processedEntryIds.filter((id) => typeof id === "string" && id.length > 0);
|
|
62709
|
+
return {
|
|
62710
|
+
type: "feedback_applied",
|
|
62711
|
+
timestamp: marker.timestamp,
|
|
62712
|
+
processedEntryIds
|
|
62713
|
+
};
|
|
62714
|
+
}
|
|
62715
|
+
function readFeedbackAppliedEntryIds(directory) {
|
|
62716
|
+
const resolved = resolveLogPath(directory);
|
|
62717
|
+
const processed = new Set;
|
|
62718
|
+
if (!_internals26.existsSync(resolved))
|
|
62719
|
+
return processed;
|
|
62720
|
+
const raw = _internals26.readFileSync(resolved, "utf-8");
|
|
62721
|
+
for (const line of raw.split(`
|
|
62722
|
+
`)) {
|
|
62723
|
+
const trimmed = line.trim();
|
|
62724
|
+
if (!trimmed)
|
|
62725
|
+
continue;
|
|
62726
|
+
try {
|
|
62727
|
+
const marker = parseFeedbackMarker(JSON.parse(trimmed));
|
|
62728
|
+
if (!marker)
|
|
62729
|
+
continue;
|
|
62730
|
+
for (const id of marker.processedEntryIds)
|
|
62731
|
+
processed.add(id);
|
|
62732
|
+
} catch {}
|
|
62733
|
+
}
|
|
62734
|
+
return processed;
|
|
62735
|
+
}
|
|
62736
|
+
function appendFeedbackAppliedMarker(directory, processedEntryIds) {
|
|
62737
|
+
if (processedEntryIds.length === 0)
|
|
62738
|
+
return;
|
|
62739
|
+
const resolved = resolveLogPath(directory);
|
|
62740
|
+
const dir = path37.dirname(resolved);
|
|
62741
|
+
if (!_internals26.existsSync(dir)) {
|
|
62742
|
+
_internals26.mkdirSync(dir, { recursive: true });
|
|
62743
|
+
}
|
|
62744
|
+
const marker = {
|
|
62745
|
+
type: "feedback_applied",
|
|
62746
|
+
timestamp: new Date().toISOString(),
|
|
62747
|
+
processedEntryIds: [...new Set(processedEntryIds)]
|
|
62748
|
+
};
|
|
62749
|
+
_internals26.appendFileSync(resolved, `${JSON.stringify(marker)}
|
|
62750
|
+
`, "utf-8");
|
|
62751
|
+
}
|
|
62439
62752
|
function appendSkillUsageEntry(directory, entry) {
|
|
62440
62753
|
const {
|
|
62441
62754
|
skillPath,
|
|
@@ -62479,7 +62792,7 @@ function appendSkillUsageEntry(directory, entry) {
|
|
|
62479
62792
|
agentName,
|
|
62480
62793
|
taskID,
|
|
62481
62794
|
timestamp,
|
|
62482
|
-
complianceVerdict,
|
|
62795
|
+
complianceVerdict: normalizeComplianceVerdict(complianceVerdict),
|
|
62483
62796
|
sessionID,
|
|
62484
62797
|
...reviewerNotes !== undefined && { reviewerNotes },
|
|
62485
62798
|
...skillVersion !== undefined && { skillVersion }
|
|
@@ -62487,8 +62800,8 @@ function appendSkillUsageEntry(directory, entry) {
|
|
|
62487
62800
|
_internals26.appendFileSync(resolved, `${JSON.stringify(fullEntry)}
|
|
62488
62801
|
`, "utf-8");
|
|
62489
62802
|
try {
|
|
62490
|
-
const
|
|
62491
|
-
if (
|
|
62803
|
+
const stat4 = _internals26.statSync(resolved);
|
|
62804
|
+
if (stat4.size > SKILL_USAGE_LOG_ROTATE_BYTES) {
|
|
62492
62805
|
_internals26.pruneSkillUsageLog(directory, SKILL_USAGE_LOG_MAX_ENTRIES_PER_SKILL);
|
|
62493
62806
|
}
|
|
62494
62807
|
} catch {}
|
|
@@ -62506,9 +62819,9 @@ function readSkillUsageEntries(directory, options) {
|
|
|
62506
62819
|
if (!trimmed)
|
|
62507
62820
|
continue;
|
|
62508
62821
|
try {
|
|
62509
|
-
const entry = JSON.parse(trimmed);
|
|
62510
|
-
|
|
62511
|
-
|
|
62822
|
+
const entry = parseSkillUsageEntry(JSON.parse(trimmed));
|
|
62823
|
+
if (entry)
|
|
62824
|
+
entries.push(entry);
|
|
62512
62825
|
} catch {}
|
|
62513
62826
|
}
|
|
62514
62827
|
if (!options)
|
|
@@ -62542,11 +62855,11 @@ function readSkillUsageEntriesTail(directory, filters, maxBytes = TAIL_BYTES_DEF
|
|
|
62542
62855
|
try {
|
|
62543
62856
|
const normalizedMaxBytes = Number.isFinite(maxBytes) ? maxBytes : TAIL_BYTES_DEFAULT;
|
|
62544
62857
|
const boundedMaxBytes = Math.min(Math.max(1, normalizedMaxBytes), MAX_TAIL_BYTES);
|
|
62545
|
-
const
|
|
62546
|
-
const start2 = Math.max(0,
|
|
62858
|
+
const stat4 = _internals26.statSync(logPath);
|
|
62859
|
+
const start2 = Math.max(0, stat4.size - boundedMaxBytes);
|
|
62547
62860
|
const fd = _internals26.openSync(logPath, "r");
|
|
62548
62861
|
try {
|
|
62549
|
-
const readLen =
|
|
62862
|
+
const readLen = stat4.size - start2;
|
|
62550
62863
|
if (readLen === 0)
|
|
62551
62864
|
return [];
|
|
62552
62865
|
const buf = Buffer.alloc(readLen);
|
|
@@ -62566,8 +62879,9 @@ function readSkillUsageEntriesTail(directory, filters, maxBytes = TAIL_BYTES_DEF
|
|
|
62566
62879
|
if (!line.trim())
|
|
62567
62880
|
continue;
|
|
62568
62881
|
try {
|
|
62569
|
-
const entry = JSON.parse(line);
|
|
62570
|
-
|
|
62882
|
+
const entry = parseSkillUsageEntry(JSON.parse(line));
|
|
62883
|
+
if (!entry)
|
|
62884
|
+
continue;
|
|
62571
62885
|
if (filters.sessionID !== undefined && entry.sessionID !== filters.sessionID) {
|
|
62572
62886
|
continue;
|
|
62573
62887
|
}
|
|
@@ -62602,8 +62916,9 @@ function computeComplianceByVersion(entries, skillPath) {
|
|
|
62602
62916
|
stats.total += 1;
|
|
62603
62917
|
if (e.complianceVerdict === "compliant")
|
|
62604
62918
|
stats.compliant += 1;
|
|
62605
|
-
if (e.complianceVerdict === "violated")
|
|
62919
|
+
if (normalizeComplianceVerdict(e.complianceVerdict) === "violated") {
|
|
62606
62920
|
stats.violation += 1;
|
|
62921
|
+
}
|
|
62607
62922
|
}
|
|
62608
62923
|
for (const stats of map3.values()) {
|
|
62609
62924
|
stats.rate = stats.total === 0 ? 0 : stats.compliant / stats.total;
|
|
@@ -62714,6 +63029,7 @@ async function applySkillUsageFeedback(directory, options) {
|
|
|
62714
63029
|
let bumps = 0;
|
|
62715
63030
|
try {
|
|
62716
63031
|
const allEntries = readSkillUsageEntries(directory);
|
|
63032
|
+
const alreadyProcessed = readFeedbackAppliedEntryIds(directory);
|
|
62717
63033
|
const actionable = allEntries.filter((e) => {
|
|
62718
63034
|
if (e.complianceVerdict !== "compliant" && e.complianceVerdict !== "violated") {
|
|
62719
63035
|
return false;
|
|
@@ -62721,6 +63037,9 @@ async function applySkillUsageFeedback(directory, options) {
|
|
|
62721
63037
|
if (options?.sinceTimestamp && e.timestamp <= options.sinceTimestamp) {
|
|
62722
63038
|
return false;
|
|
62723
63039
|
}
|
|
63040
|
+
if (alreadyProcessed.has(e.id)) {
|
|
63041
|
+
return false;
|
|
63042
|
+
}
|
|
62724
63043
|
return true;
|
|
62725
63044
|
});
|
|
62726
63045
|
if (actionable.length === 0) {
|
|
@@ -62735,6 +63054,7 @@ async function applySkillUsageFeedback(directory, options) {
|
|
|
62735
63054
|
groups.set(entry.skillPath, [entry]);
|
|
62736
63055
|
}
|
|
62737
63056
|
const allDeltas = [];
|
|
63057
|
+
const processedEntryIds = [];
|
|
62738
63058
|
for (const [skillPath, entries] of Array.from(groups)) {
|
|
62739
63059
|
let compliantCount = 0;
|
|
62740
63060
|
let violationCount = 0;
|
|
@@ -62753,6 +63073,7 @@ async function applySkillUsageFeedback(directory, options) {
|
|
|
62753
63073
|
for (const id of sourceIds) {
|
|
62754
63074
|
allDeltas.push({ id, delta });
|
|
62755
63075
|
}
|
|
63076
|
+
processedEntryIds.push(...entries.map((entry) => entry.id));
|
|
62756
63077
|
processed++;
|
|
62757
63078
|
bumps += sourceIds.length;
|
|
62758
63079
|
}
|
|
@@ -62766,6 +63087,7 @@ async function applySkillUsageFeedback(directory, options) {
|
|
|
62766
63087
|
}));
|
|
62767
63088
|
if (clampedDeltas.length > 0) {
|
|
62768
63089
|
await bumpKnowledgeConfidenceBatch(directory, clampedDeltas);
|
|
63090
|
+
appendFeedbackAppliedMarker(directory, processedEntryIds);
|
|
62769
63091
|
}
|
|
62770
63092
|
} catch (err2) {
|
|
62771
63093
|
console.warn("[skill-usage-log] applySkillUsageFeedback failed (fail-open):", err2 instanceof Error ? err2.message : String(err2));
|
|
@@ -62792,7 +63114,10 @@ var init_skill_usage_log = __esm(() => {
|
|
|
62792
63114
|
resolveSourceKnowledgeIds,
|
|
62793
63115
|
applySkillUsageFeedback,
|
|
62794
63116
|
parseGeneratedFromKnowledge,
|
|
62795
|
-
computeComplianceByVersion
|
|
63117
|
+
computeComplianceByVersion,
|
|
63118
|
+
normalizeComplianceVerdict,
|
|
63119
|
+
readFeedbackAppliedEntryIds,
|
|
63120
|
+
appendFeedbackAppliedMarker
|
|
62796
63121
|
};
|
|
62797
63122
|
TAIL_BYTES_DEFAULT = 64 * 1024;
|
|
62798
63123
|
MAX_TAIL_BYTES = TAIL_BYTES_DEFAULT;
|
|
@@ -62825,7 +63150,7 @@ async function autoRetireSkills(directory, curatorKnowledgePath, excludeSlugs) {
|
|
|
62825
63150
|
return true;
|
|
62826
63151
|
return false;
|
|
62827
63152
|
});
|
|
62828
|
-
const violations = skillUsage.filter((e) => e.complianceVerdict === "violated").length;
|
|
63153
|
+
const violations = skillUsage.filter((e) => normalizeComplianceVerdict(e.complianceVerdict) === "violated").length;
|
|
62829
63154
|
const violationRate = skillUsage.length > 0 ? violations / skillUsage.length : 0;
|
|
62830
63155
|
let allArchived = false;
|
|
62831
63156
|
try {
|
|
@@ -63490,7 +63815,7 @@ ${phaseDigest.summary}`,
|
|
|
63490
63815
|
});
|
|
63491
63816
|
if (skillUsage.length === 0)
|
|
63492
63817
|
continue;
|
|
63493
|
-
const violations = skillUsage.filter((e) => e.complianceVerdict === "violated").length;
|
|
63818
|
+
const violations = skillUsage.filter((e) => normalizeComplianceVerdict(e.complianceVerdict) === "violated").length;
|
|
63494
63819
|
const violationRate = violations / skillUsage.length;
|
|
63495
63820
|
if (violationRate > REVISION_VIOLATION_THRESHOLD && violationRate <= 0.3) {
|
|
63496
63821
|
const content = await _internals27.readFileAsync(active.path, "utf-8");
|
|
@@ -63498,7 +63823,7 @@ ${phaseDigest.summary}`,
|
|
|
63498
63823
|
if (fm && fm.skillOrigin === "promoted_external")
|
|
63499
63824
|
continue;
|
|
63500
63825
|
const currentVersion = fm?.version ?? 1;
|
|
63501
|
-
const violationContexts = skillUsage.filter((e) => e.complianceVerdict === "violated").slice(-10).map((e) => ({
|
|
63826
|
+
const violationContexts = skillUsage.filter((e) => normalizeComplianceVerdict(e.complianceVerdict) === "violated").slice(-10).map((e) => ({
|
|
63502
63827
|
taskId: e.taskID,
|
|
63503
63828
|
agent: e.agentName,
|
|
63504
63829
|
verdict: e.complianceVerdict,
|
|
@@ -63792,6 +64117,9 @@ function isAlreadyInHive(entry, hiveEntries, threshold) {
|
|
|
63792
64117
|
return findNearDuplicate(entry.lesson, hiveEntries, threshold) !== undefined;
|
|
63793
64118
|
}
|
|
63794
64119
|
function isHiveEligible(entry, autoPromoteDays) {
|
|
64120
|
+
if (!isActiveForHivePromotion(entry)) {
|
|
64121
|
+
return false;
|
|
64122
|
+
}
|
|
63795
64123
|
const phaseNumbers = new Set;
|
|
63796
64124
|
for (const record3 of entry.confirmed_by ?? []) {
|
|
63797
64125
|
if (record3 && typeof record3.phase_number === "number") {
|
|
@@ -63812,6 +64140,9 @@ function isHiveEligible(entry, autoPromoteDays) {
|
|
|
63812
64140
|
}
|
|
63813
64141
|
return false;
|
|
63814
64142
|
}
|
|
64143
|
+
function isActiveForHivePromotion(entry) {
|
|
64144
|
+
return !["archived", "quarantined", "quarantined_unactionable"].includes(entry.status);
|
|
64145
|
+
}
|
|
63815
64146
|
function countDistinctProjects(confirmedBy) {
|
|
63816
64147
|
const projectNames = new Set;
|
|
63817
64148
|
for (const record3 of confirmedBy) {
|
|
@@ -63894,7 +64225,7 @@ async function checkHivePromotions(swarmEntries, config3) {
|
|
|
63894
64225
|
}
|
|
63895
64226
|
let hiveModified = false;
|
|
63896
64227
|
for (const hiveEntry of hiveEntries) {
|
|
63897
|
-
const nearDuplicate = findNearDuplicate(hiveEntry.lesson, swarmEntries, config3.dedup_threshold);
|
|
64228
|
+
const nearDuplicate = findNearDuplicate(hiveEntry.lesson, swarmEntries.filter(isActiveForHivePromotion), config3.dedup_threshold);
|
|
63898
64229
|
if (!nearDuplicate) {
|
|
63899
64230
|
continue;
|
|
63900
64231
|
}
|
|
@@ -64052,9 +64383,9 @@ import {
|
|
|
64052
64383
|
mkdir as mkdir9,
|
|
64053
64384
|
readFile as readFile10,
|
|
64054
64385
|
rename as rename6,
|
|
64055
|
-
stat as
|
|
64386
|
+
stat as stat4,
|
|
64056
64387
|
unlink as unlink2,
|
|
64057
|
-
writeFile as
|
|
64388
|
+
writeFile as writeFile7
|
|
64058
64389
|
} from "node:fs/promises";
|
|
64059
64390
|
import * as path40 from "node:path";
|
|
64060
64391
|
function emptySynonymMap() {
|
|
@@ -64241,7 +64572,7 @@ async function readSynonymMap(directory, maxPairs = DEFAULT_MAX_PAIRS) {
|
|
|
64241
64572
|
}
|
|
64242
64573
|
try {
|
|
64243
64574
|
const ceiling = Math.max(MIN_READ_CEILING_BYTES, Math.floor(maxPairs) * APPROX_BYTES_PER_PAIR);
|
|
64244
|
-
const st = await
|
|
64575
|
+
const st = await stat4(filePath);
|
|
64245
64576
|
if (st.size > ceiling)
|
|
64246
64577
|
return emptySynonymMap();
|
|
64247
64578
|
const raw = await readFile10(filePath, "utf-8");
|
|
@@ -64254,7 +64585,7 @@ async function writeSynonymMapAtomic(filePath, map3) {
|
|
|
64254
64585
|
await mkdir9(path40.dirname(filePath), { recursive: true });
|
|
64255
64586
|
const tmp = `${filePath}.tmp.${Date.now()}.${Math.floor(Math.random() * 1e9)}`;
|
|
64256
64587
|
try {
|
|
64257
|
-
await
|
|
64588
|
+
await writeFile7(tmp, JSON.stringify(map3, null, 2), "utf-8");
|
|
64258
64589
|
await rename6(tmp, filePath);
|
|
64259
64590
|
} finally {
|
|
64260
64591
|
try {
|
|
@@ -64463,12 +64794,12 @@ function extractKeywords(text) {
|
|
|
64463
64794
|
const words = text.toLowerCase().split(/[^a-z0-9]+/).filter((w) => w.length >= MIN_KEYWORD_LENGTH);
|
|
64464
64795
|
return new Set(words);
|
|
64465
64796
|
}
|
|
64466
|
-
function computeContextMatchScore(taskDescription, skillPath) {
|
|
64797
|
+
function computeContextMatchScore(taskDescription, skillPath, metadata2) {
|
|
64467
64798
|
const taskKeywords = extractKeywords(taskDescription);
|
|
64468
64799
|
if (taskKeywords.size === 0)
|
|
64469
64800
|
return 0;
|
|
64470
64801
|
const skillName = extractSkillName(skillPath);
|
|
64471
|
-
const skillText = `${skillPath} ${skillName}`;
|
|
64802
|
+
const skillText = `${skillPath} ${skillName} ${metadata2?.name ?? ""} ${metadata2?.description ?? ""}`;
|
|
64472
64803
|
const skillKeywords = extractKeywords(skillText);
|
|
64473
64804
|
let matchCount = 0;
|
|
64474
64805
|
for (const kw of taskKeywords) {
|
|
@@ -64479,7 +64810,7 @@ function computeContextMatchScore(taskDescription, skillPath) {
|
|
|
64479
64810
|
return matchCount / taskKeywords.size;
|
|
64480
64811
|
}
|
|
64481
64812
|
function computeSkillRelevanceScore(skillPath, taskDescription, usageHistory, metadata2) {
|
|
64482
|
-
const contextScore = computeContextMatchScore(taskDescription, skillPath) * CONTEXT_WEIGHT;
|
|
64813
|
+
const contextScore = computeContextMatchScore(taskDescription, skillPath, metadata2) * CONTEXT_WEIGHT;
|
|
64483
64814
|
if (usageHistory.length === 0)
|
|
64484
64815
|
return Math.min(1, contextScore);
|
|
64485
64816
|
const usageCount = usageHistory.length;
|
|
@@ -64554,8 +64885,8 @@ function formatSkillIndexWithContext(skills, directory) {
|
|
|
64554
64885
|
const usageLogPath = path41.join(directory, ".swarm", "skill-usage.jsonl");
|
|
64555
64886
|
let hasHistory = false;
|
|
64556
64887
|
try {
|
|
64557
|
-
const
|
|
64558
|
-
hasHistory =
|
|
64888
|
+
const stat5 = fs21.statSync(usageLogPath);
|
|
64889
|
+
hasHistory = stat5.size > 0;
|
|
64559
64890
|
} catch {}
|
|
64560
64891
|
if (!hasHistory) {
|
|
64561
64892
|
return skills.map((sp) => {
|
|
@@ -65076,24 +65407,32 @@ async function skillPropagationTransformScan(directory, output, sessionID) {
|
|
|
65076
65407
|
if (!text)
|
|
65077
65408
|
continue;
|
|
65078
65409
|
const skillPaths = [];
|
|
65410
|
+
let explicitReviewerTaskID;
|
|
65079
65411
|
for (const line of text.split(`
|
|
65080
65412
|
`)) {
|
|
65081
|
-
const
|
|
65413
|
+
const trimmed = line.trim();
|
|
65414
|
+
const taskMatch = trimmed.match(REVIEWER_TASK_PATTERN);
|
|
65415
|
+
if (taskMatch) {
|
|
65416
|
+
explicitReviewerTaskID = taskMatch[1];
|
|
65417
|
+
}
|
|
65418
|
+
const coderMatch = trimmed.match(CODER_SKILLS_PATTERN);
|
|
65082
65419
|
if (coderMatch) {
|
|
65083
65420
|
const parsed = _internals29.parseSkillPaths(coderMatch[1]);
|
|
65084
65421
|
skillPaths.push(...parsed);
|
|
65085
65422
|
}
|
|
65086
65423
|
}
|
|
65087
|
-
let resolvedTaskID = "unknown";
|
|
65424
|
+
let resolvedTaskID = explicitReviewerTaskID ?? "unknown";
|
|
65088
65425
|
if (existingEntries.length > 0) {
|
|
65089
|
-
|
|
65090
|
-
|
|
65091
|
-
|
|
65092
|
-
|
|
65093
|
-
|
|
65094
|
-
|
|
65095
|
-
|
|
65096
|
-
|
|
65426
|
+
if (!explicitReviewerTaskID) {
|
|
65427
|
+
const latestDelegation = [...existingEntries].reverse().find((e) => e.agentName !== "reviewer" && e.skillPath !== "__overall__");
|
|
65428
|
+
if (latestDelegation) {
|
|
65429
|
+
resolvedTaskID = latestDelegation.taskID;
|
|
65430
|
+
}
|
|
65431
|
+
}
|
|
65432
|
+
if (skillPaths.length === 0 && resolvedTaskID !== "unknown") {
|
|
65433
|
+
const delegatedPaths = existingEntries.filter((e) => e.agentName !== "reviewer" && e.skillPath !== "__overall__" && e.taskID === resolvedTaskID).map((e) => e.skillPath);
|
|
65434
|
+
if (delegatedPaths.length > 0) {
|
|
65435
|
+
skillPaths.push(...new Set(delegatedPaths));
|
|
65097
65436
|
}
|
|
65098
65437
|
}
|
|
65099
65438
|
}
|
|
@@ -65183,7 +65522,7 @@ async function skillPropagationTransformScan(directory, output, sessionID) {
|
|
|
65183
65522
|
break;
|
|
65184
65523
|
}
|
|
65185
65524
|
}
|
|
65186
|
-
var SKILL_CAPABLE_AGENTS, SKILL_SEARCH_ROOTS, MAX_SCORING_SESSION_ENTRIES = 500, _internals29, COMPLIANCE_PATTERN, CODER_SKILLS_PATTERN;
|
|
65525
|
+
var SKILL_CAPABLE_AGENTS, SKILL_SEARCH_ROOTS, MAX_SCORING_SESSION_ENTRIES = 500, _internals29, COMPLIANCE_PATTERN, CODER_SKILLS_PATTERN, REVIEWER_TASK_PATTERN;
|
|
65187
65526
|
var init_skill_propagation_gate = __esm(() => {
|
|
65188
65527
|
init_schema();
|
|
65189
65528
|
init_logger();
|
|
@@ -65229,6 +65568,7 @@ var init_skill_propagation_gate = __esm(() => {
|
|
|
65229
65568
|
};
|
|
65230
65569
|
COMPLIANCE_PATTERN = /SKILL_COMPLIANCE\s*:\s*(COMPLIANT|PARTIAL|VIOLATED)(?:\s*(?:—|-)\s*(.*))?\s*$/i;
|
|
65231
65570
|
CODER_SKILLS_PATTERN = /SKILLS_USED_BY_CODER\s*:\s*(.+)/i;
|
|
65571
|
+
REVIEWER_TASK_PATTERN = /TASK\s*:\s*(\S+)/i;
|
|
65232
65572
|
_internals29.skillPropagationGateBefore = skillPropagationGateBefore;
|
|
65233
65573
|
_internals29.skillPropagationTransformScan = skillPropagationTransformScan;
|
|
65234
65574
|
_internals29.writeWarnEvent = writeWarnEvent;
|
|
@@ -65243,7 +65583,7 @@ var init_skill_propagation_gate = __esm(() => {
|
|
|
65243
65583
|
|
|
65244
65584
|
// src/hooks/micro-reflector.ts
|
|
65245
65585
|
import { existsSync as existsSync22 } from "node:fs";
|
|
65246
|
-
import { readFile as readFile11, writeFile as
|
|
65586
|
+
import { readFile as readFile11, writeFile as writeFile8 } from "node:fs/promises";
|
|
65247
65587
|
import * as path43 from "node:path";
|
|
65248
65588
|
function resolveInsightCandidatesPath(directory) {
|
|
65249
65589
|
return validateSwarmPath(directory, "insight-candidates.jsonl");
|
|
@@ -65312,7 +65652,7 @@ async function appendInsightCandidates(directory, candidates) {
|
|
|
65312
65652
|
const body2 = data.length === 0 ? "" : `${data.map((c) => JSON.stringify(c)).join(`
|
|
65313
65653
|
`)}
|
|
65314
65654
|
`;
|
|
65315
|
-
await
|
|
65655
|
+
await writeFile8(p, body2, "utf-8");
|
|
65316
65656
|
}, (all) => {
|
|
65317
65657
|
const merged = [...all, ...candidates];
|
|
65318
65658
|
const capped = merged.length > INSIGHT_CANDIDATES_MAX_ENTRIES ? merged.slice(-INSIGHT_CANDIDATES_MAX_ENTRIES) : merged;
|
|
@@ -65433,7 +65773,8 @@ async function runMicroReflection(params) {
|
|
|
65433
65773
|
const reservation = await reserveQuota(params.directory, {
|
|
65434
65774
|
nCalls: 1,
|
|
65435
65775
|
maxCalls: quota.maxCalls,
|
|
65436
|
-
window: quota.window
|
|
65776
|
+
window: quota.window,
|
|
65777
|
+
scope: "knowledge-enrichment"
|
|
65437
65778
|
});
|
|
65438
65779
|
if (!reservation.allowed)
|
|
65439
65780
|
return result;
|
|
@@ -65520,7 +65861,7 @@ var init_micro_reflector = __esm(() => {
|
|
|
65520
65861
|
|
|
65521
65862
|
// src/hooks/knowledge-curator.ts
|
|
65522
65863
|
import { existsSync as existsSync23 } from "node:fs";
|
|
65523
|
-
import { appendFile as appendFile7, mkdir as mkdir10, readFile as readFile12, writeFile as
|
|
65864
|
+
import { appendFile as appendFile7, mkdir as mkdir10, readFile as readFile12, writeFile as writeFile9 } from "node:fs/promises";
|
|
65524
65865
|
import * as path44 from "node:path";
|
|
65525
65866
|
function pruneSeenRetroSections() {
|
|
65526
65867
|
const cutoff = Date.now() - 86400000;
|
|
@@ -65761,7 +66102,8 @@ async function enrichLessonToV3(params) {
|
|
|
65761
66102
|
const reservation = await reserveQuota(params.directory, {
|
|
65762
66103
|
nCalls: 1,
|
|
65763
66104
|
maxCalls: quota.maxCalls,
|
|
65764
|
-
window: quota.window
|
|
66105
|
+
window: quota.window,
|
|
66106
|
+
scope: "knowledge-enrichment"
|
|
65765
66107
|
});
|
|
65766
66108
|
if (!reservation.allowed)
|
|
65767
66109
|
return null;
|
|
@@ -65815,7 +66157,7 @@ async function consumeInsightCandidates(directory, batchLimit = MESO_INSIGHT_BAT
|
|
|
65815
66157
|
const body2 = data.length === 0 ? "" : `${data.map((c) => JSON.stringify(c)).join(`
|
|
65816
66158
|
`)}
|
|
65817
66159
|
`;
|
|
65818
|
-
await
|
|
66160
|
+
await writeFile9(p, body2, "utf-8");
|
|
65819
66161
|
}, (all) => {
|
|
65820
66162
|
if (all.length === 0)
|
|
65821
66163
|
return null;
|
|
@@ -66106,7 +66448,7 @@ async function runAutoPromotion(directory, config3) {
|
|
|
66106
66448
|
await rewriteKnowledge(knowledgePath, entries);
|
|
66107
66449
|
}
|
|
66108
66450
|
}
|
|
66109
|
-
function createKnowledgeCuratorHook(directory, config3) {
|
|
66451
|
+
function createKnowledgeCuratorHook(directory, config3, options = {}) {
|
|
66110
66452
|
const handler = async (input, _output) => {
|
|
66111
66453
|
pruneSeenRetroSections();
|
|
66112
66454
|
if (!config3.enabled)
|
|
@@ -66151,7 +66493,10 @@ function createKnowledgeCuratorHook(directory, config3) {
|
|
|
66151
66493
|
recordSeenRetroSection(evidenceKey, evidenceHash, Date.now());
|
|
66152
66494
|
const projectName2 = evidenceData.project_name ?? "unknown";
|
|
66153
66495
|
const phaseNumber2 = typeof evidenceData.phase_number === "number" ? evidenceData.phase_number : 1;
|
|
66154
|
-
await _internals30.curateAndStoreSwarm(lessons, projectName2, { phase_number: phaseNumber2 }, directory, config3
|
|
66496
|
+
await _internals30.curateAndStoreSwarm(lessons, projectName2, { phase_number: phaseNumber2 }, directory, config3, {
|
|
66497
|
+
llmDelegate: options.llmDelegateFactory?.(sessionID),
|
|
66498
|
+
enrichmentQuota: options.enrichmentQuota
|
|
66499
|
+
});
|
|
66155
66500
|
return;
|
|
66156
66501
|
}
|
|
66157
66502
|
const planContent = await readSwarmFileAsync(directory, "plan.md");
|
|
@@ -66173,7 +66518,10 @@ function createKnowledgeCuratorHook(directory, config3) {
|
|
|
66173
66518
|
const projectName = projectNameMatch ? projectNameMatch[1].trim() : "unknown";
|
|
66174
66519
|
const phaseMatch = /^Phase:\s*(\d+)/m.exec(planContent);
|
|
66175
66520
|
const phaseNumber = phaseMatch ? parseInt(phaseMatch[1], 10) : 1;
|
|
66176
|
-
await _internals30.curateAndStoreSwarm(normalLessons, projectName, { phase_number: phaseNumber }, directory, config3
|
|
66521
|
+
await _internals30.curateAndStoreSwarm(normalLessons, projectName, { phase_number: phaseNumber }, directory, config3, {
|
|
66522
|
+
llmDelegate: options.llmDelegateFactory?.(sessionID),
|
|
66523
|
+
enrichmentQuota: options.enrichmentQuota
|
|
66524
|
+
});
|
|
66177
66525
|
};
|
|
66178
66526
|
return safeHook(handler);
|
|
66179
66527
|
}
|
|
@@ -66332,7 +66680,7 @@ var init_skill_improver_llm_factory = __esm(() => {
|
|
|
66332
66680
|
});
|
|
66333
66681
|
|
|
66334
66682
|
// src/services/trajectory-cluster.ts
|
|
66335
|
-
import { mkdir as mkdir11, writeFile as
|
|
66683
|
+
import { mkdir as mkdir11, writeFile as writeFile10 } from "node:fs/promises";
|
|
66336
66684
|
import * as path45 from "node:path";
|
|
66337
66685
|
function failureKind(e) {
|
|
66338
66686
|
const tool3 = (e.tool ?? "").toLowerCase();
|
|
@@ -66467,7 +66815,7 @@ async function writeMotifProposals(directory, opts = {}) {
|
|
|
66467
66815
|
for (const motif of motifs.slice(0, max)) {
|
|
66468
66816
|
const slug = `motif-${slugify2(motif.signature)}`;
|
|
66469
66817
|
const filePath = path45.join(proposalsDir, `${slug}.md`);
|
|
66470
|
-
await
|
|
66818
|
+
await writeFile10(filePath, buildMotifProposal(motif), "utf-8");
|
|
66471
66819
|
result.proposalsWritten.push(filePath);
|
|
66472
66820
|
}
|
|
66473
66821
|
return result;
|
|
@@ -66611,7 +66959,7 @@ async function writeSuccessMotifProposals(directory, opts = {}) {
|
|
|
66611
66959
|
for (const motif of motifs.slice(0, max)) {
|
|
66612
66960
|
const slug = workflowSlug(motif.signature);
|
|
66613
66961
|
const filePath = path45.join(proposalsDir, `${slug}.md`);
|
|
66614
|
-
await
|
|
66962
|
+
await writeFile10(filePath, buildWorkflowProposal(motif), "utf-8");
|
|
66615
66963
|
result.proposalsWritten.push(filePath);
|
|
66616
66964
|
}
|
|
66617
66965
|
return result;
|
|
@@ -66742,7 +67090,7 @@ var init_unactionable_hardening = __esm(() => {
|
|
|
66742
67090
|
|
|
66743
67091
|
// src/services/skill-improver.ts
|
|
66744
67092
|
import { existsSync as existsSync25 } from "node:fs";
|
|
66745
|
-
import { mkdir as mkdir12, readFile as readFile13, rename as rename7, writeFile as
|
|
67093
|
+
import { mkdir as mkdir12, readFile as readFile13, rename as rename7, writeFile as writeFile11 } from "node:fs/promises";
|
|
66746
67094
|
import * as path46 from "node:path";
|
|
66747
67095
|
function timestampSlug(d) {
|
|
66748
67096
|
return d.toISOString().replace(/[:.]/g, "-");
|
|
@@ -66750,7 +67098,7 @@ function timestampSlug(d) {
|
|
|
66750
67098
|
async function atomicWrite3(p, content) {
|
|
66751
67099
|
await mkdir12(path46.dirname(p), { recursive: true });
|
|
66752
67100
|
const tmp = `${p}.tmp-${process.pid}-${Date.now()}`;
|
|
66753
|
-
await
|
|
67101
|
+
await writeFile11(tmp, content, "utf-8");
|
|
66754
67102
|
await rename7(tmp, p);
|
|
66755
67103
|
}
|
|
66756
67104
|
async function gatherInventory(directory) {
|
|
@@ -66804,7 +67152,10 @@ async function gatherInventory(directory) {
|
|
|
66804
67152
|
});
|
|
66805
67153
|
}
|
|
66806
67154
|
}
|
|
66807
|
-
const matureCandidates =
|
|
67155
|
+
const matureCandidates = await selectCandidateEntries(directory, {
|
|
67156
|
+
minConfidence: DEFAULT_SKILL_MIN_CONFIDENCE,
|
|
67157
|
+
minConfirmations: DEFAULT_SKILL_MIN_CONFIRMATIONS
|
|
67158
|
+
});
|
|
66808
67159
|
return {
|
|
66809
67160
|
knowledge: { swarm: swarm.length, hive: hive.length, archived },
|
|
66810
67161
|
skills: {
|
|
@@ -67070,8 +67421,8 @@ async function runSkillImprover(req) {
|
|
|
67070
67421
|
const gen = await generateSkills({
|
|
67071
67422
|
directory: req.directory,
|
|
67072
67423
|
mode: "draft",
|
|
67073
|
-
minConfidence:
|
|
67074
|
-
minConfirmations:
|
|
67424
|
+
minConfidence: DEFAULT_SKILL_MIN_CONFIDENCE,
|
|
67425
|
+
minConfirmations: DEFAULT_SKILL_MIN_CONFIRMATIONS
|
|
67075
67426
|
});
|
|
67076
67427
|
draftSkillsWritten = gen.written.map((w) => ({
|
|
67077
67428
|
slug: w.slug,
|
|
@@ -67107,7 +67458,7 @@ async function runSkillImprover(req) {
|
|
|
67107
67458
|
unactionableHardening = await hardenUnactionableEntries({
|
|
67108
67459
|
directory: req.directory,
|
|
67109
67460
|
llmDelegate: delegate,
|
|
67110
|
-
quota:
|
|
67461
|
+
quota: req.enrichmentQuota
|
|
67111
67462
|
});
|
|
67112
67463
|
}
|
|
67113
67464
|
const motifResult = await writeMotifProposals(req.directory);
|
|
@@ -67933,8 +68284,8 @@ async function copyDirRecursive(src, dest) {
|
|
|
67933
68284
|
const srcEntry = path48.join(src, entry);
|
|
67934
68285
|
const destEntry = path48.join(dest, entry);
|
|
67935
68286
|
try {
|
|
67936
|
-
const
|
|
67937
|
-
if (
|
|
68287
|
+
const stat5 = await fs23.stat(srcEntry);
|
|
68288
|
+
if (stat5.isDirectory()) {
|
|
67938
68289
|
const subCount = await copyDirRecursive(srcEntry, destEntry).catch(() => 0);
|
|
67939
68290
|
count += subCount;
|
|
67940
68291
|
} else {
|
|
@@ -67970,8 +68321,8 @@ function guaranteeAllPlansComplete(planData) {
|
|
|
67970
68321
|
async function handleCloseCommand(directory, args2, options = {}) {
|
|
67971
68322
|
const swarmDir = path48.join(directory, ".swarm");
|
|
67972
68323
|
try {
|
|
67973
|
-
const
|
|
67974
|
-
if (
|
|
68324
|
+
const stat5 = fsSync5.lstatSync(swarmDir);
|
|
68325
|
+
if (stat5.isSymbolicLink()) {
|
|
67975
68326
|
return `❌ Refused: .swarm/ is a symlink or junction. Refusing to operate on a redirected directory for safety.`;
|
|
67976
68327
|
}
|
|
67977
68328
|
} catch (err2) {
|
|
@@ -68125,12 +68476,11 @@ async function handleCloseCommand(directory, args2, options = {}) {
|
|
|
68125
68476
|
let curationSucceeded = false;
|
|
68126
68477
|
let curationResult;
|
|
68127
68478
|
try {
|
|
68128
|
-
const skillImproverCfg = SkillImproverConfigSchema.parse(loadedConfig.skill_improver ?? {});
|
|
68129
68479
|
curationResult = await curateAndStoreSwarm(allLessons, projectName, { phase_number: 0 }, directory, config3, {
|
|
68130
68480
|
llmDelegate: createCuratorLLMDelegate(directory, "phase", options.sessionID),
|
|
68131
68481
|
enrichmentQuota: {
|
|
68132
|
-
maxCalls:
|
|
68133
|
-
window:
|
|
68482
|
+
maxCalls: config3.enrichment.max_calls_per_day,
|
|
68483
|
+
window: config3.enrichment.quota_window
|
|
68134
68484
|
}
|
|
68135
68485
|
});
|
|
68136
68486
|
curationSucceeded = true;
|
|
@@ -68195,7 +68545,11 @@ async function handleCloseCommand(directory, args2, options = {}) {
|
|
|
68195
68545
|
config: skillImproverConfig,
|
|
68196
68546
|
targets: ["skills", "knowledge"],
|
|
68197
68547
|
mode: "proposal",
|
|
68198
|
-
sessionId: options.sessionID
|
|
68548
|
+
sessionId: options.sessionID,
|
|
68549
|
+
enrichmentQuota: {
|
|
68550
|
+
maxCalls: config3.enrichment.max_calls_per_day,
|
|
68551
|
+
window: config3.enrichment.quota_window
|
|
68552
|
+
}
|
|
68199
68553
|
}, options.skillReviewTimeoutMs ?? CLOSE_SKILL_REVIEW_TIMEOUT_MS);
|
|
68200
68554
|
if (skillReviewResult.ran) {
|
|
68201
68555
|
const proposal = skillReviewResult.proposalPath ? ` Proposal: ${skillReviewResult.proposalPath}.` : "";
|
|
@@ -68784,7 +69138,7 @@ function buildStatusMessage(session, plan) {
|
|
|
68784
69138
|
const overrideActive = session.maxConcurrencyOverride !== undefined;
|
|
68785
69139
|
const configuredOverride = session.maxConcurrencyOverride ?? "absent";
|
|
68786
69140
|
const hasPlan = plan !== null && plan !== undefined;
|
|
68787
|
-
const planBaseline = hasPlan ? plan.execution_profile?.max_concurrent_tasks ??
|
|
69141
|
+
const planBaseline = hasPlan ? plan.execution_profile?.max_concurrent_tasks ?? 10 : 10;
|
|
68788
69142
|
const parallelizationEnabled = hasPlan ? plan.execution_profile?.parallelization_enabled ?? false : false;
|
|
68789
69143
|
const operationalEffective = !parallelizationEnabled ? 1 : session.maxConcurrencyOverride ?? planBaseline;
|
|
68790
69144
|
let description;
|
|
@@ -68813,8 +69167,8 @@ var init_concurrency = __esm(() => {
|
|
|
68813
69167
|
init_state();
|
|
68814
69168
|
PRESETS = {
|
|
68815
69169
|
min: 1,
|
|
68816
|
-
medium:
|
|
68817
|
-
max:
|
|
69170
|
+
medium: 8,
|
|
69171
|
+
max: 16
|
|
68818
69172
|
};
|
|
68819
69173
|
});
|
|
68820
69174
|
|
|
@@ -68964,7 +69318,7 @@ __export(exports_co_change_analyzer, {
|
|
|
68964
69318
|
});
|
|
68965
69319
|
import * as child_process3 from "node:child_process";
|
|
68966
69320
|
import { randomUUID as randomUUID5 } from "node:crypto";
|
|
68967
|
-
import { readdir as readdir2, readFile as readFile14, stat as
|
|
69321
|
+
import { readdir as readdir2, readFile as readFile14, stat as stat5 } from "node:fs/promises";
|
|
68968
69322
|
import * as path50 from "node:path";
|
|
68969
69323
|
import { promisify } from "node:util";
|
|
68970
69324
|
function getExecFileAsync() {
|
|
@@ -69115,7 +69469,7 @@ async function getStaticEdges(directory) {
|
|
|
69115
69469
|
for (const ext of extensions) {
|
|
69116
69470
|
const testPath = resolvedPath + ext;
|
|
69117
69471
|
try {
|
|
69118
|
-
const testStat = await
|
|
69472
|
+
const testStat = await stat5(testPath);
|
|
69119
69473
|
if (testStat.isFile()) {
|
|
69120
69474
|
targetFile = testPath;
|
|
69121
69475
|
break;
|
|
@@ -75495,7 +75849,7 @@ var KNOWLEDGE_SCHEMA_VERSION = 2;
|
|
|
75495
75849
|
// src/hooks/knowledge-migrator.ts
|
|
75496
75850
|
import { randomUUID as randomUUID6 } from "node:crypto";
|
|
75497
75851
|
import { existsSync as existsSync33, readFileSync as readFileSync18 } from "node:fs";
|
|
75498
|
-
import { mkdir as mkdir13, readFile as readFile16, writeFile as
|
|
75852
|
+
import { mkdir as mkdir13, readFile as readFile16, writeFile as writeFile12 } from "node:fs/promises";
|
|
75499
75853
|
import * as os13 from "node:os";
|
|
75500
75854
|
import * as path58 from "node:path";
|
|
75501
75855
|
async function migrateKnowledgeToExternal(_directory, _config) {
|
|
@@ -75844,7 +76198,7 @@ async function writeSentinel(sentinelPath, migrated, dropped) {
|
|
|
75844
76198
|
migration_tool: "knowledge-migrator.ts"
|
|
75845
76199
|
};
|
|
75846
76200
|
await mkdir13(path58.dirname(sentinelPath), { recursive: true });
|
|
75847
|
-
await
|
|
76201
|
+
await writeFile12(sentinelPath, JSON.stringify(sentinel, null, 2), "utf-8");
|
|
75848
76202
|
}
|
|
75849
76203
|
function resolveLegacyHiveKnowledgePath() {
|
|
75850
76204
|
const platform = process.platform;
|
|
@@ -76275,7 +76629,7 @@ var init_redaction = __esm(() => {
|
|
|
76275
76629
|
});
|
|
76276
76630
|
|
|
76277
76631
|
// src/memory/schema.ts
|
|
76278
|
-
import { createHash as
|
|
76632
|
+
import { createHash as createHash7 } from "node:crypto";
|
|
76279
76633
|
function normalizeMemoryText(text) {
|
|
76280
76634
|
return text.replace(/\s+/g, " ").trim();
|
|
76281
76635
|
}
|
|
@@ -76299,7 +76653,7 @@ function stableScopeKey(scope) {
|
|
|
76299
76653
|
}
|
|
76300
76654
|
function computeMemoryContentHash(recordLike) {
|
|
76301
76655
|
const normalized = normalizeMemoryText(recordLike.text).toLowerCase();
|
|
76302
|
-
return
|
|
76656
|
+
return createHash7("sha256").update(`${stableScopeKey(recordLike.scope)}
|
|
76303
76657
|
${recordLike.kind}
|
|
76304
76658
|
${normalized}`).digest("hex");
|
|
76305
76659
|
}
|
|
@@ -76307,14 +76661,14 @@ function createMemoryId(recordLike) {
|
|
|
76307
76661
|
return `mem_${computeMemoryContentHash(recordLike).slice(0, 16)}`;
|
|
76308
76662
|
}
|
|
76309
76663
|
function createProposalId(input) {
|
|
76310
|
-
const hash4 =
|
|
76664
|
+
const hash4 = createHash7("sha256").update(`${input.createdAt}
|
|
76311
76665
|
${input.proposer}
|
|
76312
76666
|
${normalizeMemoryText(input.text)}`).digest("hex");
|
|
76313
76667
|
return `prop_${hash4.slice(0, 16)}`;
|
|
76314
76668
|
}
|
|
76315
76669
|
function createBundleId(query, generatedAt) {
|
|
76316
76670
|
const compactTimestamp = generatedAt.replace(/[-:.TZ]/g, "").slice(0, 14);
|
|
76317
|
-
const hash4 =
|
|
76671
|
+
const hash4 = createHash7("sha256").update(`${generatedAt}
|
|
76318
76672
|
${query}`).digest("hex").slice(0, 8);
|
|
76319
76673
|
return `bundle_${compactTimestamp}_${hash4}`;
|
|
76320
76674
|
}
|
|
@@ -77066,7 +77420,7 @@ import {
|
|
|
77066
77420
|
mkdir as mkdir14,
|
|
77067
77421
|
readFile as readFile17,
|
|
77068
77422
|
rename as rename8,
|
|
77069
|
-
writeFile as
|
|
77423
|
+
writeFile as writeFile13
|
|
77070
77424
|
} from "node:fs/promises";
|
|
77071
77425
|
import * as path59 from "node:path";
|
|
77072
77426
|
|
|
@@ -77477,7 +77831,7 @@ async function writeJsonlAtomic(filePath, values) {
|
|
|
77477
77831
|
const content = values.map((value) => JSON.stringify(value)).join(`
|
|
77478
77832
|
`) + (values.length > 0 ? `
|
|
77479
77833
|
` : "");
|
|
77480
|
-
await
|
|
77834
|
+
await writeFile13(tmp, content, "utf-8");
|
|
77481
77835
|
await rename8(tmp, filePath);
|
|
77482
77836
|
}
|
|
77483
77837
|
var init_local_jsonl_provider = __esm(() => {
|
|
@@ -77572,7 +77926,7 @@ var init_prompt_block = __esm(() => {
|
|
|
77572
77926
|
|
|
77573
77927
|
// src/memory/jsonl-migration.ts
|
|
77574
77928
|
import { existsSync as existsSync35 } from "node:fs";
|
|
77575
|
-
import { copyFile, mkdir as mkdir15, readFile as readFile18, stat as
|
|
77929
|
+
import { copyFile, mkdir as mkdir15, readFile as readFile18, stat as stat6, writeFile as writeFile14 } from "node:fs/promises";
|
|
77576
77930
|
import * as path60 from "node:path";
|
|
77577
77931
|
function resolveMemoryStorageDir(rootDirectory, config3 = {}) {
|
|
77578
77932
|
const resolved = resolveConfig(config3);
|
|
@@ -77620,14 +77974,14 @@ async function writeJsonlExport(rootDirectory, config3, memories, proposals) {
|
|
|
77620
77974
|
await mkdir15(exportDir, { recursive: true });
|
|
77621
77975
|
const memoriesPath = path60.join(exportDir, "memories.jsonl");
|
|
77622
77976
|
const proposalsPath = path60.join(exportDir, "proposals.jsonl");
|
|
77623
|
-
await
|
|
77624
|
-
await
|
|
77977
|
+
await writeFile14(memoriesPath, toJsonl(memories), "utf-8");
|
|
77978
|
+
await writeFile14(proposalsPath, toJsonl(proposals), "utf-8");
|
|
77625
77979
|
return { directory: exportDir, memoriesPath, proposalsPath };
|
|
77626
77980
|
}
|
|
77627
77981
|
async function writeMigrationReport(rootDirectory, report, config3 = {}) {
|
|
77628
77982
|
const reportPath = path60.join(resolveMemoryStorageDir(rootDirectory, config3), "migration-report.json");
|
|
77629
77983
|
await mkdir15(path60.dirname(reportPath), { recursive: true });
|
|
77630
|
-
await
|
|
77984
|
+
await writeFile14(reportPath, `${JSON.stringify(report, null, 2)}
|
|
77631
77985
|
`, "utf-8");
|
|
77632
77986
|
return reportPath;
|
|
77633
77987
|
}
|
|
@@ -77648,7 +78002,7 @@ async function getLegacyJsonlFileStatus(rootDirectory, config3 = {}) {
|
|
|
77648
78002
|
const filePath = path60.join(storageDir, file3);
|
|
77649
78003
|
let sizeBytes = 0;
|
|
77650
78004
|
if (existsSync35(filePath)) {
|
|
77651
|
-
sizeBytes = (await
|
|
78005
|
+
sizeBytes = (await stat6(filePath)).size;
|
|
77652
78006
|
}
|
|
77653
78007
|
statuses.push({
|
|
77654
78008
|
file: file3,
|
|
@@ -78697,7 +79051,7 @@ var init_sqlite_provider = __esm(() => {
|
|
|
78697
79051
|
});
|
|
78698
79052
|
|
|
78699
79053
|
// src/memory/gateway.ts
|
|
78700
|
-
import { createHash as
|
|
79054
|
+
import { createHash as createHash8 } from "node:crypto";
|
|
78701
79055
|
import { existsSync as existsSync36, readFileSync as readFileSync19 } from "node:fs";
|
|
78702
79056
|
import * as path62 from "node:path";
|
|
78703
79057
|
|
|
@@ -79017,7 +79371,7 @@ function sourceFromEvidence(evidenceRefs, context) {
|
|
|
79017
79371
|
return { type: "manual", ref: first };
|
|
79018
79372
|
}
|
|
79019
79373
|
function createStableId(value) {
|
|
79020
|
-
return
|
|
79374
|
+
return createHash8("sha256").update(value.toLowerCase()).digest("hex").slice(0, 16);
|
|
79021
79375
|
}
|
|
79022
79376
|
function readGitRemoteUrl(directory) {
|
|
79023
79377
|
if (gitRemoteUrlCache.has(directory))
|
|
@@ -82170,8 +82524,8 @@ var init_secretscan = __esm(() => {
|
|
|
82170
82524
|
break;
|
|
82171
82525
|
const fileFindings = scanFileForSecrets(filePath);
|
|
82172
82526
|
try {
|
|
82173
|
-
const
|
|
82174
|
-
if (
|
|
82527
|
+
const stat7 = fs30.statSync(filePath);
|
|
82528
|
+
if (stat7.size > MAX_FILE_SIZE_BYTES) {
|
|
82175
82529
|
skippedFiles++;
|
|
82176
82530
|
continue;
|
|
82177
82531
|
}
|
|
@@ -82981,8 +83335,8 @@ function sharedTrailingSegments(a, b) {
|
|
|
82981
83335
|
function isCacheStale(impactMap, generatedAtMs) {
|
|
82982
83336
|
for (const sourcePath of Object.keys(impactMap)) {
|
|
82983
83337
|
try {
|
|
82984
|
-
const
|
|
82985
|
-
if (
|
|
83338
|
+
const stat7 = fs34.statSync(sourcePath);
|
|
83339
|
+
if (stat7.mtimeMs > generatedAtMs) {
|
|
82986
83340
|
return true;
|
|
82987
83341
|
}
|
|
82988
83342
|
} catch {
|
|
@@ -84328,8 +84682,8 @@ function manifestHash(dir) {
|
|
|
84328
84682
|
if (!entries.has(name2))
|
|
84329
84683
|
continue;
|
|
84330
84684
|
try {
|
|
84331
|
-
const
|
|
84332
|
-
parts2.push(`${name2}:${
|
|
84685
|
+
const stat7 = fs39.statSync(path77.join(dir, name2));
|
|
84686
|
+
parts2.push(`${name2}:${stat7.size}:${stat7.mtimeMs}:${stat7.ino}`);
|
|
84333
84687
|
} catch {}
|
|
84334
84688
|
}
|
|
84335
84689
|
return parts2.join("|");
|
|
@@ -94313,6 +94667,7 @@ SKILL COMPLIANCE REVIEW: When SKILLS_USED_BY_CODER is provided and not "none":
|
|
|
94313
94667
|
- For each skill rule, verify the coder's changes comply
|
|
94314
94668
|
- Flag violations at the same severity as logic errors
|
|
94315
94669
|
- Report the overall compliance verdict in SKILL_COMPLIANCE field of your output
|
|
94670
|
+
- Report TASK: <task id> immediately before SKILL_COMPLIANCE when a task id is available
|
|
94316
94671
|
- If you cannot load a skill (SKILL_LOAD_FAILED), report SKILL_COMPLIANCE: PARTIAL — [skill path] could not be loaded
|
|
94317
94672
|
|
|
94318
94673
|
PROCESSING: If GATES is provided and includes passing results for lint, SAST, placeholder-scan, or secret-scan: skip the corresponding Tier 2 checks that those gates already cover. Focus Tier 2 time on checks NOT covered by automated gates.
|
|
@@ -94324,6 +94679,7 @@ VERDICT: APPROVED | REJECTED
|
|
|
94324
94679
|
REUSE_RE_VERIFICATION: [VERIFIED | DUPLICATION_DETECTED | SKIPPED] — DUPLICATION_DETECTED is only valid when VERDICT is REJECTED
|
|
94325
94680
|
RISK: LOW | MEDIUM | HIGH | CRITICAL
|
|
94326
94681
|
ISSUES: list with line numbers, grouped by CHECK dimension
|
|
94682
|
+
TASK: [task id being reviewed, or "unknown"]
|
|
94327
94683
|
SKILL_COMPLIANCE: COMPLIANT | PARTIAL | VIOLATED — [list of violations or "all rules followed"]
|
|
94328
94684
|
DIRECTIVE_COMPLIANCE: one line per knowledge directive shown during this phase (IDs listed in the DIRECTIVES TO VERIFY block of your prompt, when present). Use exactly one of:
|
|
94329
94685
|
VERIFIED:<id> evidence=<file:line | predicate_passed>
|
|
@@ -94904,7 +95260,7 @@ COVERAGE REPORTING:
|
|
|
94904
95260
|
`;
|
|
94905
95261
|
|
|
94906
95262
|
// src/agents/index.ts
|
|
94907
|
-
import { mkdir as mkdir17, writeFile as
|
|
95263
|
+
import { mkdir as mkdir17, writeFile as writeFile15 } from "node:fs/promises";
|
|
94908
95264
|
import * as path88 from "node:path";
|
|
94909
95265
|
function stripSwarmPrefix(agentName, swarmPrefix) {
|
|
94910
95266
|
if (!swarmPrefix || !agentName)
|
|
@@ -95384,7 +95740,7 @@ function getAgentConfigs(config3, directory, sessionId, projectContext) {
|
|
|
95384
95740
|
generatedAt: new Date().toISOString(),
|
|
95385
95741
|
agents: agentToolSnapshot
|
|
95386
95742
|
}, null, 2);
|
|
95387
|
-
mkdir17(evidenceDir, { recursive: true }).then(() =>
|
|
95743
|
+
mkdir17(evidenceDir, { recursive: true }).then(() => writeFile15(path88.join(evidenceDir, filename), snapshotData)).catch(() => {});
|
|
95388
95744
|
}
|
|
95389
95745
|
return result;
|
|
95390
95746
|
}
|
|
@@ -100096,8 +100452,8 @@ import {
|
|
|
100096
100452
|
readdir as readdir6,
|
|
100097
100453
|
readFile as readFile22,
|
|
100098
100454
|
realpath as realpath3,
|
|
100099
|
-
stat as
|
|
100100
|
-
writeFile as
|
|
100455
|
+
stat as stat9,
|
|
100456
|
+
writeFile as writeFile17
|
|
100101
100457
|
} from "node:fs/promises";
|
|
100102
100458
|
import * as path119 from "node:path";
|
|
100103
100459
|
function normalizeSeparators(filePath) {
|
|
@@ -100179,8 +100535,8 @@ async function scanDocIndex(directory) {
|
|
|
100179
100535
|
for (const file3 of existingManifest.files) {
|
|
100180
100536
|
try {
|
|
100181
100537
|
const fullPath = path119.join(directory, file3.path);
|
|
100182
|
-
const
|
|
100183
|
-
if (
|
|
100538
|
+
const stat10 = fs71.statSync(fullPath);
|
|
100539
|
+
if (stat10.mtimeMs > file3.mtime) {
|
|
100184
100540
|
cacheValid = false;
|
|
100185
100541
|
break;
|
|
100186
100542
|
}
|
|
@@ -100218,7 +100574,7 @@ async function scanDocIndex(directory) {
|
|
|
100218
100574
|
const rel = path119.relative(resolvedDirectory, resolved);
|
|
100219
100575
|
if (rel.startsWith("..") || path119.isAbsolute(rel))
|
|
100220
100576
|
continue;
|
|
100221
|
-
const targetStat = await
|
|
100577
|
+
const targetStat = await stat9(symlinkPath);
|
|
100222
100578
|
isFile = targetStat.isFile();
|
|
100223
100579
|
} catch {
|
|
100224
100580
|
continue;
|
|
@@ -100247,7 +100603,7 @@ async function scanDocIndex(directory) {
|
|
|
100247
100603
|
continue;
|
|
100248
100604
|
let fileStat;
|
|
100249
100605
|
try {
|
|
100250
|
-
fileStat = await
|
|
100606
|
+
fileStat = await stat9(fullPath);
|
|
100251
100607
|
} catch {
|
|
100252
100608
|
continue;
|
|
100253
100609
|
}
|
|
@@ -100295,7 +100651,7 @@ async function scanDocIndex(directory) {
|
|
|
100295
100651
|
};
|
|
100296
100652
|
try {
|
|
100297
100653
|
await mkdir20(path119.dirname(manifestPath), { recursive: true });
|
|
100298
|
-
await
|
|
100654
|
+
await writeFile17(manifestPath, JSON.stringify(manifest, null, 2), "utf-8");
|
|
100299
100655
|
} catch {}
|
|
100300
100656
|
return { manifest, cached: false };
|
|
100301
100657
|
}
|
|
@@ -100982,7 +101338,7 @@ async function searchKnowledge(params) {
|
|
|
100982
101338
|
const confBoost = context && entry.confidence >= minConf && (ds.actionHit || ds.agentHit) ? 0.25 : 0;
|
|
100983
101339
|
const generatedSkillBoost = entry.generated_skill_path && entry.status !== "archived" ? 0.05 : 0;
|
|
100984
101340
|
const outcomeBoost = computeOutcomeSignal(retrievalOutcomes) * OUTCOME_RANK_WEIGHT;
|
|
100985
|
-
const coldStartBonus = retrievalOutcomes.
|
|
101341
|
+
const coldStartBonus = (retrievalOutcomes.applied_explicit_count ?? 0) === 0 && entryAgePhases(entry) < (config3.retrieval?.cold_start_max_age_phases ?? DEFAULT_COLD_START_MAX_AGE_PHASES) ? config3.retrieval?.cold_start_bonus ?? DEFAULT_COLD_START_BONUS : 0;
|
|
100986
101342
|
let synonymBoost = 0;
|
|
100987
101343
|
if (synonymTokens.length > 0) {
|
|
100988
101344
|
const entryHay = normalize4(entryText(entry));
|
|
@@ -101007,6 +101363,7 @@ async function searchKnowledge(params) {
|
|
|
101007
101363
|
...entry,
|
|
101008
101364
|
retrieval_outcomes: retrievalOutcomes,
|
|
101009
101365
|
finalScore,
|
|
101366
|
+
coldStartBoost: coldStartBonus,
|
|
101010
101367
|
__critical: isCritical
|
|
101011
101368
|
};
|
|
101012
101369
|
});
|
|
@@ -101038,7 +101395,8 @@ async function searchKnowledge(params) {
|
|
|
101038
101395
|
}
|
|
101039
101396
|
}
|
|
101040
101397
|
results = top.map(({ __critical: _c, ...rest }) => rest);
|
|
101041
|
-
} catch {
|
|
101398
|
+
} catch (err2) {
|
|
101399
|
+
warn(`[search-knowledge] retrieval failed: ${err2 instanceof Error ? err2.message : String(err2)}`);
|
|
101042
101400
|
results = [];
|
|
101043
101401
|
}
|
|
101044
101402
|
if (emitEvent) {
|
|
@@ -101078,6 +101436,7 @@ var TEXT_WEIGHT = 0.6, META_WEIGHT = 0.4, DIRECTIVE_BOOST_MIN_CONFIDENCE = 0.75,
|
|
|
101078
101436
|
var init_search_knowledge = __esm(() => {
|
|
101079
101437
|
init_schema();
|
|
101080
101438
|
init_synonym_map();
|
|
101439
|
+
init_logger();
|
|
101081
101440
|
init_knowledge_events();
|
|
101082
101441
|
init_knowledge_reader();
|
|
101083
101442
|
init_knowledge_store();
|
|
@@ -101463,8 +101822,8 @@ async function runDesignDocDriftCheck(directory, phase, outDir) {
|
|
|
101463
101822
|
const traceabilityAbs = path165.join(outAbs, TRACEABILITY_REL);
|
|
101464
101823
|
let registry3 = null;
|
|
101465
101824
|
try {
|
|
101466
|
-
const
|
|
101467
|
-
if (
|
|
101825
|
+
const stat11 = await fs112.promises.stat(traceabilityAbs);
|
|
101826
|
+
if (stat11.size <= MAX_TRACEABILITY_BYTES) {
|
|
101468
101827
|
const raw = await fs112.promises.readFile(traceabilityAbs, "utf-8");
|
|
101469
101828
|
const parsed = JSON.parse(raw);
|
|
101470
101829
|
registry3 = parsed && typeof parsed === "object" && !Array.isArray(parsed) ? parsed : null;
|
|
@@ -102777,8 +103136,8 @@ function writeProjectConfigIfNew(directory, quiet = false) {
|
|
|
102777
103136
|
const dest = path92.join(opencodeDir, "opencode-swarm.json");
|
|
102778
103137
|
const normalizePathForCompare = (p) => process.platform === "win32" ? p.toLowerCase() : p;
|
|
102779
103138
|
try {
|
|
102780
|
-
const
|
|
102781
|
-
if (
|
|
103139
|
+
const stat7 = fs50.lstatSync(opencodeDir);
|
|
103140
|
+
if (stat7.isSymbolicLink())
|
|
102782
103141
|
return;
|
|
102783
103142
|
const resolvedDir = fs50.realpathSync(opencodeDir);
|
|
102784
103143
|
const canonicalOpencode = path92.join(fs50.realpathSync(directory), ".opencode");
|
|
@@ -102951,8 +103310,8 @@ function extractFileSummary(filePath, content, absolutePath, existingEntry) {
|
|
|
102951
103310
|
let mtimeMs = 0;
|
|
102952
103311
|
if (absolutePath) {
|
|
102953
103312
|
try {
|
|
102954
|
-
const
|
|
102955
|
-
mtimeMs =
|
|
103313
|
+
const stat7 = fs52.statSync(absolutePath);
|
|
103314
|
+
mtimeMs = stat7.mtimeMs;
|
|
102956
103315
|
} catch {}
|
|
102957
103316
|
}
|
|
102958
103317
|
const base = {
|
|
@@ -105902,9 +106261,9 @@ function createPhaseMonitorHook(directory, preflightManager, curatorRunner, dele
|
|
|
105902
106261
|
const initResult = await runner(directory, curatorConfig, llmDelegate);
|
|
105903
106262
|
if (initResult.briefing) {
|
|
105904
106263
|
const briefingPath = path103.join(directory, ".swarm", "curator-briefing.md");
|
|
105905
|
-
const { mkdir: mkdir18, writeFile:
|
|
106264
|
+
const { mkdir: mkdir18, writeFile: writeFile16 } = await import("node:fs/promises");
|
|
105906
106265
|
await mkdir18(path103.dirname(briefingPath), { recursive: true });
|
|
105907
|
-
await
|
|
106266
|
+
await writeFile16(briefingPath, initResult.briefing, "utf-8");
|
|
105908
106267
|
const { buildApprovedReceipt: buildApprovedReceipt2, persistReviewReceipt: persistReviewReceipt2 } = await Promise.resolve().then(() => (init_review_receipt(), exports_review_receipt));
|
|
105909
106268
|
const initReceipt = buildApprovedReceipt2({
|
|
105910
106269
|
agent: "curator",
|
|
@@ -108493,16 +108852,16 @@ function tryResolveTSJS(rawModule, sourceFileAbs) {
|
|
|
108493
108852
|
for (const ext of RESOLVE_EXTENSION_CANDIDATES) {
|
|
108494
108853
|
const test = basePath + ext;
|
|
108495
108854
|
try {
|
|
108496
|
-
const
|
|
108497
|
-
if (
|
|
108855
|
+
const stat9 = fs66.statSync(test);
|
|
108856
|
+
if (stat9.isFile())
|
|
108498
108857
|
return test;
|
|
108499
108858
|
} catch {}
|
|
108500
108859
|
}
|
|
108501
108860
|
for (const indexFile of RESOLVE_INDEX_CANDIDATES) {
|
|
108502
108861
|
const test = path113.join(basePath, indexFile);
|
|
108503
108862
|
try {
|
|
108504
|
-
const
|
|
108505
|
-
if (
|
|
108863
|
+
const stat9 = fs66.statSync(test);
|
|
108864
|
+
if (stat9.isFile())
|
|
108506
108865
|
return test;
|
|
108507
108866
|
} catch {}
|
|
108508
108867
|
}
|
|
@@ -108533,8 +108892,8 @@ function tryResolvePython(rawModule, sourceFileAbs, workspaceRoot) {
|
|
|
108533
108892
|
const baseAbs = path113.resolve(sourceDir, upDirs + remainder);
|
|
108534
108893
|
const accept = (test) => {
|
|
108535
108894
|
try {
|
|
108536
|
-
const
|
|
108537
|
-
if (
|
|
108895
|
+
const stat9 = fs66.statSync(test);
|
|
108896
|
+
if (stat9.isFile()) {
|
|
108538
108897
|
const rel = path113.relative(workspaceRoot, test).replace(/\\/g, "/");
|
|
108539
108898
|
if (rel.startsWith(".."))
|
|
108540
108899
|
return null;
|
|
@@ -109387,8 +109746,8 @@ function saveGraph2(workspaceRoot, graph) {
|
|
|
109387
109746
|
const file3 = getGraphPath2(workspaceRoot);
|
|
109388
109747
|
const dir = path116.dirname(file3);
|
|
109389
109748
|
try {
|
|
109390
|
-
const
|
|
109391
|
-
if (
|
|
109749
|
+
const stat9 = fs68.lstatSync(dir);
|
|
109750
|
+
if (stat9.isSymbolicLink()) {
|
|
109392
109751
|
throw new Error(`refusing to write graph: ${SWARM_DIR}/ is a symbolic link`);
|
|
109393
109752
|
}
|
|
109394
109753
|
} catch (err2) {
|
|
@@ -109424,15 +109783,15 @@ function isGraphFresh(graph, maxAgeMs = 5 * 60 * 1000) {
|
|
|
109424
109783
|
var cache2 = new Map;
|
|
109425
109784
|
function getCachedGraph2(directory) {
|
|
109426
109785
|
const file3 = getGraphPath2(directory);
|
|
109427
|
-
let
|
|
109786
|
+
let stat9;
|
|
109428
109787
|
try {
|
|
109429
|
-
|
|
109788
|
+
stat9 = fs69.statSync(file3);
|
|
109430
109789
|
} catch {
|
|
109431
109790
|
cache2.delete(directory);
|
|
109432
109791
|
return null;
|
|
109433
109792
|
}
|
|
109434
109793
|
const cached3 = cache2.get(directory);
|
|
109435
|
-
if (cached3 && cached3.mtimeMs ===
|
|
109794
|
+
if (cached3 && cached3.mtimeMs === stat9.mtimeMs && cached3.size === stat9.size) {
|
|
109436
109795
|
return cached3.graph;
|
|
109437
109796
|
}
|
|
109438
109797
|
const graph = loadGraph2(directory);
|
|
@@ -109440,7 +109799,7 @@ function getCachedGraph2(directory) {
|
|
|
109440
109799
|
cache2.delete(directory);
|
|
109441
109800
|
return null;
|
|
109442
109801
|
}
|
|
109443
|
-
cache2.set(directory, { graph, mtimeMs:
|
|
109802
|
+
cache2.set(directory, { graph, mtimeMs: stat9.mtimeMs, size: stat9.size });
|
|
109444
109803
|
return graph;
|
|
109445
109804
|
}
|
|
109446
109805
|
function buildCoderLocalizationBlock(directory, targetFile) {
|
|
@@ -112001,6 +112360,7 @@ import { appendFile as appendFile13, mkdir as mkdir22 } from "node:fs/promises";
|
|
|
112001
112360
|
import * as path124 from "node:path";
|
|
112002
112361
|
|
|
112003
112362
|
// src/hooks/knowledge-application.ts
|
|
112363
|
+
init_task_file();
|
|
112004
112364
|
init_logger();
|
|
112005
112365
|
init_knowledge_store();
|
|
112006
112366
|
var import_proper_lockfile9 = __toESM(require_proper_lockfile(), 1);
|
|
@@ -112010,6 +112370,7 @@ import * as path122 from "node:path";
|
|
|
112010
112370
|
function resolveApplicationLogPath(directory) {
|
|
112011
112371
|
return path122.join(directory, ".swarm", "knowledge-application.jsonl");
|
|
112012
112372
|
}
|
|
112373
|
+
var MAX_LEGACY_APPLICATION_LOG_ENTRIES = 5000;
|
|
112013
112374
|
var ACK_PATTERN = /KNOWLEDGE_(APPLIED|IGNORED|VIOLATED|N_A)\s*:\s*([0-9a-fA-F-]{8,64})(?:\s+reason\s*=\s*([^\n\r]+?))?(?=$|[\n\r]|\s+KNOWLEDGE_)/g;
|
|
112014
112375
|
function parseAcknowledgments(text) {
|
|
112015
112376
|
if (!text || typeof text !== "string")
|
|
@@ -112026,9 +112387,29 @@ function parseAcknowledgments(text) {
|
|
|
112026
112387
|
}
|
|
112027
112388
|
async function appendAudit(directory, record3) {
|
|
112028
112389
|
const filePath = resolveApplicationLogPath(directory);
|
|
112029
|
-
|
|
112030
|
-
await
|
|
112390
|
+
const dirPath = path122.dirname(filePath);
|
|
112391
|
+
await mkdir21(dirPath, { recursive: true });
|
|
112392
|
+
let release;
|
|
112393
|
+
try {
|
|
112394
|
+
release = await import_proper_lockfile9.default.lock(dirPath, {
|
|
112395
|
+
retries: { retries: 50, minTimeout: 10, maxTimeout: 100 },
|
|
112396
|
+
stale: 5000
|
|
112397
|
+
});
|
|
112398
|
+
await appendFile11(filePath, `${JSON.stringify(record3)}
|
|
112031
112399
|
`, "utf-8");
|
|
112400
|
+
const content = await readFile24(filePath, "utf-8");
|
|
112401
|
+
const lines = content.split(`
|
|
112402
|
+
`).filter((line) => line.trim().length > 0);
|
|
112403
|
+
if (lines.length > MAX_LEGACY_APPLICATION_LOG_ENTRIES) {
|
|
112404
|
+
const trimmed = lines.slice(-MAX_LEGACY_APPLICATION_LOG_ENTRIES);
|
|
112405
|
+
await atomicWriteFile(filePath, `${trimmed.join(`
|
|
112406
|
+
`)}
|
|
112407
|
+
`);
|
|
112408
|
+
}
|
|
112409
|
+
} finally {
|
|
112410
|
+
if (release)
|
|
112411
|
+
await release().catch(() => {});
|
|
112412
|
+
}
|
|
112032
112413
|
}
|
|
112033
112414
|
async function bumpCountersBatch(directory, bumps) {
|
|
112034
112415
|
const filteredBumps = bumps.filter((b) => b.ids.length > 0);
|
|
@@ -112066,14 +112447,10 @@ async function bumpCountersBatch(directory, bumps) {
|
|
|
112066
112447
|
return updated;
|
|
112067
112448
|
};
|
|
112068
112449
|
const swarmPath = resolveSwarmKnowledgePath(directory);
|
|
112069
|
-
|
|
112070
|
-
if (applyOne(swarm))
|
|
112071
|
-
await rewriteKnowledge(swarmPath, swarm);
|
|
112450
|
+
await transactKnowledge(swarmPath, (swarm) => applyOne(swarm) ? swarm : null);
|
|
112072
112451
|
const hivePath = resolveHiveKnowledgePath();
|
|
112073
112452
|
if (existsSync69(hivePath)) {
|
|
112074
|
-
|
|
112075
|
-
if (applyOne(hive))
|
|
112076
|
-
await rewriteKnowledge(hivePath, hive);
|
|
112453
|
+
await transactKnowledge(hivePath, (hive) => applyOne(hive) ? hive : null);
|
|
112077
112454
|
}
|
|
112078
112455
|
}
|
|
112079
112456
|
async function bumpCounters(directory, ids, field) {
|
|
@@ -112143,7 +112520,7 @@ init_knowledge_events();
|
|
|
112143
112520
|
// src/hooks/knowledge-injector.ts
|
|
112144
112521
|
init_schema();
|
|
112145
112522
|
init_manager();
|
|
112146
|
-
import { createHash as
|
|
112523
|
+
import { createHash as createHash12 } from "node:crypto";
|
|
112147
112524
|
|
|
112148
112525
|
// src/services/run-memory.ts
|
|
112149
112526
|
import * as crypto11 from "node:crypto";
|
|
@@ -112320,6 +112697,7 @@ init_extractors();
|
|
|
112320
112697
|
init_knowledge_escalator();
|
|
112321
112698
|
init_knowledge_events();
|
|
112322
112699
|
init_knowledge_store();
|
|
112700
|
+
init_model_limits();
|
|
112323
112701
|
init_search_knowledge();
|
|
112324
112702
|
init_utils2();
|
|
112325
112703
|
var INJECTION_SENTINEL = `${String.fromCharCode(8204)}[[KNOWLEDGE-INJECTED]]`;
|
|
@@ -112636,7 +113014,7 @@ function injectKnowledgeMessage(output, text) {
|
|
|
112636
113014
|
};
|
|
112637
113015
|
output.messages.splice(insertIdx, 0, knowledgeMessage);
|
|
112638
113016
|
}
|
|
112639
|
-
function createKnowledgeInjectorHook(directory, config3) {
|
|
113017
|
+
function createKnowledgeInjectorHook(directory, config3, modelLimitOverrides = {}) {
|
|
112640
113018
|
function buildContextCacheKey(phase, ctx) {
|
|
112641
113019
|
const parts2 = [
|
|
112642
113020
|
String(phase),
|
|
@@ -112646,7 +113024,7 @@ function createKnowledgeInjectorHook(directory, config3) {
|
|
|
112646
113024
|
ctx.taskId ?? "",
|
|
112647
113025
|
(ctx.filePaths ?? []).slice(0, 8).join(",")
|
|
112648
113026
|
].join("|");
|
|
112649
|
-
return
|
|
113027
|
+
return createHash12("sha1").update(parts2).digest("hex").slice(0, 16);
|
|
112650
113028
|
}
|
|
112651
113029
|
let lastSeenCacheKey = null;
|
|
112652
113030
|
let cachedInjectionText = null;
|
|
@@ -112657,7 +113035,9 @@ function createKnowledgeInjectorHook(directory, config3) {
|
|
|
112657
113035
|
const plan = await loadPlan(directory);
|
|
112658
113036
|
const currentPhase = plan?.current_phase ?? 1;
|
|
112659
113037
|
const CHARS_PER_TOKEN = 1 / 0.33;
|
|
112660
|
-
const
|
|
113038
|
+
const { modelID, providerID } = extractModelInfo(output.messages);
|
|
113039
|
+
const modelLimitTokens = resolveModelLimit(modelID, providerID, modelLimitOverrides);
|
|
113040
|
+
const MODEL_LIMIT_CHARS = Math.floor(modelLimitTokens * CHARS_PER_TOKEN);
|
|
112661
113041
|
const existingChars = output.messages.reduce((sum, msg) => {
|
|
112662
113042
|
return sum + (msg.parts?.reduce((s, p) => s + (p.text?.length ?? 0), 0) ?? 0);
|
|
112663
113043
|
}, 0);
|
|
@@ -115897,8 +116277,8 @@ async function cleanupOldTrajectoryFiles(directory, maxAgeDays = 7) {
|
|
|
115897
116277
|
continue;
|
|
115898
116278
|
const filePath = path131.join(dirPath, entry.name);
|
|
115899
116279
|
try {
|
|
115900
|
-
const
|
|
115901
|
-
if (now -
|
|
116280
|
+
const stat11 = await fs81.stat(filePath);
|
|
116281
|
+
if (now - stat11.mtimeMs > cutoffMs) {
|
|
115902
116282
|
await fs81.unlink(filePath);
|
|
115903
116283
|
}
|
|
115904
116284
|
} catch {}
|
|
@@ -118764,8 +119144,8 @@ function estimateCyclomaticComplexity(content) {
|
|
|
118764
119144
|
}
|
|
118765
119145
|
function getComplexityForFile(filePath) {
|
|
118766
119146
|
try {
|
|
118767
|
-
const
|
|
118768
|
-
if (
|
|
119147
|
+
const stat11 = fs87.statSync(filePath);
|
|
119148
|
+
if (stat11.size > MAX_FILE_SIZE_BYTES4) {
|
|
118769
119149
|
return null;
|
|
118770
119150
|
}
|
|
118771
119151
|
const content = fs87.readFileSync(filePath, "utf-8");
|
|
@@ -118966,8 +119346,8 @@ async function computeDuplicationRatio(files, workingDir) {
|
|
|
118966
119346
|
continue;
|
|
118967
119347
|
}
|
|
118968
119348
|
try {
|
|
118969
|
-
const
|
|
118970
|
-
if (
|
|
119349
|
+
const stat11 = fs87.statSync(fullPath);
|
|
119350
|
+
if (stat11.size > MAX_FILE_SIZE_BYTES4) {
|
|
118971
119351
|
continue;
|
|
118972
119352
|
}
|
|
118973
119353
|
const content = fs87.readFileSync(fullPath, "utf-8");
|
|
@@ -119427,8 +119807,8 @@ async function getGitChurn(days, directory) {
|
|
|
119427
119807
|
}
|
|
119428
119808
|
function getComplexityForFile2(filePath) {
|
|
119429
119809
|
try {
|
|
119430
|
-
const
|
|
119431
|
-
if (
|
|
119810
|
+
const stat11 = fs88.statSync(filePath);
|
|
119811
|
+
if (stat11.size > MAX_FILE_SIZE_BYTES5) {
|
|
119432
119812
|
return null;
|
|
119433
119813
|
}
|
|
119434
119814
|
const content = fs88.readFileSync(filePath, "utf-8");
|
|
@@ -121897,8 +122277,8 @@ function readEvidenceFiles(evidenceDir, _cwd) {
|
|
|
121897
122277
|
if (!resolvedPath.startsWith(evidenceDirResolved)) {
|
|
121898
122278
|
continue;
|
|
121899
122279
|
}
|
|
121900
|
-
const
|
|
121901
|
-
if (!
|
|
122280
|
+
const stat11 = fs93.lstatSync(filePath);
|
|
122281
|
+
if (!stat11.isFile()) {
|
|
121902
122282
|
continue;
|
|
121903
122283
|
}
|
|
121904
122284
|
} catch {
|
|
@@ -122320,11 +122700,11 @@ var external_skill_delete = createSwarmTool({
|
|
|
122320
122700
|
// src/tools/external-skill-discover.ts
|
|
122321
122701
|
init_zod();
|
|
122322
122702
|
init_loader();
|
|
122323
|
-
import { createHash as
|
|
122703
|
+
import { createHash as createHash14, randomUUID as randomUUID13 } from "node:crypto";
|
|
122324
122704
|
|
|
122325
122705
|
// src/services/external-skill-validator.ts
|
|
122326
122706
|
init_knowledge_validator();
|
|
122327
|
-
import { createHash as
|
|
122707
|
+
import { createHash as createHash13 } from "node:crypto";
|
|
122328
122708
|
var PROMPT_INJECTION_PATTERNS = [
|
|
122329
122709
|
{
|
|
122330
122710
|
pattern: /system\s*:/i,
|
|
@@ -122458,31 +122838,31 @@ var UNSAFE_INSTRUCTION_PATTERNS = [
|
|
|
122458
122838
|
pattern: /\bkill\s+-9\b/,
|
|
122459
122839
|
name: "force_kill",
|
|
122460
122840
|
description: "Force process termination",
|
|
122461
|
-
severity: "
|
|
122841
|
+
severity: "warning"
|
|
122462
122842
|
},
|
|
122463
122843
|
{
|
|
122464
122844
|
pattern: /\bpkill\b/,
|
|
122465
122845
|
name: "process_group_kill",
|
|
122466
122846
|
description: "Process group kill",
|
|
122467
|
-
severity: "
|
|
122847
|
+
severity: "warning"
|
|
122468
122848
|
},
|
|
122469
122849
|
{
|
|
122470
122850
|
pattern: /\bkillall\b/,
|
|
122471
122851
|
name: "kill_all_processes",
|
|
122472
122852
|
description: "Kill all processes by name",
|
|
122473
|
-
severity: "
|
|
122853
|
+
severity: "warning"
|
|
122474
122854
|
},
|
|
122475
122855
|
{
|
|
122476
122856
|
pattern: /`[^`]*`/,
|
|
122477
122857
|
name: "backtick_execution",
|
|
122478
122858
|
description: "Backtick shell execution",
|
|
122479
|
-
severity: "
|
|
122859
|
+
severity: "warning"
|
|
122480
122860
|
},
|
|
122481
122861
|
{
|
|
122482
122862
|
pattern: /\$\([^)]*\)/,
|
|
122483
122863
|
name: "shell_substitution",
|
|
122484
122864
|
description: "Shell command substitution",
|
|
122485
|
-
severity: "
|
|
122865
|
+
severity: "warning"
|
|
122486
122866
|
},
|
|
122487
122867
|
{
|
|
122488
122868
|
pattern: /disable\s+.{0,50}firewall/i,
|
|
@@ -122617,6 +122997,9 @@ function scanInvisibleFormatChars(text, fieldName) {
|
|
|
122617
122997
|
}
|
|
122618
122998
|
return findings;
|
|
122619
122999
|
}
|
|
123000
|
+
function stripMarkdownCodeForUnsafeScan(text) {
|
|
123001
|
+
return text.replace(/```[\s\S]*?```/g, " ").replace(/~~~[\s\S]*?~~~/g, " ").replace(/`[^`\n]*`/g, " ");
|
|
123002
|
+
}
|
|
122620
123003
|
function scanPromptInjection(candidate, trustLevel = "low") {
|
|
122621
123004
|
const fields = extractCandidateFields(candidate);
|
|
122622
123005
|
const findings = [];
|
|
@@ -122683,8 +123066,9 @@ function scanUnsafeInstructions(candidate, trustLevel = "low") {
|
|
|
122683
123066
|
const fieldsScanned = [];
|
|
122684
123067
|
for (const { field, value } of fields) {
|
|
122685
123068
|
fieldsScanned.push(field);
|
|
123069
|
+
const scanValue = field === "skill_body" ? stripMarkdownCodeForUnsafeScan(value) : value;
|
|
122686
123070
|
for (const entry of UNSAFE_INSTRUCTION_PATTERNS) {
|
|
122687
|
-
const match = entry.pattern.exec(
|
|
123071
|
+
const match = entry.pattern.exec(scanValue);
|
|
122688
123072
|
if (match !== null) {
|
|
122689
123073
|
findings.push({
|
|
122690
123074
|
pattern: entry.name,
|
|
@@ -122855,7 +123239,8 @@ function evaluateCandidate(candidate, options) {
|
|
|
122855
123239
|
}
|
|
122856
123240
|
var _internals78 = {
|
|
122857
123241
|
getTimestamp: () => new Date().toISOString(),
|
|
122858
|
-
computeSha256: (content) =>
|
|
123242
|
+
computeSha256: (content) => createHash13("sha256").update(content).digest("hex"),
|
|
123243
|
+
stripMarkdownCodeForUnsafeScan
|
|
122859
123244
|
};
|
|
122860
123245
|
|
|
122861
123246
|
// src/tools/external-skill-discover.ts
|
|
@@ -122876,7 +123261,7 @@ var _internals79 = {
|
|
|
122876
123261
|
return { content, finalUrl: response.url };
|
|
122877
123262
|
},
|
|
122878
123263
|
getTimestamp: () => new Date().toISOString(),
|
|
122879
|
-
computeSha256: (content) =>
|
|
123264
|
+
computeSha256: (content) => createHash14("sha256").update(content).digest("hex"),
|
|
122880
123265
|
uuid: () => randomUUID13()
|
|
122881
123266
|
};
|
|
122882
123267
|
var SOURCE_TRUST_LEVELS = {
|
|
@@ -123262,7 +123647,7 @@ var external_skill_list = createSwarmTool({
|
|
|
123262
123647
|
// src/tools/external-skill-promote.ts
|
|
123263
123648
|
init_zod();
|
|
123264
123649
|
init_loader();
|
|
123265
|
-
import { createHash as
|
|
123650
|
+
import { createHash as createHash15 } from "node:crypto";
|
|
123266
123651
|
import * as fs95 from "node:fs/promises";
|
|
123267
123652
|
import * as path146 from "node:path";
|
|
123268
123653
|
init_create_tool();
|
|
@@ -123427,7 +123812,7 @@ var external_skill_promote = createSwarmTool({
|
|
|
123427
123812
|
}
|
|
123428
123813
|
throw writeErr;
|
|
123429
123814
|
}
|
|
123430
|
-
const promotedContentHash =
|
|
123815
|
+
const promotedContentHash = createHash15("sha256").update(skillMarkdown).digest("hex");
|
|
123431
123816
|
const prePromotionHistory = candidate.evaluation_history;
|
|
123432
123817
|
const lastPrePromotionEntry = prePromotionHistory.length > 0 ? prePromotionHistory[prePromotionHistory.length - 1] : undefined;
|
|
123433
123818
|
const originalEvaluation = lastPrePromotionEntry ? {
|
|
@@ -124396,8 +124781,8 @@ var git_blame = createSwarmTool({
|
|
|
124396
124781
|
lines: []
|
|
124397
124782
|
});
|
|
124398
124783
|
}
|
|
124399
|
-
const
|
|
124400
|
-
if (
|
|
124784
|
+
const stat11 = fs97.statSync(resolvedPath);
|
|
124785
|
+
if (stat11.isDirectory()) {
|
|
124401
124786
|
return JSON.stringify({
|
|
124402
124787
|
error: "path is a directory, not a file",
|
|
124403
124788
|
file: file3,
|
|
@@ -124784,9 +125169,9 @@ function findSourceFiles3(dir, files = [], stats = { skippedDirs: [], skippedFil
|
|
|
124784
125169
|
continue;
|
|
124785
125170
|
}
|
|
124786
125171
|
const fullPath = path150.join(dir, entry);
|
|
124787
|
-
let
|
|
125172
|
+
let stat11;
|
|
124788
125173
|
try {
|
|
124789
|
-
|
|
125174
|
+
stat11 = fs98.statSync(fullPath);
|
|
124790
125175
|
} catch (e) {
|
|
124791
125176
|
stats.fileErrors.push({
|
|
124792
125177
|
path: fullPath,
|
|
@@ -124794,9 +125179,9 @@ function findSourceFiles3(dir, files = [], stats = { skippedDirs: [], skippedFil
|
|
|
124794
125179
|
});
|
|
124795
125180
|
continue;
|
|
124796
125181
|
}
|
|
124797
|
-
if (
|
|
125182
|
+
if (stat11.isDirectory()) {
|
|
124798
125183
|
findSourceFiles3(fullPath, files, stats);
|
|
124799
|
-
} else if (
|
|
125184
|
+
} else if (stat11.isFile()) {
|
|
124800
125185
|
const ext = path150.extname(fullPath).toLowerCase();
|
|
124801
125186
|
if (SUPPORTED_EXTENSIONS3.includes(ext)) {
|
|
124802
125187
|
files.push(fullPath);
|
|
@@ -124891,8 +125276,8 @@ var imports = createSwarmTool({
|
|
|
124891
125276
|
if (consumers.length >= MAX_CONSUMERS)
|
|
124892
125277
|
break;
|
|
124893
125278
|
try {
|
|
124894
|
-
const
|
|
124895
|
-
if (
|
|
125279
|
+
const stat11 = fs98.statSync(filePath);
|
|
125280
|
+
if (stat11.size > MAX_FILE_SIZE_BYTES7) {
|
|
124896
125281
|
skippedFileCount++;
|
|
124897
125282
|
continue;
|
|
124898
125283
|
}
|
|
@@ -125254,10 +125639,12 @@ init_knowledge_store();
|
|
|
125254
125639
|
init_logger();
|
|
125255
125640
|
init_create_tool();
|
|
125256
125641
|
var MODES2 = ["archive", "quarantine", "purge"];
|
|
125642
|
+
var TIERS = ["swarm", "hive"];
|
|
125257
125643
|
var knowledge_archive = createSwarmTool({
|
|
125258
|
-
description: "Archive (default), quarantine, or purge a swarm knowledge entry by ID, appending an immutable audit tombstone. 'archive'/'quarantine' set the entry status reversibly and hide it from recall; 'purge' hard-deletes and requires allow_purge:true.",
|
|
125644
|
+
description: "Archive (default), quarantine, or purge a swarm or hive knowledge entry by ID, appending an immutable audit tombstone. 'archive'/'quarantine' set the entry status reversibly and hide it from recall; 'purge' hard-deletes and requires allow_purge:true.",
|
|
125259
125645
|
args: {
|
|
125260
125646
|
id: exports_external.string().min(1).describe("UUID of the knowledge entry"),
|
|
125647
|
+
tier: exports_external.enum(TIERS).optional().describe("Knowledge tier to modify; default 'swarm'"),
|
|
125261
125648
|
reason: exports_external.string().min(1).max(500).describe("Why the entry is being archived/quarantined/purged"),
|
|
125262
125649
|
evidence: exports_external.string().max(1000).optional().describe('Supporting evidence (e.g. "ignored 8 times, contradicted by tests")'),
|
|
125263
125650
|
mode: exports_external.enum(MODES2).optional().describe("Default 'archive'"),
|
|
@@ -125280,6 +125667,7 @@ var knowledge_archive = createSwarmTool({
|
|
|
125280
125667
|
});
|
|
125281
125668
|
}
|
|
125282
125669
|
const evidence = typeof a.evidence === "string" ? a.evidence : undefined;
|
|
125670
|
+
const tier = a.tier === "hive" ? "hive" : "swarm";
|
|
125283
125671
|
const mode = a.mode === "quarantine" || a.mode === "purge" ? a.mode : "archive";
|
|
125284
125672
|
if (mode === "purge" && a.allow_purge !== true) {
|
|
125285
125673
|
return JSON.stringify({
|
|
@@ -125287,44 +125675,40 @@ var knowledge_archive = createSwarmTool({
|
|
|
125287
125675
|
error: "purge requires allow_purge:true (admin flag)"
|
|
125288
125676
|
});
|
|
125289
125677
|
}
|
|
125290
|
-
const
|
|
125291
|
-
let
|
|
125292
|
-
|
|
125293
|
-
entries = await readKnowledge(swarmPath);
|
|
125294
|
-
} catch (err2) {
|
|
125295
|
-
return JSON.stringify({
|
|
125296
|
-
success: false,
|
|
125297
|
-
error: err2 instanceof Error ? err2.message : "Unknown error"
|
|
125298
|
-
});
|
|
125299
|
-
}
|
|
125300
|
-
const target = entries.find((e) => e.id === id);
|
|
125301
|
-
if (!target) {
|
|
125302
|
-
return JSON.stringify({ success: false, message: "entry not found" });
|
|
125303
|
-
}
|
|
125304
|
-
const previousStatus = target.status;
|
|
125678
|
+
const knowledgePath = tier === "hive" ? resolveHiveKnowledgePath() : resolveSwarmKnowledgePath(directory);
|
|
125679
|
+
let found = false;
|
|
125680
|
+
let previousStatus;
|
|
125305
125681
|
const now = new Date().toISOString();
|
|
125306
|
-
let nextEntries;
|
|
125307
125682
|
let resultStatus;
|
|
125308
|
-
if (mode === "purge") {
|
|
125309
|
-
warn(`[knowledge_archive] PURGE: hard-deleting entry id=${id} actor=${ctx?.agent ?? "unknown"} reason=${reason}`);
|
|
125310
|
-
nextEntries = entries.filter((e) => e.id !== id);
|
|
125311
|
-
resultStatus = "purged";
|
|
125312
|
-
} else {
|
|
125313
|
-
const newStatus = mode === "quarantine" ? "quarantined" : "archived";
|
|
125314
|
-
nextEntries = entries.map((e) => e.id === id ? { ...e, status: newStatus, updated_at: now } : e);
|
|
125315
|
-
resultStatus = newStatus;
|
|
125316
|
-
}
|
|
125317
125683
|
try {
|
|
125318
|
-
await
|
|
125684
|
+
await transactKnowledge(knowledgePath, (entries) => {
|
|
125685
|
+
const target = entries.find((e) => e.id === id);
|
|
125686
|
+
if (!target)
|
|
125687
|
+
return null;
|
|
125688
|
+
found = true;
|
|
125689
|
+
previousStatus = target.status;
|
|
125690
|
+
if (mode === "purge") {
|
|
125691
|
+
warn(`[knowledge_archive] PURGE: hard-deleting ${tier} entry id=${id} actor=${ctx?.agent ?? "unknown"} reason=${reason}`);
|
|
125692
|
+
resultStatus = "purged";
|
|
125693
|
+
return entries.filter((e) => e.id !== id);
|
|
125694
|
+
}
|
|
125695
|
+
const newStatus = mode === "quarantine" ? "quarantined" : "archived";
|
|
125696
|
+
resultStatus = newStatus;
|
|
125697
|
+
return entries.map((e) => e.id === id ? { ...e, status: newStatus, updated_at: now } : e);
|
|
125698
|
+
});
|
|
125319
125699
|
} catch (err2) {
|
|
125320
125700
|
return JSON.stringify({
|
|
125321
125701
|
success: false,
|
|
125322
125702
|
error: err2 instanceof Error ? err2.message : "Unknown error"
|
|
125323
125703
|
});
|
|
125324
125704
|
}
|
|
125705
|
+
if (!found) {
|
|
125706
|
+
return JSON.stringify({ success: false, message: "entry not found" });
|
|
125707
|
+
}
|
|
125325
125708
|
await recordKnowledgeEvent(directory, {
|
|
125326
125709
|
type: "archived",
|
|
125327
125710
|
entry_id: id,
|
|
125711
|
+
tier,
|
|
125328
125712
|
actor: ctx?.agent ?? "unknown",
|
|
125329
125713
|
reason,
|
|
125330
125714
|
mode,
|
|
@@ -125334,6 +125718,7 @@ var knowledge_archive = createSwarmTool({
|
|
|
125334
125718
|
return JSON.stringify({
|
|
125335
125719
|
success: true,
|
|
125336
125720
|
id,
|
|
125721
|
+
tier,
|
|
125337
125722
|
mode,
|
|
125338
125723
|
previous_status: previousStatus,
|
|
125339
125724
|
status: resultStatus
|
|
@@ -130304,12 +130689,11 @@ async function executePhaseComplete(args2, workingDirectory, directory) {
|
|
|
130304
130689
|
if (retroFound && retroEntry?.lessons_learned && retroEntry.lessons_learned.length > 0) {
|
|
130305
130690
|
try {
|
|
130306
130691
|
const projectName = path166.basename(dir);
|
|
130307
|
-
const skillImproverCfg = SkillImproverConfigSchema.parse(config3.skill_improver ?? {});
|
|
130308
130692
|
const curationResult = await curateAndStoreSwarm(retroEntry.lessons_learned, projectName, { phase_number: phase }, dir, knowledgeConfig, {
|
|
130309
130693
|
llmDelegate: createCuratorLLMDelegate(dir, "phase", sessionID),
|
|
130310
130694
|
enrichmentQuota: {
|
|
130311
|
-
maxCalls:
|
|
130312
|
-
window:
|
|
130695
|
+
maxCalls: knowledgeConfig.enrichment.max_calls_per_day,
|
|
130696
|
+
window: knowledgeConfig.enrichment.quota_window
|
|
130313
130697
|
}
|
|
130314
130698
|
});
|
|
130315
130699
|
if (curationResult) {
|
|
@@ -132410,8 +132794,8 @@ async function placeholderScan(input, directory) {
|
|
|
132410
132794
|
}
|
|
132411
132795
|
let content;
|
|
132412
132796
|
try {
|
|
132413
|
-
const
|
|
132414
|
-
if (
|
|
132797
|
+
const stat11 = fs115.statSync(fullPath);
|
|
132798
|
+
if (stat11.size > MAX_FILE_SIZE) {
|
|
132415
132799
|
continue;
|
|
132416
132800
|
}
|
|
132417
132801
|
content = fs115.readFileSync(fullPath, "utf-8");
|
|
@@ -134592,14 +134976,14 @@ async function runSecretscanWithFiles(files, directory) {
|
|
|
134592
134976
|
skippedFiles++;
|
|
134593
134977
|
continue;
|
|
134594
134978
|
}
|
|
134595
|
-
let
|
|
134979
|
+
let stat11;
|
|
134596
134980
|
try {
|
|
134597
|
-
|
|
134981
|
+
stat11 = fs119.statSync(file3);
|
|
134598
134982
|
} catch {
|
|
134599
134983
|
skippedFiles++;
|
|
134600
134984
|
continue;
|
|
134601
134985
|
}
|
|
134602
|
-
if (
|
|
134986
|
+
if (stat11.size > MAX_FILE_SIZE_BYTES9) {
|
|
134603
134987
|
skippedFiles++;
|
|
134604
134988
|
continue;
|
|
134605
134989
|
}
|
|
@@ -135378,8 +135762,8 @@ function readTouchedFiles(evidenceDir, phase, cwd) {
|
|
|
135378
135762
|
for (const entry of entries) {
|
|
135379
135763
|
const entryPath = path174.join(evidenceDir, entry);
|
|
135380
135764
|
try {
|
|
135381
|
-
const
|
|
135382
|
-
if (!
|
|
135765
|
+
const stat11 = fs120.statSync(entryPath);
|
|
135766
|
+
if (!stat11.isDirectory()) {
|
|
135383
135767
|
continue;
|
|
135384
135768
|
}
|
|
135385
135769
|
} catch {
|
|
@@ -135399,11 +135783,11 @@ function readTouchedFiles(evidenceDir, phase, cwd) {
|
|
|
135399
135783
|
if (!resolvedPath.startsWith(evidenceDirResolved + path174.sep)) {
|
|
135400
135784
|
continue;
|
|
135401
135785
|
}
|
|
135402
|
-
const
|
|
135403
|
-
if (!
|
|
135786
|
+
const stat11 = fs120.lstatSync(evidenceFilePath);
|
|
135787
|
+
if (!stat11.isFile()) {
|
|
135404
135788
|
continue;
|
|
135405
135789
|
}
|
|
135406
|
-
if (
|
|
135790
|
+
if (stat11.size > MAX_FILE_SIZE_BYTES9) {
|
|
135407
135791
|
continue;
|
|
135408
135792
|
}
|
|
135409
135793
|
} catch {
|
|
@@ -138154,6 +138538,11 @@ var skill_improve = createSwarmTool({
|
|
|
138154
138538
|
const a = args2 ?? {};
|
|
138155
138539
|
const { config: config3 } = loadPluginConfigWithMeta(directory);
|
|
138156
138540
|
const parsed = SkillImproverConfigSchema.parse(config3.skill_improver ?? {});
|
|
138541
|
+
const knowledgeConfig = KnowledgeConfigSchema.parse(config3.knowledge ?? {});
|
|
138542
|
+
const enrichmentConfig = knowledgeConfig.enrichment ?? {
|
|
138543
|
+
max_calls_per_day: 30,
|
|
138544
|
+
quota_window: "utc"
|
|
138545
|
+
};
|
|
138157
138546
|
if (!parsed.enabled) {
|
|
138158
138547
|
return JSON.stringify({
|
|
138159
138548
|
ran: false,
|
|
@@ -138166,7 +138555,11 @@ var skill_improve = createSwarmTool({
|
|
|
138166
138555
|
targets: a.targets,
|
|
138167
138556
|
mode: a.mode,
|
|
138168
138557
|
maxCalls: a.max_calls,
|
|
138169
|
-
sessionId: ctx?.sessionID
|
|
138558
|
+
sessionId: ctx?.sessionID,
|
|
138559
|
+
enrichmentQuota: {
|
|
138560
|
+
maxCalls: enrichmentConfig.max_calls_per_day,
|
|
138561
|
+
window: enrichmentConfig.quota_window
|
|
138562
|
+
}
|
|
138170
138563
|
});
|
|
138171
138564
|
return JSON.stringify(result, null, 2);
|
|
138172
138565
|
}
|
|
@@ -138248,7 +138641,7 @@ init_zod();
|
|
|
138248
138641
|
init_config();
|
|
138249
138642
|
init_schema();
|
|
138250
138643
|
init_create_tool();
|
|
138251
|
-
import { mkdir as mkdir30, rename as rename12, writeFile as
|
|
138644
|
+
import { mkdir as mkdir30, rename as rename12, writeFile as writeFile21 } from "node:fs/promises";
|
|
138252
138645
|
import * as path179 from "node:path";
|
|
138253
138646
|
var MAX_SPEC_BYTES2 = 256 * 1024;
|
|
138254
138647
|
var spec_write = createSwarmTool({
|
|
@@ -138310,7 +138703,7 @@ ${content}
|
|
|
138310
138703
|
}
|
|
138311
138704
|
} catch {}
|
|
138312
138705
|
}
|
|
138313
|
-
await
|
|
138706
|
+
await writeFile21(tmp, finalContent, "utf-8");
|
|
138314
138707
|
await rename12(tmp, target);
|
|
138315
138708
|
return JSON.stringify({ written: true, path: target, bytes: finalContent.length }, null, 2);
|
|
138316
138709
|
}
|
|
@@ -139529,8 +139922,8 @@ async function syntaxCheck(input, directory, config3) {
|
|
|
139529
139922
|
return { result, counted: false, failed: false, skipped: true };
|
|
139530
139923
|
}
|
|
139531
139924
|
try {
|
|
139532
|
-
const
|
|
139533
|
-
if (
|
|
139925
|
+
const stat11 = fs126.statSync(fullPath);
|
|
139926
|
+
if (stat11.size >= MAX_FILE_SIZE2) {
|
|
139534
139927
|
result.skipped_reason = "file_too_large";
|
|
139535
139928
|
return { result, counted: false, failed: false, skipped: true };
|
|
139536
139929
|
}
|
|
@@ -139762,15 +140155,15 @@ function findSourceFiles4(dir, files = []) {
|
|
|
139762
140155
|
continue;
|
|
139763
140156
|
}
|
|
139764
140157
|
const fullPath = path183.join(dir, entry);
|
|
139765
|
-
let
|
|
140158
|
+
let stat11;
|
|
139766
140159
|
try {
|
|
139767
|
-
|
|
140160
|
+
stat11 = fs127.statSync(fullPath);
|
|
139768
140161
|
} catch {
|
|
139769
140162
|
continue;
|
|
139770
140163
|
}
|
|
139771
|
-
if (
|
|
140164
|
+
if (stat11.isDirectory()) {
|
|
139772
140165
|
findSourceFiles4(fullPath, files);
|
|
139773
|
-
} else if (
|
|
140166
|
+
} else if (stat11.isFile()) {
|
|
139774
140167
|
if (isSupportedExtension(fullPath)) {
|
|
139775
140168
|
files.push(fullPath);
|
|
139776
140169
|
}
|
|
@@ -139867,8 +140260,8 @@ var todo_extract = createSwarmTool({
|
|
|
139867
140260
|
return JSON.stringify(errorResult, null, 2);
|
|
139868
140261
|
}
|
|
139869
140262
|
const filesToScan = [];
|
|
139870
|
-
const
|
|
139871
|
-
if (
|
|
140263
|
+
const stat11 = fs127.statSync(scanPath);
|
|
140264
|
+
if (stat11.isFile()) {
|
|
139872
140265
|
if (isSupportedExtension(scanPath)) {
|
|
139873
140266
|
filesToScan.push(scanPath);
|
|
139874
140267
|
} else {
|
|
@@ -140988,7 +141381,7 @@ import * as zlib from "node:zlib";
|
|
|
140988
141381
|
// src/evidence/documents.ts
|
|
140989
141382
|
init_utils2();
|
|
140990
141383
|
init_redaction();
|
|
140991
|
-
import { createHash as
|
|
141384
|
+
import { createHash as createHash17 } from "node:crypto";
|
|
140992
141385
|
import { appendFile as appendFile17, mkdir as mkdir31 } from "node:fs/promises";
|
|
140993
141386
|
import * as path188 from "node:path";
|
|
140994
141387
|
var EVIDENCE_CACHE_FILE = "evidence-cache/documents.jsonl";
|
|
@@ -141032,7 +141425,7 @@ function createEvidenceDocumentRecord(input, defaultCapturedAt) {
|
|
|
141032
141425
|
};
|
|
141033
141426
|
}
|
|
141034
141427
|
function createEvidenceDocumentId(input) {
|
|
141035
|
-
const hash4 =
|
|
141428
|
+
const hash4 = createHash17("sha256").update([
|
|
141036
141429
|
input.sourceType,
|
|
141037
141430
|
input.query ?? "",
|
|
141038
141431
|
input.title ?? "",
|
|
@@ -142082,13 +142475,12 @@ var write_architecture_supervisor_evidence = createSwarmTool({
|
|
|
142082
142475
|
if (config3.architectural_supervision?.persist_knowledge_recommendations && args2.knowledge_recommendations.length > 0) {
|
|
142083
142476
|
const knowledgeConfig = KnowledgeConfigSchema.parse(config3.knowledge ?? {});
|
|
142084
142477
|
const lessons = args2.knowledge_recommendations.map((r) => r.lesson);
|
|
142085
|
-
const skillImproverCfg = SkillImproverConfigSchema.parse(config3.skill_improver ?? {});
|
|
142086
142478
|
const result = await curateAndStoreSwarm(lessons, path189.basename(dirResult.directory), { phase_number: args2.phase }, dirResult.directory, knowledgeConfig, {
|
|
142087
142479
|
skipAutoPromotion: true,
|
|
142088
142480
|
llmDelegate: createCuratorLLMDelegate(dirResult.directory, "phase"),
|
|
142089
142481
|
enrichmentQuota: {
|
|
142090
|
-
maxCalls:
|
|
142091
|
-
window:
|
|
142482
|
+
maxCalls: knowledgeConfig.enrichment.max_calls_per_day,
|
|
142483
|
+
window: knowledgeConfig.enrichment.quota_window
|
|
142092
142484
|
}
|
|
142093
142485
|
});
|
|
142094
142486
|
knowledgeProposed = result.stored;
|
|
@@ -143105,11 +143497,16 @@ async function initializeOpenCodeSwarm(ctx) {
|
|
|
143105
143497
|
const summaryConfig = SummaryConfigSchema.parse(config3.summaries ?? {});
|
|
143106
143498
|
const toolSummarizerHook = createToolSummarizerHook(summaryConfig, ctx.directory);
|
|
143107
143499
|
const knowledgeConfig = KnowledgeConfigSchema.parse(config3.knowledge ?? {});
|
|
143108
|
-
const skillImproverConfig = SkillImproverConfigSchema.parse(config3.skill_improver ?? {});
|
|
143109
143500
|
const skillPropagationConfig = SkillPropagationConfigSchema.parse(config3.skillPropagation ?? {});
|
|
143110
|
-
const knowledgeCuratorHook = knowledgeConfig.enabled ? createKnowledgeCuratorHook(ctx.directory, knowledgeConfig
|
|
143501
|
+
const knowledgeCuratorHook = knowledgeConfig.enabled ? createKnowledgeCuratorHook(ctx.directory, knowledgeConfig, {
|
|
143502
|
+
llmDelegateFactory: (sessionID) => createCuratorLLMDelegate(ctx.directory, "phase", sessionID),
|
|
143503
|
+
enrichmentQuota: {
|
|
143504
|
+
maxCalls: knowledgeConfig.enrichment.max_calls_per_day,
|
|
143505
|
+
window: knowledgeConfig.enrichment.quota_window
|
|
143506
|
+
}
|
|
143507
|
+
}) : undefined;
|
|
143111
143508
|
const hivePromoterHook = knowledgeConfig.enabled && knowledgeConfig.hive_enabled ? createHivePromoterHook(ctx.directory, knowledgeConfig) : undefined;
|
|
143112
|
-
const knowledgeInjectorHook = knowledgeConfig.enabled ? createKnowledgeInjectorHook(ctx.directory, knowledgeConfig) : undefined;
|
|
143509
|
+
const knowledgeInjectorHook = knowledgeConfig.enabled ? createKnowledgeInjectorHook(ctx.directory, knowledgeConfig, config3.context_budget?.model_limits ?? {}) : undefined;
|
|
143113
143510
|
const steeringConsumedHook = createSteeringConsumedHook(ctx.directory);
|
|
143114
143511
|
const coChangeSuggesterHook = createCoChangeSuggesterHook(ctx.directory);
|
|
143115
143512
|
const darkMatterDetectorHook = createDarkMatterDetectorHook(ctx.directory);
|
|
@@ -143836,8 +144233,8 @@ ${usedByCoderLine}`;
|
|
|
143836
144233
|
await safeHook(() => collectDelegateAcksAfter(ctx.directory, input, output))(input, output);
|
|
143837
144234
|
await safeHook(() => collectReviewerVerdictsAfter(ctx.directory, input, output))(input, output);
|
|
143838
144235
|
await safeHook(() => microReflectorAfter(ctx.directory, input, output, createCuratorLLMDelegate(ctx.directory, "phase", input.sessionID), {
|
|
143839
|
-
maxCalls:
|
|
143840
|
-
window:
|
|
144236
|
+
maxCalls: knowledgeConfig.enrichment.max_calls_per_day,
|
|
144237
|
+
window: knowledgeConfig.enrichment.quota_window
|
|
143841
144238
|
}))(input, output);
|
|
143842
144239
|
}
|
|
143843
144240
|
await safeHook(prmHook.toolAfter)(input, output);
|