@unson/brainbase-mcp 0.1.0 → 0.2.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -154,6 +154,9 @@ export interface ValueDemo {
154
154
  };
155
155
  answer: string;
156
156
  sampleResult: string;
157
+ resultKind: 'local_context_sample';
158
+ agentConnection: 'not_verified';
159
+ realVerification: string;
157
160
  valueExplanation: string;
158
161
  operationalization: OperationalizationPlan;
159
162
  nextStep: string;
@@ -168,7 +171,7 @@ export declare function buildConnectorRecommendations(input: RecommendationInput
168
171
  export declare function renderAgentProtocol(format: OnboardingFormat): string;
169
172
  export declare function renderConnectorRecommendations(input: RecommendationInput, format: OnboardingFormat): string;
170
173
  export declare function renderSourceDiagnosis(input: SourceDiagnosisInput, format: OnboardingFormat): string;
171
- export declare function renderValueDemo(input: ValueDemoInput, format: OnboardingFormat): string;
174
+ export declare function renderValueDemo(input: ValueDemoInput, format: OnboardingFormat, details?: boolean): string;
172
175
  export declare function renderCandidateDrafts(input: CandidateInput, format: OnboardingFormat): string;
173
176
  export declare function renderLocalOnboardingPlan(input: LocalOnboardingPlanInput, format: OnboardingFormat): string;
174
177
  export declare function parseOnboardingFormat(value: string | undefined): OnboardingFormat;
@@ -91,7 +91,7 @@ export function buildAgentOnboardingProtocol() {
91
91
  };
92
92
  }
93
93
  export function buildValueDemo(input) {
94
- const scenario = input.scenario?.trim() || 'Draft the first message or working note that should use my saved Brainbase context.';
94
+ const scenario = input.scenario?.trim() || '保存した文脈を使って、次に進めるメモを作って';
95
95
  const seeded = seededAreas(input.os);
96
96
  const missing = Object.entries(seeded)
97
97
  .filter(([, value]) => !value)
@@ -120,7 +120,7 @@ export function buildValueDemo(input) {
120
120
  firstValueReady: ready
121
121
  });
122
122
  return {
123
- goal: 'Show one useful answer from the context the user just saved before any setup follow-up.',
123
+ goal: '追加設定へ進む前に、保存した文脈が役立つ回答を一つ確認する。',
124
124
  ready,
125
125
  missing,
126
126
  scenario,
@@ -139,11 +139,14 @@ export function buildValueDemo(input) {
139
139
  },
140
140
  answer: sampleResult,
141
141
  sampleResult,
142
+ resultKind: 'local_context_sample',
143
+ agentConnection: 'not_verified',
144
+ realVerification: 'MCP設定を実際のエージェントへ反映した後、同じ依頼をCodex / Claude Codeへ送って実際の応答を確認します。',
142
145
  valueExplanation,
143
146
  operationalization,
144
147
  nextStep: ready
145
- ? 'Do not stop here. Use the operationalization checklist below to install skills, register routines with confirmation, merge MCP config, decide source allowlists, and verify MCP get_context/search.'
146
- : `First save the minimum missing memo: ${missing.map(missingLabel).join(', ')}.`,
148
+ ? '必要なら --details で、スキル、ルーティン、MCP設定、参照許可、動作確認の残作業を確認します。'
149
+ : `まず最小文脈を保存します: ${missing.map(missingLabel).join(', ')}。`,
147
150
  completionSignal: ready ? 'first_value_demo_ready' : 'needs_seed'
148
151
  };
149
152
  }
@@ -495,45 +498,44 @@ export function renderSourceDiagnosis(input, format) {
495
498
  ''
496
499
  ].join('\n');
497
500
  }
