wecom-cli-smoke-test.js 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384
  1. #!/usr/bin/env node
  2. const assert = require('assert');
  3. const fs = require('fs');
  4. const os = require('os');
  5. const path = require('path');
  6. async function main() {
  7. const tempRoot = fs.mkdtempSync(path.join(os.tmpdir(), 'qiwei-official-cli-test-'));
  8. const runtimeRoot = path.join(tempRoot, 'runtime');
  9. const configDir = path.join(tempRoot, 'config');
  10. process.env.QIWEI_OFFICIAL_CLI_RUNTIME_DIR = runtimeRoot;
  11. process.env.WECOM_CLI_CONFIG_DIR = configDir;
  12. const runtime = require('../mcp/src/core/wecom-cli-runtime');
  13. const provider = require('../mcp/src/providers/wecom-official-cli');
  14. try {
  15. const emptyStatus = await runtime.getOfficialCliStatus();
  16. assert.strictEqual(emptyStatus.installed, false);
  17. assert.strictEqual(emptyStatus.ready, false);
  18. const packageDir = path.join(runtime.getRuntimeDir(), 'node_modules', '@wecom', 'cli');
  19. fs.mkdirSync(path.join(packageDir, 'bin'), { recursive: true });
  20. fs.writeFileSync(
  21. path.join(packageDir, 'package.json'),
  22. JSON.stringify({
  23. name: runtime.runtimeManifest.package,
  24. version: runtime.runtimeManifest.version
  25. })
  26. );
  27. fs.writeFileSync(
  28. path.join(packageDir, 'bin', 'wecom.js'),
  29. [
  30. "const args = process.argv.slice(2);",
  31. "if (args.join(' ') === 'auth show --auth-status') { console.log('authorized'); process.exit(0); }",
  32. "if (args.at(-1) === '--help') { console.log(`help:${args.slice(0, -1).join('.') || 'root'}`); process.exit(0); }",
  33. "const jsonIndex = args.indexOf('--json');",
  34. "const input = jsonIndex >= 0 ? JSON.parse(args[jsonIndex + 1]) : {};",
  35. "console.log(JSON.stringify({ errcode: 0, category: args[0], method: args[1], input, bot_secret: 'test-only-secret', accessToken: 'test-only-token', providerName: 'private-provider', doc_url: 'https://docs.example.test/document/1' }));"
  36. ].join('\n')
  37. );
  38. fs.mkdirSync(configDir, { recursive: true });
  39. fs.writeFileSync(path.join(configDir, 'bot.enc'), 'test');
  40. fs.writeFileSync(path.join(configDir, 'mcp_config.enc'), 'test');
  41. const readyStatus = await runtime.getOfficialCliStatus();
  42. assert.strictEqual(readyStatus.valid, true);
  43. assert.strictEqual(readyStatus.authorized, true);
  44. assert.strictEqual(readyStatus.ready, true);
  45. const help = await provider.qiweiOfficialHelp({ category: 'meeting', method: 'create_meeting' });
  46. assert.strictEqual(help.status, 'ok');
  47. assert.strictEqual(help.data.help, 'help:meeting.create_meeting');
  48. const call = await provider.qiweiOfficialCall({
  49. category: 'doc',
  50. method: 'create_doc',
  51. args: { doc_type: 3, doc_name: '测试文档; echo unsafe' }
  52. });
  53. assert.strictEqual(call.status, 'ok');
  54. assert.strictEqual(call.data.response.category, 'doc');
  55. assert.strictEqual(call.data.response.method, 'create_doc');
  56. assert.strictEqual(call.data.response.input.doc_name, '测试文档; echo unsafe');
  57. assert(!Object.hasOwn(call.data.response, 'bot_secret'));
  58. assert(!Object.hasOwn(call.data.response, 'accessToken'));
  59. assert(!Object.hasOwn(call.data.response, 'providerName'));
  60. assert.strictEqual(call.data.response.doc_url, 'https://docs.example.test/document/1');
  61. const invalidMethod = await provider.qiweiOfficialCall({
  62. category: 'doc',
  63. method: 'create_doc; echo unsafe',
  64. args: {}
  65. });
  66. assert.strictEqual(invalidMethod.status, 'error');
  67. console.log('[ok] official CLI runtime status, structured help and shell-safe calls');
  68. } finally {
  69. fs.rmSync(tempRoot, { recursive: true, force: true });
  70. }
  71. }
  72. main().catch(error => {
  73. console.error('official CLI smoke test failed:', error);
  74. process.exit(1);
  75. });