@haaaiawd/second-nature 0.1.18 → 0.1.20
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/index.js +911 -855
- package/openclaw.plugin.json +29 -29
- package/package.json +52 -52
- package/runtime/cli/commands/index.d.ts +14 -14
- package/runtime/cli/commands/index.js +224 -193
- package/runtime/cli/explain/explain-surface-subject.d.ts +8 -8
- package/runtime/cli/explain/explain-surface-subject.js +9 -9
- package/runtime/cli/explain/format-explanation.d.ts +12 -12
- package/runtime/cli/explain/format-explanation.js +12 -12
- package/runtime/cli/explain/resolve-subject.js +41 -41
- package/runtime/cli/host-capability/classify-delivery.d.ts +14 -14
- package/runtime/cli/host-capability/classify-delivery.js +20 -20
- package/runtime/cli/host-capability/probe-host-capability.d.ts +2 -2
- package/runtime/cli/host-capability/probe-host-capability.js +58 -58
- package/runtime/cli/host-capability/record-host-capability.d.ts +6 -6
- package/runtime/cli/host-capability/record-host-capability.js +14 -14
- package/runtime/cli/host-capability/types.d.ts +71 -71
- package/runtime/cli/host-capability/types.js +6 -6
- package/runtime/cli/host-smoke/run-host-smoke.d.ts +2 -2
- package/runtime/cli/host-smoke/run-host-smoke.js +40 -40
- package/runtime/cli/host-smoke/types.d.ts +35 -35
- package/runtime/cli/host-smoke/types.js +6 -6
- package/runtime/cli/index.js +67 -58
- package/runtime/cli/ops/heartbeat-surface.d.ts +45 -38
- package/runtime/cli/ops/heartbeat-surface.js +79 -73
- package/runtime/cli/ops/ops-router.d.ts +32 -19
- package/runtime/cli/ops/ops-router.js +188 -89
- package/runtime/cli/ops/show-operator-fallback.d.ts +13 -13
- package/runtime/cli/ops/show-operator-fallback.js +22 -22
- package/runtime/cli/ops/workspace-heartbeat-runner.d.ts +40 -19
- package/runtime/cli/ops/workspace-heartbeat-runner.js +93 -39
- package/runtime/cli/read-models/index.d.ts +46 -29
- package/runtime/cli/read-models/index.js +391 -256
- package/runtime/cli/read-models/operator-explain-map.d.ts +6 -6
- package/runtime/cli/read-models/operator-explain-map.js +10 -10
- package/runtime/cli/read-models/types.d.ts +129 -79
- package/runtime/cli/runtime/runtime-artifact-boundary.d.ts +28 -28
- package/runtime/cli/runtime/runtime-artifact-boundary.js +94 -94
- package/runtime/connectors/base/contract.d.ts +87 -87
- package/runtime/connectors/base/execution-policy.d.ts +47 -47
- package/runtime/connectors/base/execution-policy.js +82 -82
- package/runtime/connectors/base/index.d.ts +8 -8
- package/runtime/connectors/base/index.js +8 -8
- package/runtime/connectors/base/manifest.d.ts +64 -64
- package/runtime/connectors/base/manifest.js +86 -86
- package/runtime/connectors/base/map-life-evidence.d.ts +16 -16
- package/runtime/connectors/base/map-life-evidence.js +79 -79
- package/runtime/connectors/base/policy-layer.d.ts +29 -29
- package/runtime/connectors/base/policy-layer.js +198 -198
- package/runtime/connectors/base/route-planner.js +99 -99
- package/runtime/connectors/index.d.ts +5 -5
- package/runtime/connectors/index.js +5 -5
- package/runtime/connectors/near-real/near-real-connector-smoke.d.ts +19 -19
- package/runtime/connectors/near-real/near-real-connector-smoke.js +152 -152
- package/runtime/core/second-nature/heartbeat/heartbeat-executor.js +114 -114
- package/runtime/core/second-nature/heartbeat/heartbeat-loop.d.ts +63 -63
- package/runtime/core/second-nature/heartbeat/heartbeat-loop.js +162 -139
- package/runtime/core/second-nature/heartbeat/index.d.ts +8 -8
- package/runtime/core/second-nature/heartbeat/index.js +7 -7
- package/runtime/core/second-nature/heartbeat/run-heartbeat-cycle.d.ts +21 -21
- package/runtime/core/second-nature/heartbeat/run-heartbeat-cycle.js +35 -35
- package/runtime/core/second-nature/heartbeat/runtime-snapshot.d.ts +28 -28
- package/runtime/core/second-nature/heartbeat/runtime-snapshot.js +35 -35
- package/runtime/core/second-nature/heartbeat/signal.d.ts +42 -42
- package/runtime/core/second-nature/heartbeat/snapshot-builder.d.ts +51 -51
- package/runtime/core/second-nature/index.d.ts +22 -22
- package/runtime/core/second-nature/index.js +22 -22
- package/runtime/core/second-nature/orchestrator/effect-dispatcher.d.ts +100 -100
- package/runtime/core/second-nature/orchestrator/effect-dispatcher.js +144 -144
- package/runtime/core/second-nature/orchestrator/guard-layer.d.ts +8 -8
- package/runtime/core/second-nature/orchestrator/guard-layer.js +110 -110
- package/runtime/core/second-nature/orchestrator/intent-planner.d.ts +13 -13
- package/runtime/core/second-nature/orchestrator/intent-planner.js +199 -199
- package/runtime/core/second-nature/orchestrator/lease-manager.d.ts +14 -14
- package/runtime/core/second-nature/orchestrator/lease-manager.js +58 -58
- package/runtime/core/second-nature/outreach/build-outreach-draft-request.d.ts +6 -6
- package/runtime/core/second-nature/outreach/build-outreach-draft-request.js +63 -63
- package/runtime/core/second-nature/outreach/delivery-target.d.ts +26 -26
- package/runtime/core/second-nature/outreach/delivery-target.js +70 -70
- package/runtime/core/second-nature/outreach/dispatch-user-outreach.d.ts +38 -38
- package/runtime/core/second-nature/outreach/dispatch-user-outreach.js +119 -119
- package/runtime/core/second-nature/outreach/judge-input-from-snapshot.d.ts +7 -7
- package/runtime/core/second-nature/outreach/judge-input-from-snapshot.js +45 -45
- package/runtime/core/second-nature/outreach/judge-outreach.d.ts +40 -40
- package/runtime/core/second-nature/outreach/judge-outreach.js +121 -121
- package/runtime/core/second-nature/quiet/run-source-backed-quiet.d.ts +21 -21
- package/runtime/core/second-nature/quiet/run-source-backed-quiet.js +123 -123
- package/runtime/core/second-nature/rhythm/planner-rhythm-window.d.ts +15 -15
- package/runtime/core/second-nature/rhythm/planner-rhythm-window.js +52 -52
- package/runtime/core/second-nature/rhythm/policy-bridge.d.ts +19 -19
- package/runtime/core/second-nature/rhythm/policy-bridge.js +34 -34
- package/runtime/core/second-nature/runtime/service-entry.js +45 -45
- package/runtime/core/second-nature/types.d.ts +51 -51
- package/runtime/guidance/draft-outreach-message.d.ts +7 -7
- package/runtime/guidance/draft-outreach-message.js +42 -42
- package/runtime/guidance/evidence-guidance.d.ts +40 -40
- package/runtime/guidance/evidence-guidance.js +52 -52
- package/runtime/guidance/index.d.ts +11 -11
- package/runtime/guidance/index.js +11 -11
- package/runtime/guidance/outreach-draft-schema.d.ts +228 -228
- package/runtime/guidance/outreach-draft-schema.js +80 -80
- package/runtime/observability/audit/append-only-audit-store.d.ts +14 -14
- package/runtime/observability/audit/append-only-audit-store.js +21 -21
- package/runtime/observability/audit/audit-envelope.d.ts +51 -51
- package/runtime/observability/audit/audit-envelope.js +130 -130
- package/runtime/observability/audit/verify-audit-hash-chain.d.ts +23 -23
- package/runtime/observability/audit/verify-audit-hash-chain.js +83 -83
- package/runtime/observability/db/index.js +47 -47
- package/runtime/observability/db/schema/host-capability-reports.d.ts +180 -180
- package/runtime/observability/db/schema/host-capability-reports.js +12 -12
- package/runtime/observability/db/schema/index.d.ts +947 -947
- package/runtime/observability/db/schema/index.js +71 -71
- package/runtime/observability/index.d.ts +20 -20
- package/runtime/observability/index.js +19 -19
- package/runtime/observability/query/explain-query.d.ts +48 -48
- package/runtime/observability/query/explain-query.js +114 -114
- package/runtime/observability/query/export-audit-bundle.d.ts +22 -22
- package/runtime/observability/query/export-audit-bundle.js +27 -27
- package/runtime/observability/services/decision-ledger.d.ts +46 -46
- package/runtime/observability/services/decision-ledger.js +161 -161
- package/runtime/observability/services/governance-audit.d.ts +41 -41
- package/runtime/observability/services/governance-audit.js +163 -163
- package/runtime/observability/services/governance-plane-recorder.d.ts +47 -47
- package/runtime/observability/services/governance-plane-recorder.js +55 -55
- package/runtime/observability/services/lived-experience-audit.d.ts +97 -97
- package/runtime/observability/services/lived-experience-audit.js +162 -162
- package/runtime/observability/services/observability-retention.d.ts +10 -0
- package/runtime/observability/services/observability-retention.js +37 -0
- package/runtime/observability/services/runtime-decision-recorder.d.ts +29 -29
- package/runtime/observability/services/runtime-decision-recorder.js +94 -94
- package/runtime/storage/bootstrap/native-sqlite-probe.d.ts +7 -7
- package/runtime/storage/bootstrap/native-sqlite-probe.js +28 -28
- package/runtime/storage/bootstrap/repair-gate.d.ts +17 -17
- package/runtime/storage/bootstrap/repair-gate.js +71 -71
- package/runtime/storage/bootstrap/storage-mode-smoke.d.ts +38 -38
- package/runtime/storage/bootstrap/storage-mode-smoke.js +85 -85
- package/runtime/storage/db/index.js +61 -61
- package/runtime/storage/db/schema/delivery-attempts.d.ts +199 -199
- package/runtime/storage/db/schema/delivery-attempts.js +13 -13
- package/runtime/storage/db/schema/index.d.ts +9 -9
- package/runtime/storage/db/schema/index.js +9 -9
- package/runtime/storage/db/schema/life-evidence-index.d.ts +161 -161
- package/runtime/storage/db/schema/life-evidence-index.js +11 -11
- package/runtime/storage/db/schema/operator-fallback-artifacts.d.ts +161 -161
- package/runtime/storage/db/schema/operator-fallback-artifacts.js +11 -11
- package/runtime/storage/db/schema/policies.d.ts +98 -98
- package/runtime/storage/db/schema/policies.js +8 -8
- package/runtime/storage/delivery/query-delivery-attempts.d.ts +3 -3
- package/runtime/storage/delivery/query-delivery-attempts.js +32 -32
- package/runtime/storage/delivery/types.d.ts +27 -27
- package/runtime/storage/delivery/types.js +1 -1
- package/runtime/storage/delivery/write-delivery-attempt.d.ts +6 -6
- package/runtime/storage/delivery/write-delivery-attempt.js +36 -36
- package/runtime/storage/fallback/load-operator-fallback.d.ts +14 -14
- package/runtime/storage/fallback/load-operator-fallback.js +47 -47
- package/runtime/storage/fallback/operator-fallback-types.d.ts +9 -9
- package/runtime/storage/fallback/operator-fallback-types.js +1 -1
- package/runtime/storage/fallback/operator-fallback-view.d.ts +11 -11
- package/runtime/storage/fallback/operator-fallback-view.js +1 -1
- package/runtime/storage/fallback/write-operator-fallback.d.ts +6 -6
- package/runtime/storage/fallback/write-operator-fallback.js +21 -21
- package/runtime/storage/index.d.ts +37 -37
- package/runtime/storage/index.js +30 -30
- package/runtime/storage/life-evidence/append-life-evidence.d.ts +7 -7
- package/runtime/storage/life-evidence/append-life-evidence.js +64 -64
- package/runtime/storage/life-evidence/types.d.ts +45 -45
- package/runtime/storage/life-evidence/types.js +6 -6
- package/runtime/storage/quiet/persist-quiet-artifact.d.ts +7 -7
- package/runtime/storage/quiet/persist-quiet-artifact.js +22 -22
- package/runtime/storage/quiet/quiet-artifact-types.d.ts +18 -18
- package/runtime/storage/quiet/quiet-artifact-types.js +1 -1
- package/runtime/storage/quiet/quiet-artifact-writer.d.ts +15 -15
- package/runtime/storage/quiet/quiet-artifact-writer.js +56 -56
- package/runtime/storage/repositories/credential-repository.js +30 -30
- package/runtime/storage/rhythm/rhythm-policy-snapshot.d.ts +10 -10
- package/runtime/storage/rhythm/rhythm-policy-snapshot.js +34 -34
- package/runtime/storage/services/credential-vault.d.ts +13 -13
- package/runtime/storage/services/credential-vault.js +116 -116
- package/runtime/storage/snapshots/continuity-snapshot.d.ts +9 -9
- package/runtime/storage/snapshots/continuity-snapshot.js +41 -41
- package/runtime/storage/snapshots/life-evidence-snapshot.d.ts +6 -6
- package/runtime/storage/snapshots/life-evidence-snapshot.js +114 -114
- package/runtime/storage/snapshots/types.d.ts +58 -58
- package/runtime/storage/snapshots/types.js +1 -1
- package/runtime/storage/state-api.js +104 -104
- package/runtime/storage/user-interest/load-user-interest-snapshot.d.ts +2 -2
- package/runtime/storage/user-interest/load-user-interest-snapshot.js +150 -150
- package/runtime/storage/user-interest/types.d.ts +25 -25
- package/runtime/storage/user-interest/types.js +1 -1
- package/workspace-ops-bridge.js +90 -81
|
@@ -1,89 +1,188 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Shared ops command dispatch for CLI + tool surfaces (T1.1.3, T1.2.2).
|
|
3
|
-
*/
|
|
4
|
-
import { heartbeatCheck } from "./heartbeat-surface.js";
|
|
5
|
-
import { showOperatorFallback, OperatorFallbackNotFoundError } from "./show-operator-fallback.js";
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
return
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
1
|
+
/**
|
|
2
|
+
* Shared ops command dispatch for CLI + tool surfaces (T1.1.3, T1.2.2).
|
|
3
|
+
*/
|
|
4
|
+
import { heartbeatCheck, } from "./heartbeat-surface.js";
|
|
5
|
+
import { showOperatorFallback, OperatorFallbackNotFoundError, } from "./show-operator-fallback.js";
|
|
6
|
+
import { probeHostCapability } from "../host-capability/probe-host-capability.js";
|
|
7
|
+
import { recordHostCapability } from "../host-capability/record-host-capability.js";
|
|
8
|
+
import { runNearRealConnectorSmoke } from "../../connectors/near-real/near-real-connector-smoke.js";
|
|
9
|
+
function coerceProbeOnlyFlag(input) {
|
|
10
|
+
const v = input?.probeOnly;
|
|
11
|
+
return v === true || v === "true" || v === 1 || v === "1";
|
|
12
|
+
}
|
|
13
|
+
/**
|
|
14
|
+
* T1.2.8 — static local adapter: all checks return `unknown` when no real host is available.
|
|
15
|
+
* Allows `capability_probe` to be called from CLI / workspace bridge without requiring a live host.
|
|
16
|
+
*/
|
|
17
|
+
function createStaticUnknownAdapter() {
|
|
18
|
+
const now = new Date().toISOString();
|
|
19
|
+
const unknownResult = (name) => ({
|
|
20
|
+
name,
|
|
21
|
+
verdict: "unknown",
|
|
22
|
+
observedAt: now,
|
|
23
|
+
reason: "static_local_probe_no_host_context",
|
|
24
|
+
evidenceRefs: [],
|
|
25
|
+
});
|
|
26
|
+
return {
|
|
27
|
+
checkPluginLoad: () => unknownResult("plugin_load"),
|
|
28
|
+
checkHeartbeatBridge: () => unknownResult("heartbeat_bridge"),
|
|
29
|
+
checkHeartbeatToolInvocation: () => unknownResult("heartbeat_tool_invocation"),
|
|
30
|
+
checkDeliveryTarget: () => ({ status: "unknown", evidenceRefs: [] }),
|
|
31
|
+
checkAckDropBehavior: () => unknownResult("ack_drop"),
|
|
32
|
+
checkHookSupport: () => [],
|
|
33
|
+
};
|
|
34
|
+
}
|
|
35
|
+
export function createOpsRouter(deps) {
|
|
36
|
+
return {
|
|
37
|
+
heartbeatCheck: (input) => heartbeatCheck({
|
|
38
|
+
...input,
|
|
39
|
+
runtimeAvailable: input.runtimeAvailable ?? deps.runtimeAvailable,
|
|
40
|
+
readModels: input.readModels ?? deps.readModels,
|
|
41
|
+
runtimeRecorder: input.runtimeRecorder ?? deps.runtimeRecorder,
|
|
42
|
+
state: input.state ?? deps.state,
|
|
43
|
+
workspaceRoot: input.workspaceRoot ?? deps.workspaceRoot,
|
|
44
|
+
}),
|
|
45
|
+
dispatch(command, input) {
|
|
46
|
+
if (command === "heartbeat_check") {
|
|
47
|
+
const runtimeAvailable = typeof input?.runtimeAvailable === "boolean"
|
|
48
|
+
? input.runtimeAvailable
|
|
49
|
+
: deps.runtimeAvailable;
|
|
50
|
+
return heartbeatCheck({
|
|
51
|
+
probeOnly: coerceProbeOnlyFlag(input),
|
|
52
|
+
runtimeAvailable,
|
|
53
|
+
fakeControlPlanePassthrough: input?.fakeControlPlanePassthrough &&
|
|
54
|
+
typeof input.fakeControlPlanePassthrough === "object"
|
|
55
|
+
? input.fakeControlPlanePassthrough
|
|
56
|
+
: undefined,
|
|
57
|
+
readModels: input?.readModels ??
|
|
58
|
+
deps.readModels,
|
|
59
|
+
runtimeRecorder: input
|
|
60
|
+
?.runtimeRecorder ?? deps.runtimeRecorder,
|
|
61
|
+
state: input?.state ??
|
|
62
|
+
deps.state,
|
|
63
|
+
workspaceRoot: input
|
|
64
|
+
?.workspaceRoot ?? deps.workspaceRoot,
|
|
65
|
+
timestamp: typeof input?.timestamp === "string" ? input.timestamp : undefined,
|
|
66
|
+
sessionContext: typeof input?.sessionContext === "string"
|
|
67
|
+
? input.sessionContext
|
|
68
|
+
: undefined,
|
|
69
|
+
scopeHint: input?.scopeHint,
|
|
70
|
+
});
|
|
71
|
+
}
|
|
72
|
+
if (command === "fallback") {
|
|
73
|
+
const ref = typeof input?.ref === "string" ? input.ref.trim() : "";
|
|
74
|
+
if (!ref) {
|
|
75
|
+
return {
|
|
76
|
+
ok: false,
|
|
77
|
+
error: {
|
|
78
|
+
code: "MISSING_FALLBACK_REF",
|
|
79
|
+
message: "fallback requires args.ref (e.g. fallback:…)",
|
|
80
|
+
requiredUserInput: ["ref"],
|
|
81
|
+
nextStep: "reinvoke_with_ref",
|
|
82
|
+
},
|
|
83
|
+
};
|
|
84
|
+
}
|
|
85
|
+
if (!deps.readModels?.loadFallbackView) {
|
|
86
|
+
return {
|
|
87
|
+
ok: false,
|
|
88
|
+
error: {
|
|
89
|
+
code: "FALLBACK_READ_MODEL_UNAVAILABLE",
|
|
90
|
+
message: "Operator fallback view requires workspace read models",
|
|
91
|
+
requiredUserInput: ["ref"],
|
|
92
|
+
nextStep: "wire_read_models_into_ops_router",
|
|
93
|
+
},
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
return (async () => {
|
|
97
|
+
try {
|
|
98
|
+
const data = await showOperatorFallback(ref, deps.readModels);
|
|
99
|
+
return { ok: true, command: "fallback", data };
|
|
100
|
+
}
|
|
101
|
+
catch (error) {
|
|
102
|
+
if (error instanceof OperatorFallbackNotFoundError) {
|
|
103
|
+
return {
|
|
104
|
+
ok: false,
|
|
105
|
+
command: "fallback",
|
|
106
|
+
error: {
|
|
107
|
+
code: error.code,
|
|
108
|
+
message: error.message,
|
|
109
|
+
requiredUserInput: ["ref"],
|
|
110
|
+
nextStep: "verify_fallback_ref_from_delivery_audit",
|
|
111
|
+
},
|
|
112
|
+
};
|
|
113
|
+
}
|
|
114
|
+
throw error;
|
|
115
|
+
}
|
|
116
|
+
})();
|
|
117
|
+
}
|
|
118
|
+
if (command === "capability_probe") {
|
|
119
|
+
// T1.2.8 (SN-CODE-03): run host capability probe with static unknown adapter (CLI context).
|
|
120
|
+
// Persists report when observabilityDb is available; returns safe JSON subset.
|
|
121
|
+
return (async () => {
|
|
122
|
+
const adapter = createStaticUnknownAdapter();
|
|
123
|
+
const docCheckedAt = new Date().toISOString();
|
|
124
|
+
const report = probeHostCapability({
|
|
125
|
+
adapter,
|
|
126
|
+
docLinks: [],
|
|
127
|
+
docCheckedAt,
|
|
128
|
+
});
|
|
129
|
+
if (deps.observabilityDb) {
|
|
130
|
+
await recordHostCapability(deps.observabilityDb, report);
|
|
131
|
+
}
|
|
132
|
+
return {
|
|
133
|
+
ok: true,
|
|
134
|
+
command: "capability_probe",
|
|
135
|
+
data: {
|
|
136
|
+
reportId: report.reportId,
|
|
137
|
+
generatedAt: report.generatedAt,
|
|
138
|
+
deliveryTarget: report.deliveryTarget,
|
|
139
|
+
pluginLoad: { verdict: report.pluginLoad.verdict },
|
|
140
|
+
heartbeatBridge: { verdict: report.heartbeatBridge.verdict },
|
|
141
|
+
heartbeatToolInvocation: {
|
|
142
|
+
verdict: report.heartbeatToolInvocation.verdict,
|
|
143
|
+
},
|
|
144
|
+
ackDropBehavior: { verdict: report.ackDropBehavior.verdict },
|
|
145
|
+
conflictCount: report.conflictRecords.length,
|
|
146
|
+
recommendedNextStep: report.recommendedNextStep,
|
|
147
|
+
note: "static_local_probe: all verdicts are unknown without live host context",
|
|
148
|
+
},
|
|
149
|
+
};
|
|
150
|
+
})();
|
|
151
|
+
}
|
|
152
|
+
if (command === "near_real_smoke") {
|
|
153
|
+
// T3.3.2 (SN-CODE-05): wrap runNearRealConnectorSmoke as an ops surface command.
|
|
154
|
+
// Requires state + observabilityDb + workspaceRoot to be wired into OpsRouterDeps.
|
|
155
|
+
if (!deps.state || !deps.observabilityDb || !deps.workspaceRoot) {
|
|
156
|
+
return {
|
|
157
|
+
ok: false,
|
|
158
|
+
command: "near_real_smoke",
|
|
159
|
+
error: {
|
|
160
|
+
code: "NEAR_REAL_SMOKE_DEPS_UNAVAILABLE",
|
|
161
|
+
message: "near_real_smoke requires state, observabilityDb, and workspaceRoot in OpsRouterDeps",
|
|
162
|
+
nextStep: "wire_deps_into_ops_router",
|
|
163
|
+
},
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
return (async () => {
|
|
167
|
+
const result = await runNearRealConnectorSmoke({
|
|
168
|
+
state: deps.state,
|
|
169
|
+
observabilityDb: deps.observabilityDb,
|
|
170
|
+
workspaceRoot: deps.workspaceRoot,
|
|
171
|
+
});
|
|
172
|
+
return {
|
|
173
|
+
ok: true,
|
|
174
|
+
command: "near_real_smoke",
|
|
175
|
+
data: result,
|
|
176
|
+
};
|
|
177
|
+
})();
|
|
178
|
+
}
|
|
179
|
+
return {
|
|
180
|
+
ok: false,
|
|
181
|
+
error: {
|
|
182
|
+
code: "unknown_ops_command",
|
|
183
|
+
message: `Unknown ops command: ${command}`,
|
|
184
|
+
},
|
|
185
|
+
};
|
|
186
|
+
},
|
|
187
|
+
};
|
|
188
|
+
}
|
|
@@ -1,13 +1,13 @@
|
|
|
1
|
-
import type { OperatorFallbackView } from "../../storage/fallback/operator-fallback-view.js";
|
|
2
|
-
export declare class OperatorFallbackNotFoundError extends Error {
|
|
3
|
-
readonly ref: string;
|
|
4
|
-
readonly code: "FALLBACK_NOT_FOUND";
|
|
5
|
-
constructor(ref: string);
|
|
6
|
-
}
|
|
7
|
-
export interface ShowOperatorFallbackReadModels {
|
|
8
|
-
loadFallbackView(ref: string): Promise<OperatorFallbackView | null>;
|
|
9
|
-
}
|
|
10
|
-
/**
|
|
11
|
-
* T1.2.2 — Operator-visible fallback: always `status: not_sent` (ADR-007), never sent/delivered.
|
|
12
|
-
*/
|
|
13
|
-
export declare function showOperatorFallback(ref: string, readModels: ShowOperatorFallbackReadModels): Promise<OperatorFallbackView>;
|
|
1
|
+
import type { OperatorFallbackView } from "../../storage/fallback/operator-fallback-view.js";
|
|
2
|
+
export declare class OperatorFallbackNotFoundError extends Error {
|
|
3
|
+
readonly ref: string;
|
|
4
|
+
readonly code: "FALLBACK_NOT_FOUND";
|
|
5
|
+
constructor(ref: string);
|
|
6
|
+
}
|
|
7
|
+
export interface ShowOperatorFallbackReadModels {
|
|
8
|
+
loadFallbackView(ref: string): Promise<OperatorFallbackView | null>;
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* T1.2.2 — Operator-visible fallback: always `status: not_sent` (ADR-007), never sent/delivered.
|
|
12
|
+
*/
|
|
13
|
+
export declare function showOperatorFallback(ref: string, readModels: ShowOperatorFallbackReadModels): Promise<OperatorFallbackView>;
|
|
@@ -1,22 +1,22 @@
|
|
|
1
|
-
export class OperatorFallbackNotFoundError extends Error {
|
|
2
|
-
ref;
|
|
3
|
-
code = "FALLBACK_NOT_FOUND";
|
|
4
|
-
constructor(ref) {
|
|
5
|
-
super(`No operator fallback artifact for ref: ${ref}`);
|
|
6
|
-
this.ref = ref;
|
|
7
|
-
this.name = "OperatorFallbackNotFoundError";
|
|
8
|
-
}
|
|
9
|
-
}
|
|
10
|
-
/**
|
|
11
|
-
* T1.2.2 — Operator-visible fallback: always `status: not_sent` (ADR-007), never sent/delivered.
|
|
12
|
-
*/
|
|
13
|
-
export async function showOperatorFallback(ref, readModels) {
|
|
14
|
-
const view = await readModels.loadFallbackView(ref);
|
|
15
|
-
if (!view) {
|
|
16
|
-
throw new OperatorFallbackNotFoundError(ref.trim());
|
|
17
|
-
}
|
|
18
|
-
return {
|
|
19
|
-
...view,
|
|
20
|
-
status: "not_sent",
|
|
21
|
-
};
|
|
22
|
-
}
|
|
1
|
+
export class OperatorFallbackNotFoundError extends Error {
|
|
2
|
+
ref;
|
|
3
|
+
code = "FALLBACK_NOT_FOUND";
|
|
4
|
+
constructor(ref) {
|
|
5
|
+
super(`No operator fallback artifact for ref: ${ref}`);
|
|
6
|
+
this.ref = ref;
|
|
7
|
+
this.name = "OperatorFallbackNotFoundError";
|
|
8
|
+
}
|
|
9
|
+
}
|
|
10
|
+
/**
|
|
11
|
+
* T1.2.2 — Operator-visible fallback: always `status: not_sent` (ADR-007), never sent/delivered.
|
|
12
|
+
*/
|
|
13
|
+
export async function showOperatorFallback(ref, readModels) {
|
|
14
|
+
const view = await readModels.loadFallbackView(ref);
|
|
15
|
+
if (!view) {
|
|
16
|
+
throw new OperatorFallbackNotFoundError(ref.trim());
|
|
17
|
+
}
|
|
18
|
+
return {
|
|
19
|
+
...view,
|
|
20
|
+
status: "not_sent",
|
|
21
|
+
};
|
|
22
|
+
}
|
|
@@ -1,19 +1,40 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Wires CLI read models into control-plane `runHeartbeatCycle` for `heartbeat_check` (US-001 / CH-09-02 / T1.2.3).
|
|
3
|
-
*
|
|
4
|
-
* Snapshot inputs are derived from aggregated status; delivery defaults to none until host capability is modeled here.
|
|
5
|
-
*
|
|
6
|
-
* T1.2.3: when a `RuntimeDecisionRecorder` is provided, persist a `sn-runtime-*` ledger row +
|
|
7
|
-
* `second-nature-runtime` execution attempt after each cycle so `loadStatus` exits its `unknown`
|
|
8
|
-
* baseline once the runtime has actually executed at least one full-runtime turn.
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
|
|
1
|
+
/**
|
|
2
|
+
* Wires CLI read models into control-plane `runHeartbeatCycle` for `heartbeat_check` (US-001 / CH-09-02 / T1.2.3).
|
|
3
|
+
*
|
|
4
|
+
* Snapshot inputs are derived from aggregated status; delivery defaults to none until host capability is modeled here.
|
|
5
|
+
*
|
|
6
|
+
* T1.2.3: when a `RuntimeDecisionRecorder` is provided, persist a `sn-runtime-*` ledger row +
|
|
7
|
+
* `second-nature-runtime` execution attempt after each cycle so `loadStatus` exits its `unknown`
|
|
8
|
+
* baseline once the runtime has actually executed at least one full-runtime turn.
|
|
9
|
+
*
|
|
10
|
+
* T2.2.2: when `state` + `workspaceRoot` are supplied, call `loadLifeEvidenceSnapshot` to fill
|
|
11
|
+
* `lifeEvidenceRefs`, `platformEventCount`, `workEventCount`, and `lifeEvidenceEmptyReason` on
|
|
12
|
+
* `SnapshotInputs` so planner/guard paths that require source refs see real DB truth.
|
|
13
|
+
* Falls back gracefully to `lifeEvidenceEmptyReason: "state_unavailable"` when state is absent.
|
|
14
|
+
*/
|
|
15
|
+
import type { HeartbeatSignal, HeartbeatCycleResult } from "../../core/second-nature/heartbeat/signal.js";
|
|
16
|
+
import type { SnapshotInputs } from "../../core/second-nature/heartbeat/snapshot-builder.js";
|
|
17
|
+
import type { CliReadModels } from "../read-models/index.js";
|
|
18
|
+
import type { RuntimeDecisionRecorder } from "../../observability/services/runtime-decision-recorder.js";
|
|
19
|
+
import type { StateDatabase } from "../../storage/db/index.js";
|
|
20
|
+
export interface WorkspaceHeartbeatRunnerOptions {
|
|
21
|
+
/** When supplied, the runner persists the cycle so `loadStatus` can read it (T1.2.3). */
|
|
22
|
+
runtimeRecorder?: RuntimeDecisionRecorder;
|
|
23
|
+
/**
|
|
24
|
+
* T2.2.2: when state + workspaceRoot are provided, life evidence is loaded from DB and merged
|
|
25
|
+
* into SnapshotInputs so planner/guard paths have real source-ref truth.
|
|
26
|
+
*/
|
|
27
|
+
state?: StateDatabase;
|
|
28
|
+
workspaceRoot?: string;
|
|
29
|
+
/**
|
|
30
|
+
* T1.2.4: when true (and workspaceRoot is set), inject a `quietWorkflow` dep into the heartbeat
|
|
31
|
+
* cycle so quiet/reflection intents can call `runSourceBackedQuiet` and write artifacts to disk.
|
|
32
|
+
* Defaults to true when workspaceRoot is provided, since this is the host-safe workspace path.
|
|
33
|
+
*/
|
|
34
|
+
enableQuietWorkflow?: boolean;
|
|
35
|
+
}
|
|
36
|
+
export declare function loadSnapshotInputsForWorkspaceHeartbeat(readModels: CliReadModels, options?: {
|
|
37
|
+
state?: StateDatabase;
|
|
38
|
+
workspaceRoot?: string;
|
|
39
|
+
}): Promise<SnapshotInputs>;
|
|
40
|
+
export declare function createWorkspaceHeartbeatRunner(readModels: CliReadModels, options?: WorkspaceHeartbeatRunnerOptions): (signal: HeartbeatSignal) => Promise<HeartbeatCycleResult>;
|
|
@@ -1,39 +1,93 @@
|
|
|
1
|
-
import { runHeartbeatCycle } from "../../core/second-nature/heartbeat/run-heartbeat-cycle.js";
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
const
|
|
5
|
-
const
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
1
|
+
import { runHeartbeatCycle } from "../../core/second-nature/heartbeat/run-heartbeat-cycle.js";
|
|
2
|
+
import { loadLifeEvidenceSnapshot } from "../../storage/snapshots/life-evidence-snapshot.js";
|
|
3
|
+
export async function loadSnapshotInputsForWorkspaceHeartbeat(readModels, options = {}) {
|
|
4
|
+
const status = await readModels.loadStatus();
|
|
5
|
+
const mode = status.rhythm.mode === "unknown" ? "active" : status.rhythm.mode;
|
|
6
|
+
// CH-15-03: quietEnabledBridge should reflect whether the quiet *execution path* is wired
|
|
7
|
+
// (workspaceRoot available), not whether the last observed rhythm decision was "quiet".
|
|
8
|
+
// status.quiet.mode is typically "unknown" until a Quiet artifact has been persisted, which
|
|
9
|
+
// means binding to it would permanently suppress the quiet window — the opposite of intent.
|
|
10
|
+
// We instead enable the bridge whenever workspaceRoot is provided (same condition as
|
|
11
|
+
// `createWorkspaceHeartbeatRunner` uses for injecting quietWorkflow).
|
|
12
|
+
const quietEnabledBridge = !!options.workspaceRoot;
|
|
13
|
+
// T2.2.2: Load life evidence from state DB when available so SnapshotInputs carries real refs.
|
|
14
|
+
let lifeEvidenceRefs;
|
|
15
|
+
let platformEventCount;
|
|
16
|
+
let workEventCount;
|
|
17
|
+
let lifeEvidenceEmptyReason;
|
|
18
|
+
if (options.state && options.workspaceRoot) {
|
|
19
|
+
try {
|
|
20
|
+
const snapshot = await loadLifeEvidenceSnapshot(options.state, options.workspaceRoot, { limit: 50 },
|
|
21
|
+
// Skip repair gate here — runner is called inside a live cycle; gate ran at startup.
|
|
22
|
+
{ runRepairGate: false });
|
|
23
|
+
lifeEvidenceRefs = snapshot.evidenceRefs.map((ref) => ({
|
|
24
|
+
id: ref.id,
|
|
25
|
+
kind: ref.kind,
|
|
26
|
+
uri: ref.uri,
|
|
27
|
+
}));
|
|
28
|
+
platformEventCount = snapshot.platformEvents.length;
|
|
29
|
+
workEventCount = snapshot.workEvents.length;
|
|
30
|
+
if (snapshot.empty) {
|
|
31
|
+
lifeEvidenceEmptyReason = "no_sources";
|
|
32
|
+
}
|
|
33
|
+
}
|
|
34
|
+
catch {
|
|
35
|
+
// If evidence load fails, signal state_unavailable rather than crashing the cycle.
|
|
36
|
+
lifeEvidenceRefs = [];
|
|
37
|
+
platformEventCount = 0;
|
|
38
|
+
workEventCount = 0;
|
|
39
|
+
lifeEvidenceEmptyReason = "state_unavailable";
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
else {
|
|
43
|
+
// No state wired — record that life evidence wasn't loaded so guards can reason honestly.
|
|
44
|
+
lifeEvidenceEmptyReason = "state_unavailable";
|
|
45
|
+
}
|
|
46
|
+
return {
|
|
47
|
+
mode,
|
|
48
|
+
currentWindowId: status.rhythm.windowId ?? "workspace-default",
|
|
49
|
+
pendingObligations: [],
|
|
50
|
+
recentOutreachHashes: [],
|
|
51
|
+
deniedIntents: [],
|
|
52
|
+
budgets: { socialUsed: 0, socialLimit: 5 },
|
|
53
|
+
awaitingUserInput: false,
|
|
54
|
+
quietEnabledBridge,
|
|
55
|
+
deliveryCapability: { target: "none" },
|
|
56
|
+
lifeEvidenceRefs,
|
|
57
|
+
platformEventCount,
|
|
58
|
+
workEventCount,
|
|
59
|
+
lifeEvidenceEmptyReason,
|
|
60
|
+
};
|
|
61
|
+
}
|
|
62
|
+
export function createWorkspaceHeartbeatRunner(readModels, options = {}) {
|
|
63
|
+
// T1.2.4: inject quietWorkflow dep when workspaceRoot is set so quiet/reflection intents
|
|
64
|
+
// can trigger runSourceBackedQuiet and persist artifacts to disk.
|
|
65
|
+
const quietEnabled = options.workspaceRoot && options.enableQuietWorkflow !== false;
|
|
66
|
+
return async (signal) => {
|
|
67
|
+
const cycle = await runHeartbeatCycle({
|
|
68
|
+
signal,
|
|
69
|
+
runtimeAvailable: true,
|
|
70
|
+
deps: {
|
|
71
|
+
loadSnapshotInputs: () => loadSnapshotInputsForWorkspaceHeartbeat(readModels, {
|
|
72
|
+
state: options.state,
|
|
73
|
+
workspaceRoot: options.workspaceRoot,
|
|
74
|
+
}),
|
|
75
|
+
// T1.2.4: pass quietWorkflow dep so runSourceBackedQuiet can persist artifacts.
|
|
76
|
+
quietWorkflow: quietEnabled
|
|
77
|
+
? { workspaceRoot: options.workspaceRoot }
|
|
78
|
+
: undefined,
|
|
79
|
+
},
|
|
80
|
+
});
|
|
81
|
+
if (options.runtimeRecorder) {
|
|
82
|
+
try {
|
|
83
|
+
await options.runtimeRecorder.recordHeartbeatCycle({ cycle, signal });
|
|
84
|
+
}
|
|
85
|
+
catch {
|
|
86
|
+
// T1.2.3: recorder must never break the heartbeat surface response.
|
|
87
|
+
// Failure here means status simply remains at its previous aggregate; the
|
|
88
|
+
// cycle outcome itself is still returned to the caller.
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
return cycle;
|
|
92
|
+
};
|
|
93
|
+
}
|
|
@@ -1,29 +1,46 @@
|
|
|
1
|
-
import type { StateDatabase } from "../../storage/db/index.js";
|
|
2
|
-
import type { ObservabilityDatabase } from "../../observability/db/index.js";
|
|
3
|
-
import { AppendOnlyAuditStore } from "../../observability/audit/append-only-audit-store.js";
|
|
4
|
-
import type { StatusReadModel, DailyReportReadModel, QuietReadModel, SessionDetailReadModel, CredentialReadModel, ExplainReadModel, ExplainSubjectKind } from "./types.js";
|
|
5
|
-
export type {
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
/** T1.2.
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
export
|
|
1
|
+
import type { StateDatabase } from "../../storage/db/index.js";
|
|
2
|
+
import type { ObservabilityDatabase } from "../../observability/db/index.js";
|
|
3
|
+
import { AppendOnlyAuditStore } from "../../observability/audit/append-only-audit-store.js";
|
|
4
|
+
import type { StatusReadModel, DailyReportReadModel, QuietReadModel, SessionDetailReadModel, CredentialReadModel, ExplainReadModel, ExplainSubjectKind, AuditSummaryReadModel } from "./types.js";
|
|
5
|
+
export type { AuditSummaryReadModel } from "./types.js";
|
|
6
|
+
export type { ExplainSubjectKind } from "./types.js";
|
|
7
|
+
import type { OperatorFallbackView } from "../../storage/fallback/operator-fallback-view.js";
|
|
8
|
+
import { type RhythmPolicySnapshot } from "../../storage/rhythm/rhythm-policy-snapshot.js";
|
|
9
|
+
export type { RhythmPolicySnapshot };
|
|
10
|
+
export interface CliReadModels {
|
|
11
|
+
loadStatus(scope?: string): Promise<StatusReadModel>;
|
|
12
|
+
loadDailyReport(day: string): Promise<DailyReportReadModel>;
|
|
13
|
+
loadQuiet(scope?: string): Promise<QuietReadModel>;
|
|
14
|
+
loadSession(sessionId: string): Promise<SessionDetailReadModel>;
|
|
15
|
+
loadCredential(platformId: string): Promise<CredentialReadModel>;
|
|
16
|
+
explain(subject: ExplainSubject): Promise<ExplainReadModel>;
|
|
17
|
+
/** T1.2.2 — persisted operator fallback; view status is always not_sent. */
|
|
18
|
+
loadFallbackView(ref: string): Promise<OperatorFallbackView | null>;
|
|
19
|
+
/** T1.2.6 — rhythm policy snapshot for operator `policy show`. */
|
|
20
|
+
loadPolicy(): Promise<RhythmPolicySnapshot>;
|
|
21
|
+
/**
|
|
22
|
+
* T1.2.7 (SN-CODE-02) — minimal audit read-side view for operator `audit` command.
|
|
23
|
+
* Returns a summary of all in-memory audit events in the default store.
|
|
24
|
+
* Empty store returns `{ totalEvents: 0, events: [] }` (honest empty, not an error).
|
|
25
|
+
*/
|
|
26
|
+
loadAuditSummary(): Promise<AuditSummaryReadModel>;
|
|
27
|
+
}
|
|
28
|
+
/** T1.2.1 / T1.2.2 — operator-facing read surface (subset of full CLI read models). */
|
|
29
|
+
export type OpsReadModelPort = Pick<CliReadModels, "loadStatus" | "loadDailyReport" | "loadQuiet" | "loadSession" | "loadCredential" | "explain" | "loadFallbackView">;
|
|
30
|
+
export interface ExplainSubject {
|
|
31
|
+
kind: ExplainSubjectKind;
|
|
32
|
+
id: string;
|
|
33
|
+
}
|
|
34
|
+
export interface CliReadModelsDeps {
|
|
35
|
+
stateDb: StateDatabase;
|
|
36
|
+
observabilityDb: ObservabilityDatabase;
|
|
37
|
+
/** When set, explain can resolve delivery/fallback/report/source_ref and enrich decision subjects from lived-experience audit envelopes (T5.3.1 / T1.2.1). */
|
|
38
|
+
livedExperienceAuditStore?: AppendOnlyAuditStore;
|
|
39
|
+
/**
|
|
40
|
+
* T1.2.4: when set, `loadQuiet` and `loadDailyReport` also scan `.second-nature/quiet/{day}/`
|
|
41
|
+
* for persisted Quiet artifact JSON files (from `persistQuietArtifactToWorkspace`) and merge
|
|
42
|
+
* them into the read model so operators see non-zero counts after Quiet actually runs.
|
|
43
|
+
*/
|
|
44
|
+
workspaceRoot?: string;
|
|
45
|
+
}
|
|
46
|
+
export declare function createCliReadModels(deps: CliReadModelsDeps): CliReadModels;
|