secondbrainos-mcp-server 1.2.3 → 1.2.5

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.
Files changed (3) hide show
  1. package/README.md +30 -10
  2. package/bin/cli.js +137 -29
  3. package/package.json +1 -1
package/README.md CHANGED
@@ -1,11 +1,11 @@
1
1
  # Second Brain OS MCP Server
2
2
 
3
- This package provides a Model Context Protocol (MCP) server for integrating Second Brain OS with Claude Desktop.
3
+ This package provides a Model Context Protocol (MCP) server for integrating Second Brain OS with Claude Desktop and Claude Code.
4
4
 
5
5
  ## Prerequisites
6
6
 
7
7
  - Node.js v16 or higher
8
- - Claude Desktop application
8
+ - Claude Desktop application and/or Claude Code CLI
9
9
  - A valid Second Brain OS account with the Claude MCP feature enabled
10
10
 
11
11
  ## Installation
@@ -28,6 +28,16 @@ This will:
28
28
  3. Create the necessary configuration files for Claude Desktop
29
29
  4. Configure the server to dynamically fetch your available API endpoints
30
30
 
31
+ ### Claude Code
32
+
33
+ To add the server to Claude Code:
34
+
35
+ ```bash
36
+ claude mcp add secondbrainos-mcp-server -- npx secondbrainos-mcp-server
37
+ ```
38
+
39
+ Or add it to your project's `.mcp.json` file.
40
+
31
41
  ## Features
32
42
 
33
43
  ### Enhanced OpenAPI Support
@@ -41,13 +51,23 @@ The server uses `@samchon/openapi` library for robust OpenAPI handling, providin
41
51
  - Automatic request formatting based on OpenAPI specifications
42
52
  - Support for complex parameters and nested objects
43
53
 
44
- ### Prompts (Workflows)
45
- The server exposes your Second Brain OS workflows as MCP prompts, making them available in Claude Desktop's attach menu:
54
+ ### Prompts
55
+ The server exposes three types of MCP prompts, available in the client's attach menu:
56
+
57
+ #### Skills (Workflows)
46
58
  - Automatically discovers your workflows via the `runPromptChain` service
47
- - Each workflow appears as a selectable prompt with its name and description
48
- - Selecting a prompt fetches the full prompt chain (ordered instructions) and injects them into the conversation
59
+ - Each skill appears with a `[Skill]` prefix and returns a structured document with `skill_id`, `name`, `description`, and an ordered list of prompts (metadata only, no instructions)
49
60
  - Supports an optional `user_input` argument to provide additional context
50
61
 
62
+ #### Agents
63
+ - Discovers your AI agents via the `getAIAgentsSchema` service
64
+ - Each agent appears with an `[Agent]` prefix and returns a structured document containing `agent_id`, `name`, `description`, `behaviour_and_instructions`, `searchMyKnowledge_collection_id`, `actions` (with id, name, description, body_parameters), and `workflows` (with enriched prompt metadata)
65
+ - Supports an optional `user_input` argument
66
+
67
+ #### Knowledge Bases
68
+ - Aggregates all `searchMyKnowledge_collection_id` values from your agents
69
+ - Appears as a single `[Knowledge Bases]` prompt returning an array of collection IDs
70
+
51
71
  ### Better Error Handling
52
72
  - Detailed error messages for debugging
53
73
  - Proper handling of authentication failures, bad requests, and service errors
@@ -124,14 +144,14 @@ The server requires the following environment variables:
124
144
  1. **Schema Fetching**: On startup, the server fetches your personalized OpenAPI schema from Second Brain OS
125
145
  2. **Schema Conversion**: The `@samchon/openapi` library converts the schema to an optimized format for LLM function calling
126
146
  3. **MCP Tools**: Each API endpoint becomes an MCP tool that Claude can use
127
- 4. **MCP Prompts**: If the `runPromptChain` service is available, your workflows are exposed as selectable prompts in the client UI
147
+ 4. **MCP Prompts**: Your skills (workflows), AI agents, and knowledge bases are exposed as selectable prompts in the client UI
128
148
  5. **Function Execution**: When Claude calls a tool, the server executes the corresponding API call with proper authentication
