@foxden-app/foxclaw 0.2.1 → 0.2.3
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.
- package/dist/codex_app/client.js +13 -1
- package/dist/main.js +36 -13
- package/package.json +19 -19
package/dist/codex_app/client.js
CHANGED
|
@@ -3,7 +3,9 @@ import fs from 'node:fs';
|
|
|
3
3
|
import net from 'node:net';
|
|
4
4
|
import path from 'node:path';
|
|
5
5
|
import { spawn } from 'node:child_process';
|
|
6
|
+
import { fileURLToPath } from 'node:url';
|
|
6
7
|
import { buildThreadDeepLink, openUrl } from './deeplink.js';
|
|
8
|
+
const CLIENT_VERSION = readPackageVersion();
|
|
7
9
|
export class CodexAppClient extends EventEmitter {
|
|
8
10
|
codexCliBin;
|
|
9
11
|
launchCommand;
|
|
@@ -593,7 +595,7 @@ export class CodexAppClient extends EventEmitter {
|
|
|
593
595
|
clientInfo: {
|
|
594
596
|
name: 'foxclaw',
|
|
595
597
|
title: 'FoxClaw',
|
|
596
|
-
version:
|
|
598
|
+
version: CLIENT_VERSION,
|
|
597
599
|
},
|
|
598
600
|
capabilities: {
|
|
599
601
|
experimentalApi: true,
|
|
@@ -770,6 +772,16 @@ export class CodexAppClient extends EventEmitter {
|
|
|
770
772
|
this.clearServerState();
|
|
771
773
|
}
|
|
772
774
|
}
|
|
775
|
+
function readPackageVersion() {
|
|
776
|
+
try {
|
|
777
|
+
const pkgPath = path.resolve(path.dirname(fileURLToPath(import.meta.url)), '..', '..', 'package.json');
|
|
778
|
+
const pkg = JSON.parse(fs.readFileSync(pkgPath, 'utf8'));
|
|
779
|
+
return typeof pkg.version === 'string' && pkg.version.trim() ? pkg.version : '0.0.0';
|
|
780
|
+
}
|
|
781
|
+
catch {
|
|
782
|
+
return '0.0.0';
|
|
783
|
+
}
|
|
784
|
+
}
|
|
773
785
|
async function reservePort() {
|
|
774
786
|
return new Promise((resolve, reject) => {
|
|
775
787
|
const server = net.createServer();
|
package/dist/main.js
CHANGED
|
@@ -5,19 +5,6 @@ import process from 'node:process';
|
|
|
5
5
|
import { spawnSync } from 'node:child_process';
|
|
6
6
|
import { fileURLToPath } from 'node:url';
|
|
7
7
|
import { APP_HOME, DEFAULT_ENV_PATH, DEFAULT_LOG_PATH, DEFAULT_STATUS_PATH, loadConfig, loadEnv, } from './config.js';
|
|
8
|
-
import { BridgeMessagingRouter } from './channels/bridge_messaging_router.js';
|
|
9
|
-
import { TelegramMessagingPort } from './channels/telegram/telegram_messaging_port.js';
|
|
10
|
-
import { WeixinChannelAdapter } from './channels/weixin/weixin_channel_adapter.js';
|
|
11
|
-
import { WeixinMessagingPort } from './channels/weixin/weixin_messaging_port.js';
|
|
12
|
-
import { attachIlinkRuntimeFromBridgeLogger } from './channels/weixin/ilink/runtime_attach.js';
|
|
13
|
-
import { startWeixinLoginWithQr, waitForWeixinLogin } from './channels/weixin/ilink/login_qr.js';
|
|
14
|
-
import { accountFilePath, loadWeixinAccount, saveWeixinAccount } from './channels/weixin/account_store.js';
|
|
15
|
-
import { Logger } from './logger.js';
|
|
16
|
-
import { BridgeStore } from './store/database.js';
|
|
17
|
-
import { TelegramGateway } from './telegram/gateway.js';
|
|
18
|
-
import { CodexAppClient } from './codex_app/client.js';
|
|
19
|
-
import { BridgeSessionCore } from './controller/controller.js';
|
|
20
|
-
import { TelegramChannelAdapter } from './channels/telegram/telegram_channel_adapter.js';
|
|
21
8
|
import { acquireProcessLock, LockHeldError } from './lock.js';
|
|
22
9
|
import { readRuntimeStatus, writeRuntimeStatus } from './runtime.js';
|
|
23
10
|
const command = process.argv[2] || 'serve';
|
|
@@ -30,6 +17,7 @@ async function main() {
|
|
|
30
17
|
return;
|
|
31
18
|
}
|
|
32
19
|
if (command === 'install-systemd') {
|
|
20
|
+
requireNode24(command);
|
|
33
21
|
installSystemd();
|
|
34
22
|
return;
|
|
35
23
|
}
|
|
@@ -38,6 +26,7 @@ async function main() {
|
|
|
38
26
|
return;
|
|
39
27
|
}
|
|
40
28
|
if (command === 'install-launchd') {
|
|
29
|
+
requireNode24(command);
|
|
41
30
|
installLaunchd();
|
|
42
31
|
return;
|
|
43
32
|
}
|
|
@@ -91,9 +80,28 @@ async function main() {
|
|
|
91
80
|
process.exit(failed ? 1 : 0);
|
|
92
81
|
}
|
|
93
82
|
if (command === 'weixin-login') {
|
|
83
|
+
requireNode24(command);
|
|
94
84
|
await runWeixinLoginCli();
|
|
95
85
|
return;
|
|
96
86
|
}
|
|
87
|
+
requireNode24(command);
|
|
88
|
+
await runServeCli();
|
|
89
|
+
}
|
|
90
|
+
async function runServeCli() {
|
|
91
|
+
const [{ BridgeMessagingRouter }, { TelegramMessagingPort }, { WeixinChannelAdapter }, { WeixinMessagingPort }, { attachIlinkRuntimeFromBridgeLogger }, { loadWeixinAccount }, { Logger }, { BridgeStore }, { TelegramGateway }, { CodexAppClient }, { BridgeSessionCore }, { TelegramChannelAdapter },] = await Promise.all([
|
|
92
|
+
import('./channels/bridge_messaging_router.js'),
|
|
93
|
+
import('./channels/telegram/telegram_messaging_port.js'),
|
|
94
|
+
import('./channels/weixin/weixin_channel_adapter.js'),
|
|
95
|
+
import('./channels/weixin/weixin_messaging_port.js'),
|
|
96
|
+
import('./channels/weixin/ilink/runtime_attach.js'),
|
|
97
|
+
import('./channels/weixin/account_store.js'),
|
|
98
|
+
import('./logger.js'),
|
|
99
|
+
import('./store/database.js'),
|
|
100
|
+
import('./telegram/gateway.js'),
|
|
101
|
+
import('./codex_app/client.js'),
|
|
102
|
+
import('./controller/controller.js'),
|
|
103
|
+
import('./channels/telegram/telegram_channel_adapter.js'),
|
|
104
|
+
]);
|
|
97
105
|
const config = loadConfig();
|
|
98
106
|
const logger = new Logger(config.logLevel, config.logPath);
|
|
99
107
|
attachIlinkRuntimeFromBridgeLogger(logger, config.wxIlinkRouteTag);
|
|
@@ -322,6 +330,12 @@ function xmlEscape(value) {
|
|
|
322
330
|
.replace(/'/g, ''');
|
|
323
331
|
}
|
|
324
332
|
async function runWeixinLoginCli() {
|
|
333
|
+
const [{ attachIlinkRuntimeFromBridgeLogger }, { startWeixinLoginWithQr, waitForWeixinLogin }, { accountFilePath, saveWeixinAccount }, { Logger },] = await Promise.all([
|
|
334
|
+
import('./channels/weixin/ilink/runtime_attach.js'),
|
|
335
|
+
import('./channels/weixin/ilink/login_qr.js'),
|
|
336
|
+
import('./channels/weixin/account_store.js'),
|
|
337
|
+
import('./logger.js'),
|
|
338
|
+
]);
|
|
325
339
|
const logPath = process.env.LOG_PATH || DEFAULT_LOG_PATH;
|
|
326
340
|
const level = process.env.LOG_LEVEL === 'debug' || process.env.LOG_LEVEL === 'warn' || process.env.LOG_LEVEL === 'error'
|
|
327
341
|
? process.env.LOG_LEVEL
|
|
@@ -410,6 +424,15 @@ function hasConfiguredCodexBin(binPath) {
|
|
|
410
424
|
return false;
|
|
411
425
|
}
|
|
412
426
|
}
|
|
427
|
+
function requireNode24(commandName) {
|
|
428
|
+
if (Number(process.versions.node.split('.')[0]) >= 24)
|
|
429
|
+
return;
|
|
430
|
+
console.error(`FoxClaw ${commandName} requires Node.js 24+. Current Node.js is ${process.version}.`);
|
|
431
|
+
console.error('Install or activate Node 24, then reinstall/re-run FoxClaw:');
|
|
432
|
+
console.error(' nvm install 24 && nvm use 24');
|
|
433
|
+
console.error(' npm install -g @foxden-app/foxclaw@latest');
|
|
434
|
+
process.exit(1);
|
|
435
|
+
}
|
|
413
436
|
function serializeError(error) {
|
|
414
437
|
if (error instanceof Error) {
|
|
415
438
|
return { message: error.message, stack: error.stack };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
|
-
"name": "@foxden-app/foxclaw",
|
|
3
|
-
"version": "0.2.
|
|
2
|
+
"name": "@foxden-app/foxclaw",
|
|
3
|
+
"version": "0.2.3",
|
|
4
4
|
"description": "Foxden local execution claw for controlling Codex from trusted chat interfaces.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/main.js",
|
|
@@ -8,13 +8,13 @@
|
|
|
8
8
|
"foxclaw": "dist/main.js"
|
|
9
9
|
},
|
|
10
10
|
"files": [
|
|
11
|
-
"dist",
|
|
12
|
-
"docs",
|
|
13
|
-
"scripts",
|
|
11
|
+
"dist",
|
|
12
|
+
"docs",
|
|
13
|
+
"scripts",
|
|
14
14
|
"skills",
|
|
15
15
|
".env.example",
|
|
16
|
-
"README.md",
|
|
17
|
-
"README_EN.md",
|
|
16
|
+
"README.md",
|
|
17
|
+
"README_EN.md",
|
|
18
18
|
"LICENSE"
|
|
19
19
|
],
|
|
20
20
|
"private": false,
|
|
@@ -32,23 +32,23 @@
|
|
|
32
32
|
"engines": {
|
|
33
33
|
"node": ">=24"
|
|
34
34
|
},
|
|
35
|
-
"scripts": {
|
|
36
|
-
"clean": "node -e \"require('node:fs').rmSync('dist', { recursive: true, force: true })\"",
|
|
37
|
-
"build": "npm run clean && tsc -p tsconfig.build.json",
|
|
38
|
-
"dev": "tsx src/main.ts serve",
|
|
39
|
-
"serve": "node dist/main.js serve",
|
|
35
|
+
"scripts": {
|
|
36
|
+
"clean": "node -e \"require('node:fs').rmSync('dist', { recursive: true, force: true })\"",
|
|
37
|
+
"build": "npm run clean && tsc -p tsconfig.build.json",
|
|
38
|
+
"dev": "tsx src/main.ts serve",
|
|
39
|
+
"serve": "node dist/main.js serve",
|
|
40
40
|
"weixin-login": "node dist/main.js weixin-login",
|
|
41
41
|
"status": "node dist/main.js status",
|
|
42
42
|
"doctor": "node dist/main.js doctor",
|
|
43
|
-
"init": "node dist/main.js init",
|
|
44
|
-
"install-systemd": "node dist/main.js install-systemd",
|
|
45
|
-
"uninstall-systemd": "node dist/main.js uninstall-systemd",
|
|
46
|
-
"install-launchd": "node dist/main.js install-launchd",
|
|
43
|
+
"init": "node dist/main.js init",
|
|
44
|
+
"install-systemd": "node dist/main.js install-systemd",
|
|
45
|
+
"uninstall-systemd": "node dist/main.js uninstall-systemd",
|
|
46
|
+
"install-launchd": "node dist/main.js install-launchd",
|
|
47
47
|
"typecheck": "tsc --noEmit",
|
|
48
48
|
"lint": "eslint .",
|
|
49
|
-
"test": "node --test --import tsx \"src/**/*.test.ts\"",
|
|
50
|
-
"prepack": "npm run build"
|
|
51
|
-
},
|
|
49
|
+
"test": "node --test --import tsx \"src/**/*.test.ts\"",
|
|
50
|
+
"prepack": "npm run build"
|
|
51
|
+
},
|
|
52
52
|
"dependencies": {
|
|
53
53
|
"dotenv": "^16.6.1",
|
|
54
54
|
"qrcode-terminal": "^0.12.0"
|