@yancyyu/openhermit 1.6.19 → 1.6.20

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 (2) hide show
  1. package/bin/hermit.mjs +46 -55
  2. package/package.json +1 -1
package/bin/hermit.mjs CHANGED
@@ -15,7 +15,6 @@
15
15
  */
16
16
 
17
17
  import { spawn, execSync } from 'node:child_process';
18
- import crypto from 'node:crypto';
19
18
  import { appendFileSync, closeSync, existsSync, mkdirSync, openSync, readFileSync, unlinkSync, writeFileSync } from 'node:fs';
20
19
  import { createRequire } from 'node:module';
21
20
  import os from 'node:os';
@@ -350,10 +349,6 @@ Please install dependencies first:
350
349
  // cc-connect sidecar
351
350
  // ---------------------------------------------------------------------------
352
351
 
353
- function randomToken() {
354
- return crypto.randomBytes(16).toString('hex');
355
- }
356
-
357
352
  function escapeTomlPath(value) {
358
353
  return value.replace(/\\/g, '\\\\').replace(/"/g, '\\"');
359
354
  }
@@ -384,51 +379,6 @@ function isManagedBootstrapBlock(block) {
384
379
  );
385
380
  }
386
381
 
387
- function buildStarterConfigToml(managementToken, bridgeToken) {
388
- return `# cc-connect configuration
389
- # Docs: https://github.com/chenhg5/cc-connect
390
-
391
- data_dir = "${escapeTomlPath(path.join(hermitHome, 'cc-connect', 'data'))}"
392
- language = "zh"
393
-
394
- [management]
395
- enabled = true
396
- host = "127.0.0.1"
397
- port = 9820
398
- token = "${managementToken}"
399
-
400
- [bridge]
401
- enabled = true
402
- host = "127.0.0.1"
403
- port = 9810
404
- token = "${bridgeToken}"
405
- path = "/bridge/ws"
406
-
407
- [log]
408
- level = "info"
409
-
410
- [[projects]]
411
- name = "my-project"
412
-
413
- [projects.agent]
414
- type = "claudecode" # "claudecode", "codex", "cursor", "gemini", "qoder", "opencode", or "iflow"
415
-
416
- [projects.agent.options]
417
- work_dir = "/path/to/your/project"
418
- mode = "default"
419
- # model = "claude-sonnet-4-20250514"
420
-
421
- # --- Choose at least one platform below ---
422
-
423
- [[projects.platforms]]
424
- type = "feishu"
425
-
426
- [projects.platforms.options]
427
- app_id = "your-feishu-app-id"
428
- app_secret = "your-feishu-app-secret"
429
- `;
430
- }
431
-
432
382
  function isStarterProjectConfig(raw) {
433
383
  const block = findProjectBlock(raw, starterProjectName);
434
384
  if (!block) return false;
@@ -452,17 +402,22 @@ function hasRunnableProjectEntries(raw) {
452
402
  return false;
453
403
  }
454
404
 
455
- function ensureCcConnectConfig() {
405
+ function readCcConnectConfigState() {
456
406
  mkdirSync(path.dirname(ccConnectConfigPath), { recursive: true });
457
407
  if (!existsSync(ccConnectConfigPath)) {
458
- const managementToken = randomToken();
459
- const bridgeToken = randomToken();
460
- writeFileSync(ccConnectConfigPath, buildStarterConfigToml(managementToken, bridgeToken), 'utf-8');
408
+ return {
409
+ configExists: false,
410
+ managementToken: process.env.CC_CONNECT_TOKEN || process.env.CC_CONNECT_MANAGEMENT_TOKEN || '',
411
+ bridgeToken: process.env.CC_CONNECT_BRIDGE_TOKEN || process.env.CC_CONNECT_TOKEN || '',
412
+ hasRunnableProjects: false,
413
+ isStarterConfig: false,
414
+ };
461
415
  }
462
416
 
463
417
  const raw = readFileSync(ccConnectConfigPath, 'utf-8');
464
418
 
465
419
  return {
420
+ configExists: true,
466
421
  managementToken:
467
422
  process.env.CC_CONNECT_TOKEN ||
468
423
  process.env.CC_CONNECT_MANAGEMENT_TOKEN ||
@@ -561,11 +516,47 @@ let ccTokens = {
561
516
  };
562
517
 
563
518
  if (!skipCcConnect) {
564
- ccTokens = ensureCcConnectConfig();
519
+ ccTokens = readCcConnectConfigState();
565
520
  const ccBaseUrl = process.env.CC_CONNECT_BASE_URL || 'http://127.0.0.1:9820';
566
521
  const alreadyRunning = await waitForCcConnect(ccBaseUrl, ccTokens.managementToken, 1_000);
567
522
  if (alreadyRunning) {
568
523
  console.log(`[openHermit] Runtime service already running: ${ccBaseUrl}`);
524
+ } else if (!ccTokens.configExists) {
525
+ console.log('[openHermit] Initializing runtime config with bundled runtime service...');
526
+ console.log(`[openHermit] Runtime config: ${ccConnectConfigPath}`);
527
+ const initProcess = spawn(process.execPath, [resolveCcConnectRunner(), '-config', ccConnectConfigPath], {
528
+ cwd: repoRoot,
529
+ env: {
530
+ ...process.env,
531
+ CC_CONNECT_TOKEN: ccTokens.managementToken,
532
+ CC_CONNECT_MANAGEMENT_TOKEN: ccTokens.managementToken,
533
+ CC_CONNECT_BRIDGE_TOKEN: ccTokens.bridgeToken,
534
+ },
535
+ stdio: ['ignore', 'pipe', 'pipe'],
536
+ });
537
+ initProcess.stdout?.on('data', (chunk) => {
538
+ process.stdout.write(chunk);
539
+ appendLog(runtimeLogPath, chunk);
540
+ });
541
+ initProcess.stderr?.on('data', (chunk) => {
542
+ process.stderr.write(chunk);
543
+ appendLog(runtimeLogPath, chunk);
544
+ });
545
+
546
+ const initCode = await new Promise((resolve) => {
547
+ initProcess.on('exit', (code) => resolve(code ?? 1));
548
+ initProcess.on('error', () => resolve(1));
549
+ });
550
+
551
+ ccTokens = readCcConnectConfigState();
552
+ if (initCode === 0 && ccTokens.configExists) {
553
+ console.log('[openHermit] Runtime starter config created.');
554
+ console.log('[openHermit] Open the panel to finish setup before starting the runtime service.');
555
+ } else {
556
+ console.error(`[openHermit] Runtime config initialization failed (code ${initCode}).`);
557
+ printLogTail('Runtime', runtimeLogPath);
558
+ process.exit(1);
559
+ }
569
560
  } else if (!ccTokens.hasRunnableProjects) {
570
561
  console.log('[openHermit] Runtime config is a starter template; starting control panel only.');
571
562
  console.log(`[openHermit] Edit runtime config in the UI before starting the runtime service.`);
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@yancyyu/openhermit",
3
3
  "type": "module",
4
- "version": "1.6.19",
4
+ "version": "1.6.20",
5
5
  "description": "openHermit: team-oriented agent management workbench atop cc-connect.",
6
6
  "license": "AGPL-3.0",
7
7
  "author": {