autowonder 0.2.129 → 0.2.131

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/README.md CHANGED
@@ -6,17 +6,22 @@ AutoWonder 本地 agent runtime。安装后启动 daemon,持续轮询本地 as
6
6
 
7
7
  ```bash
8
8
  # Qoder CLI(模型使用 provider model ID;Context Window 使用固定档位)
9
- npx -y autowonder@0.2.129 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider qoder --model qmodel_latest --reasoning-effort medium --context-window 260000
9
+ npx -y autowonder@0.2.131 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider qoder --model qmodel_latest --reasoning-effort medium --context-window 260000
10
+
11
+ # Qoder CLI CN
12
+ npx -y autowonder@0.2.131 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider qodercn
10
13
 
11
14
  # Claude Code
12
- npx -y autowonder@0.2.129 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider claude
15
+ npx -y autowonder@0.2.131 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider claude
13
16
 
14
17
  # Codex CLI
15
- npx -y autowonder@0.2.129 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider codex --model gpt-5.5 --reasoning-effort medium
18
+ npx -y autowonder@0.2.131 connect --ws-url <wss-endpoint> --token <executor-token> --executor-id <executor-id> --provider codex --model gpt-5.5 --reasoning-effort medium
16
19
  ```
17
20
 
18
21
  `connect` 会安装当前 npm 包内置的 daemon,并使用页面生成的 WebSocket endpoint、Token 和执行器 ID 建立连接。选择 Qoder 时需要 Node.js 20+;runtime 会在缺少 `qodercli` 时自动通过 npm 安装,并在尚未登录时打开 Qoder 浏览器登录。Claude Code 和 Codex CLI 仍需提前安装并登录。runtime 会继承当前用户的 HOME、环境变量和 CLI 登录状态。
19
22
 
23
+ `qodercn` 是国内版 Qoder CLI。runtime 会在缺少 `qodercn` 时自动把 `@qodercn-ai/qoderclicn` 安装到 `~/.autowonder/qoder-cn-cli`,并在尚未登录时打开浏览器登录。它使用自己的配置根(`QODERCN_CONFIG_DIR`,默认 `~/.qoder-cn`),与国际版 `qoder` 不共享可执行文件、凭证和会话。可用 `AUTOWONDER_QODERCN_CLI` 指定自定义可执行文件路径。
24
+
20
25
  Qoder 的 Context Window 只能使用 `1000000`、`400000` 或 `260000`,Reasoning Effort 只能使用 `none`、`low`、`medium`、`high`、`xhigh` 或 `max`。建议直接复制 AutoWonder 执行器页面生成的命令,避免把模型展示名称误当成 provider model ID。
21
26
 
22
27
  ## 自动更新
@@ -57,14 +62,14 @@ mv "$queue/.assignment.tmp" "$queue/assignment.json"
57
62
  也可以直接提交到本地 API:
58
63
 
59
64
  ```bash
60
- npx -y autowonder@0.2.129 dispatch ./assignment.json
65
+ npx -y autowonder@0.2.131 dispatch ./assignment.json
61
66
  ```
62
67
 
63
68
  ## 管理 daemon
64
69
 
65
70
  ```bash
66
- npx -y autowonder@0.2.129 status
67
- npx -y autowonder@0.2.129 stop
71
+ npx -y autowonder@0.2.131 status
72
+ npx -y autowonder@0.2.131 stop
68
73
  ```
69
74
 
70
75
  默认 API 是 `http://127.0.0.1:34989`,日志位于 `~/.autowonder/daemon.log`。npm 包不包含任何 agent、MCP 或服务端凭证。
package/bin/cli.js CHANGED
@@ -24,6 +24,46 @@ const PID_PATH = path.join(AUTOWONDER_HOME, "daemon.pid");
24
24
  const STATE_PATH = path.join(AUTOWONDER_HOME, "daemon-state.json");
25
25
  const LOG_PATH = path.join(AUTOWONDER_HOME, "daemon.log");
26
26
  const MANAGED_QODER_DIR = path.join(AUTOWONDER_HOME, "qoder-cli");