498
- export function renderValueDemo(input, format) {
501
+ export function renderValueDemo(input, format, details = false) {
499
502
  const demo = buildValueDemo(input);
500
503
  if (format === 'json') {
501
504
  return `${JSON.stringify(demo, null, 2)}\n`;
502
505
  }
503
- return [
504
- '# Brainbase First Value Demo',
506
+ const lines = [
507
+ '# Brainbase 初回価値デモ',
505
508
  '',
506
509
  demo.goal,
507
510
  '',
508
- `- Ready: ${String(demo.ready)}`,
509
- `- Completion signal: ${demo.completionSignal}`,
510
- `- Missing: ${demo.missing.length === 0 ? 'none' : demo.missing.map(missingLabel).join(', ')}`,
511
+ `- 状態: ${demo.ready ? '準備済み' : '要設定'}`,
512
+ `- 完了シグナル: ${demo.completionSignal}`,
513
+ `- 不足: ${demo.missing.length === 0 ? 'なし' : demo.missing.map(missingLabel).join(', ')}`,
511
514
  '',
512
- '## Try This Now',
515
+ '## 今すぐ試す',
513
516
  demo.tryPrompt,
514
517
  '',
515
- '## Sample Result',
518
+ '## サンプル結果',
519
+ 'これはCLIが保存済み文脈から組み立てたサンプルです。実際のエージェント応答ではありません。',
520
+ '- 実エージェント接続: 未確認',
521
+ `- 実応答の確認方法: ${demo.realVerification}`,
522
+ '',
516
523
  demo.sampleResult,
517
524
  '',
518
- '## What Changed',
525
+ '## 反映された文脈',
519
526
  demo.valueExplanation,
520
527
  '',
521
- '## Operationalization Still Pending',
522
- demo.operationalization.goal,
523
- '',
524
- '### Completed',
525
- ...demo.operationalization.completed.map((item) => `- ${item}`),
526
- '',
527
- '### Next Actions',
528
- ...demo.operationalization.pending.map((item) => `- ${item.title}: \`${item.command}\` (${item.safety})`),
529
- '',
530
- '### Recommended Order',
531
- ...demo.operationalization.recommendedOrder.map((item, index) => `${index + 1}. ${item}`),
532
- '',
533
- '## Next Step',
528
+ '## 次に実行',
529
+ demo.ready
530
+ ? `\`brainbase onboard:demo --dir ${shellArg(input.os.dataDir)} --scenario ${shellArg(demo.scenario)} --details\``
531
+ : `\`brainbase onboard:start --dir ${shellArg(input.os.dataDir)} --target codex\``,
534
532
  demo.nextStep,
535
533
  ''
536
- ].join('\n');
534
+ ];
535
+ if (details) {
536
+ lines.push('## まだ残っている運用化', demo.operationalization.goal, '', '### 完了済み', ...demo.operationalization.completed.map((item) => `- ${item}`), '', '### 次の操作', ...demo.operationalization.pending.map((item) => `- ${item.title}: \`${item.command}\` (${item.safety})`), '', '### 推奨順序', ...demo.operationalization.recommendedOrder.map((item, index) => `${index + 1}. ${item}`), '');
537
+ }
538
+ return lines.join('\n');
537
539
  }
538
540
  export function renderCandidateDrafts(input, format) {
539
541
  const candidateSet = buildCandidateDrafts(input);
@@ -685,7 +687,7 @@ function seededAreas(os) {
685
687
  }
686
688
  function selfContext(os) {
687
689
  return [
688
- ...(os.graph.owner?.name ? [`Owner: ${os.graph.owner.name}`] : []),
690
+ ...(os.graph.owner?.name ? [`本人: ${os.graph.owner.name}`] : []),
689
691
  ...(os.graph.owner?.summary ? [os.graph.owner.summary] : []),
690
692
  ...os.personalKg
691
693
  .filter((entry) => entry.type === 'self' || entry.type === 'value' || entry.type === 'judgment')
@@ -696,7 +698,7 @@ function workContext(os) {
696
698
  return [
697
699
  ...os.graph.entities
698
700
  .filter((entity) => entity.type === 'project')
699
- .map((entity) => entity.summary ? `${entity.name}: ${entity.summary}` : entity.name),
701
+ .map((entity) => entity.name),
700
702
  ...os.personalKg
701
703
  .filter((entry) => entry.type === 'work' || entry.type === 'experience')
702
704
  .map((entry) => entry.text)
@@ -723,27 +725,43 @@ function relationshipTerms(name) {
723
725
  function normalizeForMatch(value) {
724
726
  return value.toLowerCase().replace(/\s+/g, '');
725
727
  }
728
+ function shellArg(value) {
729
+ return /^[A-Za-z0-9_./:@%+=,-]+$/.test(value) ? value : JSON.stringify(value);
730
+ }
726
731
  function buildReadySampleResult(input) {
727
732
  const projectLine = input.work[0] ?? '保存済みの仕事メモ';
728
733
  const ownerLine = input.self[0] ?? 'あなたの進め方';
729
734
  const relationshipLine = input.selectedRelationship
730
- ? `${input.selectedRelationship.person}${input.selectedRelationship.role ? `(${input.selectedRelationship.role})` : ''}には、${input.selectedRelationship.context}を前提に相談します。`
735
+ ? `${input.selectedRelationship.person}${input.selectedRelationship.role ? `(${input.selectedRelationship.role})` : ''}には、「${input.selectedRelationship.context}」という関係を前提に相談します。`
731
736
  : '特定の相談相手が未指定なので、まず保存済みの仕事メモから次の一手を整理します。';
732
737
  const decisionLine = input.decisions[0]
733
738
  ? `判断基準: ${input.decisions[0].decision}`
734
739
  : '追加の判断基準はまだないので、次に動ける形へ絞ります。';
740
+ const decisionCriterion = input.decisions[0]?.decision ?? '保存済みの前提を崩さず、次の一手を小さく決める';
741
+ const recipient = input.selectedRelationship
742
+ ? `${input.selectedRelationship.person}さん`
743
+ : '次の判断者';
735
744
  return [
736
745
  `「${input.scenario}」への回答例:`,
737
746
  '',
738
747
  `次に進める作業は、${projectLine}を前提に一つのメモへ整理することです。`,
739
- `進め方は、${ownerLine}を崩さず、説明を足しすぎない形にします。`,
748
+ `進め方は、${ownerLine.replace(/^本人: /u, '')}さんの前提を崩さず、説明を足しすぎない形にします。`,
740
749
  relationshipLine,
741
750
  decisionLine,
742
751
  '',
743
752
  'そのまま送れる最初のアウトプット:',
744
- input.selectedRelationship
745
- ? `${input.selectedRelationship.person}さんに確認したい論点を、背景説明ではなく「次に判断したいこと」と「相談したいこと」に分けて出します。`
746
- : '保存済みの仕事メモから、今日進める作業と追加で確認したい一点だけを出します。'
753
+ '',
754
+ '次に判断したいこと:',
755
+ `- ${projectLine}について、「${decisionCriterion}」を満たす進め方を一つ選ぶ。`,
756
+ '',
757
+ '相談したいこと:',
758
+ `- ${recipient}に、${projectLine}を進める条件、懸念、判断期限を確認する。`,
759
+ '',
760
+ '未確認事項:',
761
+ '- 期限、最終承認者、判断前に追加で必要な情報。',
762
+ '',
763
+ '次の行動:',
764
+ `- ${recipient}へこのメモを送り、回答後に実行案を一つへ絞る。`
747
765
  ].join('\n');
748
766
  }
749
767
  function buildValueExplanation(input) {
@@ -6,76 +6,76 @@ export function buildOperationalizationPlan(input = {}) {
6
6
  const skillsTarget = target === 'claude' ? 'claude' : target === 'codex' ? 'codex' : 'portable';
7
7
  const routinesTarget = target === 'claude' ? 'claude' : 'codex';
8
8
  return {
9
- goal: 'Keep onboarding open until the first value demo is followed by the operating setup the user still needs.',
9
+ goal: '初回価値を確認した後、必要な運用設定だけを順に完了する。',
10
10
  completed: input.firstValueReady
11
11
  ? [
12
- 'Initial approved context is seeded locally.',
13
- 'doctor can report the first value demo as ready.',
14
- 'onboard:demo produced a prompt, sample result, and plain-language value explanation.'
12
+ '承認した最小文脈をローカルへ保存済み。',
13
+ 'doctorで初回価値デモの準備完了を確認可能。',
14
+ 'onboard:demoでプロンプト、サンプル結果、価値の説明を確認済み。'
15
15
  ]
16
16
  : [
17
- 'Personal OS setup has started.'
17
+ 'Personal OSの準備を開始済み。'
18
18
  ],
19
19
  pending: [
20
20
  {
21
21
  id: 'public-skills',
22
- title: 'Place the public Brainbase onboarding skills',
22
+ title: '公開Brainbaseオンボーディングスキルを配置する',
23
23
  status: 'pending',
24
24
  command: `brainbase onboard:skills --target ${skillsTarget}`,
25
- why: 'Agents need the public onboarding, source import, candidate review, and daily routine instructions available where they run.',
26
- safety: 'Generation is dry-run by default; write files only with an explicit --out path and do not overwrite existing SKILL.md files.'
25
+ why: 'エージェントが実行環境で、オンボーディング、参照元取込、候補レビュー、日次ルーティンの手順を使えるようにします。',
26
+ safety: '標準はプレビューです。明示的な --out 指定時だけ書き込み、既存のSKILL.mdを上書きしません。'
27
27
  },
28
28
  {
29
29
  id: 'routines',
30
- title: 'Register ohayo / oyasumi / retro routines',
30
+ title: 'ohayo / oyasumi / retroルーティンを登録する',
31
31
  status: 'pending',
32
32
  command: `brainbase onboard:routines --target ${routinesTarget} --cwd ${commandArg(cwd)}`,
33
- why: 'The operating loop is not active until the morning, end-of-day, and weekly retrospective routines are scheduled.',
34
- safety: 'Register routines paused or confirmation-gated first; generated definitions alone do not create a live scheduler.'
33
+ why: '朝、終業時、週次振り返りの予定を登録して初めて運用ループが動きます。',
34
+ safety: '最初は一時停止または確認付きで登録します。定義生成だけではスケジュール済みになりません。'
35
35
  },
36
36
  {
37
37
  id: 'mcp-config',
38
- title: 'Merge the Brainbase MCP config into the real agent config',
38
+ title: 'Brainbase MCP設定を実際のエージェント設定へ反映する',
39
39
  status: 'pending',
40
40
  command: `brainbase onboard:install --target ${installTarget} --dir ${commandArg(dataDir)} --dry-run`,
41
- why: 'A dry-run snippet proves the config shape, but the agent cannot call Brainbase until the real Codex / Claude / CodeCode config is updated.',
42
- safety: 'Keep dry-run as preview only; merge into live config after user approval and restart the target agent.'
41
+ why: 'プレビューは設定形式の確認に留まり、実設定を更新するまでエージェントはBrainbaseを呼べません。',
42
+ safety: 'プレビュー確認後、利用者の承認を得て実設定へ反映し、対象エージェントを再起動します。'
43
43
  },
44
44
  {
45
45
  id: 'source-allowlist',
46
- title: 'Decide source allowlists, import, and candidate review',
46
+ title: '参照許可範囲、取込、候補レビューを決める',
47
47
  status: 'pending',
48
48
  command: 'brainbase onboard:diagnose-sources --email <provider> --calendar <provider> --drive <provider> --drive-folder <folder-id> --tasks <tool>',
49
- why: 'Mail, calendar, drive, files, and tasks are optional follow-up sources and need explicit allowlists before import.',
50
- safety: 'Keep imported material under sources/ and promote only reviewed candidates into approved local memory.'
49
+ why: 'メール、カレンダー、ドライブ、ファイル、タスクは任意の追加参照元であり、取込前に明示的な許可範囲が必要です。',
50
+ safety: '取込素材はsources/に置き、レビュー済み候補だけを承認済みローカル記憶へ昇格します。'
51
51
  },
52
52
  {
53
53
  id: 'verification',
54
- title: 'Verify doctor and MCP get_context / search',
54
+ title: 'doctorとMCP get_context / searchで確認する',
55
55
  status: 'pending',
56
56
  command: `brainbase doctor --dir ${commandArg(dataDir)}`,
57
- why: 'Onboarding is operational only when doctor and the MCP tools show the approved context from a fresh agent session.',
58
- safety: 'Check get_context/search after config merge instead of assuming command generation was enough.'
57
+ why: '新しいエージェントセッションでdoctorとMCPツールが承認済み文脈を示して初めて運用可能です。',
58
+ safety: 'コマンド生成だけで完了扱いせず、設定反映後にget_context/searchを確認します。'
59
59
  }
60
60
  ],
61
61
  recommendedOrder: [
62
- 'Install or write public skills for the target agent.',
63
- 'Generate ohayo / oyasumi / retro routines and register them paused or confirmation-gated.',
64
- 'Merge the Brainbase MCP snippet into the real Codex / Claude / CodeCode config and restart the agent.',
65
- 'Decide source allowlists and run import / candidate review only where more context is needed.',
66
- 'Run doctor, then verify MCP get_context and search from a fresh agent session.'
62
+ '対象エージェントへ公開スキルを配置する。',
63
+ 'ohayo / oyasumi / retroを生成し、一時停止または確認付きで登録する。',
64
+ 'Brainbase MCP設定を実際のCodex / Claude / CodeCode設定へ反映し、エージェントを再起動する。',
65
+ '追加文脈が必要な場合だけ参照許可範囲を決め、取込と候補レビューを行う。',
66
+ 'doctorを実行し、新しいエージェントセッションでMCP get_contextとsearchを確認する。'
67
67
  ],
68
68
  safetyRules: [
69
- 'Do not write live config, scheduler entries, or canonical facts without user approval.',
70
- 'Do not treat generated skills, generated routines, or MCP dry-run snippets as completed installation.',
71
- 'Do not ask users to paste OAuth tokens, passwords, API keys, or refresh tokens into chat.',
72
- 'Source imports stay local-first and reviewed before canonical promotion.'
69
+ '利用者の承認なしに実設定、スケジュール、正本ファクトを書き込みません。',
70
+ '生成したスキル、ルーティン、MCPプレビューをインストール完了扱いしません。',
71
+ 'OAuthトークン、パスワード、APIキー、更新トークンをチャットへ貼るよう求めません。',
72
+ '参照元の取込はローカル優先とし、正本化前にレビューします。'
73
73
  ],
74
74
  completionCheck: [
75
- 'The user has seen the first value output.',
76
- 'The completion report names all still-pending operationalization actions.',
77
- 'The target agent can call Brainbase MCP get_context/search after real config merge.',
78
- 'Source allowlists and candidate review are either completed or explicitly deferred.'
75
+ '利用者が初回価値の出力を確認済み。',
76
+ '完了報告に残っている運用設定をすべて記載済み。',
77
+ '実設定反映後、対象エージェントからBrainbase MCP get_context/searchを呼び出せる。',
78
+ '参照許可範囲と候補レビューを完了、または明示的に延期済み。'
79
79
  ]
80
80
  };
81
81
  }
package/dist/server.d.ts CHANGED
@@ -26,7 +26,7 @@ export declare const toolDefinitions: readonly [{
26
26
  };
27
27
  }, {
28
28
  readonly name: "search";
29
- readonly description: "Search canonical local Graph, Personal KG, relationships, and decisions.";
29
+ readonly description: "Search all canonical local stores: Graph entities, Personal KG, relationships, and decisions. Use this for people and projects.";
30
30
  readonly inputSchema: {
31
31
  readonly type: "object";
32
32
  readonly required: readonly ["query"];
@@ -44,7 +44,7 @@ export declare const toolDefinitions: readonly [{
44
44
  };
45
45
  }, {
46
46
  readonly name: "search_personal_kg";
47
- readonly description: "Search owner-local Personal KG only.";
47
+ readonly description: "Search owner-local Personal KG only. People and projects are Graph entities, so use search for them.";
48
48
  readonly inputSchema: {
49
49
  readonly type: "object";
50
50
  readonly required: readonly ["query"];
@@ -71,9 +71,301 @@ export declare const toolDefinitions: readonly [{
71
71
  };
72
72
  };
73
73
  };
74
+ }, {
75
+ readonly name: "brainbase_onboarding_start";
76
+ readonly description: "Start a local first-value onboarding run from actually callable sources. The result exposes runId (also id); pass runId to every later onboarding tool.";
77
+ readonly inputSchema: {
78
+ readonly type: "object";
79
+ readonly required: readonly ["valueTarget", "sources"];
80
+ readonly additionalProperties: false;
81
+ readonly properties: {
82
+ readonly dataDir: {
83
+ readonly type: "string";
84
+ readonly description: "Optional Personal OS directory.";
85
+ };
86
+ readonly valueTarget: {
87
+ readonly type: "string";
88
+ readonly description: "One concrete question the first useful answer should resolve.";
89
+ };
90
+ readonly sources: {
91
+ readonly type: "array";
92
+ readonly maxItems: 50;
93
+ readonly items: {
94
+ readonly type: "object";
95
+ readonly required: readonly ["id", "mode", "status"];
96
+ readonly additionalProperties: false;
97
+ readonly properties: {
98
+ readonly id: {
99
+ readonly type: "string";
100
+ };
101
+ readonly mode: {
102
+ readonly enum: readonly ["mcp", "drive", "gmail", "local_folder", "single_document"];
103
+ };
104
+ readonly status: {
105
+ readonly enum: readonly ["ready", "waiting_for_authorization", "unavailable", "error", "unconfirmed"];
106
+ };
107
+ readonly evidencePointer: {
108
+ readonly type: "string";
109
+ };
110
+ readonly permissionScope: {
111
+ readonly type: "array";
112
+ readonly items: {
113
+ readonly type: "string";
114
+ };
115
+ };
116
+ readonly detail: {
117
+ readonly type: "string";
118
+ };
119
+ };
120
+ };
121
+ };
122
+ };
123
+ };
124
+ }, {
125
+ readonly name: "brainbase_onboarding_get";
126
+ readonly description: "Read a connected-world onboarding run without exposing source or answer bodies.";
127
+ readonly inputSchema: {
128
+ readonly type: "object";
129
+ readonly required: readonly ["runId"];
130
+ readonly additionalProperties: false;
131
+ readonly properties: {
132
+ readonly dataDir: {
133
+ readonly type: "string";
134
+ };
135
+ readonly runId: {
136
+ readonly type: "string";
137
+ };
138
+ };
139
+ };
140
+ }, {
141
+ readonly name: "brainbase_onboarding_ingest";
142
+ readonly description: "Ingest one selected source receipt under source plus review candidates. Do not flatten sourceId or receipt fields at the top level.";
143
+ readonly inputSchema: {
144
+ readonly type: "object";
145
+ readonly required: readonly ["runId", "source", "candidates"];
146
+ readonly additionalProperties: false;
147
+ readonly properties: {
148
+ readonly dataDir: {
149
+ readonly type: "string";
150
+ };
151
+ readonly runId: {
152
+ readonly type: "string";
153
+ readonly description: "runId returned by brainbase_onboarding_start.";
154
+ };
155
+ readonly source: {
156
+ readonly type: "object";
157
+ readonly required: readonly ["sourceId", "evidencePointer", "contentHash", "permissionSnapshot", "collectionStatus"];
158
+ readonly additionalProperties: false;
159
+ readonly properties: {
160
+ readonly sourceId: {
161
+ readonly type: "string";
162
+ };
163
+ readonly evidencePointer: {
164
+ readonly type: "string";
165
+ };
166
+ readonly contentHash: {
167
+ readonly type: "string";
168
+ };
169
+ readonly permissionSnapshot: {
170
+ readonly type: "object";
171
+ };
172
+ readonly collectionStatus: {
173
+ readonly const: "collected";
174
+ };
175
+ };
176
+ };
177
+ readonly candidates: {
178
+ readonly type: "array";
179
+ readonly maxItems: 50;
180
+ readonly items: {
181
+ readonly type: "object";
182
+ readonly required: readonly ["kind", "payload", "observationClass", "evidenceId"];
183
+ readonly additionalProperties: false;
184
+ readonly properties: {
185
+ readonly kind: {
186
+ readonly type: "string";
187
+ };
188
+ readonly payload: {
189
+ readonly type: "object";
190
+ };
191
+ readonly observationClass: {
192
+ readonly enum: readonly ["observed", "inferred"];
193
+ };
194
+ readonly evidenceId: {
195
+ readonly type: "string";
196
+ };
197
+ };
198
+ };
199
+ };
200
+ };
201
+ };
202
+ }, {
203
+ readonly name: "brainbase_onboarding_review";
204
+ readonly description: "Submit review decisions in actions. Inferred candidates cannot be approved or merged; use edit with a human-confirmed payload, or reject.";
205
+ readonly inputSchema: {
206
+ readonly type: "object";
207
+ readonly required: readonly ["runId", "actions"];
208
+ readonly additionalProperties: false;
209
+ readonly properties: {
210
+ readonly dataDir: {
211
+ readonly type: "string";
212
+ };
213
+ readonly runId: {
214
+ readonly type: "string";
215
+ readonly minLength: 1;
216
+ readonly maxLength: 200;
217
+ };
218
+ readonly actions: {
219
+ readonly type: "array";
220
+ readonly minItems: 1;
221
+ readonly maxItems: 50;
222
+ readonly items: {
223
+ readonly oneOf: readonly [{
224
+ readonly type: "object";
225
+ readonly required: readonly ["candidateId", "decision", "reason"];
226
+ readonly additionalProperties: false;
227
+ readonly properties: {
228
+ readonly candidateId: {
229
+ readonly type: "string";
230
+ readonly minLength: 1;
231
+ readonly maxLength: 200;
232
+ };
233
+ readonly decision: {
234
+ readonly const: "approve";
235
+ };
236
+ readonly reason: {
237
+ readonly type: "string";
238
+ readonly minLength: 1;
239
+ readonly maxLength: 500;
240
+ };
241
+ };
242
+ }, {
243
+ readonly type: "object";
244
+ readonly required: readonly ["candidateId", "decision", "reason", "payload"];
245
+ readonly additionalProperties: false;
246
+ readonly properties: {
247
+ readonly candidateId: {
248
+ readonly type: "string";
249
+ readonly minLength: 1;
250
+ readonly maxLength: 200;
251
+ };
252
+ readonly decision: {
253
+ readonly const: "edit";
254
+ };
255
+ readonly reason: {
256
+ readonly type: "string";
257
+ readonly minLength: 1;
258
+ readonly maxLength: 500;
259
+ };
260
+ readonly payload: {
261
+ readonly type: "object";
262
+ };
263
+ };
264
+ }, {
265
+ readonly type: "object";
266
+ readonly required: readonly ["candidateId", "decision", "reason"];
267
+ readonly additionalProperties: false;
268
+ readonly properties: {
269
+ readonly candidateId: {
270
+ readonly type: "string";
271
+ readonly minLength: 1;
272
+ readonly maxLength: 200;
273
+ };
274
+ readonly decision: {
275
+ readonly const: "reject";
276
+ };
277
+ readonly reason: {
278
+ readonly type: "string";
279
+ readonly minLength: 1;
280
+ readonly maxLength: 500;
281
+ };
282
+ };
283
+ }, {
284
+ readonly type: "object";
285
+ readonly required: readonly ["candidateId", "decision", "reason", "mergeIntoCandidateId"];
286
+ readonly additionalProperties: false;
287
+ readonly properties: {
288
+ readonly candidateId: {
289
+ readonly type: "string";
290
+ readonly minLength: 1;
291
+ readonly maxLength: 200;
292
+ };
293
+ readonly decision: {
294
+ readonly const: "merge";
295
+ };
296
+ readonly reason: {
297
+ readonly type: "string";
298
+ readonly minLength: 1;
299
+ readonly maxLength: 500;
300
+ };
301
+ readonly mergeIntoCandidateId: {
302
+ readonly type: "string";
303
+ readonly minLength: 1;
304
+ readonly maxLength: 200;
305
+ };
306
+ };
307
+ }];
308
+ };
309
+ };
310
+ };
311
+ };
312
+ }, {
313
+ readonly name: "brainbase_onboarding_first_value";
314
+ readonly description: "Finish onboarding in two calls. First choose action=record with an answer hash and promoted canonical IDs. Then choose action=review with useful or not_useful.";
315
+ readonly inputSchema: {
316
+ readonly type: "object";
317
+ readonly required: readonly ["runId", "action"];
318
+ readonly additionalProperties: false;
319
+ readonly properties: {
320
+ readonly dataDir: {
321
+ readonly type: "string";
322
+ readonly description: "Optional Personal OS directory.";
323
+ };
324
+ readonly runId: {
325
+ readonly type: "string";
326
+ readonly minLength: 1;
327
+ readonly maxLength: 200;
328
+ readonly description: "runId returned by the previous onboarding step.";
329
+ };
330
+ readonly action: {
331
+ readonly enum: readonly ["record", "review"];
332
+ readonly description: "Use record first. Use review only after the answer receipt has been recorded.";
333
+ };
334
+ readonly answerHash: {
335
+ readonly type: "string";
336
+ readonly pattern: "^sha256:[a-f0-9]{64}$";
337
+ readonly description: "Required for action=record. SHA-256 of the answer body; the body itself is not stored.";
338
+ };
339
+ readonly usedCanonicalIds: {
340
+ readonly type: "array";
341
+ readonly minItems: 1;
342
+ readonly maxItems: 50;
343
+ readonly items: {
344
+ readonly type: "string";
345
+ readonly minLength: 1;
346
+ readonly maxLength: 200;
347
+ };
348
+ readonly description: "Required for action=record. Use only promotedCanonicalIds returned by review.";
349
+ };
350
+ readonly verdict: {
351
+ readonly enum: readonly ["useful", "not_useful"];
352
+ readonly description: "Required for action=review.";
353
+ };
354
+ readonly missingContext: {
355
+ readonly type: "array";
356
+ readonly maxItems: 50;
357
+ readonly items: {
358
+ readonly type: "string";
359
+ readonly minLength: 1;
360
+ readonly maxLength: 200;
361
+ };
362
+ readonly description: "Optional short labels for context the answer still lacked.";
363
+ };
364
+ };
365
+ };
74
366
  }, {
75
367
  readonly name: "get_ontology";
76
- readonly description: "Return the bundled immutable Brainbase Portable Ontology Kernel release.";
368
+ readonly description: "Return a beginner guide followed by the bundled immutable Brainbase Portable Ontology Kernel release.";
77
369
  readonly inputSchema: {
78
370
  readonly type: "object";
79
371
  readonly properties: {};