UNPKG

hdc-mcp

Version:

MCP server for HDC (OpenHarmony Device Connector) tools

642 lines (611 loc) 24.4 kB
#!/usr/bin/env node import { Server } from '@modelcontextprotocol/sdk/server/index.js'; import { StdioServerTransport } from '@modelcontextprotocol/sdk/server/stdio.js'; import { CallToolRequestSchema, ListToolsRequestSchema, } from '@modelcontextprotocol/sdk/types.js'; import { HdcWrapper } from './utils/hdc-wrapper.js'; const server = new Server({ name: 'hdc-mcp', version: '1.0.0', }, { capabilities: { tools: {}, resources: {}, }, }); const hdc = new HdcWrapper(); server.setRequestHandler(ListToolsRequestSchema, async (request) => { console.error('🔍 收到请求:', JSON.stringify(request.params, null, 2)); return { tools: [ { name: 'hdc_get_version', description: '获取 HDC 工具版本信息,命令: hdc -v', inputSchema: { type: 'object', properties: {}, }, }, { name: 'hdc_list_devices', description: '列出所有连接的鸿蒙设备,命令: hdc list targets', inputSchema: { type: 'object', properties: {}, }, }, { name: 'hdc_get_device_info', description: '获取指定设备的详细信息,命令: hdc [-t <deviceId>] shell param get <参数>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, }, required: ['deviceId'], }, }, { name: 'hdc_install_app', description: '在设备上安装应用,命令: hdc [-t <deviceId>] install <appPath>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, appPath: { type: 'string', description: '应用文件路径 (.hap 文件)', }, }, required: ['deviceId', 'appPath'], }, }, { name: 'hdc_uninstall_app', description: '从设备上卸载应用,命令: hdc [-t <deviceId>] uninstall <bundleName>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, bundleName: { type: 'string', description: '应用包名', }, }, required: ['deviceId', 'bundleName'], }, }, { name: 'hdc_list_apps', description: '列出设备上已安装的应用,命令: hdc [-t <deviceId>] shell bm dump -a', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, }, required: ['deviceId'], }, }, { name: 'hdc_start_app', description: '启动指定应用,命令: hdc [-t <deviceId>] shell aa start -b <bundleName> -a <abilityName>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, bundleName: { type: 'string', description: '应用包名', }, abilityName: { type: 'string', description: 'Ability 名称 (可选, 默认为 MainAbility)', }, }, required: ['deviceId', 'bundleName'], }, }, { name: 'hdc_stop_app', description: '停止指定应用,命令: hdc [-t <deviceId>] shell aa force-stop <bundleName>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, bundleName: { type: 'string', description: '应用包名', }, }, required: ['deviceId', 'bundleName'], }, }, { name: 'hdc_clear_app_data', description: '清除应用数据,命令: hdc [-t <deviceId>] shell bm clean -n <bundleName> -c data', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, bundleName: { type: 'string', description: '应用包名', }, }, required: ['deviceId', 'bundleName'], }, }, { name: 'hdc_push_file', description: '将文件推送到设备,命令: hdc [-t <deviceId>] file send <localPath> <remotePath>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, localPath: { type: 'string', description: '本地文件路径', }, remotePath: { type: 'string', description: '设备上的目标路径', }, }, required: ['deviceId', 'localPath', 'remotePath'], }, }, { name: 'hdc_pull_file', description: '从设备拉取文件,命令: hdc [-t <deviceId>] file recv <remotePath> <localPath>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, remotePath: { type: 'string', description: '设备上的文件路径', }, localPath: { type: 'string', description: '本地保存路径', }, }, required: ['deviceId', 'remotePath', 'localPath'], }, }, { name: 'hdc_take_screenshot', description: '截取设备屏幕截图,命令: hdc [-t <deviceId>] shell snapshot_display -f <savePath>', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, savePath: { type: 'string', description: '截图保存路径', }, }, required: ['deviceId', 'savePath'], }, }, { name: 'hdc_reboot_device', description: '重启设备,命令: hdc [-t <deviceId>] target boot', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, }, required: ['deviceId'], }, }, { name: 'hdc_get_logs', description: '获取设备日志,命令: hdc [-t <deviceId>] shell hilog', inputSchema: { type: 'object', properties: { deviceId: { type: 'string', description: '设备连接标识符', }, tag: { type: 'string', description: '日志标签 (可选)', }, lines: { type: 'number', description: '要获取的日志行数 (默认100)', default: 100, }, }, required: ['deviceId'], }, }, { name: 'hdc_ui_tool', description: `HDC UI模拟操作使用说明`, inputSchema: { type: 'object', properties: {}, }, }, { name: 'hdc_aa_tool', description: 'HDC aa工具使用说明', inputSchema: { type: 'object', properties: {}, }, }, { name: 'hdc_bm_tool', description: 'HDC bm工具使用说明', inputSchema: { type: 'object', properties: {}, }, }, { name: 'hdc_param_tool', description: 'HDC param工具使用说明', inputSchema: { type: 'object', properties: {}, }, }, { name: 'hdc_hidumper_tool', description: 'HDC hidumper工具使用说明', inputSchema: { type: 'object', properties: {}, }, }, ], }; }); //@ts-ignore server.setRequestHandler(CallToolRequestSchema, async (request) => { const { name, arguments: args } = request.params; console.error('🔍 收到请求:', JSON.stringify(request.params, null, 2)); try { switch (name) { case 'hdc_get_version': const version = await hdc.getVersion(); return { content: [ { type: 'text', text: `HDC Version: ${version}`, }, ], }; case 'hdc_list_devices': const devices = await hdc.listDevices(); return { content: [ { type: 'text', text: devices.length > 0 ? `Connected devices:\n${devices.map(d => `- ${d.connectKey} (${d.connectionType}) - ${d.status}`).join('\n')}` : 'No devices connected', }, ], }; case 'hdc_get_device_info': const deviceInfo = await hdc.getDeviceInfo(args.deviceId); return { content: [ { type: 'text', text: `Device Information:\n` + `Name: ${deviceInfo.name}\n` + `Brand: ${deviceInfo.brand}\n` + `Model: ${deviceInfo.model}\n` + `Version: ${deviceInfo.version}\n` + `API Version: ${deviceInfo.apiVersion}\n` + `CPU Architecture: ${deviceInfo.cpuArch}\n` + `Resolution: ${deviceInfo.resolution}\n` + `IP Address: ${deviceInfo.ipAddress}\n` + `Battery: ${deviceInfo.battery}%\n` + `Temperature: ${deviceInfo.temperature}°C`, }, ], }; case 'hdc_install_app': const installResult = await hdc.installApp(args.deviceId, args.appPath); return { content: [ { type: 'text', text: `Install result: ${installResult}`, }, ], }; case 'hdc_uninstall_app': const uninstallResult = await hdc.uninstallApp(args.deviceId, args.bundleName); return { content: [ { type: 'text', text: `Uninstall result: ${uninstallResult}`, }, ], }; case 'hdc_list_apps': const apps = await hdc.listApps(args.deviceId); return { content: [ { type: 'text', text: apps.length > 0 ? `Installed apps:\n${apps.map(app => `- ${app.bundleName} v${app.version} (${app.label}) ${app.debuggable ? '[Debuggable]' : ''}`).join('\n')}` : 'No apps found', }, ], }; case 'hdc_start_app': const startResult = await hdc.startApp(args.deviceId, args.bundleName, args.abilityName); return { content: [ { type: 'text', text: `Start app result: ${startResult}`, }, ], }; case 'hdc_stop_app': const stopResult = await hdc.stopApp(args.deviceId, args.bundleName); return { content: [ { type: 'text', text: `Stop app result: ${stopResult}`, }, ], }; case 'hdc_clear_app_data': const clearResult = await hdc.clearAppData(args.deviceId, args.bundleName); return { content: [ { type: 'text', text: `Clear app data result: ${clearResult}`, }, ], }; case 'hdc_push_file': const pushResult = await hdc.pushFile(args.deviceId, args.localPath, args.remotePath); return { content: [ { type: 'text', text: `Push file result: ${pushResult}`, }, ], }; case 'hdc_pull_file': const pullResult = await hdc.pullFile(args.deviceId, args.remotePath, args.localPath); return { content: [ { type: 'text', text: `Pull file result: ${pullResult}`, }, ], }; case 'hdc_take_screenshot': const screenshotResult = await hdc.takeScreenshot(args.deviceId, args.savePath); return { content: [ { type: 'text', text: `Screenshot saved: ${screenshotResult}`, }, ], }; case 'hdc_reboot_device': const rebootResult = await hdc.rebootDevice(args.deviceId); return { content: [ { type: 'text', text: `Reboot result: ${rebootResult}`, }, ], }; case 'hdc_get_logs': const logs = await hdc.getLogs(args.deviceId, args.tag, args.lines); return { content: [ { type: 'text', text: `Device logs:\n${logs}`, }, ], }; case 'hdc_ui_tool': return { content: [ { type: 'text', text: `支持操作类型:点击、双击、长按、慢滑、快滑、拖拽、输入文字、KeyEvent 操作命令格式:hdc shell uitest uiInput <操作类型> <参数> 1. click - 模拟单击操作 参数: point_x (必选,点击x坐标), point_y (必选,点击y坐标) 示例: hdc shell uitest uiInput click 100 100 2. doubleClick - 模拟双击操作 参数: point_x (必选,双击x坐标), point_y (必选,双击y坐标) 示例: hdc shell uitest uiInput doubleClick 100 100 3. longClick - 模拟长按操作 参数: point_x (必选,长按x坐标), point_y (必选,长按y坐标) 示例: hdc shell uitest uiInput longClick 100 100 4. fling - 模拟快滑操作 参数: from_x (必选,起点x坐标), from_y (必选,起点y坐标), to_x (必选,终点x坐标), to_y (必选,终点y坐标), swipeVelocityPps_ (可选,速度200-40000px/s,默认600), stepLength (可选,步长,默认距离/50px) 示例: hdc shell uitest uiInput fling 400 400 400 1600 20000 5. swipe - 模拟慢滑操作 参数: from_x (必选,起点x坐标), from_y (必选,起点y坐标), to_x (必选,终点x坐标), to_y (必选,终点y坐标), swipeVelocityPps_ (可选,速度200-40000px/s,默认600) 示例: hdc shell uitest uiInput swipe 10 10 200 200 500 6. drag - 模拟拖拽操作 参数: from_x (必选,起点x坐标), from_y (必选,起点y坐标), to_x (必选,终点x坐标), to_y (必选,终点y坐标), swipeVelocityPps_ (可选,速度200-40000px/s,默认600) 示例: hdc shell uitest uiInput drag 10 10 100 100 500 7. dircFling - 指定方向滑动 参数: direction (可选,方向[0左,1右,2上,3下],默认0), swipeVelocityPps_ (可选,速度), stepLength (可选,步长) 示例: - 左滑: hdc shell uitest uiInput dircFling 0 500 - 右滑: hdc shell uitest uiInput dircFling 1 600 - 上滑: hdc shell uitest uiInput dircFling 2 - 下滑: hdc shell uitest uiInput dircFling 3 8. inputText - 输入框输入文本 参数: point_x (必选,输入框x坐标), point_y (必选,输入框y坐标), text (输入文本) 示例: hdc shell uitest uiInput inputText 100 100 hello 9. keyEvent - 实体按键事件 参数: keyID (必选,按键ID), keyID2 (可选,组合键ID) 常用示例: - 返回主页: hdc shell uitest uiInput keyEvent Home - 返回上一步: hdc shell uitest uiInput keyEvent Back - 组合键粘贴: hdc shell uitest uiInput keyEvent 2072 2038 keyEvent映射表: https://docs.openharmony.cn/pages/v4.1/en/application-dev/reference/apis-input-kit/js-apis-keycode.md`, }, ], }; case 'hdc_aa_tool': return { content: [ { type: 'text', text: `aa工具使用说明 - start: 启动Ability hdc shell aa start -a {abilityName} -b {bundleName} - stop-service: 停止服务 hdc shell aa stop-service - force-stop: 强制退出应用 hdc shell aa force-stop {bundleName} - test: 启动单元测试 hdc shell aa test -b <bundle-name> -p <package-name> -m <module-name> -r <test-runner> -u <user-id> - attach: 附加调试器 hdc shell aa attach - detach: 分离调试器 hdc shell aa detach - appdebug: 启动应用进行调试 hdc shell aa appdebug -b <bundle-name> -p <process-name> --start --gdb`, }, ], }; case 'hdc_bm_tool': return { content: [ { type: 'text', text: `bm工具使用说明 - install: 安装应用 hdc shell bm install -p <path> -u <user-id> -r <flags> - uninstall: 卸载应用 hdc shell bm uninstall -n <bundle-name> -k - dump: Dump应用信息 hdc shell bm dump -n <bundle-name> - clean: 清除应用数据 hdc shell bm clean -n <bundle-name> -c <cache|data> - enable: 启用应用 hdc shell bm enable -n <bundle-name> - disable: 禁用应用 hdc shell bm disable -n <bundle-name> - get: 获取信息 hdc shell bm get --udid`, }, ], }; case 'hdc_param_tool': return { content: [ { type: 'text', text: `param工具使用说明 获取设备信息 - const.product.name: 名称 - const.product.brand: Brand - const.product.model: Model - const.product.software.version: 系统版本 - const.ohos.apiversion: OS版本 - const.product.cpu.abilist: CPU架构 示例: hdc shell param get const.product.name`, }, ], }; case 'hdc_hidumper_tool': return { content: [ { type: 'text', text: `hidumper工具使用说明 获取系统服务信息 - RenderService: 渲染服务 (包含屏幕信息) - DisplayManagerService: 显示管理服务 - PowerManagerService: 电源管理服务 - BatteryService: 电池服务 - NetConnManager: 网络连接管理 - MemoryManagerService: 内存管理服务 - StorageManager: 存储管理 示例: hdc shell hidumper -s RenderService -a screen`, }, ], }; default: throw new Error(`Unknown tool: ${name}`); } } catch (error) { return { content: [ { type: 'text', text: `Error: ${error instanceof Error ? error.message : String(error)}`, }, ], isError: true, }; } }); async function main() { console.error('hdc-mcp server started'); const transport = new StdioServerTransport(); await server.connect(transport); } main().catch((error) => { console.error('Server error:', error); process.exit(1); }); //# sourceMappingURL=index.js.map