27
+ const MANAGED_QODERCN_DIR = path.join(AUTOWONDER_HOME, "qoder-cn-cli");
28
+
29
+ // qoder and qodercn are two distinct provider identities that share the same
30
+ // bootstrap flow. Each identity keeps its own executable, npm package, managed
31
+ // install dir and env override so the two CLIs never shadow each other.
32
+ const QODER_FAMILY_PROFILES = {
33
+ qoder: {
34
+ displayName: "Qoder CLI",
35
+ executable: "qodercli",
36
+ envVar: "AUTOWONDER_QODER_CLI",
37
+ npmPackage: "@qoder-ai/qodercli@latest",
38
+ managedDir: MANAGED_QODER_DIR,
39
+ managedBinName: "qodercli",
40
+ windowsShimName: "qodercli.cmd",
41
+ unixCandidates: [
42
+ path.join(os.homedir(), ".local", "bin", "qodercli"),
43
+ path.join(os.homedir(), ".qoder", "bin", "qodercli", "qodercli"),
44
+ ],
45
+ },
46
+ qodercn: {
47
+ displayName: "Qoder CLI CN",
48
+ executable: "qodercn",
49
+ envVar: "AUTOWONDER_QODERCN_CLI",
50
+ npmPackage: "@qodercn-ai/qoderclicn@latest",
51
+ managedDir: MANAGED_QODERCN_DIR,
52
+ managedBinName: "qodercn",
53
+ windowsShimName: "qodercn.cmd",
54
+ unixCandidates: [
55
+ path.join(os.homedir(), ".local", "bin", "qodercn"),
56
+ ],
57
+ },
58
+ };
59
+
60
+ function profileForExecutable(name) {
61
+ return Object.values(QODER_FAMILY_PROFILES).find((profile) => profile.executable === name) || null;
62
+ }
63
+
64
+ function isQoderFamilyProvider(provider) {
65
+ return provider === "qoder" || provider === "qodercn";
66
+ }
27
67
 
28
68
  const BINARY_BASE_URL = process.env.AUTOWONDER_BINARY_URL || "";
29
69
  const SOURCE_REPO = process.env.AUTOWONDER_SOURCE_REPO || "";
@@ -59,8 +99,9 @@ function detectProvider() {
59
99
  }
60
100
 
