@unson/brainbase-mcp 0.23.2 → 0.23.3
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/company-os-judgment-history.d.ts +157 -0
- package/dist/company-os-judgment-history.js +489 -0
- package/dist/judgment-history-http.d.ts +18 -0
- package/dist/judgment-history-http.js +170 -0
- package/dist/judgment-history.d.ts +178 -0
- package/dist/judgment-history.js +1519 -0
- package/dist/local-web-host.d.ts +8 -0
- package/dist/local-web-host.js +36 -0
- package/dist/problem-selection.d.ts +84 -1
- package/dist/problem-selection.js +141 -15
- package/package.json +14 -2
- package/ui/judgment-history.css +173 -0
- package/ui/judgment-history.js +1077 -32
- package/ui/local-web-shell.js +1 -1
package/dist/local-web-host.d.ts
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { type IncomingMessage, type Server, type ServerResponse } from 'node:http';
|
|
2
2
|
import { type ObjectiveDefinitionBuilder } from './foundation-http.js';
|
|
3
|
+
import type { JudgmentHistoryEntrypoint } from './judgment-history.js';
|
|
3
4
|
import { JudgmentValueProofJournalCache } from './judgment-value-proof-review.js';
|
|
4
5
|
import { type MeetingMinutesLineageCorrectionHook } from './meeting-minutes-lineage-lifecycle.js';
|
|
5
6
|
import type { MinutesLineageActor, MinutesLineageStore } from './meeting-minutes-lineage.js';
|
|
@@ -25,6 +26,7 @@ export declare const LOCAL_WEB_STATUS_PATH = "/api/local/status";
|
|
|
25
26
|
export declare const LOCAL_WEB_WORLD_MODEL_PREFIX = "/api/world-model";
|
|
26
27
|
export declare const LOCAL_WEB_GRAPH_PREFIX = "/api/graph";
|
|
27
28
|
export declare const LOCAL_WEB_MEETING_MINUTES_PREFIX = "/api/meeting-minutes";
|
|
29
|
+
export declare const LOCAL_WEB_JUDGMENT_HISTORY_PREFIX: "/api/judgment-history";
|
|
28
30
|
/**
|
|
29
31
|
* An Objective is a few KB of text and criteria. 64 KiB leaves room for long
|
|
30
32
|
* Japanese text (about 20k characters) while keeping a loopback request that
|
|
@@ -43,6 +45,8 @@ export interface LocalGraphState {
|
|
|
43
45
|
export interface LocalWebModuleContext {
|
|
44
46
|
readonly dataDir: string;
|
|
45
47
|
readonly journalRoot: string;
|
|
48
|
+
/** Explicit source label for this host's configured owner journal. */
|
|
49
|
+
readonly judgmentHistoryEntrypoint?: JudgmentHistoryEntrypoint;
|
|
46
50
|
readonly token: string;
|
|
47
51
|
readonly now: () => Date;
|
|
48
52
|
/** The host's one listing cache for the judgment journal, shared by every screen that reads it. */
|
|
@@ -98,6 +102,8 @@ export interface LocalWebHostOptions {
|
|
|
98
102
|
readonly dataDir?: string;
|
|
99
103
|
/** Judgment journal root. Defaults to the journal inside the data directory. */
|
|
100
104
|
readonly journalRoot?: string;
|
|
105
|
+
/** Source label for the owner journal; defaults to the Codex local host. */
|
|
106
|
+
readonly judgmentHistoryEntrypoint?: JudgmentHistoryEntrypoint;
|
|
101
107
|
readonly token?: string;
|
|
102
108
|
/** Directory containing the packaged `ui/` files. */
|
|
103
109
|
readonly uiDir?: string;
|
|
@@ -153,6 +159,8 @@ export declare function isTrustedLocalWrite(request: IncomingMessage, token: str
|
|
|
153
159
|
/** Reads the Graph format and owner without creating or migrating anything. */
|
|
154
160
|
export declare function readLocalGraphState(dataDir: string): Promise<LocalGraphState>;
|
|
155
161
|
export declare function createLocalStatusModule(context: LocalWebModuleContext): LocalWebModule;
|
|
162
|
+
/** Common normal judgment history projection over the configured owner journal. */
|
|
163
|
+
export declare function createJudgmentHistoryModule(context: LocalWebModuleContext): LocalWebModule;
|
|
156
164
|
export declare function createValueProofModule(context: LocalWebModuleContext): LocalWebModule;
|
|
157
165
|
/** Native meeting minutes use the host's authenticated local single-owner principal. */
|
|
158
166
|
export declare function createMeetingMinutesModule(context: LocalWebModuleContext): LocalWebModule;
|
package/dist/local-web-host.js
CHANGED
|
@@ -8,6 +8,8 @@ import { foundationCatalogOrEmpty, foundationKey } from './foundation-catalog.js
|
|
|
8
8
|
import { createFoundationHttpRouter, createObjectiveFoundationRoute, FOUNDATION_HTTP_PREFIX, FOUNDATION_OBJECTIVE_ROUTE_PREFIX } from './foundation-http.js';
|
|
9
9
|
import { createFoundationRevisionStore, FoundationStoreError } from './foundation-store.js';
|
|
10
10
|
import { createGraphWebHttpHandler } from './graph-web-http.js';
|
|
11
|
+
import { createJudgmentHistoryHttpHandler, JUDGMENT_HISTORY_HTTP_PREFIX } from './judgment-history-http.js';
|
|
12
|
+
import { createJudgmentHistoryReader, createLocalJudgmentHistoryFeedbackWriter, createLocalJudgmentHistorySource } from './judgment-history.js';
|
|
11
13
|
import { defaultJudgmentJournalRoot, JudgmentValueProofJournalCache } from './judgment-value-proof-review.js';
|
|
12
14
|
import { createMeetingMinutesHttpHandler } from './meeting-minutes-http.js';
|
|
13
15
|
import { createMeetingMinutesLineageHttpHandler } from './meeting-minutes-lineage-http.js';
|
|
@@ -41,6 +43,7 @@ export const LOCAL_WEB_STATUS_PATH = '/api/local/status';
|
|
|
41
43
|
export const LOCAL_WEB_WORLD_MODEL_PREFIX = '/api/world-model';
|
|
42
44
|
export const LOCAL_WEB_GRAPH_PREFIX = '/api/graph';
|
|
43
45
|
export const LOCAL_WEB_MEETING_MINUTES_PREFIX = '/api/meeting-minutes';
|
|
46
|
+
export const LOCAL_WEB_JUDGMENT_HISTORY_PREFIX = JUDGMENT_HISTORY_HTTP_PREFIX;
|
|
44
47
|
/**
|
|
45
48
|
* An Objective is a few KB of text and criteria. 64 KiB leaves room for long
|
|
46
49
|
* Japanese text (about 20k characters) while keeping a loopback request that
|
|
@@ -162,6 +165,37 @@ export function createLocalStatusModule(context) {
|
|
|
162
165
|
}
|
|
163
166
|
};
|
|
164
167
|
}
|
|
168
|
+
/** Common normal judgment history projection over the configured owner journal. */
|
|
169
|
+
export function createJudgmentHistoryModule(context) {
|
|
170
|
+
const source = createLocalJudgmentHistorySource({
|
|
171
|
+
root: context.journalRoot,
|
|
172
|
+
entrypoint: context.judgmentHistoryEntrypoint ?? 'codex'
|
|
173
|
+
});
|
|
174
|
+
const reader = createJudgmentHistoryReader({
|
|
175
|
+
source,
|
|
176
|
+
now: context.now
|
|
177
|
+
});
|
|
178
|
+
const writeFeedback = createLocalJudgmentHistoryFeedbackWriter({
|
|
179
|
+
root: context.journalRoot,
|
|
180
|
+
reader,
|
|
181
|
+
now: context.now
|
|
182
|
+
});
|
|
183
|
+
return {
|
|
184
|
+
id: 'judgment-history',
|
|
185
|
+
uiFiles: [],
|
|
186
|
+
handle: createJudgmentHistoryHttpHandler({
|
|
187
|
+
reader,
|
|
188
|
+
basePath: LOCAL_WEB_JUDGMENT_HISTORY_PREFIX,
|
|
189
|
+
writeFeedback,
|
|
190
|
+
assertWriteAllowed(request) {
|
|
191
|
+
if (isTrustedLocalWrite(request, context.token))
|
|
192
|
+
return;
|
|
193
|
+
throw rejectUntrustedWrite(request, context.token)
|
|
194
|
+
?? new LocalWebHttpError(403, 'web_token_required', 'A valid launch token is required');
|
|
195
|
+
}
|
|
196
|
+
})
|
|
197
|
+
};
|
|
198
|
+
}
|
|
165
199
|
export function createValueProofModule(context) {
|
|
166
200
|
const handler = createValueProofReviewHttpHandler({
|
|
167
201
|
journalRoot: context.journalRoot,
|
|
@@ -857,6 +891,7 @@ export function createGraphWebModule(context) {
|
|
|
857
891
|
export function defaultLocalWebModules(context) {
|
|
858
892
|
return [
|
|
859
893
|
createLocalStatusModule(context),
|
|
894
|
+
createJudgmentHistoryModule(context),
|
|
860
895
|
createValueProofModule(context),
|
|
861
896
|
createMeetingMinutesModule(context),
|
|
862
897
|
createObjectiveFoundationModule(context),
|
|
@@ -934,6 +969,7 @@ export function createLocalWebHost(options = {}) {
|
|
|
934
969
|
const context = {
|
|
935
970
|
dataDir,
|
|
936
971
|
journalRoot,
|
|
972
|
+
judgmentHistoryEntrypoint: options.judgmentHistoryEntrypoint ?? 'codex',
|
|
937
973
|
token,
|
|
938
974
|
now,
|
|
939
975
|
journalCache: new JudgmentValueProofJournalCache(),
|
|
@@ -10,7 +10,8 @@
|
|
|
10
10
|
*/
|
|
11
11
|
import type { FoundationAcl, FoundationRevision, FoundationScope } from './ontology-foundation.js';
|
|
12
12
|
import type { ProblemCandidateRecord, ProblemCandidateStore, ProblemCandidateStoreContext } from './problem-candidates.js';
|
|
13
|
-
import { type JudgmentDAGCompositionDefinition, type JudgmentDAGCompositionRunRequest, type JudgmentDAGProblemSnapshotReference } from './judgment-dag-composition.js';
|
|
13
|
+
import { type JudgmentDAGCompositionDefinition, type JudgmentDAGCompositionErrorCode, type JudgmentDAGCompositionStatus, type JudgmentDAGCompositionRunRecord, type JudgmentDAGCompositionRunRequest, type JudgmentDAGProblemSnapshotReference } from './judgment-dag-composition.js';
|
|
14
|
+
import type { JudgmentDAGJSONValue } from './judgment-dag-runner.js';
|
|
14
15
|
export declare const PROBLEM_SELECTION_CONTRACT_VERSION: "problem-selection.v1";
|
|
15
16
|
export declare const PROBLEM_SELECTION_RECORD_VERSION: "problem-selection-record.v1";
|
|
16
17
|
export declare const PROBLEM_SELECTION_DIRECTORY: "problem-selections";
|
|
@@ -98,6 +99,87 @@ export interface ProblemSelectionEvaluationResult {
|
|
|
98
99
|
readonly unknowns?: readonly ProblemSelectionUnknown[];
|
|
99
100
|
readonly objectiveConflicts?: readonly ProblemSelectionObjectiveConflict[];
|
|
100
101
|
}
|
|
102
|
+
/**
|
|
103
|
+
* The immutable identity that the Company OS producer binds to a run.
|
|
104
|
+
*
|
|
105
|
+
* This is an input from a trusted Host/Company Authority context, not an
|
|
106
|
+
* authentication assertion. OSS intentionally does not infer or authenticate
|
|
107
|
+
* a caller from these fields. The producer and Organization store must verify
|
|
108
|
+
* the binding and the current ACL before accepting an event.
|
|
109
|
+
*/
|
|
110
|
+
export interface JudgmentDAGCompositionRunHistoryBinding {
|
|
111
|
+
readonly organization_id: string;
|
|
112
|
+
readonly tenant_id: string;
|
|
113
|
+
readonly owner_person_id: string;
|
|
114
|
+
readonly project_code: string | null;
|
|
115
|
+
readonly turn_ref: string;
|
|
116
|
+
}
|
|
117
|
+
export type JudgmentDAGCompositionRunHistoryProducerName = 'company_os' | 'codex' | 'claude_code' | 'mana';
|
|
118
|
+
export interface JudgmentDAGCompositionRunHistorySource {
|
|
119
|
+
readonly producer: JudgmentDAGCompositionRunHistoryProducerName;
|
|
120
|
+
readonly producer_revision: string;
|
|
121
|
+
}
|
|
122
|
+
/** References must be supplied by the trusted producer from actual reads. */
|
|
123
|
+
export interface JudgmentDAGCompositionRunHistoryReferences {
|
|
124
|
+
readonly problem_snapshot: JudgmentDAGProblemSnapshotReference;
|
|
125
|
+
readonly foundation: readonly JudgmentDAGJSONValue[];
|
|
126
|
+
readonly evidence: readonly JudgmentDAGJSONValue[];
|
|
127
|
+
}
|
|
128
|
+
export type JudgmentDAGCompositionRunHistoryState = 'started' | JudgmentDAGCompositionStatus | 'unknown';
|
|
129
|
+
export type JudgmentDAGCompositionRunHistoryFailureCode = JudgmentDAGCompositionErrorCode | 'unknown';
|
|
130
|
+
export interface JudgmentDAGCompositionRunHistoryFailure {
|
|
131
|
+
readonly code: JudgmentDAGCompositionRunHistoryFailureCode;
|
|
132
|
+
/** This message is fixed; raw executor/store exceptions are never persisted. */
|
|
133
|
+
readonly message: string;
|
|
134
|
+
}
|
|
135
|
+
export interface JudgmentDAGCompositionRunHistoryLifecycle {
|
|
136
|
+
readonly lifecycle_event_id: string;
|
|
137
|
+
readonly state: JudgmentDAGCompositionRunHistoryState;
|
|
138
|
+
readonly recorded_at: string;
|
|
139
|
+
readonly failure: JudgmentDAGCompositionRunHistoryFailure | null;
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* Port event understood by a trusted Host adapter and the Organization native
|
|
143
|
+
* store. The adapter may map this event to its envelope/store API, but it
|
|
144
|
+
* must preserve the run body and binding fields exactly.
|
|
145
|
+
*/
|
|
146
|
+
export interface JudgmentDAGCompositionRunHistoryEvent {
|
|
147
|
+
readonly run_id: string;
|
|
148
|
+
readonly binding: JudgmentDAGCompositionRunHistoryBinding;
|
|
149
|
+
readonly source: JudgmentDAGCompositionRunHistorySource;
|
|
150
|
+
readonly semantic_scope: JudgmentDAGCompositionDefinition['scope'];
|
|
151
|
+
readonly lifecycle: JudgmentDAGCompositionRunHistoryLifecycle;
|
|
152
|
+
readonly composition_run: JudgmentDAGCompositionRunRecord | null;
|
|
153
|
+
readonly references: JudgmentDAGCompositionRunHistoryReferences;
|
|
154
|
+
}
|
|
155
|
+
/**
|
|
156
|
+
* Company OS native storage boundary. Implementations own trusted binding,
|
|
157
|
+
* current ACL, idempotency, and conflict checks. A caller that merely passes
|
|
158
|
+
* a body to this port is not thereby trusted.
|
|
159
|
+
*
|
|
160
|
+
* Retry contract: the caller supplies stable lifecycle_event_id and
|
|
161
|
+
* recorded_at values, including timestamps. A producer may retry its own
|
|
162
|
+
* transport with the identical event; this wrapper never retries the
|
|
163
|
+
* executor and never creates a new event identity or time.
|
|
164
|
+
*/
|
|
165
|
+
export interface JudgmentDAGCompositionRunHistoryProducer {
|
|
166
|
+
readonly append: (event: JudgmentDAGCompositionRunHistoryEvent) => void | Promise<void>;
|
|
167
|
+
}
|
|
168
|
+
/** Short alias for callers that name the boundary as a CompositionRun port. */
|
|
169
|
+
export type JudgmentDAGCompositionRunProducer = JudgmentDAGCompositionRunHistoryProducer;
|
|
170
|
+
export interface JudgmentDAGCompositionRunHistoryLifecycleInput {
|
|
171
|
+
readonly lifecycle_event_id: string;
|
|
172
|
+
readonly recorded_at: string;
|
|
173
|
+
}
|
|
174
|
+
export interface JudgmentDAGCompositionRunHistoryOptions {
|
|
175
|
+
readonly producer: JudgmentDAGCompositionRunHistoryProducer;
|
|
176
|
+
/** Trusted binding supplied by Host/Company Authority; OSS does not derive it. */
|
|
177
|
+
readonly binding: JudgmentDAGCompositionRunHistoryBinding;
|
|
178
|
+
readonly source: JudgmentDAGCompositionRunHistorySource;
|
|
179
|
+
readonly references: JudgmentDAGCompositionRunHistoryReferences;
|
|
180
|
+
readonly started: JudgmentDAGCompositionRunHistoryLifecycleInput;
|
|
181
|
+
readonly terminal: JudgmentDAGCompositionRunHistoryLifecycleInput;
|
|
182
|
+
}
|
|
101
183
|
export interface ProblemSelectionEvaluationRequest {
|
|
102
184
|
readonly selectionId: string;
|
|
103
185
|
readonly selectionProblem: JudgmentDAGProblemSnapshotReference;
|
|
@@ -224,6 +306,7 @@ export declare const selectProblem: typeof createProblemSelection;
|
|
|
224
306
|
export declare function evaluateProblemSelectionWithComposition(input: {
|
|
225
307
|
readonly compositionRequest: JudgmentDAGCompositionRunRequest;
|
|
226
308
|
readonly resultInvocationId?: string;
|
|
309
|
+
readonly compositionRunHistory?: JudgmentDAGCompositionRunHistoryOptions;
|
|
227
310
|
}): Promise<ProblemSelectionEvaluationResult>;
|
|
228
311
|
export declare function computeProblemSelectionRecordId(record: ProblemSelectionRecord): ProblemSelectionRecordId;
|
|
229
312
|
export declare function saveProblemSelectionRecord(request: SaveProblemSelectionRecordRequest): Promise<ProblemSelectionRecordReceipt>;
|
|
@@ -11,7 +11,7 @@
|
|
|
11
11
|
import { createHash, randomUUID } from 'node:crypto';
|
|
12
12
|
import { link, lstat, mkdir, open, readFile, unlink } from 'node:fs/promises';
|
|
13
13
|
import path from 'node:path';
|
|
14
|
-
import { createJudgmentDAGCompositionDefinition, executeJudgmentDAGComposition } from './judgment-dag-composition.js';
|
|
14
|
+
import { createJudgmentDAGCompositionDefinition, JudgmentDAGCompositionError, executeJudgmentDAGComposition } from './judgment-dag-composition.js';
|
|
15
15
|
export const PROBLEM_SELECTION_CONTRACT_VERSION = 'problem-selection.v1';
|
|
16
16
|
export const PROBLEM_SELECTION_RECORD_VERSION = 'problem-selection-record.v1';
|
|
17
17
|
export const PROBLEM_SELECTION_DIRECTORY = 'problem-selections';
|
|
@@ -695,6 +695,100 @@ export async function createProblemSelection(request) {
|
|
|
695
695
|
export const runProblemSelection = createProblemSelection;
|
|
696
696
|
/** Alias for callers that name the operation as a selection. */
|
|
697
697
|
export const selectProblem = createProblemSelection;
|
|
698
|
+
const SAFE_COMPOSITION_FAILURE_MESSAGE = 'DAG composition failed before a run record was returned';
|
|
699
|
+
const SAFE_COMPOSITION_HISTORY_FAILURE_MESSAGE = 'DAG composition history could not be saved';
|
|
700
|
+
const SAFE_COMPOSITION_RESULT_FAILURE_MESSAGE = 'selection composition result could not be read';
|
|
701
|
+
function snapshotCompositionHistoryMetadata(request, options) {
|
|
702
|
+
// Producer adapters receive a frozen JSON-only snapshot. This keeps a
|
|
703
|
+
// producer from changing the binding, references, run id, or scope between
|
|
704
|
+
// the started event and the terminal event while it performs persistence.
|
|
705
|
+
// Only metadata is cloned here: the request also contains executable
|
|
706
|
+
// snapshot/DAG/contract/port adapters and is intentionally never cloned.
|
|
707
|
+
return deepFreeze({
|
|
708
|
+
run_id: request.run_id,
|
|
709
|
+
binding: cloneJson(options.binding, 'compositionRunHistory.binding'),
|
|
710
|
+
source: cloneJson(options.source, 'compositionRunHistory.source'),
|
|
711
|
+
semantic_scope: cloneJson(request.delegation.scope, 'compositionRunHistory.semantic_scope'),
|
|
712
|
+
references: cloneJson(options.references, 'compositionRunHistory.references'),
|
|
713
|
+
started: cloneJson(options.started, 'compositionRunHistory.started'),
|
|
714
|
+
terminal: cloneJson(options.terminal, 'compositionRunHistory.terminal')
|
|
715
|
+
});
|
|
716
|
+
}
|
|
717
|
+
function compositionHistoryReview(reason) {
|
|
718
|
+
return {
|
|
719
|
+
status: 'human_review_required',
|
|
720
|
+
reason,
|
|
721
|
+
unknowns: [{ status: 'unknown', reason }],
|
|
722
|
+
objectiveConflicts: []
|
|
723
|
+
};
|
|
724
|
+
}
|
|
725
|
+
function compositionHistorySaveFailure() {
|
|
726
|
+
const reason = `selection composition history unavailable: ${SAFE_COMPOSITION_HISTORY_FAILURE_MESSAGE}`;
|
|
727
|
+
return compositionHistoryReview(reason);
|
|
728
|
+
}
|
|
729
|
+
function compositionFailureCode(cause) {
|
|
730
|
+
return cause instanceof JudgmentDAGCompositionError ? cause.code : 'unknown';
|
|
731
|
+
}
|
|
732
|
+
function compositionHistoryEvent(metadata, lifecycle, state, compositionRun, failure) {
|
|
733
|
+
return deepFreeze({
|
|
734
|
+
run_id: metadata.run_id,
|
|
735
|
+
binding: metadata.binding,
|
|
736
|
+
source: metadata.source,
|
|
737
|
+
semantic_scope: metadata.semantic_scope,
|
|
738
|
+
lifecycle: {
|
|
739
|
+
lifecycle_event_id: lifecycle.lifecycle_event_id,
|
|
740
|
+
state,
|
|
741
|
+
recorded_at: lifecycle.recorded_at,
|
|
742
|
+
failure
|
|
743
|
+
},
|
|
744
|
+
composition_run: compositionRun,
|
|
745
|
+
references: metadata.references
|
|
746
|
+
});
|
|
747
|
+
}
|
|
748
|
+
async function appendCompositionHistoryEvent(options, event) {
|
|
749
|
+
try {
|
|
750
|
+
await options.producer.append(event);
|
|
751
|
+
return true;
|
|
752
|
+
}
|
|
753
|
+
catch {
|
|
754
|
+
// The persistence implementation may retry its own transport. The
|
|
755
|
+
// wrapper does not retry or expose the store's raw error.
|
|
756
|
+
return false;
|
|
757
|
+
}
|
|
758
|
+
}
|
|
759
|
+
function isCompositionRunStatus(value) {
|
|
760
|
+
return value === 'completed' || value === 'failed' || value === 'held';
|
|
761
|
+
}
|
|
762
|
+
function sameCompositionHistoryJson(left, right) {
|
|
763
|
+
try {
|
|
764
|
+
return canonicalJson(left) === canonicalJson(right);
|
|
765
|
+
}
|
|
766
|
+
catch {
|
|
767
|
+
return false;
|
|
768
|
+
}
|
|
769
|
+
}
|
|
770
|
+
function isCompositionRunBoundToHistoryMetadata(run, metadata) {
|
|
771
|
+
return (run.run_id === metadata.run_id &&
|
|
772
|
+
isCompositionRunStatus(run.status) &&
|
|
773
|
+
sameCompositionHistoryJson(run.delegation.scope, metadata.semantic_scope) &&
|
|
774
|
+
sameCompositionHistoryJson(run.problem_snapshot, metadata.references.problem_snapshot));
|
|
775
|
+
}
|
|
776
|
+
function compositionResultFromRun(run, resultInvocationId) {
|
|
777
|
+
if (run.status !== 'completed') {
|
|
778
|
+
const reason = `selection composition status is ${run.status}`;
|
|
779
|
+
return compositionHistoryReview(reason);
|
|
780
|
+
}
|
|
781
|
+
const child = resultInvocationId === undefined
|
|
782
|
+
? run.children[run.children.length - 1]
|
|
783
|
+
: run.children.find((entry) => entry.invocation_id === resultInvocationId);
|
|
784
|
+
if (child === undefined)
|
|
785
|
+
return compositionHistoryReview('selection composition returned no designated result child');
|
|
786
|
+
if (child.result.status !== 'completed' || !isPlainRecord(child.result.conclusion)) {
|
|
787
|
+
const reason = child.result.reason ?? `selection child status is ${child.result.status}`;
|
|
788
|
+
return compositionHistoryReview(reason);
|
|
789
|
+
}
|
|
790
|
+
return child.result.conclusion;
|
|
791
|
+
}
|
|
698
792
|
/**
|
|
699
793
|
* Adapter helper for a composition whose designated child returns the
|
|
700
794
|
* selection contract in its conclusion. The meta Problem remains the exact
|
|
@@ -702,28 +796,60 @@ export const selectProblem = createProblemSelection;
|
|
|
702
796
|
* requires a later Problem creation request.
|
|
703
797
|
*/
|
|
704
798
|
export async function evaluateProblemSelectionWithComposition(input) {
|
|
799
|
+
const history = input.compositionRunHistory;
|
|
800
|
+
let historyMetadata;
|
|
801
|
+
if (history !== undefined) {
|
|
802
|
+
try {
|
|
803
|
+
historyMetadata = snapshotCompositionHistoryMetadata(input.compositionRequest, history);
|
|
804
|
+
}
|
|
805
|
+
catch {
|
|
806
|
+
return compositionHistoryReview(`selection composition unavailable: ${SAFE_COMPOSITION_FAILURE_MESSAGE}`);
|
|
807
|
+
}
|
|
808
|
+
}
|
|
809
|
+
if (history !== undefined) {
|
|
810
|
+
const startedEvent = compositionHistoryEvent(historyMetadata, historyMetadata.started, 'started', null, null);
|
|
811
|
+
if (!await appendCompositionHistoryEvent(history, startedEvent))
|
|
812
|
+
return compositionHistorySaveFailure();
|
|
813
|
+
}
|
|
705
814
|
let run;
|
|
706
815
|
try {
|
|
707
816
|
run = await executeJudgmentDAGComposition(input.compositionRequest);
|
|
708
817
|
}
|
|
709
818
|
catch (cause) {
|
|
710
|
-
const
|
|
711
|
-
|
|
819
|
+
const failureCode = compositionFailureCode(cause);
|
|
820
|
+
if (history !== undefined) {
|
|
821
|
+
const failureEvent = compositionHistoryEvent(historyMetadata, historyMetadata.terminal, failureCode === 'unknown' ? 'unknown' : 'failed', null, { code: failureCode, message: SAFE_COMPOSITION_FAILURE_MESSAGE });
|
|
822
|
+
if (!await appendCompositionHistoryEvent(history, failureEvent))
|
|
823
|
+
return compositionHistorySaveFailure();
|
|
824
|
+
}
|
|
825
|
+
return compositionHistoryReview(`selection composition unavailable: ${SAFE_COMPOSITION_FAILURE_MESSAGE}`);
|
|
712
826
|
}
|
|
713
|
-
if (
|
|
714
|
-
|
|
715
|
-
|
|
827
|
+
if (history !== undefined) {
|
|
828
|
+
let terminalEvent;
|
|
829
|
+
try {
|
|
830
|
+
if (!isCompositionRunBoundToHistoryMetadata(run, historyMetadata)) {
|
|
831
|
+
terminalEvent = compositionHistoryEvent(historyMetadata, historyMetadata.terminal, 'unknown', null, { code: 'unknown', message: SAFE_COMPOSITION_FAILURE_MESSAGE });
|
|
832
|
+
}
|
|
833
|
+
else {
|
|
834
|
+
terminalEvent = compositionHistoryEvent(historyMetadata, historyMetadata.terminal, run.status, cloneJson(run, 'compositionRunHistory.composition_run'), null);
|
|
835
|
+
}
|
|
836
|
+
}
|
|
837
|
+
catch {
|
|
838
|
+
terminalEvent = compositionHistoryEvent(historyMetadata, historyMetadata.terminal, 'unknown', null, { code: 'unknown', message: SAFE_COMPOSITION_FAILURE_MESSAGE });
|
|
839
|
+
}
|
|
840
|
+
if (!await appendCompositionHistoryEvent(history, terminalEvent))
|
|
841
|
+
return compositionHistorySaveFailure();
|
|
842
|
+
if (terminalEvent.composition_run === null)
|
|
843
|
+
return compositionHistoryReview(SAFE_COMPOSITION_RESULT_FAILURE_MESSAGE);
|
|
716
844
|
}
|
|
717
|
-
|
|
718
|
-
|
|
719
|
-
|
|
720
|
-
|
|
721
|
-
|
|
722
|
-
|
|
723
|
-
|
|
724
|
-
return { status: 'human_review_required', reason, unknowns: [{ status: 'unknown', reason }], objectiveConflicts: [] };
|
|
845
|
+
try {
|
|
846
|
+
return compositionResultFromRun(run, input.resultInvocationId);
|
|
847
|
+
}
|
|
848
|
+
catch {
|
|
849
|
+
// The terminal event was appended before this extraction. Keep the
|
|
850
|
+
// persisted run while requiring a human review of the derived selection.
|
|
851
|
+
return compositionHistoryReview(SAFE_COMPOSITION_RESULT_FAILURE_MESSAGE);
|
|
725
852
|
}
|
|
726
|
-
return child.result.conclusion;
|
|
727
853
|
}
|
|
728
854
|
function selectionRecordPayload(record) {
|
|
729
855
|
return record;
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@unson/brainbase-mcp",
|
|
3
|
-
"version": "0.23.
|
|
3
|
+
"version": "0.23.3",
|
|
4
4
|
"description": "Local-first Brainbase judgment OS that lets supported AI agents reuse a user's approved goals, priorities, decisions, and judgment criteria.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "MIT",
|
|
@@ -31,6 +31,14 @@
|
|
|
31
31
|
"types": "./dist/judgment-frame.d.ts",
|
|
32
32
|
"import": "./dist/judgment-frame.js"
|
|
33
33
|
},
|
|
34
|
+
"./judgment-history": {
|
|
35
|
+
"types": "./dist/judgment-history.d.ts",
|
|
36
|
+
"import": "./dist/judgment-history.js"
|
|
37
|
+
},
|
|
38
|
+
"./judgment-history-http": {
|
|
39
|
+
"types": "./dist/judgment-history-http.d.ts",
|
|
40
|
+
"import": "./dist/judgment-history-http.js"
|
|
41
|
+
},
|
|
34
42
|
"./judgment-value-proof": {
|
|
35
43
|
"types": "./dist/judgment-value-proof.d.ts",
|
|
36
44
|
"import": "./dist/judgment-value-proof.js"
|
|
@@ -115,6 +123,10 @@
|
|
|
115
123
|
"types": "./dist/company-os-learning-adoption.d.ts",
|
|
116
124
|
"import": "./dist/company-os-learning-adoption.js"
|
|
117
125
|
},
|
|
126
|
+
"./company-os-judgment-history": {
|
|
127
|
+
"types": "./dist/company-os-judgment-history.d.ts",
|
|
128
|
+
"import": "./dist/company-os-judgment-history.js"
|
|
129
|
+
},
|
|
118
130
|
"./meeting-minutes-lineage": {
|
|
119
131
|
"types": "./dist/meeting-minutes-lineage.d.ts",
|
|
120
132
|
"import": "./dist/meeting-minutes-lineage.js"
|
|
@@ -407,5 +419,5 @@
|
|
|
407
419
|
"engines": {
|
|
408
420
|
"node": ">=20"
|
|
409
421
|
},
|
|
410
|
-
"gitHead": "
|
|
422
|
+
"gitHead": "51eca010f2f8df4d24b44bd705467bee1161719d"
|
|
411
423
|
}
|
package/ui/judgment-history.css
CHANGED
|
@@ -26,6 +26,35 @@
|
|
|
26
26
|
gap: 6px;
|
|
27
27
|
}
|
|
28
28
|
|
|
29
|
+
.bb-jh-normal-filters {
|
|
30
|
+
display: flex;
|
|
31
|
+
flex: 1 1 280px;
|
|
32
|
+
flex-wrap: wrap;
|
|
33
|
+
gap: 8px;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
.bb-jh-filter {
|
|
37
|
+
display: grid;
|
|
38
|
+
min-width: 130px;
|
|
39
|
+
gap: 4px;
|
|
40
|
+
color: var(--bb-color-muted);
|
|
41
|
+
font-size: 11px;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
.bb-jh-filter span {
|
|
45
|
+
line-height: 1.2;
|
|
46
|
+
}
|
|
47
|
+
|
|
48
|
+
.bb-jh-filter select {
|
|
49
|
+
min-height: 38px;
|
|
50
|
+
border: 1px solid var(--bb-color-border-strong);
|
|
51
|
+
border-radius: var(--bb-radius-sm);
|
|
52
|
+
padding: 7px 28px 7px 10px;
|
|
53
|
+
background: var(--bb-color-panel);
|
|
54
|
+
color: var(--bb-color-ink);
|
|
55
|
+
font: inherit;
|
|
56
|
+
}
|
|
57
|
+
|
|
29
58
|
.bb-jh-search {
|
|
30
59
|
display: flex;
|
|
31
60
|
flex: 1 1 230px;
|
|
@@ -167,17 +196,161 @@
|
|
|
167
196
|
line-height: 1.5;
|
|
168
197
|
}
|
|
169
198
|
|
|
199
|
+
.bb-jh-reference-availability,
|
|
200
|
+
.bb-jh-missing-fields {
|
|
201
|
+
color: var(--bb-color-warning-strong, var(--bb-color-muted)) !important;
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
.bb-jh-alternative-list {
|
|
205
|
+
display: grid;
|
|
206
|
+
gap: 10px;
|
|
207
|
+
margin: 0;
|
|
208
|
+
padding: 0 0 0 18px;
|
|
209
|
+
}
|
|
210
|
+
|
|
211
|
+
.bb-jh-alternative-list li {
|
|
212
|
+
display: grid;
|
|
213
|
+
gap: 2px;
|
|
214
|
+
line-height: 1.45;
|
|
215
|
+
}
|
|
216
|
+
|
|
217
|
+
.bb-jh-alternative-list li span {
|
|
218
|
+
color: var(--bb-color-muted);
|
|
219
|
+
font-size: 12px;
|
|
220
|
+
}
|
|
221
|
+
|
|
222
|
+
.bb-jh-pagination {
|
|
223
|
+
display: flex;
|
|
224
|
+
align-items: center;
|
|
225
|
+
justify-content: space-between;
|
|
226
|
+
gap: 12px;
|
|
227
|
+
margin: 14px 0 0;
|
|
228
|
+
color: var(--bb-color-muted);
|
|
229
|
+
font-size: 12px;
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
.bb-jh-pagination-count {
|
|
233
|
+
font-variant-numeric: tabular-nums;
|
|
234
|
+
}
|
|
235
|
+
|
|
170
236
|
.bb-jh .bb-ws-definition dd > span {
|
|
171
237
|
display: block;
|
|
172
238
|
line-height: 1.5;
|
|
173
239
|
}
|
|
174
240
|
|
|
241
|
+
.bb-jh-feedback-events,
|
|
242
|
+
.bb-jh-feedback-composer {
|
|
243
|
+
display: grid;
|
|
244
|
+
gap: 10px;
|
|
245
|
+
}
|
|
246
|
+
|
|
247
|
+
.bb-jh-feedback-event {
|
|
248
|
+
display: grid;
|
|
249
|
+
gap: 5px;
|
|
250
|
+
padding: 10px 0;
|
|
251
|
+
border-bottom: 1px solid var(--bb-color-border);
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
.bb-jh-feedback-event:last-child {
|
|
255
|
+
border-bottom: 0;
|
|
256
|
+
}
|
|
257
|
+
|
|
258
|
+
.bb-jh-feedback-event strong {
|
|
259
|
+
color: var(--bb-color-ink);
|
|
260
|
+
}
|
|
261
|
+
|
|
262
|
+
.bb-jh-feedback-event code,
|
|
263
|
+
.bb-jh-reference-export > code,
|
|
264
|
+
.bb-jh-feedback-composer > code {
|
|
265
|
+
color: var(--bb-color-quiet);
|
|
266
|
+
font-family: var(--bb-font-mono);
|
|
267
|
+
font-size: 10px;
|
|
268
|
+
overflow-wrap: anywhere;
|
|
269
|
+
}
|
|
270
|
+
|
|
271
|
+
.bb-jh-feedback-event p,
|
|
272
|
+
.bb-jh-reference-export p {
|
|
273
|
+
margin: 0;
|
|
274
|
+
color: var(--bb-color-muted);
|
|
275
|
+
font-size: 12px;
|
|
276
|
+
line-height: 1.5;
|
|
277
|
+
overflow-wrap: anywhere;
|
|
278
|
+
}
|
|
279
|
+
|
|
280
|
+
.bb-jh-reference-export {
|
|
281
|
+
display: grid;
|
|
282
|
+
gap: 7px;
|
|
283
|
+
margin-top: 7px;
|
|
284
|
+
padding: 9px;
|
|
285
|
+
border: 1px solid var(--bb-color-border);
|
|
286
|
+
border-radius: var(--bb-radius-sm);
|
|
287
|
+
background: var(--bb-color-panel-muted, var(--bb-color-panel));
|
|
288
|
+
}
|
|
289
|
+
|
|
290
|
+
.bb-jh-reference-export label,
|
|
291
|
+
.bb-jh-feedback-composer label {
|
|
292
|
+
color: var(--bb-color-muted);
|
|
293
|
+
font-size: 11px;
|
|
294
|
+
}
|
|
295
|
+
|
|
296
|
+
.bb-jh-reference-export textarea,
|
|
297
|
+
.bb-jh-feedback-composer textarea,
|
|
298
|
+
.bb-jh-feedback-composer select {
|
|
299
|
+
width: 100%;
|
|
300
|
+
min-height: 36px;
|
|
301
|
+
border: 1px solid var(--bb-color-border-strong);
|
|
302
|
+
border-radius: var(--bb-radius-sm);
|
|
303
|
+
padding: 8px 10px;
|
|
304
|
+
background: var(--bb-color-panel);
|
|
305
|
+
color: var(--bb-color-ink);
|
|
306
|
+
font: inherit;
|
|
307
|
+
resize: vertical;
|
|
308
|
+
}
|
|
309
|
+
|
|
310
|
+
.bb-jh-reference-payload {
|
|
311
|
+
margin: 0;
|
|
312
|
+
padding: 8px;
|
|
313
|
+
border-radius: var(--bb-radius-sm);
|
|
314
|
+
background: var(--bb-color-code, var(--bb-color-panel));
|
|
315
|
+
color: var(--bb-color-quiet);
|
|
316
|
+
font-family: var(--bb-font-mono);
|
|
317
|
+
font-size: 10px;
|
|
318
|
+
line-height: 1.45;
|
|
319
|
+
white-space: pre-wrap;
|
|
320
|
+
overflow-wrap: anywhere;
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
.bb-jh-copy-status,
|
|
324
|
+
.bb-jh-feedback-status {
|
|
325
|
+
color: var(--bb-color-muted);
|
|
326
|
+
font-size: 11px;
|
|
327
|
+
line-height: 1.45;
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
.bb-jh-feedback-status.is-saved {
|
|
331
|
+
color: var(--bb-color-success-strong, var(--bb-color-accent-strong));
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
.bb-jh-feedback-status.is-unavailable,
|
|
335
|
+
.bb-jh-feedback-status.is-unconfirmed,
|
|
336
|
+
.bb-jh-feedback-status.is-error {
|
|
337
|
+
color: var(--bb-color-warning-strong, var(--bb-color-muted));
|
|
338
|
+
}
|
|
339
|
+
|
|
175
340
|
@media (max-width: 760px) {
|
|
176
341
|
.bb-jh-controls {
|
|
177
342
|
align-items: stretch;
|
|
178
343
|
flex-direction: column;
|
|
179
344
|
}
|
|
180
345
|
|
|
346
|
+
.bb-jh-normal-filters {
|
|
347
|
+
flex-direction: column;
|
|
348
|
+
}
|
|
349
|
+
|
|
350
|
+
.bb-jh-filter select {
|
|
351
|
+
width: 100%;
|
|
352
|
+
}
|
|
353
|
+
|
|
181
354
|
.bb-jh-search {
|
|
182
355
|
max-width: none;
|
|
183
356
|
}
|