@neuroverseos/governance 0.3.0 → 0.3.3
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/.well-known/ai-plugin.json +34 -9
- package/AGENTS.md +72 -24
- package/README.md +352 -237
- package/dist/adapters/autoresearch.cjs +1152 -3
- package/dist/adapters/autoresearch.d.cts +11 -3
- package/dist/adapters/autoresearch.d.ts +11 -3
- package/dist/adapters/autoresearch.js +9 -4
- package/dist/adapters/deep-agents.cjs +1528 -0
- package/dist/adapters/deep-agents.d.cts +181 -0
- package/dist/adapters/deep-agents.d.ts +181 -0
- package/dist/adapters/deep-agents.js +17 -0
- package/dist/adapters/express.cjs +171 -32
- package/dist/adapters/express.d.cts +1 -1
- package/dist/adapters/express.d.ts +1 -1
- package/dist/adapters/express.js +5 -5
- package/dist/adapters/index.cjs +564 -121
- package/dist/adapters/index.d.cts +3 -1
- package/dist/adapters/index.d.ts +3 -1
- package/dist/adapters/index.js +38 -16
- package/dist/adapters/langchain.cjs +217 -57
- package/dist/adapters/langchain.d.cts +5 -5
- package/dist/adapters/langchain.d.ts +5 -5
- package/dist/adapters/langchain.js +6 -5
- package/dist/adapters/openai.cjs +219 -59
- package/dist/adapters/openai.d.cts +5 -5
- package/dist/adapters/openai.d.ts +5 -5
- package/dist/adapters/openai.js +6 -5
- package/dist/adapters/openclaw.cjs +217 -57
- package/dist/adapters/openclaw.d.cts +6 -6
- package/dist/adapters/openclaw.d.ts +6 -6
- package/dist/adapters/openclaw.js +6 -5
- package/dist/add-ROOZLU62.js +314 -0
- package/dist/behavioral-MJO34S6Q.js +118 -0
- package/dist/{bootstrap-GXVDZNF7.js → bootstrap-CQRZVOXK.js} +6 -4
- package/dist/bootstrap-emitter-Q7UIJZ2O.js +7 -0
- package/dist/bootstrap-parser-EEF36XDU.js +7 -0
- package/dist/browser.global.js +941 -0
- package/dist/{build-P42YFKQV.js → build-QKOBBC23.js} +7 -5
- package/dist/{chunk-COT5XS4V.js → chunk-3WQLXYTP.js} +17 -35
- package/dist/{chunk-ER62HNGF.js → chunk-4FLICVVA.js} +17 -37
- package/dist/chunk-5TPFNWRU.js +215 -0
- package/dist/chunk-5U2MQO5P.js +57 -0
- package/dist/{chunk-NF5POFCI.js → chunk-6S5CFQXY.js} +6 -4
- package/dist/{chunk-QPASI2BR.js → chunk-A7GKPPU7.js} +49 -10
- package/dist/{chunk-OGL7QXZS.js → chunk-B6OXJLJ5.js} +17 -3
- package/dist/{chunk-2PQU3VAN.js → chunk-BNKJPUPQ.js} +17 -35
- package/dist/chunk-BQZMOEML.js +43 -0
- package/dist/chunk-CNSO6XW5.js +207 -0
- package/dist/{chunk-JZPQGIKR.js → chunk-CTZHONLA.js} +65 -9
- package/dist/chunk-D2UCV5AK.js +326 -0
- package/dist/{chunk-XPDMYECO.js → chunk-EMQDLDAF.js} +1 -185
- package/dist/{chunk-GR6DGCZ2.js → chunk-F66BVUYB.js} +3 -3
- package/dist/{chunk-2NICNKOM.js → chunk-G7DJ6VOD.js} +5 -4
- package/dist/{chunk-4A7LISES.js → chunk-IS4WUH6Y.js} +45 -6
- package/dist/{chunk-MWDQ4MJB.js → chunk-MH7BT4VH.js} +5 -1
- package/dist/chunk-O5ABKEA7.js +304 -0
- package/dist/chunk-PVTQQS3Y.js +186 -0
- package/dist/{chunk-4QXB6PEO.js → chunk-QLPTHTVB.js} +37 -16
- package/dist/chunk-QWGCMQQD.js +16 -0
- package/dist/{chunk-T5EUJQE5.js → chunk-QXBFT7NI.js} +31 -2
- package/dist/{chunk-PDOZHZWL.js → chunk-TG6SEF24.js} +25 -4
- package/dist/chunk-U6U7EJZL.js +177 -0
- package/dist/{chunk-4JRYGIO7.js → chunk-W7LLXRGY.js} +110 -7
- package/dist/{chunk-BUWWN2NX.js → chunk-ZJTDUCC2.js} +9 -7
- package/dist/{chunk-FYS2CBUW.js → chunk-ZWI3NIXK.js} +10 -0
- package/dist/cli/neuroverse.cjs +5091 -2348
- package/dist/cli/neuroverse.js +52 -21
- package/dist/cli/plan.cjs +881 -41
- package/dist/cli/plan.js +7 -15
- package/dist/cli/run.cjs +289 -34
- package/dist/cli/run.js +4 -4
- package/dist/{configure-ai-TK67ZWZL.js → configure-ai-6TZ3MCSI.js} +1 -1
- package/dist/decision-flow-M63D47LO.js +61 -0
- package/dist/demo-G43RLCPK.js +469 -0
- package/dist/{derive-TLIV4OOU.js → derive-FJZVIPUZ.js} +5 -4
- package/dist/{doctor-XPDLEYXN.js → doctor-6BC6X2VO.js} +6 -4
- package/dist/equity-penalties-SG5IZQ7I.js +244 -0
- package/dist/{explain-IDCRWMPX.js → explain-RHBU2GBR.js} +6 -25
- package/dist/{guard-RV65TT4L.js → guard-AJCCGZMF.js} +8 -12
- package/dist/{guard-contract-WZx__PmU.d.cts → guard-contract-DqFcTScd.d.cts} +117 -5
- package/dist/{guard-contract-WZx__PmU.d.ts → guard-contract-DqFcTScd.d.ts} +117 -5
- package/dist/{guard-engine-JLTUARGU.js → guard-engine-PNR6MHCM.js} +3 -3
- package/dist/{impact-XPECYRLH.js → impact-3XVDSCBU.js} +5 -5
- package/dist/{improve-GPUBKTEA.js → improve-TQP4ECSY.js} +7 -26
- package/dist/index.cjs +5597 -4279
- package/dist/index.d.cts +597 -18
- package/dist/index.d.ts +597 -18
- package/dist/index.js +134 -41
- package/dist/{infer-world-7GVZWFX4.js → infer-world-IFXCACJ5.js} +1 -1
- package/dist/{init-PKPIYHYE.js → init-FYPV4SST.js} +1 -1
- package/dist/{init-world-VWMQZQC7.js → init-world-TI7ARHBT.js} +1 -1
- package/dist/mcp-server-5Y3ZM7TV.js +13 -0
- package/dist/{model-adapter-BB7G4MFI.js → model-adapter-VXEKB4LS.js} +1 -1
- package/dist/{playground-E664U4T6.js → playground-VZBNPPBO.js} +29 -19
- package/dist/{redteam-Z7WREJ44.js → redteam-MZPZD3EF.js} +4 -4
- package/dist/session-JYOARW54.js +15 -0
- package/dist/shared-7RLUHNMU.js +16 -0
- package/dist/shared-B8dvUUD8.d.cts +60 -0
- package/dist/shared-Dr5Wiay8.d.ts +60 -0
- package/dist/{simulate-VDOYQFRO.js → simulate-LJXYBC6M.js} +8 -33
- package/dist/{test-OGXJK4QU.js → test-BOOR4A5F.js} +4 -4
- package/dist/{trace-JVF67VR3.js → trace-PKV4KX56.js} +4 -4
- package/dist/{validate-LLBWVPGV.js → validate-RALX7CZS.js} +2 -2
- package/dist/{validate-engine-UIABSIHD.js → validate-engine-7ZXFVGF2.js} +1 -1
- package/dist/viz/assets/index-B8SaeJZZ.js +23 -0
- package/dist/viz/index.html +23 -0
- package/dist/{world-LAXO6DOX.js → world-BIP4GZBZ.js} +9 -11
- package/dist/world-loader-Y6HMQH2D.js +13 -0
- package/dist/worlds/coding-agent.nv-world.md +211 -0
- package/dist/worlds/research-agent.nv-world.md +169 -0
- package/dist/worlds/social-media.nv-world.md +198 -0
- package/dist/worlds/trading-agent.nv-world.md +218 -0
- package/examples/social-media-sim/bridge.py +209 -0
- package/examples/social-media-sim/simulation.py +927 -0
- package/package.json +30 -4
- package/policies/content-moderation-rules.txt +8 -0
- package/policies/marketing-rules.txt +8 -0
- package/policies/science-research-rules.txt +11 -0
- package/policies/social-media-rules.txt +7 -0
- package/policies/strict-rules.txt +8 -0
- package/policies/trading-rules.txt +8 -0
- package/simulate.html +1567 -0
- package/dist/chunk-YZFATT7X.js +0 -9
- package/dist/mcp-server-FPVSU32Z.js +0 -13
- package/dist/session-EKTRSR7C.js +0 -14
- package/dist/world-loader-HMPTOEA2.js +0 -9
|
@@ -0,0 +1,304 @@
|
|
|
1
|
+
import {
|
|
2
|
+
GovernanceBlockedError,
|
|
3
|
+
buildEngineOptions,
|
|
4
|
+
extractScope,
|
|
5
|
+
trackPlanProgress
|
|
6
|
+
} from "./chunk-5U2MQO5P.js";
|
|
7
|
+
import {
|
|
8
|
+
evaluateGuard
|
|
9
|
+
} from "./chunk-W7LLXRGY.js";
|
|
10
|
+
import {
|
|
11
|
+
loadWorld
|
|
12
|
+
} from "./chunk-CTZHONLA.js";
|
|
13
|
+
|
|
14
|
+
// src/engine/tool-classifier.ts
|
|
15
|
+
var TOOL_CATEGORY_MAP = {
|
|
16
|
+
// File operations
|
|
17
|
+
read_file: "file_read",
|
|
18
|
+
read: "file_read",
|
|
19
|
+
glob: "file_read",
|
|
20
|
+
grep: "file_read",
|
|
21
|
+
list_files: "file_read",
|
|
22
|
+
write_file: "file_write",
|
|
23
|
+
write: "file_write",
|
|
24
|
+
create_file: "file_write",
|
|
25
|
+
edit_file: "file_write",
|
|
26
|
+
edit: "file_write",
|
|
27
|
+
patch: "file_write",
|
|
28
|
+
delete_file: "file_delete",
|
|
29
|
+
remove_file: "file_delete",
|
|
30
|
+
// Shell
|
|
31
|
+
shell: "shell",
|
|
32
|
+
bash: "shell",
|
|
33
|
+
execute: "shell",
|
|
34
|
+
run_command: "shell",
|
|
35
|
+
terminal: "shell",
|
|
36
|
+
// Git
|
|
37
|
+
git: "git",
|
|
38
|
+
git_commit: "git",
|
|
39
|
+
git_push: "git",
|
|
40
|
+
git_checkout: "git",
|
|
41
|
+
// Network
|
|
42
|
+
http: "network",
|
|
43
|
+
fetch: "network",
|
|
44
|
+
curl: "network",
|
|
45
|
+
web_search: "network",
|
|
46
|
+
// Sub-agents
|
|
47
|
+
sub_agent: "sub_agent",
|
|
48
|
+
spawn_agent: "sub_agent",
|
|
49
|
+
delegate: "sub_agent",
|
|
50
|
+
// Context management
|
|
51
|
+
summarize: "context",
|
|
52
|
+
compress_context: "context"
|
|
53
|
+
};
|
|
54
|
+
function classifyTool(toolName) {
|
|
55
|
+
const normalized = toolName.toLowerCase().replace(/[-\s]/g, "_");
|
|
56
|
+
return TOOL_CATEGORY_MAP[normalized] ?? "unknown";
|
|
57
|
+
}
|
|
58
|
+
var DANGEROUS_SHELL_PATTERNS = [
|
|
59
|
+
{ pattern: /rm\s+(-[a-zA-Z]*f[a-zA-Z]*\s+|.*-rf\s+|.*--force)/, label: "force-delete" },
|
|
60
|
+
{ pattern: /rm\s+-[a-zA-Z]*r/, label: "recursive-delete" },
|
|
61
|
+
{ pattern: />\s*\/dev\/sd/, label: "disk-overwrite" },
|
|
62
|
+
{ pattern: /mkfs\./, label: "format-disk" },
|
|
63
|
+
{ pattern: /dd\s+if=/, label: "disk-dump" },
|
|
64
|
+
{ pattern: /chmod\s+(-R\s+)?777/, label: "world-writable" },
|
|
65
|
+
{ pattern: /curl\s+.*\|\s*(bash|sh|zsh)/, label: "pipe-to-shell" },
|
|
66
|
+
{ pattern: /wget\s+.*\|\s*(bash|sh|zsh)/, label: "pipe-to-shell" },
|
|
67
|
+
{ pattern: /:(){ :\|:& };:/, label: "fork-bomb" },
|
|
68
|
+
{ pattern: />\s*\/etc\//, label: "system-config-overwrite" },
|
|
69
|
+
{ pattern: /shutdown|reboot|halt|poweroff/, label: "system-shutdown" },
|
|
70
|
+
{ pattern: /kill\s+-9\s+1\b/, label: "kill-init" }
|
|
71
|
+
];
|
|
72
|
+
var DANGEROUS_GIT_PATTERNS = [
|
|
73
|
+
{ pattern: /push\s+.*--force/, label: "force-push" },
|
|
74
|
+
{ pattern: /push\s+.*-f\b/, label: "force-push" },
|
|
75
|
+
{ pattern: /push\s+(origin\s+)?main\b/, label: "push-main" },
|
|
76
|
+
{ pattern: /push\s+(origin\s+)?master\b/, label: "push-master" },
|
|
77
|
+
{ pattern: /reset\s+--hard/, label: "hard-reset" },
|
|
78
|
+
{ pattern: /clean\s+-fd/, label: "clean-force" },
|
|
79
|
+
{ pattern: /branch\s+-D/, label: "force-delete-branch" }
|
|
80
|
+
];
|
|
81
|
+
function isDangerousCommand(command) {
|
|
82
|
+
const matched = DANGEROUS_SHELL_PATTERNS.filter((p) => p.pattern.test(command)).map((p) => p.label);
|
|
83
|
+
return { dangerous: matched.length > 0, labels: matched };
|
|
84
|
+
}
|
|
85
|
+
function isDangerousGitCommand(command) {
|
|
86
|
+
const matched = DANGEROUS_GIT_PATTERNS.filter((p) => p.pattern.test(command)).map((p) => p.label);
|
|
87
|
+
return { dangerous: matched.length > 0, labels: matched };
|
|
88
|
+
}
|
|
89
|
+
function assessRiskLevel(category) {
|
|
90
|
+
if (category === "file_read" || category === "context") return "low";
|
|
91
|
+
if (category === "file_write" || category === "sub_agent") return "medium";
|
|
92
|
+
if (category === "shell" || category === "file_delete" || category === "git" || category === "network") return "high";
|
|
93
|
+
return void 0;
|
|
94
|
+
}
|
|
95
|
+
function categoryToActionCategory(category) {
|
|
96
|
+
if (category === "file_read" || category === "context") return "read";
|
|
97
|
+
if (category === "file_write") return "write";
|
|
98
|
+
if (category === "file_delete") return "delete";
|
|
99
|
+
if (category === "shell") return "shell";
|
|
100
|
+
if (category === "network") return "network";
|
|
101
|
+
return "other";
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
// src/adapters/deep-agents.ts
|
|
105
|
+
var GovernanceBlockedError2 = class extends GovernanceBlockedError {
|
|
106
|
+
toolCall;
|
|
107
|
+
category;
|
|
108
|
+
constructor(verdict, toolCall, category) {
|
|
109
|
+
super(verdict);
|
|
110
|
+
this.toolCall = toolCall;
|
|
111
|
+
this.category = category;
|
|
112
|
+
}
|
|
113
|
+
};
|
|
114
|
+
function defaultMapToolCall(toolCall) {
|
|
115
|
+
const category = classifyTool(toolCall.tool);
|
|
116
|
+
const args = toolCall.args;
|
|
117
|
+
const scope = extractScope(args);
|
|
118
|
+
let intent = toolCall.tool;
|
|
119
|
+
if (category === "shell" && typeof args.command === "string") {
|
|
120
|
+
intent = `shell: ${args.command}`;
|
|
121
|
+
} else if (category === "git" && typeof args.command === "string") {
|
|
122
|
+
intent = `git ${args.command}`;
|
|
123
|
+
} else if (category === "file_write" && scope) {
|
|
124
|
+
intent = `write ${scope}`;
|
|
125
|
+
} else if (category === "file_delete" && scope) {
|
|
126
|
+
intent = `delete ${scope}`;
|
|
127
|
+
}
|
|
128
|
+
const riskLevel = assessRiskLevel(category);
|
|
129
|
+
let irreversible = false;
|
|
130
|
+
if (category === "shell" && typeof args.command === "string") {
|
|
131
|
+
irreversible = DANGEROUS_SHELL_PATTERNS.some((p) => p.pattern.test(args.command));
|
|
132
|
+
} else if (category === "git" && typeof args.command === "string") {
|
|
133
|
+
irreversible = DANGEROUS_GIT_PATTERNS.some((p) => p.pattern.test(args.command));
|
|
134
|
+
} else if (category === "file_delete") {
|
|
135
|
+
irreversible = true;
|
|
136
|
+
}
|
|
137
|
+
return {
|
|
138
|
+
intent,
|
|
139
|
+
tool: toolCall.tool,
|
|
140
|
+
scope,
|
|
141
|
+
args,
|
|
142
|
+
direction: "input",
|
|
143
|
+
actionCategory: categoryToActionCategory(category),
|
|
144
|
+
riskLevel,
|
|
145
|
+
irreversible
|
|
146
|
+
};
|
|
147
|
+
}
|
|
148
|
+
var DeepAgentsGuard = class {
|
|
149
|
+
name = "neuroverse-deep-agents-guard";
|
|
150
|
+
world;
|
|
151
|
+
options;
|
|
152
|
+
engineOptions;
|
|
153
|
+
mapToolCall;
|
|
154
|
+
activePlan;
|
|
155
|
+
constructor(world, options = {}) {
|
|
156
|
+
this.world = world;
|
|
157
|
+
this.options = options;
|
|
158
|
+
this.activePlan = options.plan;
|
|
159
|
+
this.engineOptions = buildEngineOptions(options, this.activePlan);
|
|
160
|
+
this.mapToolCall = options.mapToolCall ?? defaultMapToolCall;
|
|
161
|
+
}
|
|
162
|
+
/**
|
|
163
|
+
* Evaluate a tool call against governance rules.
|
|
164
|
+
* Returns the result without side effects.
|
|
165
|
+
*/
|
|
166
|
+
evaluate(toolCall) {
|
|
167
|
+
const event = this.mapToolCall(toolCall);
|
|
168
|
+
this.engineOptions.plan = this.activePlan;
|
|
169
|
+
const verdict = evaluateGuard(event, this.world, this.engineOptions);
|
|
170
|
+
const category = classifyTool(toolCall.tool);
|
|
171
|
+
const result = {
|
|
172
|
+
allowed: verdict.status === "ALLOW",
|
|
173
|
+
verdict,
|
|
174
|
+
toolCall,
|
|
175
|
+
category
|
|
176
|
+
};
|
|
177
|
+
this.options.onEvaluate?.(result);
|
|
178
|
+
if (verdict.status === "ALLOW" && this.activePlan) {
|
|
179
|
+
this.trackPlanProgressInternal(event);
|
|
180
|
+
}
|
|
181
|
+
return result;
|
|
182
|
+
}
|
|
183
|
+
/**
|
|
184
|
+
* Evaluate and enforce governance on a tool call.
|
|
185
|
+
*
|
|
186
|
+
* @throws GovernanceBlockedError if BLOCKED
|
|
187
|
+
* @throws GovernanceBlockedError if PAUSED and onPause returns false
|
|
188
|
+
* @returns DeepAgentsGuardResult on ALLOW
|
|
189
|
+
*/
|
|
190
|
+
async enforce(toolCall) {
|
|
191
|
+
const result = this.evaluate(toolCall);
|
|
192
|
+
if (result.verdict.status === "BLOCK") {
|
|
193
|
+
this.options.onBlock?.(result);
|
|
194
|
+
throw new GovernanceBlockedError2(result.verdict, toolCall, result.category);
|
|
195
|
+
}
|
|
196
|
+
if (result.verdict.status === "PAUSE") {
|
|
197
|
+
const approved = await this.options.onPause?.(result);
|
|
198
|
+
if (!approved) {
|
|
199
|
+
throw new GovernanceBlockedError2(result.verdict, toolCall, result.category);
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
return result;
|
|
203
|
+
}
|
|
204
|
+
/**
|
|
205
|
+
* Evaluate and execute a tool call with governance enforcement.
|
|
206
|
+
*
|
|
207
|
+
* If ALLOW: runs the executor and returns its result.
|
|
208
|
+
* If BLOCK: returns a governance-blocked message.
|
|
209
|
+
* If PAUSE: calls onPause; blocks if not approved.
|
|
210
|
+
*
|
|
211
|
+
* @param toolCall - The Deep Agents tool call to evaluate
|
|
212
|
+
* @param executor - The actual tool execution function
|
|
213
|
+
* @returns The tool execution result or a blocked message
|
|
214
|
+
*/
|
|
215
|
+
async execute(toolCall, executor) {
|
|
216
|
+
const guardResult = this.evaluate(toolCall);
|
|
217
|
+
if (guardResult.verdict.status === "BLOCK") {
|
|
218
|
+
this.options.onBlock?.(guardResult);
|
|
219
|
+
return {
|
|
220
|
+
blocked: true,
|
|
221
|
+
verdict: guardResult.verdict,
|
|
222
|
+
reason: guardResult.verdict.reason ?? "Action blocked by governance policy."
|
|
223
|
+
};
|
|
224
|
+
}
|
|
225
|
+
if (guardResult.verdict.status === "PAUSE") {
|
|
226
|
+
const approved = await this.options.onPause?.(guardResult);
|
|
227
|
+
if (!approved) {
|
|
228
|
+
return {
|
|
229
|
+
blocked: true,
|
|
230
|
+
verdict: guardResult.verdict,
|
|
231
|
+
reason: guardResult.verdict.reason ?? "Action requires approval."
|
|
232
|
+
};
|
|
233
|
+
}
|
|
234
|
+
}
|
|
235
|
+
const result = await executor(toolCall);
|
|
236
|
+
return { result, verdict: guardResult.verdict };
|
|
237
|
+
}
|
|
238
|
+
/**
|
|
239
|
+
* Returns a middleware function compatible with Deep Agents' tool pipeline.
|
|
240
|
+
*
|
|
241
|
+
* The middleware intercepts tool calls before execution:
|
|
242
|
+
* agent.use(guard.middleware());
|
|
243
|
+
*/
|
|
244
|
+
middleware() {
|
|
245
|
+
return async (toolCall, next) => {
|
|
246
|
+
await this.enforce(toolCall);
|
|
247
|
+
return next();
|
|
248
|
+
};
|
|
249
|
+
}
|
|
250
|
+
/**
|
|
251
|
+
* Returns a callback-handler-style object for LangChain integration.
|
|
252
|
+
* Compatible with Deep Agents' callback system.
|
|
253
|
+
*/
|
|
254
|
+
callbacks() {
|
|
255
|
+
return {
|
|
256
|
+
handleToolStart: async (tool, input) => {
|
|
257
|
+
let parsedInput;
|
|
258
|
+
try {
|
|
259
|
+
parsedInput = typeof input === "string" ? JSON.parse(input) : input;
|
|
260
|
+
} catch {
|
|
261
|
+
parsedInput = { raw: input };
|
|
262
|
+
}
|
|
263
|
+
await this.enforce({ tool: tool.name, args: parsedInput });
|
|
264
|
+
}
|
|
265
|
+
};
|
|
266
|
+
}
|
|
267
|
+
/**
|
|
268
|
+
* Check if a shell command contains dangerous patterns.
|
|
269
|
+
* Useful for pre-screening before full governance evaluation.
|
|
270
|
+
*/
|
|
271
|
+
static isDangerousCommand(command) {
|
|
272
|
+
return isDangerousCommand(command);
|
|
273
|
+
}
|
|
274
|
+
/**
|
|
275
|
+
* Check if a git command contains dangerous patterns.
|
|
276
|
+
*/
|
|
277
|
+
static isDangerousGitCommand(command) {
|
|
278
|
+
return isDangerousGitCommand(command);
|
|
279
|
+
}
|
|
280
|
+
/**
|
|
281
|
+
* Classify a tool name into a category.
|
|
282
|
+
*/
|
|
283
|
+
static classifyTool(toolName) {
|
|
284
|
+
return classifyTool(toolName);
|
|
285
|
+
}
|
|
286
|
+
// ─── Private ──────────────────────────────────────────────────────────────
|
|
287
|
+
trackPlanProgressInternal(event) {
|
|
288
|
+
trackPlanProgress(event, this, this.options);
|
|
289
|
+
}
|
|
290
|
+
};
|
|
291
|
+
async function createDeepAgentsGuard(worldPath, options) {
|
|
292
|
+
const world = await loadWorld(worldPath);
|
|
293
|
+
return new DeepAgentsGuard(world, options);
|
|
294
|
+
}
|
|
295
|
+
function createDeepAgentsGuardFromWorld(world, options) {
|
|
296
|
+
return new DeepAgentsGuard(world, options);
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
export {
|
|
300
|
+
GovernanceBlockedError2 as GovernanceBlockedError,
|
|
301
|
+
DeepAgentsGuard,
|
|
302
|
+
createDeepAgentsGuard,
|
|
303
|
+
createDeepAgentsGuardFromWorld
|
|
304
|
+
};
|
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
// src/engine/bootstrap-emitter.ts
|
|
2
|
+
var GATE_DEFAULTS = {
|
|
3
|
+
THRIVING: { color: "#0f6b3a", icon: "\u2726" },
|
|
4
|
+
STABLE: { color: "#1856b8", icon: "\u25CF" },
|
|
5
|
+
COMPRESSED: { color: "#a16207", icon: "\u25B2" },
|
|
6
|
+
CRITICAL: { color: "#b91c1c", icon: "\u26A0" },
|
|
7
|
+
MODEL_COLLAPSES: { color: "#7f1d1d", icon: "\u2715" }
|
|
8
|
+
};
|
|
9
|
+
function emitWorldDefinition(parsed) {
|
|
10
|
+
const issues = [];
|
|
11
|
+
const fm = parsed.frontmatter;
|
|
12
|
+
const defaultProfile = fm.default_profile ?? parsed.assumptions[0]?.id ?? "baseline";
|
|
13
|
+
const altProfile = fm.alternative_profile ?? parsed.assumptions[1]?.id ?? "alternative";
|
|
14
|
+
const world = {
|
|
15
|
+
world_id: fm.world_id,
|
|
16
|
+
name: fm.name,
|
|
17
|
+
thesis: parsed.thesis,
|
|
18
|
+
version: fm.version ?? "1.0.0",
|
|
19
|
+
runtime_mode: fm.runtime_mode ?? "SIMULATION",
|
|
20
|
+
default_assumption_profile: defaultProfile,
|
|
21
|
+
default_alternative_profile: altProfile,
|
|
22
|
+
modules: parsed.rules.map((r) => r.id),
|
|
23
|
+
players: {
|
|
24
|
+
thinking_space: true,
|
|
25
|
+
experience_space: true,
|
|
26
|
+
action_space: true
|
|
27
|
+
}
|
|
28
|
+
};
|
|
29
|
+
const invariants = parsed.invariants.map((inv) => ({
|
|
30
|
+
id: inv.id,
|
|
31
|
+
label: inv.label,
|
|
32
|
+
enforcement: inv.enforcement === "prompt" ? "prompt" : "structural",
|
|
33
|
+
mutable: false
|
|
34
|
+
}));
|
|
35
|
+
const profiles = {};
|
|
36
|
+
const parameterDefinitions = {};
|
|
37
|
+
for (let i = 0; i < parsed.assumptions.length; i++) {
|
|
38
|
+
const profile = parsed.assumptions[i];
|
|
39
|
+
const params = {};
|
|
40
|
+
for (const [key, val] of Object.entries(profile.parameters)) {
|
|
41
|
+
params[key] = String(val);
|
|
42
|
+
if (!parameterDefinitions[key]) {
|
|
43
|
+
parameterDefinitions[key] = {
|
|
44
|
+
type: typeof val === "boolean" ? "boolean" : typeof val === "number" ? "number" : "enum",
|
|
45
|
+
label: key.replace(/_/g, " ").replace(/\b\w/g, (c) => c.toUpperCase()),
|
|
46
|
+
description: `Parameter: ${key}`
|
|
47
|
+
};
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
profiles[profile.id] = {
|
|
51
|
+
name: profile.name,
|
|
52
|
+
description: profile.description,
|
|
53
|
+
is_default_baseline: i === 0 || profile.id === defaultProfile,
|
|
54
|
+
is_default_alternative: i === 1 || profile.id === altProfile,
|
|
55
|
+
parameters: params
|
|
56
|
+
};
|
|
57
|
+
}
|
|
58
|
+
const assumptions = { profiles, parameter_definitions: parameterDefinitions };
|
|
59
|
+
const variables = {};
|
|
60
|
+
for (const v of parsed.stateVariables) {
|
|
61
|
+
const stateVar = {
|
|
62
|
+
type: v.type,
|
|
63
|
+
default: v.default,
|
|
64
|
+
mutable: true,
|
|
65
|
+
label: v.label,
|
|
66
|
+
description: v.description
|
|
67
|
+
};
|
|
68
|
+
if (v.type === "number") {
|
|
69
|
+
if (v.min !== void 0) stateVar.min = v.min;
|
|
70
|
+
if (v.max !== void 0) stateVar.max = v.max;
|
|
71
|
+
if (v.step !== void 0) stateVar.step = v.step;
|
|
72
|
+
}
|
|
73
|
+
if (v.type === "enum" && v.options) {
|
|
74
|
+
stateVar.options = v.options;
|
|
75
|
+
}
|
|
76
|
+
variables[v.id] = stateVar;
|
|
77
|
+
}
|
|
78
|
+
const stateSchema = { variables, presets: {} };
|
|
79
|
+
const rules = parsed.rules.map((r) => {
|
|
80
|
+
const triggers = r.triggers.map((t) => ({
|
|
81
|
+
field: t.field,
|
|
82
|
+
operator: t.operator,
|
|
83
|
+
value: t.value,
|
|
84
|
+
source: t.source
|
|
85
|
+
}));
|
|
86
|
+
const effects = r.effects.map((e) => ({
|
|
87
|
+
target: e.target,
|
|
88
|
+
operation: e.operation,
|
|
89
|
+
value: e.value
|
|
90
|
+
}));
|
|
91
|
+
let collapse_check;
|
|
92
|
+
if (r.collapse_check) {
|
|
93
|
+
collapse_check = {
|
|
94
|
+
field: r.collapse_check.field,
|
|
95
|
+
operator: r.collapse_check.operator,
|
|
96
|
+
value: r.collapse_check.value,
|
|
97
|
+
result: "MODEL_COLLAPSES"
|
|
98
|
+
};
|
|
99
|
+
}
|
|
100
|
+
const causal_translation = r.causal_translation ?? {
|
|
101
|
+
trigger_text: "",
|
|
102
|
+
rule_text: "",
|
|
103
|
+
shift_text: "",
|
|
104
|
+
effect_text: ""
|
|
105
|
+
};
|
|
106
|
+
const rule = {
|
|
107
|
+
id: r.id,
|
|
108
|
+
severity: r.severity,
|
|
109
|
+
label: r.label,
|
|
110
|
+
description: r.description ?? r.label,
|
|
111
|
+
order: r.order,
|
|
112
|
+
triggers,
|
|
113
|
+
effects: effects.length > 0 ? effects : void 0,
|
|
114
|
+
collapse_check,
|
|
115
|
+
causal_translation
|
|
116
|
+
};
|
|
117
|
+
return rule;
|
|
118
|
+
});
|
|
119
|
+
const viabilityClassification = parsed.gates.map((g) => {
|
|
120
|
+
const defaults = GATE_DEFAULTS[g.status] ?? { color: "#5c5a52", icon: "\u25CF" };
|
|
121
|
+
return {
|
|
122
|
+
status: g.status,
|
|
123
|
+
field: g.field,
|
|
124
|
+
operator: g.operator,
|
|
125
|
+
value: g.value,
|
|
126
|
+
color: defaults.color,
|
|
127
|
+
icon: defaults.icon
|
|
128
|
+
};
|
|
129
|
+
});
|
|
130
|
+
const gates = {
|
|
131
|
+
viability_classification: viabilityClassification,
|
|
132
|
+
structural_override: {
|
|
133
|
+
description: "Rules with severity=structural and triggered collapse_check force MODEL_COLLAPSES regardless of final margin.",
|
|
134
|
+
enforcement: "mandatory"
|
|
135
|
+
},
|
|
136
|
+
sustainability_threshold: 0.1,
|
|
137
|
+
collapse_visual: {
|
|
138
|
+
background: "#1c1917",
|
|
139
|
+
text: "#fef2f2",
|
|
140
|
+
border: "#b91c1c",
|
|
141
|
+
label: "Structural Failure"
|
|
142
|
+
}
|
|
143
|
+
};
|
|
144
|
+
const computedOutcomes = parsed.outcomes.map((o) => {
|
|
145
|
+
const outcome = {
|
|
146
|
+
id: o.id,
|
|
147
|
+
type: o.type,
|
|
148
|
+
label: o.label,
|
|
149
|
+
show_in_comparison: true
|
|
150
|
+
};
|
|
151
|
+
if (o.range) outcome.range = o.range;
|
|
152
|
+
if (o.display) outcome.display_as = o.display;
|
|
153
|
+
if (o.primary) outcome.primary = o.primary;
|
|
154
|
+
if (o.assignment) outcome.assignment = o.assignment;
|
|
155
|
+
return outcome;
|
|
156
|
+
});
|
|
157
|
+
const outcomes = {
|
|
158
|
+
computed_outcomes: computedOutcomes,
|
|
159
|
+
comparison_layout: {
|
|
160
|
+
primary_card: computedOutcomes.find((o) => o.primary)?.id ?? computedOutcomes[0]?.id ?? "",
|
|
161
|
+
status_badge: "viability_status",
|
|
162
|
+
structural_indicators: rules.filter((r) => r.severity === "structural").map((r) => r.id)
|
|
163
|
+
}
|
|
164
|
+
};
|
|
165
|
+
const metadata = {
|
|
166
|
+
format_version: "1.0.0",
|
|
167
|
+
created_at: (/* @__PURE__ */ new Date()).toISOString(),
|
|
168
|
+
last_modified: (/* @__PURE__ */ new Date()).toISOString(),
|
|
169
|
+
authoring_method: "manual-authoring"
|
|
170
|
+
};
|
|
171
|
+
const worldDefinition = {
|
|
172
|
+
world,
|
|
173
|
+
invariants,
|
|
174
|
+
assumptions,
|
|
175
|
+
stateSchema,
|
|
176
|
+
rules,
|
|
177
|
+
gates,
|
|
178
|
+
outcomes,
|
|
179
|
+
metadata
|
|
180
|
+
};
|
|
181
|
+
return { world: worldDefinition, issues };
|
|
182
|
+
}
|
|
183
|
+
|
|
184
|
+
export {
|
|
185
|
+
emitWorldDefinition
|
|
186
|
+
};
|
|
@@ -1,14 +1,24 @@
|
|
|
1
|
-
// src/engine/
|
|
2
|
-
function
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
1
|
+
// src/engine/text-utils.ts
|
|
2
|
+
function normalizeEventText(event) {
|
|
3
|
+
return [
|
|
4
|
+
event.intent,
|
|
5
|
+
event.tool ?? "",
|
|
6
|
+
event.scope ?? ""
|
|
7
7
|
].join(" ").toLowerCase();
|
|
8
|
-
|
|
8
|
+
}
|
|
9
|
+
function extractKeywords(text, minLength = 3) {
|
|
10
|
+
return text.toLowerCase().split(/\s+/).filter((w) => w.length > minLength);
|
|
11
|
+
}
|
|
12
|
+
function matchesAllKeywords(eventText, ruleText) {
|
|
13
|
+
const keywords = extractKeywords(ruleText);
|
|
14
|
+
if (keywords.length === 0) return false;
|
|
15
|
+
return keywords.every((kw) => eventText.includes(kw));
|
|
16
|
+
}
|
|
17
|
+
function matchesKeywordThreshold(eventText, ruleText, threshold = 0.5) {
|
|
18
|
+
const keywords = extractKeywords(ruleText);
|
|
9
19
|
if (keywords.length === 0) return false;
|
|
10
20
|
const matched = keywords.filter((kw) => eventText.includes(kw));
|
|
11
|
-
return matched.length >= Math.ceil(keywords.length *
|
|
21
|
+
return matched.length >= Math.ceil(keywords.length * threshold);
|
|
12
22
|
}
|
|
13
23
|
function tokenSimilarity(a, b) {
|
|
14
24
|
const tokensA = new Set(a.toLowerCase().split(/\s+/).filter((w) => w.length > 2));
|
|
@@ -21,6 +31,19 @@ function tokenSimilarity(a, b) {
|
|
|
21
31
|
const union = (/* @__PURE__ */ new Set([...tokensA, ...tokensB])).size;
|
|
22
32
|
return union > 0 ? intersection / union : 0;
|
|
23
33
|
}
|
|
34
|
+
|
|
35
|
+
// src/engine/plan-engine.ts
|
|
36
|
+
function keywordMatch(eventText, step) {
|
|
37
|
+
const stepText = [
|
|
38
|
+
step.label,
|
|
39
|
+
step.description ?? "",
|
|
40
|
+
...step.tags ?? []
|
|
41
|
+
].join(" ");
|
|
42
|
+
return matchesKeywordThreshold(eventText, stepText, 0.5);
|
|
43
|
+
}
|
|
44
|
+
function tokenSimilarity2(a, b) {
|
|
45
|
+
return tokenSimilarity(a, b);
|
|
46
|
+
}
|
|
24
47
|
function findMatchingStep(eventText, event, steps) {
|
|
25
48
|
const pendingOrActive = steps.filter((s) => s.status === "pending" || s.status === "active");
|
|
26
49
|
if (pendingOrActive.length === 0) {
|
|
@@ -39,7 +62,7 @@ function findMatchingStep(eventText, event, steps) {
|
|
|
39
62
|
let bestScore = 0;
|
|
40
63
|
for (const step of pendingOrActive) {
|
|
41
64
|
const stepText = [step.label, step.description ?? "", ...step.tags ?? []].join(" ");
|
|
42
|
-
const score =
|
|
65
|
+
const score = tokenSimilarity2(intentText, stepText);
|
|
43
66
|
if (score > bestScore) {
|
|
44
67
|
bestScore = score;
|
|
45
68
|
bestStep = step;
|
|
@@ -80,7 +103,7 @@ function checkConstraints(event, eventText, constraints) {
|
|
|
80
103
|
continue;
|
|
81
104
|
}
|
|
82
105
|
if (constraint.type === "scope" && constraint.trigger) {
|
|
83
|
-
const keywords = constraint.trigger
|
|
106
|
+
const keywords = extractKeywords(constraint.trigger);
|
|
84
107
|
const violated = keywords.length > 0 && keywords.every((kw) => eventText.includes(kw));
|
|
85
108
|
checks.push({
|
|
86
109
|
constraintId: constraint.id,
|
|
@@ -161,11 +184,7 @@ function evaluatePlan(event, plan) {
|
|
|
161
184
|
progress
|
|
162
185
|
};
|
|
163
186
|
}
|
|
164
|
-
const eventText =
|
|
165
|
-
event.intent,
|
|
166
|
-
event.tool ?? "",
|
|
167
|
-
event.scope ?? ""
|
|
168
|
-
].join(" ").toLowerCase();
|
|
187
|
+
const eventText = normalizeEventText(event);
|
|
169
188
|
const { matched, closest, closestScore } = findMatchingStep(eventText, event, plan.steps);
|
|
170
189
|
if (!matched) {
|
|
171
190
|
return {
|
|
@@ -206,7 +225,7 @@ function evaluatePlan(event, plan) {
|
|
|
206
225
|
};
|
|
207
226
|
}
|
|
208
227
|
function buildPlanCheck(event, plan, verdict) {
|
|
209
|
-
const eventText =
|
|
228
|
+
const eventText = normalizeEventText(event);
|
|
210
229
|
const { matched, closest, closestScore } = findMatchingStep(eventText, event, plan.steps);
|
|
211
230
|
const { checks: constraintChecks } = checkConstraints(event, eventText, plan.constraints);
|
|
212
231
|
const progress = getPlanProgress(plan);
|
|
@@ -225,6 +244,8 @@ function buildPlanCheck(event, plan, verdict) {
|
|
|
225
244
|
}
|
|
226
245
|
|
|
227
246
|
export {
|
|
247
|
+
normalizeEventText,
|
|
248
|
+
matchesAllKeywords,
|
|
228
249
|
getPlanProgress,
|
|
229
250
|
advancePlan,
|
|
230
251
|
evaluatePlan,
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
var __require = /* @__PURE__ */ ((x) => typeof require !== "undefined" ? require : typeof Proxy !== "undefined" ? new Proxy(x, {
|
|
2
|
+
get: (a, b) => (typeof require !== "undefined" ? require : a)[b]
|
|
3
|
+
}) : x)(function(x) {
|
|
4
|
+
if (typeof require !== "undefined") return require.apply(this, arguments);
|
|
5
|
+
throw Error('Dynamic require of "' + x + '" is not supported');
|
|
6
|
+
});
|
|
7
|
+
var __glob = (map) => (path) => {
|
|
8
|
+
var fn = map[path];
|
|
9
|
+
if (fn) return fn();
|
|
10
|
+
throw new Error("Module not found in bundle: " + path);
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
export {
|
|
14
|
+
__require,
|
|
15
|
+
__glob
|
|
16
|
+
};
|
|
@@ -1,9 +1,20 @@
|
|
|
1
|
+
import {
|
|
2
|
+
evaluateGuard
|
|
3
|
+
} from "./chunk-W7LLXRGY.js";
|
|
4
|
+
import {
|
|
5
|
+
loadWorldFromDirectory
|
|
6
|
+
} from "./chunk-CTZHONLA.js";
|
|
7
|
+
|
|
1
8
|
// src/adapters/autoresearch.ts
|
|
2
9
|
var AutoresearchGovernor = class {
|
|
3
10
|
config;
|
|
4
11
|
state;
|
|
12
|
+
world;
|
|
13
|
+
engineOptions;
|
|
5
14
|
constructor(config) {
|
|
6
15
|
this.config = config;
|
|
16
|
+
this.world = config.world;
|
|
17
|
+
this.engineOptions = { trace: true };
|
|
7
18
|
this.state = {
|
|
8
19
|
experiments_run: 0,
|
|
9
20
|
best_result: null,
|
|
@@ -33,10 +44,23 @@ var AutoresearchGovernor = class {
|
|
|
33
44
|
}
|
|
34
45
|
/**
|
|
35
46
|
* Evaluate an experiment proposal against governance rules.
|
|
36
|
-
*
|
|
47
|
+
* Routes through the guard engine when a world is loaded,
|
|
48
|
+
* then layers on research-specific checks (budget, constraints, drift).
|
|
37
49
|
*/
|
|
38
50
|
evaluateProposal(proposal) {
|
|
39
51
|
const warnings = [];
|
|
52
|
+
const event = this.proposalToGuardEvent(proposal);
|
|
53
|
+
if (this.world) {
|
|
54
|
+
const verdict = evaluateGuard(event, this.world, this.engineOptions);
|
|
55
|
+
if (verdict.status === "BLOCK" || verdict.status === "PAUSE") {
|
|
56
|
+
return {
|
|
57
|
+
allowed: false,
|
|
58
|
+
reason: verdict.reason ?? `Governance ${verdict.status}: ${verdict.ruleId ?? "unknown rule"}`,
|
|
59
|
+
warnings,
|
|
60
|
+
verdict
|
|
61
|
+
};
|
|
62
|
+
}
|
|
63
|
+
}
|
|
40
64
|
const estimatedMinutes = proposal.estimated_minutes || 5;
|
|
41
65
|
if (this.state.total_compute_minutes + estimatedMinutes > this.config.computeBudgetMinutes) {
|
|
42
66
|
return {
|
|
@@ -166,7 +190,12 @@ var AutoresearchGovernor = class {
|
|
|
166
190
|
return { ...this.state };
|
|
167
191
|
}
|
|
168
192
|
};
|
|
193
|
+
async function createAutoresearchGovernor(worldPath, config) {
|
|
194
|
+
const world = await loadWorldFromDirectory(worldPath);
|
|
195
|
+
return new AutoresearchGovernor({ ...config, world, worldPath });
|
|
196
|
+
}
|
|
169
197
|
|
|
170
198
|
export {
|
|
171
|
-
AutoresearchGovernor
|
|
199
|
+
AutoresearchGovernor,
|
|
200
|
+
createAutoresearchGovernor
|
|
172
201
|
};
|