@simonyea/holysheep-cli 1.7.118 → 1.7.119

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/package.json +1 -1
  2. package/src/webui/server.js +61 -42
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@simonyea/holysheep-cli",
3
- "version": "1.7.118",
3
+ "version": "1.7.119",
4
4
  "description": "Claude Code/Cursor/Cline API relay for China — ¥1=$1, WeChat/Alipay payment, no credit card, no VPN. One command setup for all AI coding tools.",
5
5
  "keywords": [
6
6
  "openai-china",
@@ -503,21 +503,26 @@ async function handleUpgrade(_req, res) {
503
503
  newVer = m ? m[1] : null
504
504
  } catch {}
505
505
 
506
- // OpenClaw 升级后:Gateway → 更新 PID → Bridge
506
+ // OpenClaw 升级后:Gateway → 等端口就绪 → 更新 PID → Bridge
507
507
  if (ok && tool.id === 'openclaw') {
508
508
  try { execSync('openclaw daemon stop', { stdio: 'ignore', timeout: 10000 }) } catch {}
509
509
  try { execSync('openclaw daemon start', { stdio: 'ignore', timeout: 30000 }) } catch {}
510
510
  const openclawTool = TOOLS.find(t => t.id === 'openclaw')
511
+ const gPort = openclawTool?.getGatewayPort?.() || 18789
512
+ let gPid = null
513
+ for (let i = 0; i < 10 && !gPid; i++) {
514
+ await new Promise(r => setTimeout(r, 1500))
515
+ try {
516
+ if (process.platform === 'win32') {
517
+ const o = execSync(`powershell -NonInteractive -Command "(Get-NetTCPConnection -LocalPort ${gPort} -State Listen -ErrorAction SilentlyContinue).OwningProcess"`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
518
+ gPid = Number(o.split(/\r?\n/)[0]) || null
519
+ } else {
520
+ const o = execSync(`lsof -iTCP:${gPort} -sTCP:LISTEN -t 2>/dev/null | head -1`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
521
+ gPid = Number(o) || null
522
+ }
523
+ } catch {}
524
+ }
511
525
  try {
512
- const gPort = openclawTool?.getGatewayPort?.() || 18789
513
- let gPid = null
514
- if (process.platform === 'win32') {
515
- const o = execSync(`powershell -NonInteractive -Command "(Get-NetTCPConnection -LocalPort ${gPort} -State Listen -ErrorAction SilentlyContinue).OwningProcess"`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
516
- gPid = Number(o.split(/\r?\n/)[0]) || null
517
- } else {
518
- const o = execSync(`lsof -iTCP:${gPort} -sTCP:LISTEN -t 2>/dev/null | head -1`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
519
- gPid = Number(o) || null
520
- }
521
526
  if (gPid) {
522
527
  const bridgeMod = require('../tools/openclaw-bridge')
523
528
  const bc = bridgeMod.readBridgeConfig()
@@ -691,25 +696,30 @@ async function handleToolUpgrade(req, res) {
691
696
  } catch {
692
697
  sseEmit(res, { type: 'progress', message: '⚠️ Gateway 启动失败' })
693
698
  }
694
- // 获取 Gateway PID 写入 bridge config
695
- try {
696
- const gatewayPort = openclawTool?.getGatewayPort?.() || 18789
697
- let gatewayPid = null
698
- if (process.platform === 'win32') {
699
- const out = execSync(`powershell -NonInteractive -Command "(Get-NetTCPConnection -LocalPort ${gatewayPort} -State Listen -ErrorAction SilentlyContinue).OwningProcess"`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
700
- gatewayPid = Number(out.split(/\r?\n/)[0]) || null
701
- } else {
702
- const out = execSync(`lsof -iTCP:${gatewayPort} -sTCP:LISTEN -t 2>/dev/null | head -1`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
703
- gatewayPid = Number(out) || null
704
- }
705
- if (gatewayPid) {
699
+ // Gateway 端口就绪,获取 PID 写入 bridge config
700
+ const gPort = openclawTool?.getGatewayPort?.() || 18789
701
+ let gPid = null
702
+ for (let i = 0; i < 10 && !gPid; i++) {
703
+ await new Promise(r => setTimeout(r, 1500))
704
+ try {
705
+ if (process.platform === 'win32') {
706
+ const o = execSync(`powershell -NonInteractive -Command "(Get-NetTCPConnection -LocalPort ${gPort} -State Listen -ErrorAction SilentlyContinue).OwningProcess"`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
707
+ gPid = Number(o.split(/\r?\n/)[0]) || null
708
+ } else {
709
+ const o = execSync(`lsof -iTCP:${gPort} -sTCP:LISTEN -t 2>/dev/null | head -1`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
710
+ gPid = Number(o) || null
711
+ }
712
+ } catch {}
713
+ }
714
+ if (gPid) {
715
+ try {
706
716
  const bridgeMod = require('../tools/openclaw-bridge')
707
717
  const bc = bridgeMod.readBridgeConfig()
708
- bc.gatewayPid = gatewayPid
718
+ bc.gatewayPid = gPid
709
719
  bc.gatewayStartedAt = new Date().toISOString()
710
720
  fs.writeFileSync(bridgeMod.BRIDGE_CONFIG_FILE, JSON.stringify(bc, null, 2), 'utf8')
711
- }
712
- } catch {}
721
+ } catch {}
722
+ }
713
723
  // 启动 Bridge
714
724
  if (openclawTool?.ensureBridgeRunning) {
715
725
  try {
@@ -841,34 +851,43 @@ async function handleToolRollback(req, res) {
841
851
  } catch {
842
852
  sseEmit(res, { type: 'progress', message: '⚠️ Gateway 启动失败' })
843
853
  }
844
- // 2. 获取 Gateway PID 并写入 bridge config,否则 bridge watchdog 会自杀
854
+ // 2. Gateway 端口就绪,获取 PID 写入 bridge config
845
855
  const openclawTool = TOOLS.find(t => t.id === 'openclaw')
846
- try {
847
- const gatewayPort = openclawTool?.getGatewayPort?.() || 18789
848
- let gatewayPid = null
849
- if (process.platform === 'win32') {
850
- const out = execSync(`powershell -NonInteractive -Command "(Get-NetTCPConnection -LocalPort ${gatewayPort} -State Listen -ErrorAction SilentlyContinue).OwningProcess"`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
851
- gatewayPid = Number(out.split(/\r?\n/)[0]) || null
852
- } else {
853
- const out = execSync(`lsof -iTCP:${gatewayPort} -sTCP:LISTEN -t 2>/dev/null | head -1`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
854
- gatewayPid = Number(out) || null
855
- }
856
- if (gatewayPid) {
856
+ const gatewayPort = openclawTool?.getGatewayPort?.() || 18789
857
+ let gatewayPid = null
858
+ for (let attempt = 0; attempt < 10 && !gatewayPid; attempt++) {
859
+ await new Promise(r => setTimeout(r, 1500))
860
+ try {
861
+ if (process.platform === 'win32') {
862
+ const out = execSync(`powershell -NonInteractive -Command "(Get-NetTCPConnection -LocalPort ${gatewayPort} -State Listen -ErrorAction SilentlyContinue).OwningProcess"`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
863
+ gatewayPid = Number(out.split(/\r?\n/)[0]) || null
864
+ } else {
865
+ const out = execSync(`lsof -iTCP:${gatewayPort} -sTCP:LISTEN -t 2>/dev/null | head -1`, { stdio: 'pipe', timeout: 5000 }).toString().trim()
866
+ gatewayPid = Number(out) || null
867
+ }
868
+ } catch {}
869
+ }
870
+ if (gatewayPid) {
871
+ try {
857
872
  const bridgeMod = require('../tools/openclaw-bridge')
858
873
  const bc = bridgeMod.readBridgeConfig()
859
874
  bc.gatewayPid = gatewayPid
860
875
  bc.gatewayStartedAt = new Date().toISOString()
861
876
  fs.writeFileSync(bridgeMod.BRIDGE_CONFIG_FILE, JSON.stringify(bc, null, 2), 'utf8')
862
877
  sseEmit(res, { type: 'progress', message: `Gateway PID: ${gatewayPid}` })
878
+ } catch (e) {
879
+ sseEmit(res, { type: 'progress', message: `⚠️ 写入 Bridge 配置失败: ${e.message}` })
863
880
  }
864
- } catch {}
881
+ } else {
882
+ sseEmit(res, { type: 'progress', message: '⚠️ 未检测到 Gateway PID,Bridge 可能无��启动' })
883
+ }
865
884
  // 3. 启动 Bridge
866
885
  if (openclawTool?.ensureBridgeRunning) {
867
886
  try {
868
- openclawTool.ensureBridgeRunning()
869
- sseEmit(res, { type: 'progress', message: '✓ HolySheep Bridge 已启动' })
870
- } catch {
871
- sseEmit(res, { type: 'progress', message: '⚠️ Bridge 启动失败' })
887
+ const bridgeOk = openclawTool.ensureBridgeRunning()
888
+ sseEmit(res, { type: 'progress', message: bridgeOk ? '✓ HolySheep Bridge 已启动' : '⚠️ Bridge 未就绪' })
889
+ } catch (e) {
890
+ sseEmit(res, { type: 'progress', message: `⚠️ Bridge 启动失败: ${e.message}` })
872
891
  }
873
892
  }
874
893
  }