@herjarsa/omo-meta-governor 0.9.2 → 0.9.8
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/package.json +1 -1
- package/dist/closed-loop-learning.d.ts +0 -32
- package/dist/config-file.d.ts +0 -71
- package/dist/config.d.ts +0 -79
- package/dist/decision-handler.d.ts +0 -35
- package/dist/decision-store.d.ts +0 -36
- package/dist/file-logger.d.ts +0 -1
- package/dist/generate-schema.d.ts +0 -45
- package/dist/graph-sync.d.ts +0 -90
- package/dist/index.d.ts +0 -40
- package/dist/index.js +0 -23
- package/dist/index.js.map +0 -25
- package/dist/memory-aggregator.d.ts +0 -124
- package/dist/orchestrator.d.ts +0 -33
- package/dist/plugin.d.ts +0 -14
- package/dist/post-repair-recorder.d.ts +0 -47
- package/dist/protocol-enforcer.d.ts +0 -33
- package/dist/scoring-engine.d.ts +0 -31
- package/dist/token-predictor.d.ts +0 -29
- package/dist/types.d.ts +0 -552
package/package.json
CHANGED
|
@@ -1,32 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Closed-loop learning for MetaGovernor.
|
|
3
|
-
*
|
|
4
|
-
* PR 3 of 8. After every repair/action cycle, observeAndLearn() decides
|
|
5
|
-
* whether to persist a lesson or decision record to agentmemory. Future
|
|
6
|
-
* sessions retrieve these via aggregateRead() (PR 2) and factor them into
|
|
7
|
-
* scoring (PR 5).
|
|
8
|
-
*
|
|
9
|
-
* Design:
|
|
10
|
-
* - Pure function with DI backend (no side effects without backend).
|
|
11
|
-
* - config.enabled=false → returns no-op with reason.
|
|
12
|
-
* - Severity threshold: minSeverityToLearn filters what gets saved.
|
|
13
|
-
* - Session cap: maxLessonsPerSession prevents flooding.
|
|
14
|
-
* - Lessons go to agentmemory_memory_save (type: "pattern").
|
|
15
|
-
* - Decisions go to agentmemory_memory_save (type: "fact").
|
|
16
|
-
* - No file I/O, no MCP calls — just decision logic + DI write.
|
|
17
|
-
*/
|
|
18
|
-
import type { AgentmemoryWriteBackend, ClosedLoopConfig, LearnFromOutcomeInput, LearnFromOutcomeOutput } from "./types";
|
|
19
|
-
/** Severity ordering for threshold comparison. */
|
|
20
|
-
declare const SEVERITY_ORDER: Record<string, number>;
|
|
21
|
-
/**
|
|
22
|
-
* Core learning function. Decides whether to save a lesson and/or decision
|
|
23
|
-
* to agentmemory based on the outcome of a repair/action cycle.
|
|
24
|
-
*
|
|
25
|
-
* Returns LearnFromOutcomeOutput describing what was saved (or why nothing was saved).
|
|
26
|
-
*/
|
|
27
|
-
export declare function observeAndLearn(input: LearnFromOutcomeInput, backend: AgentmemoryWriteBackend): Promise<LearnFromOutcomeOutput>;
|
|
28
|
-
/**
|
|
29
|
-
* Helper: create a default ClosedLoopConfig.
|
|
30
|
-
*/
|
|
31
|
-
export declare function defaultClosedLoopConfig(): ClosedLoopConfig;
|
|
32
|
-
export { SEVERITY_ORDER };
|
package/dist/config-file.d.ts
DELETED
|
@@ -1,71 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* JSONC config file loader for omo-meta-governor.
|
|
3
|
-
*
|
|
4
|
-
* Loads `omo-meta-governor.jsonc` from three layers (closer wins):
|
|
5
|
-
* 1. CLI inline options (opts object) — highest priority
|
|
6
|
-
* 2. Project config: `.opencode/omo-meta-governor.jsonc`
|
|
7
|
-
* 3. User config: `~/.config/opencode/omo-meta-governor.jsonc`
|
|
8
|
-
* 4. Defaults — lowest priority
|
|
9
|
-
*
|
|
10
|
-
* JSONC support: comments (//, /* * /) and trailing commas are stripped
|
|
11
|
-
* before parsing. The raw JSON object is then projected into
|
|
12
|
-
* `MetaGovernorPluginConfig` via `loadOrchestratorConfig()`.
|
|
13
|
-
*/
|
|
14
|
-
import type { MetaGovernorPluginConfig } from "./config";
|
|
15
|
-
/**
|
|
16
|
-
* Strip JSONC comments (single-line // style and multi-line bracket style)
|
|
17
|
-
* and trailing commas from a JSONC string so it can be parsed by JSON.parse.
|
|
18
|
-
*
|
|
19
|
-
* Handles:
|
|
20
|
-
* - // single-line comments
|
|
21
|
-
* - /asterisk ... asterisk/ multi-line comments
|
|
22
|
-
* - Trailing commas before ] or }
|
|
23
|
-
* - Strings containing comments (preserved)
|
|
24
|
-
*/
|
|
25
|
-
export declare function stripJsoncComments(jsonc: string): string;
|
|
26
|
-
/**
|
|
27
|
-
* Parse a JSONC string into a JavaScript object.
|
|
28
|
-
* Returns undefined on parse failure.
|
|
29
|
-
*/
|
|
30
|
-
export declare function parseJsonc<T = Record<string, unknown>>(jsonc: string): T | undefined;
|
|
31
|
-
/**
|
|
32
|
-
* Get the user-level config file path.
|
|
33
|
-
*/
|
|
34
|
-
export declare function getUserConfigPath(): string;
|
|
35
|
-
/**
|
|
36
|
-
* Get the project-level config file path for a given project directory.
|
|
37
|
-
*/
|
|
38
|
-
export declare function getProjectConfigPath(projectDir?: string): string;
|
|
39
|
-
/**
|
|
40
|
-
* Read and parse a single JSONC config file.
|
|
41
|
-
* Returns undefined if the file does not exist or is unparseable.
|
|
42
|
-
*/
|
|
43
|
-
export declare function loadJsoncFile<T = Record<string, unknown>>(filePath: string): Promise<T | undefined>;
|
|
44
|
-
/**
|
|
45
|
-
* Deep-merge two config objects. Arrays are replaced (not concatenated).
|
|
46
|
-
* The `source` values win when both exist.
|
|
47
|
-
* Mutually recursive with mergeArrays=false for sub-objects.
|
|
48
|
-
*/
|
|
49
|
-
export declare function deepMerge<T extends Record<string, unknown>>(target: T, source: Partial<T>): T;
|
|
50
|
-
export interface ConfigFileSources {
|
|
51
|
-
/** CLI inline options (highest priority) */
|
|
52
|
-
cliOptions?: Partial<MetaGovernorPluginConfig>;
|
|
53
|
-
/** Project directory for project-level config lookup */
|
|
54
|
-
projectDir?: string;
|
|
55
|
-
}
|
|
56
|
-
export interface ConfigFileResult {
|
|
57
|
-
/** The merged MetaGovernorPluginConfig */
|
|
58
|
-
config: Partial<MetaGovernorPluginConfig>;
|
|
59
|
-
/** Which source files were loaded */
|
|
60
|
-
sources: string[];
|
|
61
|
-
/** Which source was the effective highest-priority non-empty source */
|
|
62
|
-
effectiveSource: "cli" | "project" | "user" | "defaults";
|
|
63
|
-
}
|
|
64
|
-
/**
|
|
65
|
-
* Load the MetaGovernor config from all available sources with priority:
|
|
66
|
-
* CLI inline > project `.opencode/omo-meta-governor.jsonc` >
|
|
67
|
-
* user `~/.config/opencode/omo-meta-governor.jsonc` > defaults
|
|
68
|
-
*
|
|
69
|
-
* Higher-priority sources override lower-priority ones.
|
|
70
|
-
*/
|
|
71
|
-
export declare function loadMetaGovernorConfig(sources?: ConfigFileSources): Promise<ConfigFileResult>;
|
package/dist/config.d.ts
DELETED
|
@@ -1,79 +0,0 @@
|
|
|
1
|
-
import type { ModelOverrideConfig, OrchestratorConfig } from "./types";
|
|
2
|
-
import type { ConfigFileSources } from "./config-file";
|
|
3
|
-
/**
|
|
4
|
-
* MetaGovernor config schema exposed to users.
|
|
5
|
-
* This is a Zod-free config interface since Zod parsing is optional
|
|
6
|
-
* in the standalone plugin — the user provides JSON, we coerce with defaults.
|
|
7
|
-
*/
|
|
8
|
-
export interface MetaGovernorPluginConfig {
|
|
9
|
-
/** Master feature flag — must be true to run the orchestrator. */
|
|
10
|
-
enabled?: boolean;
|
|
11
|
-
/** Decision handler (PR 6) */
|
|
12
|
-
decision?: {
|
|
13
|
-
maxHistoryPerSession?: number;
|
|
14
|
-
forceContinueAfterStops?: number;
|
|
15
|
-
};
|
|
16
|
-
/** Memory aggregator (PR 2) */
|
|
17
|
-
memory?: {
|
|
18
|
-
agentmemoryTimeoutMs?: number;
|
|
19
|
-
magicContextTimeoutMs?: number;
|
|
20
|
-
boulderStateTimeoutMs?: number;
|
|
21
|
-
query?: string;
|
|
22
|
-
};
|
|
23
|
-
/** Token predictor (PR 4) */
|
|
24
|
-
tokenPredictor?: {
|
|
25
|
-
compactBurnRateThreshold?: number;
|
|
26
|
-
compactUsageThreshold?: number;
|
|
27
|
-
switchModelUsageThreshold?: number;
|
|
28
|
-
delegateConsecutiveHighBurn?: number;
|
|
29
|
-
};
|
|
30
|
-
/** Scoring engine (PR 5) */
|
|
31
|
-
scoring?: {
|
|
32
|
-
continueThreshold?: number;
|
|
33
|
-
warnThreshold?: number;
|
|
34
|
-
escalateThreshold?: number;
|
|
35
|
-
stopThreshold?: number;
|
|
36
|
-
};
|
|
37
|
-
/** Closed-loop learning (PR 3) */
|
|
38
|
-
closedLoop?: {
|
|
39
|
-
saveDecisions?: boolean;
|
|
40
|
-
saveLessons?: boolean;
|
|
41
|
-
};
|
|
42
|
-
/** Model override for MetaGovernor internal LLM usage. */
|
|
43
|
-
modelOverride?: ModelOverrideConfig;
|
|
44
|
-
/** Intervention config for visible decision injection. */
|
|
45
|
-
intervention?: {
|
|
46
|
-
mode?: "silent" | "message" | "system";
|
|
47
|
-
includeDecisionHistory?: boolean;
|
|
48
|
-
maxHistoryMessages?: number;
|
|
49
|
-
minActionForMessage?: "warn" | "escalate" | "stop";
|
|
50
|
-
};
|
|
51
|
-
/** Sisyphus protocol enforcement config. */
|
|
52
|
-
protocolEnforcement?: {
|
|
53
|
-
enabled?: boolean;
|
|
54
|
-
path?: string;
|
|
55
|
-
injectIntoSystem?: boolean;
|
|
56
|
-
auditToolCalls?: boolean;
|
|
57
|
-
};
|
|
58
|
-
/** Graph sync config for auto-initializing codegraph/graphify. */
|
|
59
|
-
graphSync?: {
|
|
60
|
-
enabled?: boolean;
|
|
61
|
-
watch?: boolean;
|
|
62
|
-
autoInstall?: boolean;
|
|
63
|
-
installTimeoutMs?: number;
|
|
64
|
-
};
|
|
65
|
-
}
|
|
66
|
-
/**
|
|
67
|
-
* Project the full MetaGovernorPluginConfig into OrchestratorConfig.
|
|
68
|
-
* Missing sub-configs fall back to module defaults.
|
|
69
|
-
*/
|
|
70
|
-
export declare function loadOrchestratorConfig(pluginConfig: Partial<MetaGovernorPluginConfig> | undefined): OrchestratorConfig;
|
|
71
|
-
/**
|
|
72
|
-
* Check whether the MetaGovernor is enabled. Returns false if config is undefined.
|
|
73
|
-
*/
|
|
74
|
-
export declare function isMetaGovernorEnabled(config: MetaGovernorPluginConfig | undefined): boolean;
|
|
75
|
-
/**
|
|
76
|
-
* Load orchestrator config from all available sources: config file (JSONC)
|
|
77
|
-
* with priority: CLI inline > project config > user config > defaults.
|
|
78
|
-
*/
|
|
79
|
-
export declare function loadOrchestratorConfigFromSources(sources?: ConfigFileSources): Promise<OrchestratorConfig>;
|
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* MetaGovernor Decision Handler — PR 6 of 8.
|
|
3
|
-
*
|
|
4
|
-
* Takes a ScoringResult from the scoring engine and dispatches to the
|
|
5
|
-
* appropriate action: continue, warn, escalate, or stop. This is the
|
|
6
|
-
* "executor" that translates scoring decisions into concrete outcomes.
|
|
7
|
-
*
|
|
8
|
-
* Architecture invariants:
|
|
9
|
-
* - Pure dispatch: no I/O, no MCP calls, no side effects
|
|
10
|
-
* - DI pattern: backends injected via DecisionHandlerConfig
|
|
11
|
-
* - Audit trail: every decision + outcome recorded in DecisionHistory
|
|
12
|
-
* - Configurable: all thresholds and behaviors overridable
|
|
13
|
-
*/
|
|
14
|
-
import type { DecisionHandlerConfig, DecisionHandlerInput, DecisionHandlerOutput } from "./types";
|
|
15
|
-
export declare const defaultDecisionHandlerConfig: () => DecisionHandlerConfig;
|
|
16
|
-
/**
|
|
17
|
-
* Core decision handler. Takes a ScoringResult and dispatches to the
|
|
18
|
-
* appropriate action. Pure function — no side effects.
|
|
19
|
-
*
|
|
20
|
-
* @param input - ScoringResult + session context
|
|
21
|
-
* @param config - Handler configuration
|
|
22
|
-
* @returns DecisionHandlerOutput with action taken + message + history entry
|
|
23
|
-
*/
|
|
24
|
-
export declare function handleDecision(input: DecisionHandlerInput, config?: Partial<DecisionHandlerConfig>): DecisionHandlerOutput;
|
|
25
|
-
/**
|
|
26
|
-
* Trim history to max size. Returns trimmed array + entries dropped count.
|
|
27
|
-
*/
|
|
28
|
-
export declare function trimHistory(history: readonly DecisionHandlerOutput["historyEntry"][], maxSize: number): {
|
|
29
|
-
trimmed: DecisionHandlerOutput["historyEntry"][];
|
|
30
|
-
dropped: number;
|
|
31
|
-
};
|
|
32
|
-
/**
|
|
33
|
-
* Count consecutive stops in history (most recent first).
|
|
34
|
-
*/
|
|
35
|
-
export declare function countConsecutiveStops(history: readonly DecisionHandlerOutput["historyEntry"][]): number;
|
package/dist/decision-store.d.ts
DELETED
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* MetaGovernor decision store — in-memory Map for intervention feature.
|
|
3
|
-
*
|
|
4
|
-
* Stores decisions produced by tool.execute.after so they can be
|
|
5
|
-
* consumed by experimental.chat.messages.transform and
|
|
6
|
-
* experimental.chat.system.transform hooks.
|
|
7
|
-
*
|
|
8
|
-
* The store is keyed by sessionID. For hooks that receive a sessionID
|
|
9
|
-
* (system.transform), use takeDecision(sessionID). For hooks that
|
|
10
|
-
* receive no sessionID (messages.transform), use takeAnyDecision().
|
|
11
|
-
*/
|
|
12
|
-
import type { DecisionHandlerOutput } from "./types";
|
|
13
|
-
/**
|
|
14
|
-
* Store a decision for a session.
|
|
15
|
-
* Overwrites any previous pending decision for the same session.
|
|
16
|
-
*/
|
|
17
|
-
export declare function storeDecision(sessionID: string, decision: DecisionHandlerOutput): void;
|
|
18
|
-
/**
|
|
19
|
-
* Take (retrieve and remove) the pending decision for a session.
|
|
20
|
-
* Returns undefined if no decision is pending.
|
|
21
|
-
*/
|
|
22
|
-
export declare function takeDecision(sessionID: string): DecisionHandlerOutput | undefined;
|
|
23
|
-
/**
|
|
24
|
-
* Check whether a session has a pending decision without consuming it.
|
|
25
|
-
*/
|
|
26
|
-
export declare function hasDecision(sessionID: string): boolean;
|
|
27
|
-
/**
|
|
28
|
-
* Take any pending decision across all sessions.
|
|
29
|
-
* Useful for hooks that do not receive a sessionID.
|
|
30
|
-
* Returns the first pending decision found, or undefined if none.
|
|
31
|
-
*/
|
|
32
|
-
export declare function takeAnyDecision(): DecisionHandlerOutput | undefined;
|
|
33
|
-
/**
|
|
34
|
-
* Clear all stored decisions. Useful in tests or when a session ends.
|
|
35
|
-
*/
|
|
36
|
-
export declare function clearAll(): void;
|
package/dist/file-logger.d.ts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export declare function logToFile(level: "info" | "warn" | "error", message: string, data?: unknown): void;
|
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* JSON Schema generator for omo-meta-governor.jsonc.
|
|
3
|
-
*
|
|
4
|
-
* Generates a JSON Schema (draft-07) from the MetaGovernorPluginConfig
|
|
5
|
-
* interface definition. The schema is used for IDE autocompletion and
|
|
6
|
-
* validation when editing the .jsonc config file.
|
|
7
|
-
*
|
|
8
|
-
* Usage:
|
|
9
|
-
* import { generateSchema } from "./generate-schema"
|
|
10
|
-
* const schema = generateSchema()
|
|
11
|
-
* await Bun.write("assets/omo-meta-governor.schema.json", JSON.stringify(schema, null, 2))
|
|
12
|
-
*/
|
|
13
|
-
export interface JsonSchema {
|
|
14
|
-
$schema: string;
|
|
15
|
-
$id: string;
|
|
16
|
-
title: string;
|
|
17
|
-
description: string;
|
|
18
|
-
type: "object";
|
|
19
|
-
properties: Record<string, JsonSchemaProperty>;
|
|
20
|
-
additionalProperties: boolean;
|
|
21
|
-
definitions?: Record<string, JsonSchemaProperty>;
|
|
22
|
-
}
|
|
23
|
-
export interface JsonSchemaProperty {
|
|
24
|
-
type?: string | string[];
|
|
25
|
-
description?: string;
|
|
26
|
-
default?: unknown;
|
|
27
|
-
properties?: Record<string, JsonSchemaProperty>;
|
|
28
|
-
items?: JsonSchemaProperty;
|
|
29
|
-
additionalProperties?: boolean;
|
|
30
|
-
required?: string[];
|
|
31
|
-
enum?: string[];
|
|
32
|
-
oneOf?: JsonSchemaProperty[];
|
|
33
|
-
anyOf?: JsonSchemaProperty[];
|
|
34
|
-
$ref?: string;
|
|
35
|
-
minimum?: number;
|
|
36
|
-
maximum?: number;
|
|
37
|
-
}
|
|
38
|
-
/**
|
|
39
|
-
* Generate the full JSON Schema for the omo-meta-governor.jsonc config file.
|
|
40
|
-
*/
|
|
41
|
-
export declare function generateSchema(): JsonSchema;
|
|
42
|
-
/**
|
|
43
|
-
* Write the schema to a file.
|
|
44
|
-
*/
|
|
45
|
-
export declare function writeSchemaFile(outputPath: string): Promise<void>;
|
package/dist/graph-sync.d.ts
DELETED
|
@@ -1,90 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* graphSync — Auto-initialize codegraph and graphify for a project.
|
|
3
|
-
*
|
|
4
|
-
* On first session in a project, checks whether:
|
|
5
|
-
* - `npx codegraph` is available on PATH (or node_modules)
|
|
6
|
-
* - `graphify` / `graphifyy` is available as a Python package
|
|
7
|
-
*
|
|
8
|
-
* If a tool is available but the project has no index yet, runs the
|
|
9
|
-
* initialization automatically. With `--watch` mode, spawns a background
|
|
10
|
-
* process that re-indexes on file changes.
|
|
11
|
-
*
|
|
12
|
-
* Architecture invariants:
|
|
13
|
-
* - Never blocks the session — init runs async, best-effort
|
|
14
|
-
* - Never throws — all errors are silently caught and logged
|
|
15
|
-
* - Tracks session init once per project via an in-memory Set
|
|
16
|
-
*/
|
|
17
|
-
export interface GraphSyncConfig {
|
|
18
|
-
/** Enable auto-initialization. Default: true */
|
|
19
|
-
enabled: boolean;
|
|
20
|
-
/** Enable watch mode (re-index on file changes). Default: false */
|
|
21
|
-
watch: boolean;
|
|
22
|
-
/** Project directory to initialize in. Default: cwd */
|
|
23
|
-
projectDir?: string;
|
|
24
|
-
/**
|
|
25
|
-
* Auto-install missing backends. Default: true.
|
|
26
|
-
* - codegraph: installed via `npm i -D @colbymchenry/codegraph` in the project
|
|
27
|
-
* - graphify: installed via `pip install graphifyy --break-system-packages` (or `uv tool install graphifyy`)
|
|
28
|
-
*/
|
|
29
|
-
autoInstall: boolean;
|
|
30
|
-
/** Max ms to wait for each install. Default: 60_000 */
|
|
31
|
-
installTimeoutMs: number;
|
|
32
|
-
}
|
|
33
|
-
export type InstallCode = "codegraph-installed" | "codegraph-install-failed" | "codegraph-install-skipped" | "graphify-installed" | "graphify-install-failed" | "graphify-install-skipped";
|
|
34
|
-
/**
|
|
35
|
-
* Install codegraph via `npm i -D @colbymchenry/codegraph`.
|
|
36
|
-
* Best-effort, never throws.
|
|
37
|
-
*/
|
|
38
|
-
export declare function installCodegraph(projectDir: string, timeoutMs?: number): Promise<InstallCode>;
|
|
39
|
-
/**
|
|
40
|
-
* Install graphify via `pip install graphifyy --break-system-packages`.
|
|
41
|
-
* Falls back to `uv tool install graphifyy`.
|
|
42
|
-
* Best-effort, never throws.
|
|
43
|
-
*/
|
|
44
|
-
export declare function installGraphify(timeoutMs?: number): Promise<InstallCode>;
|
|
45
|
-
export declare function resetInitializedProjects(): void;
|
|
46
|
-
/**
|
|
47
|
-
* Track a new session for a project. Increments reference count.
|
|
48
|
-
* Returns the new count.
|
|
49
|
-
*/
|
|
50
|
-
export declare function trackSession(projectDir: string): number;
|
|
51
|
-
/**
|
|
52
|
-
* Untrack a session for a project. Decrements reference count.
|
|
53
|
-
* When count drops to 0, all watch processes for that project
|
|
54
|
-
* are automatically stopped.
|
|
55
|
-
* Returns the remaining count.
|
|
56
|
-
*/
|
|
57
|
-
export declare function untrackSession(projectDir: string): number;
|
|
58
|
-
/** Get active session count for a project. */
|
|
59
|
-
export declare function getSessionCount(projectDir: string): number;
|
|
60
|
-
export interface ToolAvailability {
|
|
61
|
-
/** Whether codegraph is available (via npx or node_modules) */
|
|
62
|
-
codegraph: boolean;
|
|
63
|
-
/** Whether graphify/graphifyy is available (via pip) */
|
|
64
|
-
graphify: boolean;
|
|
65
|
-
/** Whether .codegraph/ directory already exists in the project */
|
|
66
|
-
codegraphIndexExists: boolean;
|
|
67
|
-
/** Whether graphify-out/ directory already exists in the project */
|
|
68
|
-
graphifyIndexExists: boolean;
|
|
69
|
-
}
|
|
70
|
-
/**
|
|
71
|
-
* Stop all active watch processes for a project.
|
|
72
|
-
*/
|
|
73
|
-
export declare function stopWatches(projectDir?: string): void;
|
|
74
|
-
/** Check if watches are active for a project. */
|
|
75
|
-
export declare function hasActiveWatcher(projectDir: string, tool?: "codegraph" | "graphify"): boolean;
|
|
76
|
-
export interface GraphSyncResult {
|
|
77
|
-
/** Whether synchronization was attempted */
|
|
78
|
-
attempted: boolean;
|
|
79
|
-
/** Codes that describe the outcome */
|
|
80
|
-
codes: GraphSyncCode[];
|
|
81
|
-
/** Tool availability before init */
|
|
82
|
-
availability: ToolAvailability;
|
|
83
|
-
/** Whether this project was already initialized this session */
|
|
84
|
-
alreadyInitialized: boolean;
|
|
85
|
-
}
|
|
86
|
-
export type GraphSyncCode = "codegraph-initialized" | "codegraph-already-exists" | "codegraph-unavailable" | "codegraph-install-failed" | "codegraph-install-skipped" | "graphify-initialized" | "graphify-already-exists" | "graphify-unavailable" | "graphify-install-failed" | "graphify-install-skipped" | "watch-started-codegraph" | "watch-started-graphify" | "disabled" | "error";
|
|
87
|
-
/**
|
|
88
|
-
* Run the graphSync pipeline. Best-effort, never throws.
|
|
89
|
-
*/
|
|
90
|
-
export declare function runGraphSync(config?: GraphSyncConfig): Promise<GraphSyncResult>;
|
package/dist/index.d.ts
DELETED
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
import type { PluginModule } from "@opencode-ai/plugin";
|
|
2
|
-
/**
|
|
3
|
-
* @sisyphuslabs/omo-meta-governor — Self-judging agent orchestration layer.
|
|
4
|
-
*
|
|
5
|
-
* Default export is an OpenCode PluginModule that registers a
|
|
6
|
-
* `tool.execute.after` hook. The MetaGovernor reads session signals,
|
|
7
|
-
* scores them against weighted evidence, and dispatches decisions.
|
|
8
|
-
*
|
|
9
|
-
* Install:
|
|
10
|
-
* npm install @sisyphuslabs/omo-meta-governor
|
|
11
|
-
*
|
|
12
|
-
* Configure:
|
|
13
|
-
* ```jsonc
|
|
14
|
-
* {
|
|
15
|
-
* "meta_governor": {
|
|
16
|
-
* "enabled": true
|
|
17
|
-
* }
|
|
18
|
-
* }
|
|
19
|
-
* ```
|
|
20
|
-
*/
|
|
21
|
-
declare const pluginModule: PluginModule;
|
|
22
|
-
export default pluginModule;
|
|
23
|
-
export { createMetaGovernorPlugin, type MetaGovernorPluginDeps } from "./plugin";
|
|
24
|
-
export { logToFile } from "./file-logger";
|
|
25
|
-
export { runMetaGovernor, buildDecisionContext, defaultOrchestratorConfig, } from "./orchestrator";
|
|
26
|
-
export { loadOrchestratorConfig, isMetaGovernorEnabled, type MetaGovernorPluginConfig, } from "./config";
|
|
27
|
-
export { score, defaultScoringConfig } from "./scoring-engine";
|
|
28
|
-
export { predict, defaultTokenPredictorConfig, calculateBurnRate } from "./token-predictor";
|
|
29
|
-
export { handleDecision, defaultDecisionHandlerConfig, trimHistory, countConsecutiveStops } from "./decision-handler";
|
|
30
|
-
export { observeAndLearn, defaultClosedLoopConfig } from "./closed-loop-learning";
|
|
31
|
-
export { aggregateRead } from "./memory-aggregator";
|
|
32
|
-
export { recordRecovery, type RecoveryOutcome } from "./post-repair-recorder";
|
|
33
|
-
export { storeDecision, takeDecision, hasDecision, takeAnyDecision, clearAll, } from "./decision-store";
|
|
34
|
-
export type { Decision, DecisionContext, DecisionHandlerConfig, DecisionHandlerInput, DecisionHandlerOutput, Deviation, Evidence, EvidenceContribution, InterventionConfig, InterventionMode, LearnFromOutcomeInput, LearnFromOutcomeOutput, MemoryRead, MemoryBackends, AgentmemoryWriteBackend, MetaGovernorInput, MetaGovernorOutput, OrchestratorConfig, ScoringConfig, ScoringResult, SlotMemory, TokenPredictorConfig, TokenPredictorInput, TokenPredictorOutput, ClosedLoopConfig, } from "./types";
|
|
35
|
-
export { loadProtocol, buildSystemInjection, auditToolCall, DEFAULT_PROTOCOL_PATH, } from "./protocol-enforcer";
|
|
36
|
-
export { stripJsoncComments, parseJsonc, loadJsoncFile, deepMerge, loadMetaGovernorConfig, getUserConfigPath, getProjectConfigPath, type ConfigFileSources, type ConfigFileResult, } from "./config-file";
|
|
37
|
-
export { runGraphSync, stopWatches, resetInitializedProjects, type GraphSyncConfig, type GraphSyncResult, type GraphSyncCode, type ToolAvailability, } from "./graph-sync";
|
|
38
|
-
export { generateSchema, writeSchemaFile, type JsonSchema, type JsonSchemaProperty } from "./generate-schema";
|
|
39
|
-
export { loadOrchestratorConfigFromSources } from "./config";
|
|
40
|
-
export type { ProtocolViolation, ProtocolEnforcementSessionState } from "./types";
|
package/dist/index.js
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
import{createRequire as uK}from"node:module";var fK=Object.defineProperty;var mK=(K)=>K;function gK(K,Q){this[K]=mK.bind(null,Q)}var pK=(K,Q)=>{for(var X in Q)fK(K,X,{get:Q[X],enumerable:!0,configurable:!0,set:gK.bind(Q,X)})};var dK=(K,Q)=>()=>(K&&(Q=K(K=0)),Q);var WK=uK(import.meta.url);var CK={};pK(CK,{stripJsoncComments:()=>o,parseJsonc:()=>e,loadMetaGovernorConfig:()=>yK,loadJsoncFile:()=>h,getUserConfigPath:()=>KK,getProjectConfigPath:()=>QK,deepMerge:()=>T});import{readFile as RQ,access as kQ}from"node:fs/promises";import{resolve as bK}from"node:path";import{homedir as NQ}from"node:os";function o(K){let Q=[],X=0;while(X<K.length){let $=K[X];if($==='"'||$==="'"){let J=$;Q.push(J),X++;while(X<K.length){let z=K[X];if(Q.push(z),z==="\\"){if(X++,X<K.length)Q.push(K[X])}else if(z===J){X++;break}X++}continue}if($==="/"&&X+1<K.length&&K[X+1]==="/"){X+=2;while(X<K.length&&K[X]!==`
|
|
2
|
-
`)X++;continue}if($==="/"&&X+1<K.length&&K[X+1]==="*"){X+=2;while(X<K.length){if(K[X]==="*"&&X+1<K.length&&K[X+1]==="/"){X+=2;break}X++}continue}Q.push($),X++}let Z=Q.join("");for(let $=0;$<10;$++){let J=Z;if(Z=Z.replace(/,(\s*[\]}])/g,"$1"),Z===J)break}return Z}function e(K){try{let Q=o(K);return JSON.parse(Q)}catch{return}}function KK(){return bK(NQ(),".config","opencode",jK)}function QK(K){let Q=K??process.cwd();return bK(Q,".opencode",jK)}async function EQ(K){try{return await kQ(K),!0}catch{return!1}}async function h(K){if(!await EQ(K))return;try{let Q=await RQ(K,"utf-8");return e(Q)}catch{return}}function T(K,Q){let X={...K};for(let Z of Object.keys(Q)){let $=Q[Z],J=X[Z];if($===void 0)continue;if(TK($)&&TK(J))X[Z]=T(J,$);else X[Z]=$}return X}function TK(K){return typeof K==="object"&&K!==null&&!Array.isArray(K)}async function yK(K={}){let Q=[],X="defaults",Z={},$=KK(),J=await h($);if(J)Z=T(Z,J),Q.push(`user:${$}`),X="user";let z=QK(K.projectDir),q=await h(z);if(q)Z=T(Z,q),Q.push(`project:${z}`),X="project";if(K.cliOptions&&Object.keys(K.cliOptions).length>0)Z=T(Z,K.cliOptions),Q.push("cli:inline"),X="cli";return{config:Z,sources:Q,effectiveSource:X}}var jK="omo-meta-governor.jsonc";var XK=()=>{};import{execSync as P,spawn as HK}from"node:child_process";import{access as lK,stat as aK}from"node:fs/promises";import{resolve as x}from"node:path";import{constants as cK}from"node:fs";async function rK(K,Q=60000){try{return P("npm i -D @colbymchenry/codegraph",{cwd:K,stdio:"ignore",timeout:Q}),"codegraph-installed"}catch{return"codegraph-install-failed"}}async function nK(K=60000){try{return P("pip install graphifyy --break-system-packages --quiet",{stdio:"ignore",timeout:K}),"graphify-installed"}catch{try{return P("uv tool install graphifyy --quiet",{stdio:"ignore",timeout:K}),"graphify-installed"}catch{return"graphify-install-failed"}}}var m=new Set;function sK(){m.clear()}var UK=new Map;function wK(K){let X=(UK.get(K)??0)+1;return UK.set(K,X),X}async function GK(K){let Q=!1,X=!1,Z=await _K(x(K,".codegraph")),$=await _K(x(K,"graphify-out"));try{P("npx --yes codegraph --version",{stdio:"ignore",timeout:1e4}),Q=!0}catch{try{P("node node_modules/.bin/codegraph --version",{cwd:K,stdio:"ignore",timeout:5000}),Q=!0}catch{}}try{P("python3 -c 'import graphify; print(graphify.__version__)'",{stdio:"ignore",timeout:5000}),X=!0}catch{try{P("python3 -c 'import graphifyy; print(graphifyy.__version__)'",{stdio:"ignore",timeout:5000}),X=!0}catch{}}return{codegraph:Q,graphify:X,codegraphIndexExists:Z,graphifyIndexExists:$}}async function iK(K){let Q=x(K,".codegraph");await AK(Q);try{P("npx --yes codegraph init",{cwd:K,stdio:"ignore",timeout:60000})}catch{}}async function tK(K){let Q=x(K,"graphify-out");await AK(Q);try{P("python3 -m graphify . --no-viz",{cwd:K,stdio:"ignore",timeout:120000})}catch{try{P("graphifyy . --no-viz",{cwd:K,stdio:"ignore",timeout:120000})}catch{}}}var j=new Map;function FK(K,Q){let X=`${K}:${Q}`;if(j.has(X))return;try{let Z;if(Q==="codegraph")Z=HK("node",["-e",`
|
|
3
|
-
const {execSync} = require("child_process");
|
|
4
|
-
const run = () => {
|
|
5
|
-
try { execSync("npx codegraph update 2>/dev/null", {cwd: ${JSON.stringify(K)}, stdio: "ignore"}); }
|
|
6
|
-
catch(e) { /* best effort */ }
|
|
7
|
-
};
|
|
8
|
-
run();
|
|
9
|
-
setInterval(run, 30_000);
|
|
10
|
-
`],{stdio:"ignore",detached:!0});else Z=HK("python3",["-m","graphify",".","--no-viz","--watch"],{cwd:K,stdio:"ignore",detached:!0});Z.unref(),j.set(X,{process:Z,tool:Q}),Z.on("exit",()=>{j.delete(X)})}catch{}}function oK(K){for(let[Q,X]of j)if(!K||Q.startsWith(K)){try{X.process.kill("SIGTERM")}catch{}setTimeout(()=>{try{X.process.kill("SIGKILL")}catch{}},2000).unref(),j.delete(Q)}}async function g(K={enabled:!0,watch:!1,autoInstall:!0,installTimeoutMs:60000}){let Q=[],X=K.projectDir??process.cwd();if(!K.enabled)return{attempted:!1,codes:["disabled"],availability:{codegraph:!1,graphify:!1,codegraphIndexExists:!1,graphifyIndexExists:!1},alreadyInitialized:!1};if(m.has(X)){let $=await GK(X);return{attempted:!1,codes:$.codegraphIndexExists?["codegraph-already-exists"]:[],availability:$,alreadyInitialized:!0}}m.add(X);let Z;try{Z=await GK(X)}catch{return{attempted:!1,codes:["error"],availability:{codegraph:!1,graphify:!1,codegraphIndexExists:!1,graphifyIndexExists:!1},alreadyInitialized:!1}}if(K.autoInstall!==!1){if(!Z.codegraph){let $=await rK(X,K.installTimeoutMs??60000);if(Q.push($),$==="codegraph-installed")Z.codegraph=!0}if(!Z.graphify){let $=await nK(K.installTimeoutMs??60000);if(Q.push($),$==="graphify-installed")Z.graphify=!0}}else{if(!Z.codegraph)Q.push("codegraph-install-skipped");if(!Z.graphify)Q.push("graphify-install-skipped")}if(Z.codegraph)if(!Z.codegraphIndexExists)try{await iK(X),Q.push("codegraph-initialized")}catch{Q.push("error")}else Q.push("codegraph-already-exists");else Q.push("codegraph-unavailable");if(Z.graphify)if(!Z.graphifyIndexExists)try{await tK(X),Q.push("graphify-initialized")}catch{Q.push("error")}else Q.push("graphify-already-exists");else Q.push("graphify-unavailable");if(K.watch){if(Z.codegraph)FK(X,"codegraph"),Q.push("watch-started-codegraph");if(Z.graphify)FK(X,"graphify"),Q.push("watch-started-graphify")}return{attempted:!0,codes:Q,availability:Z,alreadyInitialized:!1}}async function _K(K){try{return(await aK(K)).isDirectory()}catch{return!1}}async function AK(K){try{await lK(K,cK.F_OK)}catch{let{mkdir:Q}=await import("node:fs/promises");await Q(K,{recursive:!0})}}var LK={limits:{maxLessons:10,maxSlots:20,maxTasks:10},timeouts:{agentmemoryMs:2000,magicContextMs:1000,boulderStateMs:1000}};async function l(K,Q){let X=performance.now(),Z={...LK.limits,...K.limits},$={...LK.timeouts,...K.timeouts},[J,z,q]=await Promise.allSettled([eK(K,Q.agentmemory,Z,$.agentmemoryMs),KQ(K,Q.magicContext,Z,$.magicContextMs),QQ(K,Q.boulderState,Z,$.boulderStateMs)]),B=[],W={},H=J.status==="fulfilled"?J.value:(d(B,W,"agentmemory",p(J.reason)),u.agentmemory),U=z.status==="fulfilled"?z.value:(d(B,W,"magicContext",p(z.reason)),u.magicContext),G=q.status==="fulfilled"?q.value:(d(B,W,"boulderState",p(q.reason)),u.boulderState);return{query:K.query,timestampISO:new Date().toISOString(),agentmemory:H,magicContext:U,boulderState:G,degradedSources:B,durationMs:performance.now()-X,errorMessages:W}}async function eK(K,Q,X,Z){let $=await a(Q.smartSearch({query:K.query,limit:X.maxLessons}),Z,"agentmemory");return{available:!0,lessons:XQ($.lessons).slice(0,X.maxLessons).map((z)=>({id:z.id,title:z.title,advice:"info",confidence:z.confidence,concepts:z.concepts}))}}async function KQ(K,Q,X,Z){return{available:!0,slots:(await a(Q.slotList({directory:K.directory}),Z,"magicContext")).filter((J)=>J.label.startsWith("meta_governor:")||ZQ(J,K.query)).sort((J,z)=>J.label.localeCompare(z.label)).slice(0,X.maxSlots).map((J)=>({label:J.label,content:J.content}))}}async function QQ(K,Q,X,Z){let $=await a(Q.boulderRead({directory:K.directory,sessionID:K.sessionID,query:K.query}),Z,"boulderState");return{available:!0,tasks:$.sort((z,q)=>z.priority-q.priority||q.updatedAtMs-z.updatedAtMs).slice(0,X.maxTasks).map((z)=>({id:z.id,status:z.status,title:z.title})),planProgress:$Q($)}}function XQ(K){return[...K].sort((Q,X)=>X.confidence-Q.confidence)}function ZQ(K,Q){let X=Q.toLowerCase();return K.label.toLowerCase().includes(X)||K.content.toLowerCase().includes(X)}function $Q(K){if(K.length===0)return 0;return K.filter((X)=>X.status==="done").length/K.length}function p(K){if(K instanceof Error)return K.message;if(typeof K==="string")return K;return"unknown error"}function d(K,Q,X,Z){K.push(X),Q[X]=Z}var u={agentmemory:{available:!1,lessons:[]},magicContext:{available:!1,slots:[]},boulderState:{available:!1,tasks:[],planProgress:0}};async function a(K,Q,X){return new Promise((Z,$)=>{let J=setTimeout(()=>$(Error(`${X} timeout after ${Q}ms`)),Q);K.then((z)=>{clearTimeout(J),Z(z)},(z)=>{clearTimeout(J),$(z)})})}function JQ(){return{compactBurnRateThreshold:500,compactUsageThreshold:0.85,switchModelUsageThreshold:0.95,delegateConsecutiveHighBurn:5,windowSize:10}}function PK(K){if(K.length===0)return 0;return K.reduce((X,Z)=>X+Z,0)/K.length}function qQ(K,Q){let X=0;for(let Z=K.length-1;Z>=0;Z--)if(K[Z]>=Q)X++;else break;return X}function zQ(K,Q,X,Z){let $=Q-K;if($<=0)return Z;if(X<=0)return null;let J=Math.floor($/X);if(J<=0)return Z;let z=J*2;return new Date(new Date(Z).getTime()+z*1000).toISOString()}function c(K){let{currentUsage:Q,modelLimit:X,recentTurnTokens:Z,timestampISO:$,config:J}=K,z=Z.slice(-J.windowSize),q=PK(z),B=X-Q,W=X>0?Q/X:1,H=Math.min(0.95,0.3+z.length/J.windowSize*0.65),U="no-action",G="within normal parameters";if(W>=J.switchModelUsageThreshold)U="switch-model",G=`context usage ${(W*100).toFixed(1)}% exceeds switch threshold ${(J.switchModelUsageThreshold*100).toFixed(1)}%`;if(W>=J.compactUsageThreshold||q>=J.compactBurnRateThreshold){if(U==="no-action")U="compact-now",G=W>=J.compactUsageThreshold?`context usage ${(W*100).toFixed(1)}% exceeds compact threshold ${(J.compactUsageThreshold*100).toFixed(1)}%`:`burn rate ${q.toFixed(0)} tokens/turn exceeds threshold ${J.compactBurnRateThreshold}`}let w=qQ(z,J.compactBurnRateThreshold);if(w>=J.delegateConsecutiveHighBurn&&U==="no-action")U="delegate-to-subagent",G=`${w} consecutive high-burn turns (threshold: ${J.delegateConsecutiveHighBurn})`;let F=zQ(Q,X,q,$);return{currentUsage:Q,burnRate:q,budgetLeft:B,willOverflowAt:F,recommendation:U,confidence:H,modelLimit:X,windowRemaining:Math.max(0,Math.floor(B/Math.max(q,1))),input:{...K},computedAtISO:$,turnsAnalyzed:z.length}}var M={"oracle-verified":0.25,"no-progress-detector":0.2,"deviation-detector":0.2,"iteration-budget":0.15,"lesson-recall":0.1,"token-predictor":0.1},I=()=>({continueThreshold:0.3,warnThreshold:0.3,escalateThreshold:0.6,stopThreshold:0.8,paralysisThreshold:3,defaultEscalationTarget:"oracle"});function BQ(K){let Q=[];Q.push({source:"oracle-verified",rawScore:K.oracleVerified?0.6:0,weight:M["oracle-verified"],weightedScore:K.oracleVerified?0.6*M["oracle-verified"]:0,description:K.oracleVerified?"Oracle verification passed":"No Oracle verification"}),Q.push({source:"no-progress-detector",rawScore:K.noProgress?-0.8:0,weight:M["no-progress-detector"],weightedScore:K.noProgress?-0.8*M["no-progress-detector"]:0,description:K.noProgress?"No progress detected in last turn":"Progress detected"});let X=YQ(K.deviations);Q.push({source:"deviation-detector",rawScore:X,weight:M["deviation-detector"],weightedScore:X*M["deviation-detector"],description:K.deviations.length>0?`${K.deviations.length} deviation(s) detected (worst: ${K.deviations[0].severity})`:"No deviations detected"});let Z=VQ(K.iterationRatio);Q.push({source:"iteration-budget",rawScore:Z,weight:M["iteration-budget"],weightedScore:Z*M["iteration-budget"],description:`Iteration ratio: ${K.iterationRatio.toFixed(2)} (${K.ambient.iteration}/${K.ambient.maxIterations})`});let $=WQ(K.lessonsRelevant);return Q.push({source:"lesson-recall",rawScore:$,weight:M["lesson-recall"],weightedScore:$*M["lesson-recall"],description:K.lessonsRelevant.length>0?`${K.lessonsRelevant.length} relevant lesson(s) (avg confidence: ${HQ(K.lessonsRelevant).toFixed(2)})`:"No relevant lessons"}),Q}function YQ(K){if(K.length===0)return 0;let Q={grave:-0.9,media:-0.5,leve:-0.2},X=0;for(let $ of K){let J=Q[$.severity]??-0.3;if(J<X)X=J}let Z=Math.min(K.length*0.05,0.2);return Math.max(X-Z,-1)}function VQ(K){if(K<=0.5)return-K*0.6;return-0.3-(K-0.5)*1}function WQ(K){if(K.length===0)return 0;let Q=0;for(let X of K)Q+=({continue:0.3,info:0,warn:-0.3,stop:-0.7}[X.advice]??0)*X.confidence;return Math.max(Math.min(Q/K.length,1),-1)}function HQ(K){if(K.length===0)return 0;return K.reduce((Q,X)=>Q+X.confidence,0)/K.length}function UQ(K,Q){if(K>=Q.continueThreshold)return"continue";if(K<=-Q.stopThreshold)return"stop";if(K<=-Q.escalateThreshold)return"escalate";if(K<=-Q.warnThreshold)return"warn";return"continue"}function GQ(K,Q){if(!K.oracleVerified)return"oracle";if(K.deviations.some((X)=>X.severity==="grave"))return"user";return Q.defaultEscalationTarget}function MK(K,Q,X,Z){if(Z)return`Paralysis detected: forced continue despite score ${K.toFixed(3)} (too many consecutive stops)`;let $=[...X].sort((W,H)=>W.weightedScore-H.weightedScore),J=$[0],z=$[$.length-1],q=[];if(J.weightedScore<0)q.push(`primary concern: ${J.description}`);if(z.weightedScore>0)q.push(`positive signal: ${z.description}`);return`${{continue:"Continue",warn:"Warn",escalate:"Escalate",stop:"Stop"}[Q]} (score: ${K.toFixed(3)}): ${q.join("; ")||"balanced signals"}`}function r(K,Q){let X={...I(),...Q},Z=BQ(K),$=Z.reduce((U,G)=>U+G.weightedScore,0),J=Math.max(Math.min($,1),-1),z=K.slotMemory.consecutiveStops>=X.paralysisThreshold&&J<=-X.warnThreshold,q=z?"continue":UQ(J,X),B=[];if(q!=="continue"||Math.abs(J)<X.continueThreshold){for(let U of Z)if(Math.abs(U.weightedScore)>0.01)B.push({source:U.source,value:U.description,confidence:Math.abs(U.rawScore),weight:U.weight});if(B.length===0&&q!=="continue")B.push({source:"ambient",value:MK(J,q,Z,z),confidence:0.5,weight:0.1})}let W=q==="escalate"?GQ(K,X):null;return{decision:{action:q,score:J,reasoning:MK(J,q,Z,z),evidence:B,shouldEscalateTo:W},contributions:Z,rawScore:J,paralysisOverride:z,computedAtISO:new Date().toISOString()}}var S=()=>({enabled:!0,maxHistoryPerSession:50,forceContinueAfterStops:3,warnMessageTemplate:"[MetaGovernor] Score {score}: {reasoning}. Evidence: {evidenceCount} signal(s).",escalateMessageTemplate:"[MetaGovernor] Escalating to {target}: {reasoning}",stopMessageTemplate:"[MetaGovernor] STOP — {reasoning}. Evidence: {evidenceCount} signal(s)."});function D(K,Q){let X=K;for(let[Z,$]of Object.entries(Q))X=X.replaceAll(`{${Z}}`,$);return X}function FQ(K){return K.length}function n(K,Q){let X={...S(),...Q};if(!X.enabled)return{action:"continue",message:null,historyEntry:{decision:K.scoringResult.decision,action:"continue",timestampISO:new Date().toISOString(),sessionID:K.sessionID,reasoning:"Decision handler disabled — pass-through continue"}};let Z=K.scoringResult.decision,$=Z.score,J=Z.reasoning,z=FQ(Z.evidence),q=Z.shouldEscalateTo??X.defaultEscalationTarget??"oracle";if(K.scoringResult.paralysisOverride)return{action:"continue",message:D(X.warnMessageTemplate,{score:$.toFixed(3),reasoning:`Paralysis detected — forced continue. ${J}`,evidenceCount:String(z)}),historyEntry:{decision:Z,action:"continue",timestampISO:new Date().toISOString(),sessionID:K.sessionID,reasoning:`Paralysis override: ${J}`}};switch(Z.action){case"continue":return{action:"continue",message:null,historyEntry:{decision:Z,action:"continue",timestampISO:new Date().toISOString(),sessionID:K.sessionID,reasoning:J}};case"warn":return{action:"warn",message:D(X.warnMessageTemplate,{score:$.toFixed(3),reasoning:J,evidenceCount:String(z)}),historyEntry:{decision:Z,action:"warn",timestampISO:new Date().toISOString(),sessionID:K.sessionID,reasoning:J}};case"escalate":return{action:"escalate",message:D(X.escalateMessageTemplate,{target:q,reasoning:J}),historyEntry:{decision:Z,action:"escalate",timestampISO:new Date().toISOString(),sessionID:K.sessionID,reasoning:`Escalate to ${q}: ${J}`}};case"stop":return{action:"stop",message:D(X.stopMessageTemplate,{reasoning:J,evidenceCount:String(z)}),historyEntry:{decision:Z,action:"stop",timestampISO:new Date().toISOString(),sessionID:K.sessionID,reasoning:J}}}}function _Q(K,Q){if(K.length<=Q)return{trimmed:[...K],dropped:0};let X=K.length-Q;return{trimmed:K.slice(-Q),dropped:X}}function wQ(K){let Q=0;for(let X=K.length-1;X>=0;X--)if(K[X].action==="stop")Q++;else break;return Q}var OK={leve:0,media:1,grave:2};function AQ(K,Q,X){let Z=`${K}-${Q}-${X}`.split("").reduce(($,J)=>($<<5)-$+J.charCodeAt(0)|0,0);return`D-${Math.abs(Z).toString(36)}`}function RK(K,Q){let X=OK[Q]??0;return K.some((Z)=>(OK[Z.severity]??0)>=X)}function LQ(K){let Q=new Set;for(let X of K)Q.add(X.category),Q.add(X.severity);return[...Q]}function PQ(K,Q){let X=Q.map((Z)=>`[${Z.severity}] ${Z.category}: ${Z.detail}`).join("; ");return`Action "${K.action}" (score ${K.score.toFixed(2)}) after deviations: ${X}. Reasoning: ${K.reasoning}`}async function s(K,Q){let{decision:X,config:Z,sessionID:$,directory:J,filesChanged:z}=K,q=new Date().toISOString();if(!Z.enabled)return{lessonSaved:null,decisionSaved:null,reason:"closed-loop learning disabled"};if(X.evidence.length===0&&X.action==="continue")return{lessonSaved:null,decisionSaved:null,reason:"no deviations to learn from"};let B=null,W=null;if(Z.saveDecisions){let G={id:AQ($,X.action,q),timestampISO:q,action:X.action,score:X.score,reasoning:X.reasoning,sessionID:$,directory:J,deviations:X.evidence.filter((w)=>w.source==="deviation-detector").map((w)=>({severity:"media",category:w.source,detail:w.value}))};try{await Q.saveMemory({content:`Decision: ${X.action} (score ${X.score.toFixed(2)}). ${X.reasoning}`,concepts:["meta-governor","decision",X.action],type:"fact",files:[...z]}),W=G}catch{}}let H=X.evidence.filter((G)=>G.source==="deviation-detector").map((G)=>({severity:"media",category:G.source,detail:G.value}));if(RK(H,Z.minSeverityToLearn)){let G=LQ(H),w=PQ(X,H);try{B={id:(await Q.saveLesson({content:w,context:`session:${$} dir:${J}`,confidence:Math.max(0.3,Math.min(0.8,Math.abs(X.score))),tags:G})).id,title:`${X.action} after ${H[0]?.category??"deviation"}`,content:w,type:"pattern",concepts:G,confidence:Math.max(0.3,Math.min(0.8,Math.abs(X.score))),files:[...z],sessionID:$}}catch{}}let U=[];if(W)U.push("decision saved");if(B)U.push("lesson saved");if(!W&&!B)if(!RK(H,Z.minSeverityToLearn))U.push("severity below threshold");else U.push("no saveable content");return{lessonSaved:B,decisionSaved:W,reason:U.join("; ")||"no action taken"}}function k(){return{enabled:!0,minSeverityToLearn:"media",maxLessonsPerSession:20,saveDecisions:!0}}var NK=()=>({enabled:!0,memory:{enabled:!0,query:"",timeoutMs:3000},tokenPredictor:{},scoring:{},decision:{},closedLoop:{},intervention:{mode:"silent",includeDecisionHistory:!0,maxHistoryMessages:5,minActionForMessage:"warn"},protocolEnforcement:{enabled:!1,path:void 0,injectIntoSystem:!1,auditToolCalls:!1}}),i={query:"",timestampISO:new Date().toISOString(),agentmemory:{available:!1,lessons:[]},magicContext:{available:!1,slots:[]},boulderState:{available:!1,tasks:[],planProgress:0},degradedSources:["agentmemory","magicContext","boulderState"]},MQ={consecutiveStops:0,consecutiveContinues:0,lastUpdatedISO:new Date().toISOString()},OQ={action:"continue",message:null,historyEntry:{decision:{action:"continue",score:0,reasoning:"no decision made",evidence:[],shouldEscalateTo:null},action:"continue",timestampISO:new Date().toISOString(),sessionID:"",reasoning:"no decision made"}};function EK(K,Q=i){let X=K.maxIterations>0?K.iteration/K.maxIterations:0,Z={...MQ,consecutiveStops:K.consecutiveStops??0};return{oracleVerified:K.oracleVerified,noProgress:K.noProgress,deviations:K.deviations,iterationRatio:X,lessonsRelevant:Q.agentmemory.lessons,slotMemory:Z,ambient:{sessionID:K.sessionID,directory:".",mode:"simple",agentName:K.agentName??"unknown",iteration:K.iteration,maxIterations:K.maxIterations}}}async function t(K,Q={}){let X={...NK(),...Q};if(!X.enabled)return{memoryRead:i,tokenPrediction:kK(K),scoringResult:{decision:{action:"continue",score:0,reasoning:"MetaGovernor disabled",evidence:[],shouldEscalateTo:null},contributions:[],rawScore:0,paralysisOverride:!1,computedAtISO:new Date().toISOString()},decision:OQ,lessonSaved:null,decisionHistory:[],skipped:!0,skipReason:"disabled"};let Z=i;if(X.memory.enabled)try{let W={agentmemory:K.backends.agentmemory,magicContext:K.backends.magicContext,boulderState:K.backends.boulderState};Z=await l({directory:".",sessionID:K.sessionID,query:X.memory.query||K.toolName},W)}catch{}let $;try{$=c({currentUsage:K.recentTurnTokens.reduce((W,H)=>W+H,0),modelLimit:K.modelLimit??Q.modelOverride?.modelLimit??200000,recentTurnTokens:K.recentTurnTokens,timestampISO:new Date().toISOString(),providerID:K.providerID??"",modelID:K.modelID??"",config:X.tokenPredictor})}catch{$=kK(K)}let J=r(EK(K,Z),X.scoring),z={sessionID:K.sessionID,scoringResult:J},q=n(z,X.decision),B=null;try{if(X.closedLoop.enabled!==!1)B=await s({decision:q.historyEntry.decision,memoryRead:Z,config:{...k(),...X.closedLoop},sessionID:K.sessionID,directory:".",filesChanged:[]},K.writeBackend)}catch{}return{memoryRead:Z,tokenPrediction:$,scoringResult:J,decision:q,lessonSaved:B,decisionHistory:[q.historyEntry],skipped:!1}}function kK(K){let Q=K.recentTurnTokens.reduce((X,Z)=>X+Z,0);return{burnRate:0,budgetLeft:200000,currentUsage:Q,modelLimit:200000,willOverflowAt:null,recommendation:"no-action",confidence:1,windowRemaining:200000,input:{currentUsage:Q,modelLimit:200000,recentTurnTokens:K.recentTurnTokens,timestampISO:new Date().toISOString(),providerID:K.providerID??"",modelID:K.modelID??"",config:{compactBurnRateThreshold:500,compactUsageThreshold:0.85,switchModelUsageThreshold:0.95,delegateConsecutiveHighBurn:5,windowSize:10}},computedAtISO:new Date().toISOString(),turnsAnalyzed:K.recentTurnTokens.length}}function v(K){let Q={enabled:!1,...K},X=I(),Z=S(),$=k();return{enabled:Q.enabled===!0,memory:{enabled:!0,query:Q.memory?.query??"meta_governor_context",timeoutMs:Q.memory?.agentmemoryTimeoutMs??2000},tokenPredictor:{compactBurnRateThreshold:Q.tokenPredictor?.compactBurnRateThreshold??500,compactUsageThreshold:Q.tokenPredictor?.compactUsageThreshold??0.85,switchModelUsageThreshold:Q.tokenPredictor?.switchModelUsageThreshold??0.95,delegateConsecutiveHighBurn:Q.tokenPredictor?.delegateConsecutiveHighBurn??5},scoring:{...X,...Q.scoring?.continueThreshold!==void 0?{continueThreshold:Q.scoring.continueThreshold}:{},...Q.scoring?.warnThreshold!==void 0?{warnThreshold:Q.scoring.warnThreshold}:{},...Q.scoring?.escalateThreshold!==void 0?{escalateThreshold:Q.scoring.escalateThreshold}:{},...Q.scoring?.stopThreshold!==void 0?{stopThreshold:Q.scoring.stopThreshold}:{}},closedLoop:{...$,...Q.closedLoop?.saveDecisions!==void 0?{saveDecisions:Q.closedLoop.saveDecisions}:{}},decision:{...Z,...Q.decision?.maxHistoryPerSession!==void 0?{maxHistoryPerSession:Q.decision.maxHistoryPerSession}:{},...Q.decision?.forceContinueAfterStops!==void 0?{forceContinueAfterStops:Q.decision.forceContinueAfterStops}:{}},modelOverride:Q.modelOverride?{providerID:Q.modelOverride.providerID,modelID:Q.modelOverride.modelID,modelLimit:Q.modelOverride.modelLimit,temperature:Q.modelOverride.temperature??0.2,topP:Q.modelOverride.topP??1,maxTokens:Q.modelOverride.maxTokens??2048,reasoning:Q.modelOverride.reasoning??!1,verbosity:Q.modelOverride.verbosity??"minimal"}:void 0,intervention:{mode:Q.intervention?.mode??"silent",includeDecisionHistory:Q.intervention?.includeDecisionHistory??!0,maxHistoryMessages:Q.intervention?.maxHistoryMessages??5,minActionForMessage:Q.intervention?.minActionForMessage??"warn"},protocolEnforcement:{enabled:Q.protocolEnforcement?.enabled??!1,path:Q.protocolEnforcement?.path,injectIntoSystem:Q.protocolEnforcement?.injectIntoSystem??!1,auditToolCalls:Q.protocolEnforcement?.auditToolCalls??!1}}}function TQ(K){return K?.enabled===!0}async function bQ(K={}){let{loadMetaGovernorConfig:Q}=await Promise.resolve().then(() => (XK(),CK)),X=await Q(K);return v(X.config)}var N=new Map;function ZK(K,Q){N.set(K,Q)}function $K(K){let Q=N.get(K);if(Q!==void 0)N.delete(K);return Q}function jQ(K){return N.has(K)}function JK(){for(let[K,Q]of N)return N.delete(K),Q;return}function yQ(){N.clear()}import{appendFileSync as CQ,mkdirSync as xQ}from"node:fs";import{resolve as IQ,dirname as DQ}from"node:path";import{homedir as SQ}from"node:os";var xK=IQ(SQ(),".config","opencode","meta-governor.log");function hQ(){try{xQ(DQ(xK),{recursive:!0})}catch{}}function b(K,Q,X){hQ();let Z=new Date().toISOString(),$=X!==void 0?` | ${JSON.stringify(X)}`:"",J=`[${Z}] [${K.toUpperCase()}] ${Q}${$}
|
|
11
|
-
`;try{CQ(xK,J)}catch{}if(K==="error")console.error(`[meta-governor] ${Q}`);else if(K==="warn")console.warn(`[meta-governor] ${Q}`);else console.log(`[meta-governor] ${Q}`)}import{readFile as vQ}from"node:fs/promises";import{resolve as fQ}from"node:path";import{homedir as mQ}from"node:os";var f=fQ(mQ(),".config","opencode","sisyphus-mandatory","sisyphus-mandatory.md");async function qK(K){return await vQ(K??f,"utf-8")}function zK(K){let Q=["","## Sisyphus Protocol Enforcement","","You MUST follow these Sisyphus protocol rules:","","1. **Pre-response Memory Check**: Before any action, read `<project-memory>` and `<session-history-since>` blocks in context. Cite `<memory id>` for any fact used from memory. Do not ask questions whose answers are in those blocks.","","2. **Codebase Graph First**: Before using grep/glob/read for architecture or symbol queries, check whether `.codegraph/` or `graphify-out/` exists. If so, use codegraph/graphify tools first. Fall back to AFT (aft_zoom, aft_outline), then grep/read only as last resort.","","3. **Tool Routing Table**: Match common intents to the correct tool:",' - "we did this before" / "you should know" → `agentmemory_memory_recall`',' - "the usual" / "as configured" → `ctx_memory(action="list")`'," - Starting a task that resembles a previous one → `agentmemory_memory_smart_search`",' - "what changed" / "history" → `ctx_search`'," - Before asking the user a clarifying question → `agentmemory_memory_recall` first"," - Working note for THIS session only → `ctx_note`"," - Save durable insight/decision/rule → `ctx_memory`",""];if(/\boracle\b/i.test(K))Q.push("4. **Post-task Oracle Verification**: If files touched >= 3 OR any INVOKE trigger matches, invoke Oracle with the exact format:",' `task(subagent_type="oracle", run_in_background=false, prompt="Verify: ...")`'," - INVOKE triggers: created 1+ new file, modified abstraction, touched security/auth paths, modified DB/persistence, modified CI/CD, added/removed dependency, modified perf-critical path, todo had 2+ completed items."," - SKIP only when: files touched <= 2, no new file, no dependency change, single-step task, change is typo/comment/rename only."," - Verdict: PASS → done. FAIL/CONDITIONAL → fix and re-invoke. Max 3 invocations."," - Cost: Max 3 oracle invocations per task. Skip rate: Must NOT skip Oracle on 2+ file change.","");return Q.push("5. **Parallel Query Rule**: Fire independent tool queries in the same turn. Do NOT serialize independent memory/context queries.","","6. **Empty-Result Escalation**: On empty `agentmemory_memory_recall`, fire `agentmemory_memory_smart_search` + `ctx_search` + `agentmemory_memory_export` before asking the user.","","7. **Hard Rules (No Exceptions)**:"," - Do NOT ask 'where is X?' if memory or session record already contains it."," - Do NOT claim 'I don't know' before firing at least 2 different recall tools."," - Do NOT re-issue clarifying questions whose answer is in `<project-memory>` or `<session-history-since>`."," - Do NOT use grep/find when aft_outline would answer the structure question."," - Do NOT duplicate a memory in both `agentmemory_memory_save` and `ctx_memory` — pick ONE."," - Do NOT suppress type errors with `as any`, `@ts-ignore`, or `@ts-expect-error`."," - Do NOT leave empty catch blocks `catch(e) {}`.",' - Do NOT start a fresh agent via `task()` when `task(task_id="ses_...")` (continuation) exists — use continuation IDs.'," - Do NOT batch-complete todos — mark each one `completed` immediately after finishing."," - Do NOT skip creating todos for multi-step tasks.","","8. **Self-Check Before Responding**:"," - Verify you read `<project-memory>` and `<session-history-since>` blocks."," - Verify you cited `<memory id>` for any fact used from memory."," - Verify you did not ask a question whose answer is in those blocks."," - For multi-file changes, verify Oracle was invoked."," - For codebase exploration, verify codegraph/graphify was tried before grep/read."," - After discovering something non-obvious, save it with `ctx_memory` so future sessions benefit.",""),Q.join(`
|
|
12
|
-
`)}function BK(K,Q,X){let Z=[],$=X.recentToolCalls??[],J=X.aftAvailable??!1,z=X.aftUsed??!1,q=X.recentWriteContents??[],B=X.memorySaved??!1,W=X.batchCompletions??0;if((K==="grep"||K==="glob")&&(X.hasCodegraphDir||X.hasGraphifyDir)){let F=X.hasCodegraphDir?".codegraph":"graphify-out";Z.push({rule:"codebase-graph-first",tool:K,severity:"media",detail:`Used ${K} when ${F} exists — should use codegraph/graphify first for architecture and symbol queries.`})}if((K==="read"||K==="grep")&&J&&!z)Z.push({rule:"aft-first",tool:K,severity:"media",detail:`AFT tools (aft_outline, aft_zoom) are available but were not tried before using ${K}. Use aft_outline for structure discovery, aft_zoom for symbol source, before falling back to grep/read.`});if(K==="grep"&&J&&!z&&!X.hasCodegraphDir&&!X.hasGraphifyDir)Z.push({rule:"grep-without-aft",tool:K,severity:"leve",detail:"Used grep before checking if aft_outline would answer the structure question. grep is a last resort after graph tools and AFT."});if(K==="task"&&Q&&typeof Q==="object"){let F=Q;if(!F.task_id&&typeof F.prompt==="string"&&$.length>3)Z.push({rule:"continuation-discipline",tool:K,severity:"leve",detail:`Started a new task() without task(task_id="ses_...") continuation ID. Use task_id to preserve the subagent's full context and save tokens.`})}let H=["write","edit","edit_block","desktop-commander_edit_block","desktop-commander_write_file"];if(H.includes(K)){let F=typeof Q==="object"&&Q!==null?JSON.stringify(Q):String(Q??""),A=/@ts-ignore|@ts-expect-error/.test(F),V=/\bas any\b/.test(F);if(A&&V)Z.push({rule:"no-type-suppression",tool:K,severity:"grave",detail:"File write contains both @ts-ignore/@ts-expect-error AND 'as any' — double type suppression. "+"Both are forbidden by the Sisyphus protocol."});else if(A)Z.push({rule:"no-type-suppression",tool:K,severity:"media",detail:"File write contains @ts-ignore or @ts-expect-error — both are forbidden. "+"Fix the underlying type error instead."});else if(V)Z.push({rule:"no-type-suppression",tool:K,severity:"media",detail:"File write contains 'as any' — type suppression forbidden. "+"Use proper type narrowing instead."})}if(H.includes(K)){let F=typeof Q==="object"&&Q!==null?JSON.stringify(Q):String(Q??"");if(/catch\s*\(\s*\w+\s*\)\s*\{\s*\}/.test(F))Z.push({rule:"no-empty-catch",tool:K,severity:"media",detail:"Empty catch block detected — `catch(e) {}` is forbidden. "+"Log the error or handle it gracefully."})}if(["grep","glob","read","aft_zoom","aft_outline","codegraph_explore","graphify query"].includes(K)&&$.length>=2){if(!$.slice(0,5).some((A)=>A.startsWith("ctx_memory"))&&!B)Z.push({rule:"save-discovery-to-memory",tool:K,severity:"leve",detail:`Used ${K} to discover code but ctx_memory was not used afterwards. Save non-obvious findings with ctx_memory so future sessions benefit.`})}if(W>0&&K!=="todowrite")Z.push({rule:"no-batch-todo-completion",tool:K,severity:"leve",detail:"Batch todo completion detected. Each todo must be marked `completed` immediately "+"after finishing — do not batch-complete multiple items."});if(K==="ctx_reduce"&&Q&&typeof Q==="object"){let F=Q.drop;if(typeof F==="string"&&/^\d+-\d+$/i.test(F.trim())){let[A,V]=F.trim().split("-").map(Number);if(!isNaN(A)&&!isNaN(V)&&V-A>10)Z.push({rule:"ctx-reduce-discipline",tool:K,severity:"leve",detail:`Dropped a large range (${F}) with ctx_reduce. The protocol requires reviewing each tag before dropping. Use smaller targeted drops instead of blanket ranges.`})}}if(X.emptyRecall&&!X.escalationAttempted){if(K.startsWith("question")||K==="ask")Z.push({rule:"empty-result-escalation",tool:K,severity:"grave",detail:"Memory recall returned empty but agent did not fire smart_search + ctx_search + export before asking the user. Steps 1-3 of empty-result escalation protocol are mandatory."})}let G=["agentmemory_memory_recall","agentmemory_memory_smart_search","agentmemory_memory_save","ctx_memory","ctx_search","ctx_note"];if(!X.memoryToolsUsed.some((F)=>G.some((A)=>F.startsWith(A)))&&(K.startsWith("question")||K==="ask"))Z.push({rule:"memory-first",tool:K,severity:"grave",detail:"Asked a question without first querying memory (agentmemory or ctx_memory). Must fire agentmemory_memory_recall or ctx_memory before asking the user."});if(X.filesChanged>=3&&!X.oracleInvoked){if(K!=="task"||!Q||typeof Q!=="object"||!("subagent_type"in Q))Z.push({rule:"oracle-verification",tool:K,severity:"media",detail:`Files changed (${X.filesChanged}) >= 3 but Oracle was not invoked. The POST-TASK ORACLE VERIFICATION protocol requires Oracle invocation on multi-file changes.`})}return Z}var IK={continue:0,warn:1,escalate:2,stop:3};function YK(K,Q){return IK[K]>=IK[Q]}function VK(K={},Q={}){if(K.graphSync?.enabled!==!1){let $=process.cwd();g({enabled:!0,watch:K.graphSync?.watch??!1,autoInstall:K.graphSync?.autoInstall??!0,installTimeoutMs:K.graphSync?.installTimeoutMs??60000,projectDir:$}).catch(()=>{}),wK($)}return b("info","MetaGovernor plugin loaded",{version:"0.9.0",graphSync:K.graphSync,intervention:K.intervention,protocolEnforcement:K.protocolEnforcement}),async($,J)=>{let z={...K,...J?.meta_governor??{}},q=v(z);if(!q.enabled)return{};let B=()=>q.modelOverride?.providerID??Q.providerID?.(),W=()=>q.modelOverride?.modelID??Q.modelID?.(),H=()=>q.modelOverride?.modelLimit??200000,U=B()??"unknown",G=W()??"unknown",w;if(q.protocolEnforcement.enabled||q.protocolEnforcement.injectIntoSystem){let V=q.protocolEnforcement.path??f;qK(V).then((Y)=>{w=zK(Y)}).catch((Y)=>{if(typeof console<"u"&&q.modelOverride?.verbosity!=="silent")console.warn("[meta-governor] could not load protocol:",Y instanceof Error?Y.message:Y)})}let F=new Map,A=new Map;return{"tool.execute.before":async(V)=>{if(!q.enabled)return;if(!q.protocolEnforcement.auditToolCalls)return;if(!V.sessionID)return;let Y=F.get(V.sessionID);if(!Y)Y={memoryToolsUsed:[],hasCodegraphDir:!1,hasGraphifyDir:!1,oracleInvoked:!1,filesChanged:0,emptyRecall:!1,escalationAttempted:!1,aftAvailable:!1,aftUsed:!1,recentToolCalls:[],recentWriteContents:[],memorySaved:!1,batchCompletions:0},F.set(V.sessionID,Y);if(w)console.log("[meta-governor] protocol loaded, system injection ready");let _=BK(V.tool,{},{memoryToolsUsed:Y.memoryToolsUsed,hasCodegraphDir:Y.hasCodegraphDir,hasGraphifyDir:Y.hasGraphifyDir,oracleInvoked:Y.oracleInvoked,filesChanged:Y.filesChanged,emptyRecall:Y.emptyRecall,escalationAttempted:Y.escalationAttempted,aftAvailable:Y.aftAvailable,aftUsed:Y.aftUsed,recentToolCalls:Y.recentToolCalls,recentWriteContents:Y.recentWriteContents,memorySaved:Y.memorySaved,batchCompletions:Y.batchCompletions});if(_.length>0){b("warn",`protocol violations on tool ${V.tool}`,_);let O=A.get(V.sessionID)??[];for(let L of _)O.push(`[${L.severity.toUpperCase()}] ${L.rule}: ${L.detail}`);A.set(V.sessionID,O)}else b("info",`audit OK on tool ${V.tool}`)},"tool.execute.after":async(V,Y)=>{if(!q.enabled)return;let _=F.get(V.sessionID);if(_){if(_.recentToolCalls=[V.tool].concat(_.recentToolCalls).slice(0,20),["write","edit","edit_block","desktop-commander_write_file","desktop-commander_edit_block"].includes(V.tool)){_.filesChanged++;let R=(Y.output??"").slice(0,500);_.recentWriteContents=[R].concat(_.recentWriteContents).slice(0,3)}if(["agentmemory_memory_recall","agentmemory_memory_smart_search","agentmemory_memory_save","ctx_memory","ctx_search","ctx_note"].some((R)=>V.tool.startsWith(R))&&!_.memoryToolsUsed.includes(V.tool))_.memoryToolsUsed.push(V.tool);if(V.tool.startsWith("ctx_memory")){let R=Y.output??"";if(R.includes("saved")||R.includes("written"))_.memorySaved=!0}if(V.tool.startsWith("aft_zoom")||V.tool.startsWith("aft_outline"))_.aftUsed=!0;if(V.tool==="task"&&(Y.output??"").includes("subagent_type=oracle"))_.oracleInvoked=!0;let C=(Y.output??"").toLowerCase();if(V.tool.includes("recall")&&(C.includes("returned empty")||C.includes("no results")))_.emptyRecall=!0;if(V.tool==="todowrite"&&(Y.output??"").includes("completed")){if(((Y.output??"").match(/"status":"completed"/g)??[]).length>=3)_.batchCompletions++}}let O={sessionID:V.sessionID,toolName:V.tool,toolOutput:Y.output,iteration:0,maxIterations:10,oracleVerified:!1,noProgress:!1,filesChanged:0,recentTurnTokens:[],deviations:[],backends:Q.backends??{agentmemory:{smartSearch:async()=>({lessons:[],crystals:[]})},magicContext:{slotList:async()=>[]},boulderState:{boulderRead:async()=>[]}},writeBackend:Q.writeBackend??{saveMemory:async()=>({id:""}),saveLesson:async()=>({id:""})},config:q,...B()?{providerID:B()}:{},...W()?{modelID:W()}:{},modelLimit:H()};try{let L=await t(O);if(q.intervention.mode!=="silent"){let E=L.decision;if(E.action!=="continue"&&YK(E.action,q.intervention.minActionForMessage))ZK(V.sessionID,E)}}catch{}},"experimental.chat.messages.transform":async(V,Y)=>{if(!q.enabled)return;if(q.intervention.mode!=="message")return;let O=Y.messages[Y.messages.length-1]?.info?.sessionID;if(O&&A.has(O)){let y=A.get(O);if(y.length>0){let C=`[META-GOVERNOR PROTOCOL VIOLATIONS - YOU MUST COMPLY]
|
|
13
|
-
|
|
14
|
-
${y.map((R,vK)=>`${vK+1}. ${R}`).join(`
|
|
15
|
-
`)}
|
|
16
|
-
|
|
17
|
-
Remember: use codegraph/graphify for architecture queries, do not grep without trying AFT/codegraph first, no @ts-ignore/as-any, no empty catch, check memory before asking.`;Y.messages.push({info:{role:"user",agent:"meta-governor",synthetic:!0},parts:[{type:"text",text:C,synthetic:!0}]}),A.delete(O),b("info",`injected ${y.length} violation(s) to model`)}}let L=JK();if(!L)return;if(L.action==="continue")return;if(!L.message)return;if(!YK(L.action,q.intervention.minActionForMessage))return;let E={type:"text",text:`[MetaGovernor] ${L.message}`,synthetic:!0};Y.messages.push({info:{role:"user",agent:"meta-governor"},parts:[E]})},"experimental.chat.system.transform":async(V,Y)=>{if(!q.enabled)return;if(q.protocolEnforcement.injectIntoSystem&&w)Y.system.push(`
|
|
18
|
-
### Sisyphus Protocol Enforcement`,w,"---");if(q.intervention.mode==="system"&&V.sessionID){let _=$K(V.sessionID);if(_&&_.action!=="continue"&&_.message){if(YK(_.action,q.intervention.minActionForMessage))Y.system.push(`
|
|
19
|
-
[MetaGovernor Intervention]`,_.message,"---")}}}}}}function gQ(K){let Q={severity:K.success?"leve":"grave",category:`recovery:${K.fixStrategy}`,detail:`${K.errorCode}: ${K.context??"no context"}`};return{action:K.success?"continue":"warn",score:K.success?0.5:-0.5,reasoning:`Recovery ${K.success?"succeeded":"failed"}: ${K.fixStrategy} for ${K.errorCode}`,evidence:[{source:"deviation-detector",value:Q.detail,confidence:1,weight:K.success?0.3:0.8}],shouldEscalateTo:K.success?null:"oracle"}}var DK={leve:0,media:1,grave:2};function SK(K,Q){let X=DK[Q]??0;return K.some((Z)=>(DK[Z.severity]??0)>=X)}async function pQ(K,Q,X){if(!Q)return null;let Z=X?.config??k(),$=gQ(K);if(!Z.enabled)return{lessonSaved:null,decisionSaved:null,reason:"closed-loop learning disabled"};let J=[{severity:K.success?"leve":"grave",category:`recovery:${K.fixStrategy}`,detail:`${K.errorCode}: ${K.context??"no context"}`}],z=null,q=null;if(Z.saveDecisions){let W={id:`D-${Math.abs(`${K.sessionID}-${$.action}-${Date.now()}`.split("").reduce((H,U)=>(H<<5)-H+U.charCodeAt(0)|0,0)).toString(36)}`,timestampISO:new Date().toISOString(),action:$.action,score:$.score,reasoning:$.reasoning,sessionID:K.sessionID,directory:K.directory,deviations:J.map((H)=>({severity:H.severity,category:H.category,detail:H.detail}))};try{await Q.saveMemory({content:`Decision: ${$.action} (score ${$.score.toFixed(2)}). ${$.reasoning}`,concepts:["meta-governor","decision",$.action,...J.map((H)=>H.category)],type:"fact",files:[...K.filesChanged??[]]}),q=W}catch{}}if(SK(J,Z.minSeverityToLearn)){let W=[...new Set(J.flatMap((G)=>[G.category,G.severity]))],H=J.map((G)=>`[${G.severity}] ${G.category}: ${G.detail}`).join("; "),U=`Action "${$.action}" (score ${$.score.toFixed(2)}) after deviations: ${H}. Reasoning: ${$.reasoning}`;try{z={id:(await Q.saveLesson({content:U,context:`session:${K.sessionID} dir:${K.directory}`,confidence:Math.max(0.3,Math.min(0.8,Math.abs($.score))),tags:W})).id,title:`${$.action} after ${J[0]?.category??"recovery"}`,content:U,type:"pattern",concepts:W,confidence:Math.max(0.3,Math.min(0.8,Math.abs($.score))),files:[...K.filesChanged??[]],sessionID:K.sessionID}}catch{}}let B=[];if(q)B.push("decision saved");if(z)B.push("lesson saved");else if(!SK(J,Z.minSeverityToLearn))B.push("severity below threshold");if(!q&&!z&&!B.length)B.push("no saveable content");return{lessonSaved:z,decisionSaved:q,reason:B.join("; ")||"no action taken"}}XK();function hK(){return{$schema:"http://json-schema.org/draft-07/schema#",$id:"https://raw.githubusercontent.com/herjarsa/omo-meta-governor/main/assets/omo-meta-governor.schema.json",title:"omo-meta-governor",description:"Configuration schema for @herjarsa/omo-meta-governor — Self-judging agent orchestration layer for OpenCode.",type:"object",additionalProperties:!1,properties:{$schema:{type:"string",description:"JSON Schema reference for IDE autocompletion."},enabled:{type:"boolean",description:"Master feature flag — must be true to run the orchestrator.",default:!1},decision:{type:"object",description:"Decision handler configuration.",additionalProperties:!1,properties:{maxHistoryPerSession:{type:"integer",description:"Maximum history entries per session before oldest are trimmed.",default:50,minimum:1},forceContinueAfterStops:{type:"integer",description:"How many consecutive stops before forcing continue.",default:3,minimum:1}}},memory:{type:"object",description:"Memory aggregator configuration.",additionalProperties:!1,properties:{agentmemoryTimeoutMs:{type:"integer",description:"Timeout for agentmemory queries in milliseconds.",default:2000,minimum:100},magicContextTimeoutMs:{type:"integer",description:"Timeout for magic-context queries in milliseconds.",default:1000,minimum:100},boulderStateTimeoutMs:{type:"integer",description:"Timeout for boulder-state queries in milliseconds.",default:1000,minimum:100},query:{type:"string",description:"Natural-language query for memory recall.",default:"meta_governor_context"}}},tokenPredictor:{type:"object",description:"Token predictor configuration.",additionalProperties:!1,properties:{compactBurnRateThreshold:{type:"integer",description:"Burn rate threshold (tokens/turn) above which to recommend compact-now.",default:500,minimum:0},compactUsageThreshold:{type:"number",description:"Context usage ratio (0..1) above which to recommend compact-now.",default:0.85,minimum:0,maximum:1},switchModelUsageThreshold:{type:"number",description:"Context usage ratio above which to recommend switch-model.",default:0.95,minimum:0,maximum:1},delegateConsecutiveHighBurn:{type:"integer",description:"Max consecutive high-burn turns before recommending delegate.",default:5,minimum:1}}},scoring:{type:"object",description:"Scoring engine configuration.",additionalProperties:!1,properties:{continueThreshold:{type:"number",description:"Score >= this -> continue silently.",default:0.3,minimum:0,maximum:1},warnThreshold:{type:"number",description:"Score <= -warnThreshold -> warn.",default:0.3,minimum:0,maximum:1},escalateThreshold:{type:"number",description:"Score <= -escalateThreshold -> escalate.",default:0.6,minimum:0,maximum:1},stopThreshold:{type:"number",description:"Score <= -stopThreshold -> stop.",default:0.8,minimum:0,maximum:1}}},closedLoop:{type:"object",description:"Closed-loop learning configuration.",additionalProperties:!1,properties:{saveDecisions:{type:"boolean",description:"Whether to save decision records.",default:!0},saveLessons:{type:"boolean",description:"Whether to save lessons.",default:!0}}},modelOverride:{type:"object",description:"Model override for MetaGovernor internal LLM usage.",additionalProperties:!1,properties:{providerID:{type:"string",description:"Provider ID (e.g. 'openai', 'anthropic')."},modelID:{type:"string",description:"Model ID (e.g. 'gpt-4o-mini', 'claude-sonnet-4-20250514')."},modelLimit:{type:"integer",description:"Context window size for token predictor.",minimum:1000},temperature:{type:"number",description:"Sampling temperature. Default: 0.2.",default:0.2,minimum:0,maximum:2},topP:{type:"number",description:"Top-p nucleus sampling. Default: 1.",default:1,minimum:0,maximum:1},maxTokens:{type:"integer",description:"Max output tokens for internal reasoning.",default:2048,minimum:1},reasoning:{type:"boolean",description:"Enable extended reasoning / thinking mode.",default:!1},verbosity:{type:"string",description:"Verbosity level for internal logging.",enum:["silent","minimal","verbose"],default:"minimal"}}},intervention:{type:"object",description:"Intervention config for visible decision injection.",additionalProperties:!1,properties:{mode:{type:"string",description:"How to inject: 'silent', 'message', or 'system'.",enum:["silent","message","system"],default:"silent"},includeDecisionHistory:{type:"boolean",description:"Whether to include recent decision history.",default:!0},maxHistoryMessages:{type:"integer",description:"Max history entries when includeDecisionHistory is true.",default:5,minimum:1},minActionForMessage:{type:"string",description:"Minimum action: 'warn' (all non-continue), 'escalate', or 'stop'.",enum:["warn","escalate","stop"],default:"warn"}}},protocolEnforcement:{type:"object",description:"Sisyphus protocol enforcement config.",additionalProperties:!1,properties:{enabled:{type:"boolean",description:"Master switch for protocol enforcement.",default:!1},path:{type:"string",description:"Path to protocol markdown file."},injectIntoSystem:{type:"boolean",description:"Whether to inject protocol rules into the system prompt.",default:!1},auditToolCalls:{type:"boolean",description:"Whether to audit tool calls for protocol violations.",default:!1}}},graphSync:{type:"object",description:"Graph synchronization (auto-init codegraph/graphify).",additionalProperties:!1,properties:{enabled:{type:"boolean",description:"Enable auto-initialization of codegraph and graphify.",default:!0},watch:{type:"boolean",description:"Enable watch mode (re-index on file changes).",default:!1}}}},definitions:{verbosity:{type:"string",enum:["silent","minimal","verbose"],description:"Verbosity level."},interventionMode:{type:"string",enum:["silent","message","system"],description:"Intervention injection mode."},minAction:{type:"string",enum:["warn","escalate","stop"],description:"Minimum action threshold."}}}}async function dQ(K){let Q=hK(),{writeFile:X}=await import("node:fs/promises");await X(K,JSON.stringify(Q,null,2)+`
|
|
20
|
-
`,"utf-8")}var uQ={id:"omo-meta-governor",server:VK()},fX=uQ;export{dQ as writeSchemaFile,_Q as trimHistory,$K as takeDecision,JK as takeAnyDecision,o as stripJsoncComments,ZK as storeDecision,oK as stopWatches,r as score,t as runMetaGovernor,g as runGraphSync,sK as resetInitializedProjects,pQ as recordRecovery,c as predict,e as parseJsonc,s as observeAndLearn,b as logToFile,qK as loadProtocol,bQ as loadOrchestratorConfigFromSources,v as loadOrchestratorConfig,yK as loadMetaGovernorConfig,h as loadJsoncFile,TQ as isMetaGovernorEnabled,jQ as hasDecision,n as handleDecision,KK as getUserConfigPath,QK as getProjectConfigPath,hK as generateSchema,JQ as defaultTokenPredictorConfig,I as defaultScoringConfig,NK as defaultOrchestratorConfig,S as defaultDecisionHandlerConfig,k as defaultClosedLoopConfig,fX as default,T as deepMerge,VK as createMetaGovernorPlugin,wQ as countConsecutiveStops,yQ as clearAll,PK as calculateBurnRate,zK as buildSystemInjection,EK as buildDecisionContext,BK as auditToolCall,l as aggregateRead,f as DEFAULT_PROTOCOL_PATH};
|
|
21
|
-
|
|
22
|
-
//# debugId=A6692C702C0D1D9164756E2164756E21
|
|
23
|
-
//# sourceMappingURL=index.js.map
|