fix: load ejclaw mcp tools on claude first turn

This commit is contained in:
ejclaw
2026-05-23 09:23:48 +09:00
parent 5d15af398c
commit aa481ff027
5 changed files with 97 additions and 18 deletions

View File

@@ -60,6 +60,7 @@ import {
createSanitizeBashHook, createSanitizeBashHook,
} from './runner-hooks.js'; } from './runner-hooks.js';
import { buildClaudeSdkEnv } from './sdk-env.js'; import { buildClaudeSdkEnv } from './sdk-env.js';
import { buildEjclawMcpServerConfig } from './mcp-config.js';
interface RunnerInput { interface RunnerInput {
prompt: string; prompt: string;
@@ -299,23 +300,15 @@ async function runQuery(
settingSources: ['project', 'user'], settingSources: ['project', 'user'],
abortController: agentAbortController, abortController: agentAbortController,
mcpServers: { mcpServers: {
ejclaw: { ejclaw: buildEjclawMcpServerConfig(mcpServerPath, {
command: 'node', chatJid: runnerInput.chatJid,
args: [mcpServerPath], groupFolder: runnerInput.groupFolder,
env: { isMain: runnerInput.isMain,
EJCLAW_CHAT_JID: runnerInput.chatJid, agentType: process.env.EJCLAW_AGENT_TYPE || 'claude-code',
EJCLAW_GROUP_FOLDER: runnerInput.groupFolder, roomRole: runnerInput.roomRoleContext?.role || '',
EJCLAW_IS_MAIN: runnerInput.isMain ? '1' : '0', ipcDir: process.env.EJCLAW_IPC_DIR,
EJCLAW_AGENT_TYPE: process.env.EJCLAW_AGENT_TYPE || 'claude-code', hostIpcDir: process.env.EJCLAW_HOST_IPC_DIR,
EJCLAW_ROOM_ROLE: runnerInput.roomRoleContext?.role || '',
...(process.env.EJCLAW_IPC_DIR && {
EJCLAW_IPC_DIR: process.env.EJCLAW_IPC_DIR,
}), }),
...(process.env.EJCLAW_HOST_IPC_DIR && {
EJCLAW_HOST_IPC_DIR: process.env.EJCLAW_HOST_IPC_DIR,
}),
},
},
}, },
hooks: { hooks: {
PreCompact: [ PreCompact: [

View File

@@ -0,0 +1,35 @@
import type { McpStdioServerConfig } from '@anthropic-ai/claude-agent-sdk';
export interface EjclawMcpServerConfigInput {
chatJid: string;
groupFolder: string;
isMain: boolean;
agentType: string;
roomRole: string;
ipcDir?: string;
hostIpcDir?: string;
}
export function buildEjclawMcpServerConfig(
mcpServerPath: string,
input: EjclawMcpServerConfigInput,
): McpStdioServerConfig {
return {
command: 'node',
args: [mcpServerPath],
alwaysLoad: true,
env: {
EJCLAW_CHAT_JID: input.chatJid,
EJCLAW_GROUP_FOLDER: input.groupFolder,
EJCLAW_IS_MAIN: input.isMain ? '1' : '0',
EJCLAW_AGENT_TYPE: input.agentType,
EJCLAW_ROOM_ROLE: input.roomRole,
...(input.ipcDir && {
EJCLAW_IPC_DIR: input.ipcDir,
}),
...(input.hostIpcDir && {
EJCLAW_HOST_IPC_DIR: input.hostIpcDir,
}),
},
};
}

View File

@@ -0,0 +1,32 @@
import { describe, expect, it } from 'vitest';
import { buildEjclawMcpServerConfig } from '../src/mcp-config.js';
describe('ejclaw MCP config', () => {
it('always loads EJClaw MCP tools on turn one and preserves runtime env', () => {
expect(
buildEjclawMcpServerConfig('/runner/dist/ipc-mcp-stdio.js', {
chatJid: 'dc:room',
groupFolder: 'ejclaw',
isMain: true,
agentType: 'claude-code',
roomRole: 'reviewer',
ipcDir: '/tmp/ipc/task',
hostIpcDir: '/tmp/ipc/host',
}),
).toEqual({
command: 'node',
args: ['/runner/dist/ipc-mcp-stdio.js'],
alwaysLoad: true,
env: {
EJCLAW_CHAT_JID: 'dc:room',
EJCLAW_GROUP_FOLDER: 'ejclaw',
EJCLAW_IS_MAIN: '1',
EJCLAW_AGENT_TYPE: 'claude-code',
EJCLAW_ROOM_ROLE: 'reviewer',
EJCLAW_IPC_DIR: '/tmp/ipc/task',
EJCLAW_HOST_IPC_DIR: '/tmp/ipc/host',
},
});
});
});

View File

@@ -8,7 +8,7 @@
"exports": { "exports": {
".": { ".": {
"types": "./src/index.ts", "types": "./src/index.ts",
"default": "./src/index.ts" "default": "./dist/index.js"
} }
}, },
"scripts": { "scripts": {

View File

@@ -0,0 +1,19 @@
import fs from 'fs';
import path from 'path';
import { describe, expect, it } from 'vitest';
describe('runner shared package exports', () => {
it('points runtime imports at built JavaScript for node-launched MCP servers', () => {
const packageJson = JSON.parse(
fs.readFileSync(
path.resolve(import.meta.dirname, '../package.json'),
'utf8',
),
) as { exports: { '.': { default: string; types: string } } };
expect(packageJson.exports['.']).toEqual({
types: './src/index.ts',
default: './dist/index.js',
});
});
});