61
101
  function findExecutable(name) {
62
- if (name === "qodercli" && process.env.AUTOWONDER_QODER_CLI) {
63
- const configured = resolveUserPath(process.env.AUTOWONDER_QODER_CLI);
102
+ const profile = profileForExecutable(name);
103
+ if (profile && process.env[profile.envVar]) {
104
+ const configured = resolveUserPath(process.env[profile.envVar]);
64
105
  try { fs.accessSync(configured, fs.constants.X_OK); return configured; } catch {}
65
106
  }
66
107
  const finder = process.platform === "win32" ? "where" : "which";
@@ -69,17 +110,17 @@ function findExecutable(name) {
69
110
  const first = (found.stdout || "").split(/\r?\n/).map((value) => value.trim()).find(Boolean);
70
111
  if (first) return first;
71
112
  }
72
- if (name === "qodercli" && process.platform !== "win32") {
73
- for (const candidate of [
74
- path.join(MANAGED_QODER_DIR, "node_modules", ".bin", "qodercli"),
75
- path.join(os.homedir(), ".local", "bin", "qodercli"),
76
- path.join(os.homedir(), ".qoder", "bin", "qodercli", "qodercli"),
77
- ]) {
113
+ if (profile && process.platform !== "win32") {
114
+ const candidates = [
115
+ path.join(profile.managedDir, "node_modules", ".bin", profile.managedBinName),
116
+ ...profile.unixCandidates,
117
+ ];
118
+ for (const candidate of candidates) {
78
119
  try { fs.accessSync(candidate, fs.constants.X_OK); return candidate; } catch {}
79
120
  }
80
121
  }
81
- if (name === "qodercli" && process.platform === "win32") {
82
- const candidate = path.join(MANAGED_QODER_DIR, "node_modules", ".bin", "qodercli.cmd");
122
+ if (profile && process.platform === "win32") {
123
+ const candidate = path.join(profile.managedDir, "node_modules", ".bin", profile.windowsShimName);
83
124
  try { fs.accessSync(candidate, fs.constants.F_OK); return candidate; } catch {}
84
125
  }
85
126
  return "";
@@ -100,10 +141,11 @@ function qoderAuthenticated(executable) {
100
141
  return result.status === 0 && Boolean((result.stdout || "").trim());
101
142
  }
102
143
 
103
- function installQoderCLI() {
104
- log("Qoder CLI is not installed. Installing @qoder-ai/qodercli...");
144
+ function installQoderCLI(provider) {
145
+ const profile = QODER_FAMILY_PROFILES[provider];
146
+ log(`${profile.displayName} is not installed. Installing ${profile.npmPackage}...`);
105
147
  const args = [
106
- "install", "--prefix", MANAGED_QODER_DIR, "@qoder-ai/qodercli@latest", "--no-audit", "--no-fund",
148
+ "install", "--prefix", profile.managedDir, profile.npmPackage, "--no-audit", "--no-fund",
107
149
  ];
108
150
  // npm is a .cmd shim on Windows. When launched by npx, npm_execpath points
109
151
  // at npm-cli.js, which Node can execute directly without cmd.exe quoting.
@@ -112,16 +154,16 @@ function installQoderCLI() {
112
154
  : spawnSync("npm", npmArgs, { stdio: "inherit" });
113
155
  let result = runNpm(args);
114
156
  if (result.status !== 0 && IS_WIN32) {
115
- log("Default npm registry failed; retrying Qoder CLI installation with npmmirror...");
157
+ log(`Default npm registry failed; retrying ${profile.displayName} installation with npmmirror...`);
116
158
  result = runNpm([...args, "--registry", "https://registry.npmmirror.com"]);
117
159
  }
118
160
  if (result.status !== 0) {
119
161
  const detail = result.error?.message || (result.signal ? `signal ${result.signal}` : `exit status ${result.status}`);
120
- error(`Failed to install Qoder CLI into ${MANAGED_QODER_DIR}: ${detail}`);
162
+ error(`Failed to install ${profile.displayName} into ${profile.managedDir}: ${detail}`);
121
163
  return "";
122
164
  }
123
- const executable = findExecutable("qodercli");
124
- if (!executable) error("Qoder CLI was installed but qodercli is not available on PATH.");
165
+ const executable = findExecutable(profile.executable);
166
+ if (!executable) error(`${profile.displayName} was installed but ${profile.executable} is not available on PATH.`);
125
167
  return executable;
126
168
  }
127
169
 
@@ -166,19 +208,20 @@ function qoderLoginCommand(executable) {
166
208
  return IS_WIN32 ? `& ${quoted} login` : `${quoted} login`;
167
209
  }
168
210
 
169
- async function ensureQoderReady() {
211
+ async function ensureQoderReady(provider) {
170
212
  if (process.env.AUTOWONDER_SKIP_QODER_BOOTSTRAP === "1") return true;
213
+ const profile = QODER_FAMILY_PROFILES[provider];
171
214
  const nodeVersion = qoderNodeVersion();
172
215
  const nodeMajor = Number.parseInt(nodeVersion.split(".")[0], 10);
173
216
  if (!Number.isInteger(nodeMajor) || nodeMajor < 20) {
174
- error(`Qoder CLI requires Node.js 20 or newer; current version is ${nodeVersion}. Upgrade Node.js and retry.`);
217
+ error(`${profile.displayName} requires Node.js 20 or newer; current version is ${nodeVersion}. Upgrade Node.js and retry.`);
175
218
  return false;
176
219
  }
177
- let executable = findExecutable("qodercli");
178
- if (!executable) executable = installQoderCLI();
220
+ let executable = findExecutable(profile.executable);
221
+ if (!executable) executable = installQoderCLI(provider);
179
222
  if (!executable) return false;
180
223
  if (!qoderAuthenticated(executable)) {
181
- log("Qoder login is required. Opening browser login...");
224
+ log(`${profile.displayName} login is required. Opening browser login...`);
182
225
  const login = spawnQoderSync(executable, ["login"], { stdio: "inherit" });
183
226
  if (login.status !== 0) {
184
227
  const detail = login.error?.message || `exit status ${login.status}`;
@@ -191,13 +234,13 @@ async function ensureQoderReady() {
191
234
  return false;
192
235
  }
193
236
  }
194
- process.env.AUTOWONDER_QODER_CLI = executable;
237
+ process.env[profile.envVar] = executable;
195
238
  const executableDir = path.dirname(executable);
196
239
  const pathEntries = (process.env.PATH || "").split(path.delimiter);
197
240
  if (!pathEntries.includes(executableDir)) {
198
241
  process.env.PATH = `${executableDir}${path.delimiter}${process.env.PATH || ""}`;
199
242
  }
200
- log("Qoder CLI is installed and authenticated.");
243
+ log(`${profile.displayName} is installed and authenticated.`);
201
244
  return true;
202
245
  }
203
246
 
@@ -483,12 +526,12 @@ async function cmdConnect(args) {
483
526
  const flags = parseFlags(args, ["ws-url", "token", "executor-id", "provider", "name", "max-tasks", "model", "reasoning-effort", "context-window", "memory-mode", "settings"]);
484
527
 
485
528
  if (!flags["ws-url"] || !flags.token || !flags["executor-id"]) {
486
- error("Usage: autowonder connect --ws-url <url> --token <token> --executor-id <id> [--provider qoder]");
529
+ error("Usage: autowonder connect --ws-url <url> --token <token> --executor-id <id> [--provider qoder|qodercn]");
487
530
  process.exit(1);
488
531
  }
489
532
 
490
533
  const requestedProvider = flags.provider;
491
- if (requestedProvider === "qoder" && !validateQoderOptions(flags)) process.exit(1);
534
+ if (isQoderFamilyProvider(requestedProvider) && !validateQoderOptions(flags)) process.exit(1);
492
535
 
493
536
  const providers = detectProvider();
494
537
  const provider = requestedProvider || providers[0];
@@ -496,7 +539,7 @@ async function cmdConnect(args) {
496
539
  error(`No agent CLI detected. Install one of: claude, codex, qodercli`);
497
540
  process.exit(1);
498
541
  }
499
- if (provider === "qoder" && !(await ensureQoderReady())) process.exit(1);
542
+ if (isQoderFamilyProvider(provider) && !(await ensureQoderReady(provider))) process.exit(1);
500
543
 
501
544
  // A version-pinned npx command must always run the binary bundled with that package.
502
545
  // Windows locks a running .exe. Its versioned path is immutable, so another
@@ -505,15 +548,15 @@ async function cmdConnect(args) {
505
548
  if (!installed) process.exit(1);
506
549
 
507
550
  const hasProviderSettings = Boolean(flags.model || flags["reasoning-effort"]);
508
- if (hasProviderSettings && provider !== "codex" && provider !== "qoder") {
509
- error("--model and --reasoning-effort are supported only for codex and qoder");
551
+ if (hasProviderSettings && provider !== "codex" && !isQoderFamilyProvider(provider)) {
552
+ error("--model and --reasoning-effort are supported only for codex, qoder and qodercn");
510
553
  process.exit(1);
511
554
  }
512
- if (flags["context-window"] && provider !== "qoder") {
513
- error("--context-window is supported only for qoder");
555
+ if (flags["context-window"] && !isQoderFamilyProvider(provider)) {
556
+ error("--context-window is supported only for qoder and qodercn");
514
557
  process.exit(1);
515
558
  }
516
- if (provider === "qoder" && !validateQoderOptions(flags)) process.exit(1);
559
+ if (isQoderFamilyProvider(provider) && !validateQoderOptions(flags)) process.exit(1);
517
560
  let claudeSettingsPath = "";
518
561
  if (flags.settings) {
519
562
  if (provider !== "claude") {
@@ -788,7 +831,7 @@ function cmdHelp() {
788
831
  autowonder install [--force] Install/update and start daemon
789
832
 
790
833
  Options:
791
- --provider <name> Agent provider: claude, codex, qoder (default: auto-detect)
834
+ --provider <name> Agent provider: claude, codex, qoder, qodercn (default: auto-detect; qodercn must be explicit)
792
835
  --max-tasks <n> Max concurrent dispatches (default: 10)
793
836
  --addr <host:port> Local API address (default: 127.0.0.1:34989)
794
837
  --ws-url <url> Executor WebSocket endpoint
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "autowonder",
3
- "version": "0.2.129",
3
+ "version": "0.2.131",
4
4
  "description": "AutoWonder local runtime — execute AI agent dispatch packages on your machine",
5
5
  "bin": {
6
6
  "autowonder": "bin/cli.js"