129
149
 
130
150
  ## Troubleshooting
131
151
 
132
- ### Claude Desktop doesn't see the server
133
- 1. Ensure Claude Desktop is completely quit before running the setup
134
- 2. Check the configuration file was created at the correct location
152
+ ### Client doesn't see the server
153
+ 1. **Claude Desktop**: Ensure it's completely quit before running setup. Check the configuration file was created at the correct location.
154
+ 2. **Claude Code**: Run `claude mcp add` or check your `.mcp.json` configuration.
135
155
  3. Review the logs at the platform-specific location mentioned during setup
136
156
 
137
157
  ### Authentication errors
package/bin/cli.js CHANGED
@@ -129,13 +129,103 @@ async function readExistingConfig(configPath) {
129
129
  }
130
130
  }
131
131
 
132
+ /**
133
+ * Get the credentials file path
134
+ */
135
+ function getCredentialsPath() {
136
+ return path.join(homedir(), '.secondbrainos', 'credentials.json');
137
+ }
138
+
139
+ /**
140
+ * Store credentials to ~/.secondbrainos/credentials.json
141
+ */
142
+ async function storeCredentials(USER_ID, USER_SECRET) {
143
+ const credDir = path.join(homedir(), '.secondbrainos');
144
+ await fs.mkdir(credDir, { recursive: true });
145
+ await fs.writeFile(
146
+ getCredentialsPath(),
147
+ JSON.stringify({ USER_ID, USER_SECRET, API_BASE_URL: 'https://api.secondbrainos.com' }, null, 2),
148
+ { mode: 0o600 }
149
+ );
150
+ }
151
+
152
+ /**
153
+ * Configure Claude Code via `claude mcp add`
154
+ */
155
+ async function configureClaudeCode(serverPath, nodePath) {
156
+ try {
157
+ const { stdout } = await execAsync('which claude').catch(() => ({ stdout: '' }));
158
+ if (!stdout.trim()) {
159
+ console.log('\nClaude Code CLI not found — skipping Claude Code configuration.');
160
+ console.log('To set up Claude Code later, install it and run this setup again.');
161
+ return false;
162
+ }
163
+
164
+ // Remove existing config first (ignore errors if it doesn't exist)
165
+ await execAsync('claude mcp remove secondbrainos -s user').catch(() => {});
166
+
167
+ // Add the server with serve subcommand
168
+ await execAsync(`claude mcp add secondbrainos -s user -- ${nodePath} ${serverPath} serve`);
169
+ console.log('Claude Code configured successfully!');
170
+ return true;
171
+ } catch (error) {
172
+ console.log(`\nClaude Code auto-configuration failed: ${error.message}`);
173
+ console.log('You can manually configure it by running:');
174
+ console.log(` claude mcp add secondbrainos -s user -- ${nodePath} ${serverPath} serve`);
175
+ return false;
176
+ }
177
+ }
178
+
179
+ /**
180
+ * Run the MCP server (serve mode)
181
+ */
182
+ async function serve() {
183
+ // Load credentials from stored file, with env var override
184
+ let USER_ID = process.env.USER_ID;
185
+ let USER_SECRET = process.env.USER_SECRET;
186
+ let API_BASE_URL = process.env.API_BASE_URL;
187
+
188
+ if (!USER_ID || !USER_SECRET) {
189
+ try {
190
+ const creds = JSON.parse(await fs.readFile(getCredentialsPath(), 'utf8'));
191
+ USER_ID = USER_ID || creds.USER_ID;
192
+ USER_SECRET = USER_SECRET || creds.USER_SECRET;
193
+ API_BASE_URL = API_BASE_URL || creds.API_BASE_URL;
194
+ } catch {
195
+ console.error('Error: No credentials found. Run setup first:');
196
+ console.error(' npx secondbrainos-mcp-server USER_ID USER_SECRET');
197
+ process.exit(1);
198
+ }
199
+ }
200
+
201
+ if (!USER_ID || !USER_SECRET) {
202
+ console.error('Error: Missing USER_ID or USER_SECRET.');
203
+ process.exit(1);
204
+ }
205
+
206
+ // Set env vars for the server process
207
+ process.env.USER_ID = USER_ID;
208
+ process.env.USER_SECRET = USER_SECRET;
209
+ process.env.API_BASE_URL = API_BASE_URL || 'https://api.secondbrainos.com';
210
+
211
+ // Import and run the server
212
+ const packageRoot = path.resolve(__dirname, '..');
213
+ const serverModule = path.join(packageRoot, 'build', 'index.js');
214
+ await import(serverModule);
215
+ }
216
+
132
217
  async function main() {
133
218
  try {
134
219
  // Get command line arguments
135
220
  const args = process.argv.slice(2);
136
-
221
+
222
+ // Handle serve subcommand
223
+ if (args.length === 1 && args[0] === 'serve') {
224
+ return await serve();
225
+ }
226
+
137
227
  let USER_ID, USER_SECRET;
138
-
228
+
139
229
  if (args.length === 1 && args[0].includes(':')) {
140
230
  // Handle the combined format USER_ID:USER_SECRET
141
231
  [USER_ID, USER_SECRET] = args[0].split(':');
@@ -145,70 +235,79 @@ async function main() {
145
235
  } else {
146
236
  console.error('Usage: secondbrainos-mcp USER_ID:USER_SECRET');
147
237
  console.error(' or: secondbrainos-mcp USER_ID USER_SECRET');
238
+ console.error(' or: secondbrainos-mcp serve');
148
239
  process.exit(1);
149
240
  }
150
-
241
+
151
242
  // Validate that we have both values
152
243
  if (!USER_ID || !USER_SECRET) {
153
244
  console.error('Error: Both USER_ID and USER_SECRET are required');
154
245
  process.exit(1);
155
246
  }
156
-
247
+
157
248
  console.log('Verifying user credentials...');
158
-
249
+
159
250
  // Verify user with the cloud function
160
251
  try {
161
252
  const verificationUrl = 'https://us-central1-second-brain-os.cloudfunctions.net/gcf-sbos-verifyuserdatapublic';
162
253
  const response = await axios.post(verificationUrl, {
163
254
  "x-user-api-key": `Bearer ${USER_ID}:${USER_SECRET}`
164
255
  });
165
-
256
+
166
257
  const { exists, email, features } = response.data;
167
-
258
+
168
259
  if (!exists || exists !== 1) {
169
260
  console.error('Error: User does not exist.');
170
261
  process.exit(1);
171
262
  }
172
-
263
+
173
264
  if (!email) {
174
265
  console.error('Error: User email not found.');
175
266
  process.exit(1);
176
267
  }
177
-
268
+
178
269
  // Check if claudemcp feature is enabled
179
270
  if (!features || typeof features !== 'string') {
180
271
  console.error('Error: User features not found.');
181
272
  process.exit(1);
182
273
  }
183
-
274
+
184
275
  const featuresList = features.toLowerCase().split(',').map(f => f.trim().replace(/\s+/g, ''));
185
276
  if (!featuresList.includes('claudemcp')) {
186
277
  console.error('Error: Claude MCP feature not enabled for this user.');
187
278
  process.exit(1);
188
279
  }
189
-
280
+
190
281
  console.log('User verified successfully!');
191
-
282
+
192
283
  } catch (error) {
193
284
  console.error('Error verifying user:', error.message);
194
285
  process.exit(1);
195
286
  }
196
-
197
- // Create Claude Desktop configuration directory if it doesn't exist
287
+
288
+ // Store credentials locally
289
+ try {
290
+ await storeCredentials(USER_ID, USER_SECRET);
291
+ console.log(`Credentials stored at: ${getCredentialsPath()}`);
292
+ } catch (error) {
293
+ console.error('Warning: Could not store credentials:', error.message);
294
+ }
295
+
296
+ // Configure Claude Desktop
198
297
  const claudeConfigDir = getClaudeConfigPath();
199
298
  const claudeConfigFile = path.join(claudeConfigDir, 'claude_desktop_config.json');
200
-
299
+
201
300
  try {
202
301
  await fs.mkdir(claudeConfigDir, { recursive: true });
203
302
  } catch (error) {
204
303
  console.error('Error creating config directory:', error);
205
304
  process.exit(1);
206
305
  }
207
-
306
+
208
307
  // Get the absolute path to the installed package's index.js file
209
308
  const packageRoot = path.resolve(__dirname, '..');
210
309
  const serverPath = path.join(packageRoot, 'build', 'index.js');
211
-
310
+
212
311
  // Check if serverPath exists
213
312
  try {
214
313
  await fs.access(serverPath);
@@ -217,21 +316,21 @@ async function main() {
217
316
  console.error('This might be due to an incomplete installation. Try reinstalling the package with: npm install -g secondbrainos-mcp-server');
218
317
  process.exit(1);
219
318
  }
220
-
319
+
221
320
  // Find Node.js executable
222
321
  const nodePath = await findNodeExecutable();
223
-
322
+
224
323
  // Read existing configuration
225
324
  const existingConfig = await readExistingConfig(claudeConfigFile);
226
-
325
+
227
326
  // Ensure mcpServers object exists
228
327
  if (!existingConfig.mcpServers) {
229
328
  existingConfig.mcpServers = {};
230
329
  }
231
-
330
+
232
331
  // Check if secondbrainos already exists
233
332
  const hadExistingSecondBrainOS = !!existingConfig.mcpServers.secondbrainos;
234
-
333
+
235
334
  // Add or update the secondbrainos server configuration
236
335
  existingConfig.mcpServers.secondbrainos = {
237
336
  command: nodePath,
@@ -243,30 +342,39 @@ async function main() {
243
342
  NODE_PATH: getNodeModulesPath()
244
343
  }
245
344
  };
246
-
345
+
247
346
  try {
248
347
  // Write the updated configuration back
249
348
  await fs.writeFile(claudeConfigFile, JSON.stringify(existingConfig, null, 2));
250
- console.log(`Configuration file ${hadExistingSecondBrainOS ? 'updated' : 'created'} at: ${claudeConfigFile}`);
251
-
349
+ console.log(`Claude Desktop configuration ${hadExistingSecondBrainOS ? 'updated' : 'created'} at: ${claudeConfigFile}`);
350
+
252
351
  // Show summary of configured servers
253
352
  const serverCount = Object.keys(existingConfig.mcpServers).length;
254
353
  console.log(`\nTotal MCP servers configured: ${serverCount}`);
255
354
  console.log('Configured servers:', Object.keys(existingConfig.mcpServers).join(', '));
256
-
355
+
257
356
  } catch (error) {
258
357
  console.error('Error writing configuration file:', error);
259
358
  process.exit(1);
260
359
  }
261
-
360
+
361
+ // Configure Claude Code
362
+ const cliPath = path.join(packageRoot, 'bin', 'cli.js');
363
+ const claudeCodeConfigured = await configureClaudeCode(cliPath, nodePath);
364
+
262
365
  console.log('\nInstallation successful!');
263
- console.log('\nPlease follow these steps to complete setup:');
366
+ console.log('\nClaude Desktop:');
264
367
  console.log('1. Completely quit Claude Desktop if it is running');
265
368
  console.log('2. Restart Claude Desktop');
266
369
  console.log('3. In the Chat Input inside Claude (i.e where you type your messages), you will now see a "🔨" icon which contains all the tools you have access to');
370
+ if (claudeCodeConfigured) {
371
+ console.log('\nClaude Code:');
372
+ console.log('1. Restart Claude Code if it is running');
373
+ console.log('2. Your Second Brain OS tools will be available automatically');
374
+ }
267
375
  console.log('\nIf you encounter issues, check the logs:');
268
376
  console.log(`${getLogPath()}`);
269
-
377
+
270
378
  } catch (error) {
271
379
  console.error('Unexpected error:', error);
272
380
  process.exit(1);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "secondbrainos-mcp-server",
3
- "version": "1.2.3",
3
+ "version": "1.2.5",
4
4
  "description": "Second Brain OS MCP Server for Claude Desktop",
5
5
  "type": "module",
6
6
  "main": "build/index.js",