@i14ks/ccv 0.24.1 → 0.25.0

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 (27) hide show
  1. package/README.md +2 -10
  2. package/bundle/ccv.mjs +139 -1033
  3. package/package.json +50 -53
  4. package/web/assets/{codemirror-CVe_WI3e.js → codemirror-BdKpW4CC.js} +1 -1
  5. package/web/assets/{index-EFEGjfDS.js → index-B2BGvdag.js} +1 -1
  6. package/web/assets/index-BCLbqlhA.js +134 -0
  7. package/web/assets/{index-COgGuYuk.js → index-BrkwvvWk.js} +1 -1
  8. package/web/assets/{index-BvJsiicf.js → index-BroMLvyS.js} +1 -1
  9. package/web/assets/{index-zhxDV4zv.js → index-C59b0_Vk.js} +1 -1
  10. package/web/assets/{index--b7aPip2.css → index-C6Y6TadO.css} +1 -1
  11. package/web/assets/{index-CaQnLaP1.js → index-CRsndRFc.js} +1 -1
  12. package/web/assets/{index-dESUNfha.js → index-CWTFMuFd.js} +1 -1
  13. package/web/assets/{index-BENS1Et2.js → index-CZuUjzhP.js} +1 -1
  14. package/web/assets/{index-DaeDM5ye.js → index-ChyP1fTD.js} +1 -1
  15. package/web/assets/{index-DVlOSKL1.js → index-D6DYiY6f.js} +1 -1
  16. package/web/assets/{index-BVTKBCk1.js → index-D83he8x-.js} +1 -1
  17. package/web/assets/{index-CQpgnjUL.js → index-DPrfFlZq.js} +1 -1
  18. package/web/assets/{index-ChH2BaGk.js → index-DXHZO0ym.js} +1 -1
  19. package/web/assets/{index-BTat2cjy.js → index-Dd7rh20x.js} +1 -1
  20. package/web/assets/{index-Bt4DUbpM.js → index-DqnCWDLh.js} +1 -1
  21. package/web/assets/{index-ClcgV2Ok.js → index-Si6no75_.js} +1 -1
  22. package/web/assets/{index-BS_AsIEi.js → index-UxKgaDrj.js} +1 -1
  23. package/web/assets/{index-CdS9TWKz.js → index-YCUybqa_.js} +1 -1
  24. package/web/assets/{index-BnDGCTVR.js → index-wsSNo9PM.js} +1 -1
  25. package/web/assets/{index-D3s6YlZz.js → index-yXtesgZ4.js} +1 -1
  26. package/web/index.html +2 -2
  27. package/web/assets/index-BfpRxrlX.js +0 -136
package/bundle/ccv.mjs CHANGED
@@ -1,9 +1,9 @@
1
1
  #!/usr/bin/env node
2
2
 
3
3
  // dist/ccv.js
4
- import { spawn as spawn4 } from "node:child_process";
4
+ import { spawn as spawn3 } from "node:child_process";
5
5
  import { readFile as readFile17 } from "node:fs/promises";
6
- import path25 from "node:path";
6
+ import path24 from "node:path";
7
7
  import { fileURLToPath } from "node:url";
8
8
  import { parseArgs } from "node:util";
9
9
 
@@ -145,10 +145,10 @@ function envDefaults() {
145
145
 
146
146
  // ../host/dist/server.js
147
147
  import { createServer } from "node:http";
148
- import { createReadStream, existsSync as existsSync5, statSync as statSync4 } from "node:fs";
149
- import path24 from "node:path";
150
- import { homedir as homedir7 } from "node:os";
151
- import { randomUUID as randomUUID6 } from "node:crypto";
148
+ import { createReadStream, existsSync as existsSync4, statSync as statSync3 } from "node:fs";
149
+ import path23 from "node:path";
150
+ import { homedir as homedir6 } from "node:os";
151
+ import { randomUUID as randomUUID5 } from "node:crypto";
152
152
  import { WebSocketServer } from "ws";
153
153
  import { renameSession as renameSession2 } from "@anthropic-ai/claude-agent-sdk";
154
154
 
@@ -187,12 +187,12 @@ function hashText(text) {
187
187
  // ../host/dist/workspace-ids.js
188
188
  function workspaceIdRemap(paths, sessionsOf) {
189
189
  const byLegacy = /* @__PURE__ */ new Map();
190
- for (const path26 of paths) {
191
- const id = workspaceIdFromPath(path26);
192
- for (const legacy of formerWorkspaceIdsFromPath(path26)) {
190
+ for (const path25 of paths) {
191
+ const id = workspaceIdFromPath(path25);
192
+ for (const legacy of formerWorkspaceIdsFromPath(path25)) {
193
193
  const group = byLegacy.get(legacy) ?? [];
194
194
  if (!group.some((target) => target.id === id))
195
- group.push({ id, path: path26 });
195
+ group.push({ id, path: path25 });
196
196
  byLegacy.set(legacy, group);
197
197
  }
198
198
  }
@@ -4217,865 +4217,18 @@ function describe2(error) {
4217
4217
  return error instanceof Error ? error.message : String(error);
4218
4218
  }
4219
4219
 
4220
- // ../host/dist/codex-session.js
4221
- import { EventEmitter as EventEmitter5 } from "node:events";
4222
- import { randomUUID as randomUUID3 } from "node:crypto";
4223
-
4224
- // ../host/dist/codex-cli.js
4225
- import { accessSync, constants as constants2, existsSync as existsSync2, readFileSync, statSync } from "node:fs";
4226
- import { homedir as homedir4 } from "node:os";
4227
- import path8 from "node:path";
4228
- var CODEX_MISSING_HINT = "Codex CLI \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D. \u0423\u0441\u0442\u0430\u043D\u043E\u0432\u0438\u0442\u0435: npm install -g @openai/codex, \u0437\u0430\u0442\u0435\u043C \u0432\u044B\u043F\u043E\u043B\u043D\u0438\u0442\u0435 codex login. \u0415\u0441\u043B\u0438 CLI \u0443\u0436\u0435 \u0443\u0441\u0442\u0430\u043D\u043E\u0432\u043B\u0435\u043D, \u0437\u0430\u0434\u0430\u0439\u0442\u0435 CCV_CODEX_PATH \u0438 \u043F\u0435\u0440\u0435\u0437\u0430\u043F\u0443\u0441\u0442\u0438\u0442\u0435 ccv.";
4229
- function codexLauncher() {
4230
- const forced = process.env.CCV_CODEX_PATH;
4231
- if (forced)
4232
- return launcherFor(path8.resolve(forced));
4233
- const dirs = (process.env.PATH ?? "").split(path8.delimiter).filter(Boolean);
4234
- if (process.platform === "win32") {
4235
- const local = process.env.LOCALAPPDATA ?? path8.join(homedir4(), "AppData", "Local");
4236
- dirs.push(path8.join(local, "Programs", "OpenAI", "Codex", "bin"));
4237
- dirs.push(path8.join(process.env.APPDATA ?? path8.join(homedir4(), "AppData", "Roaming"), "npm"));
4238
- } else {
4239
- dirs.push(path8.join(homedir4(), ".local", "bin"), "/usr/local/bin", "/opt/homebrew/bin");
4240
- }
4241
- for (const dir of dirs) {
4242
- for (const name of process.platform === "win32" ? ["codex.exe", "codex.cmd", "codex"] : ["codex"]) {
4243
- const found = launcherFor(path8.join(dir.replace(/^"|"$/g, ""), name));
4244
- if (found)
4245
- return found;
4246
- }
4247
- }
4248
- return null;
4249
- }
4250
- function launcherFor(file) {
4251
- try {
4252
- if (!statSync(file).isFile())
4253
- return null;
4254
- if (/\.[cm]?js$/i.test(file))
4255
- return { file: process.execPath, prefix: [file] };
4256
- if (process.platform === "win32" && /\.(cmd|bat|ps1)$/i.test(file)) {
4257
- const root = path8.dirname(file);
4258
- const candidates = [path8.join(root, "node_modules", "@openai", "codex", "bin", "codex.js")];
4259
- const shim = readFileSync(file, "utf8");
4260
- for (const match of shim.matchAll(/(?:%dp0%|%~dp0|\$basedir)[\\/]([^"\r\n]+?\.[cm]?js)/gi)) {
4261
- candidates.push(path8.resolve(root, match[1]));
4262
- }
4263
- const script = candidates.find((candidate) => existsSync2(candidate));
4264
- return script ? { file: process.execPath, prefix: [script] } : null;
4265
- }
4266
- if (process.platform === "win32" && !/\.exe$/i.test(file))
4267
- return null;
4268
- accessSync(file, constants2.X_OK);
4269
- return { file, prefix: [] };
4270
- } catch {
4271
- return null;
4272
- }
4273
- }
4274
-
4275
- // ../host/dist/codex-rpc.js
4276
- import { EventEmitter as EventEmitter4 } from "node:events";
4277
- import { execFile as execFile4, spawn as spawn3 } from "node:child_process";
4278
- import { createInterface as createInterface2 } from "node:readline";
4279
- var CodexRpc = class extends EventEmitter4 {
4280
- #child;
4281
- #pending = /* @__PURE__ */ new Map();
4282
- #nextId = 0;
4283
- #closed = false;
4284
- #stderr = "";
4285
- constructor(launcher, cwd) {
4286
- super();
4287
- this.#child = spawn3(launcher.file, [...launcher.prefix, "app-server", "--listen", "stdio://"], {
4288
- cwd,
4289
- windowsHide: true,
4290
- stdio: ["pipe", "pipe", "pipe"],
4291
- env: { ...process.env, NO_COLOR: "1" }
4292
- });
4293
- createInterface2({ input: this.#child.stdout }).on("line", (line) => {
4294
- let message;
4295
- try {
4296
- message = JSON.parse(line);
4297
- } catch {
4298
- return;
4299
- }
4300
- if (!message || typeof message !== "object")
4301
- return;
4302
- if (message.method) {
4303
- this.emit("message", message);
4304
- return;
4305
- }
4306
- const pending = typeof message.id === "number" ? this.#pending.get(message.id) : void 0;
4307
- if (!pending)
4308
- return;
4309
- this.#pending.delete(message.id);
4310
- clearTimeout(pending.timer);
4311
- if (message.error)
4312
- pending.reject(new Error(message.error.message));
4313
- else
4314
- pending.resolve(message.result);
4315
- });
4316
- this.#child.stderr.on("data", (chunk) => {
4317
- this.#stderr = (this.#stderr + chunk.toString()).slice(-4e3);
4318
- this.emit("stderr", chunk.toString());
4319
- });
4320
- this.#child.stdin.on("error", (error) => this.#finish(error));
4321
- this.#child.on("error", (error) => this.#finish(error));
4322
- this.#child.on("exit", (code) => this.#finish(new Error(`Codex \u0437\u0430\u0432\u0435\u0440\u0448\u0438\u043B\u0441\u044F (${code ?? "signal"}). ${this.#stderr.trim()}`)));
4323
- }
4324
- request(method, params = {}) {
4325
- if (this.#closed)
4326
- return Promise.reject(new Error("\u0421\u043E\u0435\u0434\u0438\u043D\u0435\u043D\u0438\u0435 \u0441 Codex \u0437\u0430\u043A\u0440\u044B\u0442\u043E"));
4327
- const id = ++this.#nextId;
4328
- return new Promise((resolve, reject) => {
4329
- const timer = setTimeout(() => {
4330
- this.#pending.delete(id);
4331
- reject(new Error(`Codex \u043D\u0435 \u043E\u0442\u0432\u0435\u0442\u0438\u043B \u043D\u0430 ${method} \u0437\u0430 60 \u0441\u0435\u043A\u0443\u043D\u0434`));
4332
- }, 6e4);
4333
- this.#pending.set(id, { resolve: (value) => resolve(value), reject, timer });
4334
- this.write({ id, method, params });
4335
- });
4336
- }
4337
- write(message) {
4338
- if (!this.#closed)
4339
- this.#child.stdin.write(JSON.stringify(message) + "\n");
4340
- }
4341
- close() {
4342
- this.#finish(new Error("\u0421\u043E\u0435\u0434\u0438\u043D\u0435\u043D\u0438\u0435 \u0441 Codex \u0437\u0430\u043A\u0440\u044B\u0442\u043E"), false);
4343
- this.#child.stdin.end();
4344
- const child = this.#child;
4345
- if (child.exitCode !== null)
4346
- return;
4347
- if (process.platform === "win32" && child.pid) {
4348
- execFile4("taskkill", ["/pid", String(child.pid), "/T", "/F"], { windowsHide: true }, () => {
4349
- if (child.exitCode === null)
4350
- child.kill();
4351
- });
4352
- } else
4353
- child.kill("SIGTERM");
4354
- }
4355
- #finish(error, notify = true) {
4356
- if (this.#closed)
4357
- return;
4358
- this.#closed = true;
4359
- for (const pending of this.#pending.values()) {
4360
- clearTimeout(pending.timer);
4361
- pending.reject(error);
4362
- }
4363
- this.#pending.clear();
4364
- if (notify)
4365
- this.emit("exit", error);
4366
- }
4367
- };
4368
-
4369
- // ../host/dist/codex-session.js
4370
- function codexPolicy(mode) {
4371
- switch (mode) {
4372
- case "default":
4373
- return { approvalPolicy: "untrusted", sandbox: "workspace-write" };
4374
- case "acceptEdits":
4375
- return { approvalPolicy: "on-request", sandbox: "workspace-write" };
4376
- case "plan":
4377
- return { approvalPolicy: "untrusted", sandbox: "read-only" };
4378
- case "bypassPermissions":
4379
- return { approvalPolicy: "never", sandbox: "danger-full-access" };
4380
- default:
4381
- throw new Error(`Codex \u043D\u0435 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442 \u0440\u0435\u0436\u0438\u043C \u043F\u0440\u0430\u0432 \xAB${mode}\xBB`);
4382
- }
4383
- }
4384
- function codexUsage(limits) {
4385
- const window = (value) => value ? {
4386
- utilization: Math.min(100, Math.max(0, value.usedPercent)),
4387
- resetsAt: value.resetsAt ? new Date(value.resetsAt * 1e3).toISOString() : ""
4388
- } : null;
4389
- return {
4390
- available: !!(limits.primary || limits.secondary),
4391
- plan: limits.planType ?? "",
4392
- fiveHour: window(limits.primary),
4393
- sevenDay: window(limits.secondary),
4394
- sevenDayOpus: null,
4395
- fetchedAt: Date.now()
4396
- };
4397
- }
4398
- var CodexSession = class extends EventEmitter5 {
4399
- provider = "codex";
4400
- id;
4401
- workspaceId;
4402
- cwd;
4403
- journal = new Journal();
4404
- #store;
4405
- #record;
4406
- #history = Promise.resolve([]);
4407
- #rpc = null;
4408
- #ready = Promise.resolve();
4409
- #state = "starting";
4410
- #lastTurn = null;
4411
- #capabilities = null;
4412
- #usage = null;
4413
- #context = null;
4414
- #turnId = null;
4415
- #turnStartedAt = 0;
4416
- #turnUsage = null;
4417
- #totalUsage = null;
4418
- #turnUsageBaseline = null;
4419
- #interruptRequested = false;
4420
- #busy = false;
4421
- #startingTurn = false;
4422
- #generation = 0;
4423
- #queue = [];
4424
- #pending = /* @__PURE__ */ new Map();
4425
- #texts = /* @__PURE__ */ new Map();
4426
- #tools = /* @__PURE__ */ new Set();
4427
- #items = /* @__PURE__ */ new Map();
4428
- #titleIsDefault;
4429
- #unsaved = [];
4430
- #flushTimer = null;
4431
- constructor(options2) {
4432
- super();
4433
- this.workspaceId = options2.workspaceId;
4434
- this.cwd = options2.cwd;
4435
- this.#store = options2.store;
4436
- this.#record = options2.record ? { ...options2.record } : {
4437
- id: randomUUID3(),
4438
- conversationId: null,
4439
- workspaceId: options2.workspaceId,
4440
- cwd: options2.cwd,
4441
- title: options2.defaultTitle ?? null,
4442
- model: options2.model ?? null,
4443
- permissionMode: options2.permissionMode ?? "default",
4444
- effort: null,
4445
- createdAt: Date.now(),
4446
- updatedAt: Date.now()
4447
- };
4448
- if (options2.permissionMode)
4449
- this.#record.permissionMode = options2.permissionMode;
4450
- if (options2.model)
4451
- this.#record.model = options2.model;
4452
- this.id = this.#record.id;
4453
- this.#context = this.#record.context ?? null;
4454
- if (!options2.record?.conversationId) {
4455
- this.#totalUsage = { inputTokens: 0, outputTokens: 0, cacheReadTokens: 0, cacheCreationTokens: 0 };
4456
- }
4457
- this.#titleIsDefault = !options2.record;
4458
- }
4459
- get state() {
4460
- return this.#state;
4461
- }
4462
- get capabilities() {
4463
- return this.#capabilities;
4464
- }
4465
- get claudeSessionId() {
4466
- return this.id;
4467
- }
4468
- get parentSessionId() {
4469
- return null;
4470
- }
4471
- get usage() {
4472
- return this.#usage;
4473
- }
4474
- get context() {
4475
- return this.#context;
4476
- }
4477
- history() {
4478
- return this.#history;
4479
- }
4480
- summary() {
4481
- return {
4482
- id: this.id,
4483
- provider: this.provider,
4484
- claudeSessionId: this.id,
4485
- workspaceId: this.workspaceId,
4486
- cwd: this.cwd,
4487
- parentSessionId: null,
4488
- title: this.#record.title,
4489
- state: this.#state,
4490
- lastTurn: this.#lastTurn,
4491
- backgroundWork: false,
4492
- tasks: [],
4493
- model: this.#record.model,
4494
- permissionMode: this.#record.permissionMode,
4495
- effort: this.#record.effort,
4496
- ultracode: false,
4497
- thinking: true,
4498
- switchModelsOnFlag: false,
4499
- createdAt: this.#record.createdAt,
4500
- updatedAt: this.#record.updatedAt,
4501
- lastSeq: this.journal.lastSeq,
4502
- totalCostUsd: 0
4503
- };
4504
- }
4505
- start() {
4506
- this.#history = this.#store.readEvents(this.id).then((entries) => {
4507
- const pending = /* @__PURE__ */ new Set();
4508
- for (const { event } of entries) {
4509
- if (event.kind === "permission.request")
4510
- pending.add(event.requestId);
4511
- if (event.kind === "permission.resolved")
4512
- pending.delete(event.requestId);
4513
- }
4514
- for (const requestId of pending)
4515
- entries.push({ seq: entries.length + 1, ts: Date.now(), event: {
4516
- kind: "permission.resolved",
4517
- requestId,
4518
- decision: "deny",
4519
- reason: "\u041F\u0440\u0435\u0434\u044B\u0434\u0443\u0449\u0438\u0439 \u043F\u0440\u043E\u0446\u0435\u0441\u0441 Codex \u0437\u0430\u0432\u0435\u0440\u0448\u0451\u043D"
4520
- } });
4521
- return entries;
4522
- });
4523
- this.#launch();
4524
- }
4525
- #launch() {
4526
- const generation = ++this.#generation;
4527
- this.#ready = this.#connect(generation);
4528
- void this.#ready.catch((error) => {
4529
- if (generation === this.#generation)
4530
- this.#fail(error);
4531
- });
4532
- }
4533
- async #connect(generation) {
4534
- await this.#history;
4535
- await this.#store.save(this.#record);
4536
- if (generation !== this.#generation)
4537
- return;
4538
- const reason = networkGuard.blockedReason();
4539
- if (reason)
4540
- throw new Error(reason);
4541
- const launcher = codexLauncher();
4542
- if (!launcher)
4543
- throw new Error(CODEX_MISSING_HINT);
4544
- const rpc = new CodexRpc(launcher, this.cwd);
4545
- this.#rpc = rpc;
4546
- rpc.on("message", (message) => {
4547
- if (this.#rpc === rpc)
4548
- this.#message(message);
4549
- });
4550
- rpc.on("stderr", (data) => this.emit("stderr", data));
4551
- rpc.on("exit", (error) => {
4552
- if (this.#rpc === rpc)
4553
- this.#fail(error);
4554
- });
4555
- await rpc.request("initialize", { clientInfo: { name: "ccv", title: "Claude Code Visual", version: "0.1.0" } });
4556
- if (this.#rpc !== rpc)
4557
- return;
4558
- rpc.write({ method: "initialized", params: {} });
4559
- const policy = codexPolicy(this.#record.permissionMode);
4560
- const result = await rpc.request(this.#record.conversationId ? "thread/resume" : "thread/start", {
4561
- ...this.#record.conversationId ? { threadId: this.#record.conversationId } : {},
4562
- cwd: this.cwd,
4563
- ...this.#record.model ? { model: this.#record.model } : {},
4564
- approvalPolicy: policy.approvalPolicy,
4565
- sandbox: policy.sandbox
4566
- });
4567
- if (this.#rpc !== rpc)
4568
- return;
4569
- this.#record.conversationId = result.thread.id;
4570
- this.#record.model = result.model;
4571
- if (!this.#record.effort && result.reasoningEffort)
4572
- this.#record.effort = result.reasoningEffort;
4573
- await this.#store.save(this.#record);
4574
- if (this.#rpc !== rpc)
4575
- return;
4576
- this.#capabilities = {
4577
- cwd: this.cwd,
4578
- model: result.model,
4579
- permissionMode: this.#record.permissionMode,
4580
- slashCommands: [],
4581
- commands: [],
4582
- models: [],
4583
- tools: ["Bash", "apply_patch", "web_search"],
4584
- agents: [],
4585
- mcpServers: [],
4586
- flags: []
4587
- };
4588
- this.emit("capabilities");
4589
- this.#setState("idle");
4590
- void this.#loadModels(rpc).catch((error) => {
4591
- if (this.#rpc === rpc)
4592
- this.#notice(error);
4593
- });
4594
- void this.refreshUsage();
4595
- }
4596
- async #loadModels(rpc) {
4597
- const models = [];
4598
- let cursor = null;
4599
- do {
4600
- const page = await rpc.request("model/list", { cursor, limit: 100 });
4601
- for (const model of page.data) {
4602
- const levels = (model.supportedReasoningEfforts ?? []).map((e) => e.reasoningEffort).filter((e) => ["low", "medium", "high", "xhigh", "max"].includes(e));
4603
- models.push({
4604
- value: model.model,
4605
- resolvedModel: model.model,
4606
- displayName: model.displayName,
4607
- description: model.description,
4608
- supportsEffort: levels.length > 0,
4609
- effortLevels: levels,
4610
- supportsThinking: false,
4611
- supportsAutoMode: false
4612
- });
4613
- }
4614
- cursor = page.nextCursor;
4615
- } while (cursor && this.#rpc === rpc);
4616
- if (this.#capabilities && this.#rpc === rpc) {
4617
- this.#capabilities.models = models;
4618
- this.emit("capabilities");
4619
- }
4620
- }
4621
- sendPrompt(text, images) {
4622
- const reason = networkGuard.blockedReason();
4623
- if (reason) {
4624
- this.#notice(new Error(reason));
4625
- return;
4626
- }
4627
- if (this.#state === "closed" || this.#state === "error") {
4628
- this.#notice(new Error("\u041F\u0435\u0440\u0435\u043F\u043E\u0434\u043A\u043B\u044E\u0447\u0438\u0442\u0435 \u0441\u0435\u0441\u0441\u0438\u044E Codex \u043F\u0435\u0440\u0435\u0434 \u043E\u0442\u043F\u0440\u0430\u0432\u043A\u043E\u0439"));
4629
- return;
4630
- }
4631
- if (!text.trim() && !images?.length)
4632
- return;
4633
- this.#append({ kind: "user.message", text, ...images?.length ? { images } : {} });
4634
- if (this.#titleIsDefault) {
4635
- this.#record.title = text.trim().split("\n")[0].slice(0, 100) || "Codex";
4636
- this.#titleIsDefault = false;
4637
- this.emit("summary", this.summary());
4638
- }
4639
- this.#queue.push({ text, images });
4640
- void this.#drain();
4641
- }
4642
- async #drain() {
4643
- if (this.#busy || this.#startingTurn || !this.#queue.length)
4644
- return;
4645
- const generation = this.#generation;
4646
- this.#busy = true;
4647
- this.#startingTurn = true;
4648
- try {
4649
- await this.#ready;
4650
- if (generation !== this.#generation)
4651
- return;
4652
- const prompt = this.#queue.shift();
4653
- if (!prompt || !this.#rpc || this.#state === "closed" || this.#state === "error") {
4654
- this.#busy = false;
4655
- return;
4656
- }
4657
- const reason = networkGuard.blockedReason();
4658
- if (reason)
4659
- throw new Error(reason);
4660
- this.#turnStartedAt = Date.now();
4661
- this.#turnUsage = null;
4662
- this.#turnUsageBaseline = this.#totalUsage;
4663
- this.#lastTurn = null;
4664
- this.#setState("running");
4665
- const policy = codexPolicy(this.#record.permissionMode);
4666
- const sandboxPolicy = this.#record.permissionMode === "bypassPermissions" ? { type: "dangerFullAccess" } : this.#record.permissionMode === "plan" ? { type: "readOnly", networkAccess: false } : {
4667
- type: "workspaceWrite",
4668
- writableRoots: [this.cwd],
4669
- networkAccess: false,
4670
- excludeTmpdirEnvVar: false,
4671
- excludeSlashTmp: false
4672
- };
4673
- const result = await this.#rpc.request("turn/start", {
4674
- threadId: this.#record.conversationId,
4675
- cwd: this.cwd,
4676
- input: [{ type: "text", text: prompt.text, text_elements: [] }, ...(prompt.images ?? []).map((image) => ({
4677
- type: "image",
4678
- url: `data:${image.mediaType};base64,${image.data}`
4679
- }))],
4680
- model: this.#record.model,
4681
- effort: this.#record.effort,
4682
- approvalPolicy: policy.approvalPolicy,
4683
- sandboxPolicy
4684
- });
4685
- if (this.#busy)
4686
- this.#turnId = result.turn.id;
4687
- if (this.#interruptRequested && this.#turnId)
4688
- await this.interrupt();
4689
- } catch (error) {
4690
- if (generation === this.#generation)
4691
- this.#fail(error);
4692
- } finally {
4693
- if (generation === this.#generation) {
4694
- this.#startingTurn = false;
4695
- if (!this.#busy)
4696
- void this.#drain();
4697
- }
4698
- }
4699
- }
4700
- #message(message) {
4701
- const p = message.params ?? {};
4702
- if (message.id !== void 0 && message.method) {
4703
- this.#request(message.id, message.method, p);
4704
- return;
4705
- }
4706
- if (p.threadId && p.threadId !== this.#record.conversationId)
4707
- return;
4708
- switch (message.method) {
4709
- case "turn/started": {
4710
- const turn = p.turn;
4711
- this.#turnId = turn.id;
4712
- break;
4713
- }
4714
- case "item/agentMessage/delta":
4715
- case "item/reasoning/summaryTextDelta": {
4716
- const id = String(p.itemId);
4717
- const thinking = message.method !== "item/agentMessage/delta";
4718
- const key = `${id}:${thinking ? "thinking" : "text"}`;
4719
- const delta = String(p.delta ?? "");
4720
- const block = this.#texts.get(key) ?? { text: "", thinking };
4721
- block.text += delta;
4722
- this.#texts.set(key, block);
4723
- this.#append({ kind: thinking ? "thinking.delta" : "assistant.delta", blockId: key, text: delta });
4724
- break;
4725
- }
4726
- case "item/started":
4727
- this.#item(p.item, false);
4728
- break;
4729
- case "item/completed":
4730
- this.#item(p.item, true);
4731
- break;
4732
- case "thread/tokenUsage/updated": {
4733
- const usage = p.tokenUsage;
4734
- if (usage?.last && usage.modelContextWindow) {
4735
- this.#context = { tokens: usage.last.totalTokens, maxTokens: usage.modelContextWindow, fetchedAt: Date.now() };
4736
- this.#record.context = this.#context;
4737
- this.emit("context", this.#context);
4738
- }
4739
- if (usage?.total) {
4740
- const total = {
4741
- inputTokens: usage.total.inputTokens,
4742
- outputTokens: usage.total.outputTokens,
4743
- cacheReadTokens: usage.total.cachedInputTokens ?? 0,
4744
- cacheCreationTokens: usage.total.cacheWriteInputTokens ?? 0
4745
- };
4746
- if (this.#busy && this.#turnUsageBaseline) {
4747
- const baseline = this.#turnUsageBaseline;
4748
- this.#turnUsage = {
4749
- inputTokens: Math.max(0, total.inputTokens - baseline.inputTokens),
4750
- outputTokens: Math.max(0, total.outputTokens - baseline.outputTokens),
4751
- cacheReadTokens: Math.max(0, total.cacheReadTokens - baseline.cacheReadTokens),
4752
- cacheCreationTokens: Math.max(0, total.cacheCreationTokens - baseline.cacheCreationTokens)
4753
- };
4754
- }
4755
- this.#totalUsage = total;
4756
- }
4757
- break;
4758
- }
4759
- case "account/rateLimits/updated":
4760
- if (p.rateLimits)
4761
- this.#setUsage(p.rateLimits);
4762
- break;
4763
- case "serverRequest/resolved": {
4764
- const requestId = String(p.requestId);
4765
- if (this.#pending.delete(requestId)) {
4766
- this.#append({ kind: "permission.resolved", requestId, decision: "deny", reason: "\u0417\u0430\u043F\u0440\u043E\u0441 \u0437\u0430\u043A\u0440\u044B\u0442 Codex" });
4767
- this.#setState(this.#pending.size ? "waiting_permission" : "running");
4768
- }
4769
- break;
4770
- }
4771
- case "turn/completed": {
4772
- const turn = p.turn;
4773
- this.#lastTurn = turn.status === "completed" ? "completed" : turn.status === "interrupted" ? "interrupted" : "failed";
4774
- if (turn.error?.message)
4775
- this.#notice(new Error(turn.error.message));
4776
- this.#finishTurn(turn.status, turn.durationMs);
4777
- void this.refreshUsage();
4778
- break;
4779
- }
4780
- case "error": {
4781
- const error = p.error;
4782
- this.#notice(new Error(error?.message ?? "\u041E\u0448\u0438\u0431\u043A\u0430 Codex"));
4783
- break;
4784
- }
4785
- }
4786
- }
4787
- #item(item, done) {
4788
- if (!item)
4789
- return;
4790
- this.#items.set(item.id, item);
4791
- if (item.type === "agentMessage" || item.type === "reasoning" || item.type === "plan") {
4792
- if (!done)
4793
- return;
4794
- const thinking = item.type === "reasoning";
4795
- const key = `${item.id}:${thinking ? "thinking" : "text"}`;
4796
- const text = item.text ?? item.summary?.join("\n") ?? this.#texts.get(key)?.text ?? "";
4797
- this.#texts.delete(key);
4798
- if (text)
4799
- this.#append({ kind: thinking ? "assistant.thinking" : "assistant.text", text, blockId: key });
4800
- return;
4801
- }
4802
- if (!["commandExecution", "fileChange", "mcpToolCall", "webSearch", "imageView", "collabAgentToolCall"].includes(item.type))
4803
- return;
4804
- if (!this.#tools.has(item.id)) {
4805
- this.#tools.add(item.id);
4806
- const name = item.type === "commandExecution" ? "Bash" : item.type === "fileChange" ? "apply_patch" : item.type === "mcpToolCall" ? `mcp__${item.server}__${item.tool}` : item.type;
4807
- const input = item.type === "commandExecution" ? { command: item.command, cwd: item.cwd } : item.type === "fileChange" ? { changes: item.changes, file_path: item.changes?.[0]?.path } : item.arguments ?? item.action ?? { query: item.query };
4808
- this.#append({ kind: "tool.use", toolUseId: item.id, name, input });
4809
- }
4810
- if (done) {
4811
- this.#tools.delete(item.id);
4812
- const output = item.aggregatedOutput ?? (item.changes ? item.changes.map((c) => `${c.path}
4813
- ${c.diff}`).join("\n") : typeof item.result === "string" ? item.result : JSON.stringify(item.error ?? item.result ?? item.action ?? "\u0413\u043E\u0442\u043E\u0432\u043E"));
4814
- this.#append({
4815
- kind: "tool.result",
4816
- toolUseId: item.id,
4817
- content: output,
4818
- isError: ["failed", "declined"].includes(item.status ?? "") || item.exitCode != null && item.exitCode !== 0 || !!item.error
4819
- });
4820
- }
4821
- }
4822
- #request(id, method, params) {
4823
- const requestId = String(id);
4824
- const questions = method === "item/tool/requestUserInput" ? params.questions.map((q) => ({ ...q, options: q.options ?? [], multiSelect: false })) : void 0;
4825
- const known = [
4826
- "item/commandExecution/requestApproval",
4827
- "item/fileChange/requestApproval",
4828
- "item/permissions/requestApproval",
4829
- "item/tool/requestUserInput"
4830
- ];
4831
- if (!known.includes(method)) {
4832
- this.#rpc?.write({ id, error: { code: -32601, message: `CCV does not support ${method}` } });
4833
- this.#notice(new Error(`Codex \u0437\u0430\u043F\u0440\u043E\u0441\u0438\u043B \u043D\u0435\u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u043C\u043E\u0435 \u0434\u0435\u0439\u0441\u0442\u0432\u0438\u0435: ${method}`));
4834
- return;
4835
- }
4836
- this.#pending.set(requestId, { id, method, params, questions });
4837
- this.#append({
4838
- kind: "permission.request",
4839
- requestId,
4840
- toolUseId: String(params.itemId ?? requestId),
4841
- toolName: questions ? "AskUserQuestion" : method.includes("commandExecution") ? "Bash" : method.includes("fileChange") ? "apply_patch" : "Codex permissions",
4842
- input: { ...params, ...this.#items.get(String(params.itemId))?.changes ? { changes: this.#items.get(String(params.itemId)).changes } : {} },
4843
- ...typeof params.reason === "string" ? { reason: params.reason } : {},
4844
- ...questions ? { questions } : {}
4845
- });
4846
- this.#setState("waiting_permission");
4847
- }
4848
- respondPermission(requestId, decision, reason, answers) {
4849
- const request2 = this.#pending.get(requestId);
4850
- if (!request2)
4851
- return;
4852
- let result = { decision: decision === "allow" ? "accept" : "decline" };
4853
- if (request2.questions) {
4854
- result = { answers: Object.fromEntries(request2.questions.map((q) => [q.id, {
4855
- answers: decision === "allow" ? [answers?.[q.question] ?? ""] : []
4856
- }])) };
4857
- } else if (request2.method === "item/permissions/requestApproval") {
4858
- result = { permissions: decision === "allow" ? request2.params.permissions : {}, scope: "turn" };
4859
- }
4860
- this.#rpc?.write({ id: request2.id, result });
4861
- this.#pending.delete(requestId);
4862
- this.#append({ kind: "permission.resolved", requestId, decision, reason, answers });
4863
- this.#setState(this.#pending.size ? "waiting_permission" : "running");
4864
- }
4865
- async interrupt() {
4866
- this.#queue = [];
4867
- if (!this.#busy)
4868
- return;
4869
- this.#interruptRequested = true;
4870
- if (this.#turnId && this.#rpc) {
4871
- await this.#rpc.request("turn/interrupt", { threadId: this.#record.conversationId, turnId: this.#turnId });
4872
- }
4873
- }
4874
- #finishTurn(subtype, durationMs) {
4875
- for (const [blockId, block] of this.#texts) {
4876
- this.#append({ kind: block.thinking ? "assistant.thinking" : "assistant.text", text: block.text, blockId });
4877
- }
4878
- this.#texts.clear();
4879
- for (const toolUseId of this.#tools) {
4880
- this.#append({ kind: "tool.result", toolUseId, content: "\u0414\u0435\u0439\u0441\u0442\u0432\u0438\u0435 \u043F\u0440\u0435\u0440\u0432\u0430\u043D\u043E", isError: true });
4881
- }
4882
- this.#tools.clear();
4883
- this.#items.clear();
4884
- this.#clearApprovals();
4885
- this.#append({
4886
- kind: "result",
4887
- subtype,
4888
- isError: this.#lastTurn === "failed",
4889
- durationMs: durationMs ?? Math.max(0, Date.now() - this.#turnStartedAt),
4890
- costUsd: null,
4891
- usage: this.#turnUsage,
4892
- contextTokens: this.#context?.tokens ?? null,
4893
- text: null
4894
- });
4895
- this.#busy = false;
4896
- this.#turnId = null;
4897
- this.#interruptRequested = false;
4898
- this.#setState("idle");
4899
- void this.#drain();
4900
- }
4901
- async setPermissionMode(mode) {
4902
- codexPolicy(mode);
4903
- this.#record.permissionMode = mode;
4904
- this.#settingsChanged();
4905
- }
4906
- async setModel(model) {
4907
- this.#record.model = model;
4908
- this.#record.effort = null;
4909
- this.#settingsChanged();
4910
- }
4911
- async setEffort(effort) {
4912
- const model = this.#capabilities?.models.find((m) => m.value === this.#record.model);
4913
- if (model && !model.effortLevels.includes(effort))
4914
- throw new Error("\u041C\u043E\u0434\u0435\u043B\u044C Codex \u043D\u0435 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442 \u044D\u0442\u043E \u0443\u0441\u0438\u043B\u0438\u0435");
4915
- this.#record.effort = effort;
4916
- this.#settingsChanged();
4917
- }
4918
- #settingsChanged() {
4919
- if (this.#capabilities) {
4920
- this.#capabilities.model = this.#record.model ?? "";
4921
- this.#capabilities.permissionMode = this.#record.permissionMode;
4922
- this.emit("capabilities");
4923
- }
4924
- void this.#store.save(this.#record);
4925
- this.emit("summary", this.summary());
4926
- }
4927
- setTitle(title) {
4928
- this.#record.title = title;
4929
- this.#titleIsDefault = false;
4930
- this.#settingsChanged();
4931
- }
4932
- async refreshUsage(_force = false) {
4933
- if (!this.#rpc || networkGuard.blockedReason())
4934
- return;
4935
- try {
4936
- const reply = await this.#rpc.request("account/rateLimits/read");
4937
- this.#setUsage(reply.rateLimits);
4938
- } catch {
4939
- }
4940
- }
4941
- #setUsage(limits) {
4942
- this.#usage = codexUsage(limits);
4943
- this.emit("usage", this.#usage);
4944
- }
4945
- async refreshContext(_force = false) {
4946
- if (this.#context)
4947
- this.emit("context", this.#context);
4948
- }
4949
- reconnect(_reason) {
4950
- this.#disconnect();
4951
- this.#setState("starting");
4952
- this.#launch();
4953
- }
4954
- suspend(reason) {
4955
- this.#disconnect();
4956
- this.#notice(new Error(reason));
4957
- this.#setState("error");
4958
- }
4959
- async close(_reason = "closed by client") {
4960
- this.#disconnect();
4961
- this.#setState("closed");
4962
- await this.#flush();
4963
- }
4964
- #disconnect() {
4965
- this.#generation += 1;
4966
- this.#startingTurn = false;
4967
- const rpc = this.#rpc;
4968
- this.#rpc = null;
4969
- rpc?.close();
4970
- this.#queue = [];
4971
- if (this.#busy) {
4972
- this.#lastTurn = "interrupted";
4973
- this.#finishTurn("interrupted");
4974
- }
4975
- this.#clearApprovals();
4976
- }
4977
- #clearApprovals() {
4978
- for (const requestId of this.#pending.keys()) {
4979
- this.#append({ kind: "permission.resolved", requestId, decision: "deny", reason: "\u0425\u043E\u0434 \u0437\u0430\u0432\u0435\u0440\u0448\u0451\u043D" });
4980
- }
4981
- this.#pending.clear();
4982
- }
4983
- #notice(error) {
4984
- this.#append({ kind: "error", message: error instanceof Error ? error.message : String(error) });
4985
- }
4986
- #fail(error) {
4987
- if (this.#state === "closed")
4988
- return;
4989
- this.#queue = [];
4990
- if (this.#busy) {
4991
- this.#lastTurn = "failed";
4992
- this.#finishTurn("failed");
4993
- }
4994
- this.#notice(error);
4995
- const rpc = this.#rpc;
4996
- this.#rpc = null;
4997
- rpc?.close();
4998
- this.#setState("error");
4999
- }
5000
- #append(event) {
5001
- this.#record.updatedAt = Date.now();
5002
- const entry = this.journal.append(event);
5003
- this.emit("event", entry);
5004
- if (["assistant.delta", "thinking.delta", "state"].includes(event.kind))
5005
- return;
5006
- this.#unsaved.push({ ts: entry.ts, event });
5007
- if (!this.#flushTimer) {
5008
- this.#flushTimer = setTimeout(() => {
5009
- void this.#flush();
5010
- }, 500);
5011
- this.#flushTimer.unref?.();
5012
- }
5013
- }
5014
- async #flush() {
5015
- if (this.#flushTimer)
5016
- clearTimeout(this.#flushTimer);
5017
- this.#flushTimer = null;
5018
- const batch = this.#unsaved;
5019
- this.#unsaved = [];
5020
- await this.#store.appendEvents(this.id, batch);
5021
- await this.#store.save(this.#record);
5022
- }
5023
- #setState(state) {
5024
- this.#state = state;
5025
- this.#append({ kind: "state", state });
5026
- if (["idle", "error", "closed"].includes(state))
5027
- void this.#flush();
5028
- this.emit("summary", this.summary());
5029
- }
5030
- async editPrompt(_index, _text, _images) {
5031
- throw new Error("\u0412 \u0441\u0435\u0441\u0441\u0438\u0438 Codex \u043F\u0440\u0430\u0432\u043A\u0430 \u043F\u0440\u043E\u0448\u043B\u044B\u0445 \u0440\u0435\u043F\u043B\u0438\u043A \u043F\u043E\u043A\u0430 \u043D\u0435 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442\u0441\u044F");
5032
- }
5033
- async setUltracode(_enabled) {
5034
- }
5035
- async setThinking(_enabled) {
5036
- }
5037
- async setSwitchModelsOnFlag(_enabled) {
5038
- }
5039
- async reloadPlugins() {
5040
- }
5041
- async mcpServerStatus() {
5042
- return [];
5043
- }
5044
- async addMcpServer(_name, _config) {
5045
- throw this.#mcpHint();
5046
- }
5047
- async removeMcpServer(_name) {
5048
- throw this.#mcpHint();
5049
- }
5050
- async reconnectMcpServer(_name) {
5051
- throw this.#mcpHint();
5052
- }
5053
- async toggleMcpServer(_name, _enabled) {
5054
- throw this.#mcpHint();
5055
- }
5056
- async authenticateMcpServer(_name) {
5057
- throw this.#mcpHint();
5058
- }
5059
- async submitMcpOAuthCallback(_name, _url) {
5060
- throw this.#mcpHint();
5061
- }
5062
- #mcpHint() {
5063
- return new Error("MCP Codex \u043D\u0430\u0441\u0442\u0440\u0430\u0438\u0432\u0430\u0435\u0442\u0441\u044F \u0447\u0435\u0440\u0435\u0437 codex mcp \u0438\u043B\u0438 ~/.codex/config.toml");
5064
- }
5065
- };
5066
-
5067
4220
  // ../host/dist/antigravity-store.js
5068
4221
  import { appendFile, mkdir as mkdir3, readFile as readFile4, rm as rm2, writeFile as writeFile3 } from "node:fs/promises";
5069
- import path9 from "node:path";
4222
+ import path8 from "node:path";
5070
4223
  var AntigravityStore = class {
5071
4224
  #dir;
5072
4225
  #file;
5073
4226
  #records = /* @__PURE__ */ new Map();
5074
4227
  #loaded = null;
5075
4228
  #writing = Promise.resolve();
5076
- constructor(dataDir, provider = "antigravity") {
5077
- this.#dir = path9.join(dataDir, provider);
5078
- this.#file = path9.join(this.#dir, "sessions.json");
4229
+ constructor(dataDir) {
4230
+ this.#dir = path8.join(dataDir, "antigravity");
4231
+ this.#file = path8.join(this.#dir, "sessions.json");
5079
4232
  }
5080
4233
  #load() {
5081
4234
  this.#loaded ??= (async () => {
@@ -5172,7 +4325,7 @@ var AntigravityStore = class {
5172
4325
  return entries;
5173
4326
  }
5174
4327
  #eventsFile(id) {
5175
- return path9.join(this.#dir, `${id.replace(/[^\w-]/g, "_")}.jsonl`);
4328
+ return path8.join(this.#dir, `${id.replace(/[^\w-]/g, "_")}.jsonl`);
5176
4329
  }
5177
4330
  #persist() {
5178
4331
  const snapshot = JSON.stringify([...this.#records.values()], null, 2);
@@ -5192,10 +4345,10 @@ var AntigravityStore = class {
5192
4345
  };
5193
4346
 
5194
4347
  // ../host/dist/git.js
5195
- import { execFile as execFile5 } from "node:child_process";
4348
+ import { execFile as execFile4 } from "node:child_process";
5196
4349
  import { mkdtemp, readFile as readFile5, rm as rm3, writeFile as writeFile4 } from "node:fs/promises";
5197
4350
  import { tmpdir as tmpdir2 } from "node:os";
5198
- import path10 from "node:path";
4351
+ import path9 from "node:path";
5199
4352
  var TIMEOUT_MS = 2e4;
5200
4353
  var NET_TIMEOUT_MS = 5 * 6e4;
5201
4354
  var MAX_BUFFER = 32 * 1024 * 1024;
@@ -5511,7 +4664,7 @@ var GitRepo = class {
5511
4664
  * важнее всего (см. `checkIgnored`).
5512
4665
  */
5513
4666
  async #withoutRepo(args) {
5514
- const dir = await mkdtemp(path10.join(tmpdir2(), "ccv-git-"));
4667
+ const dir = await mkdtemp(path9.join(tmpdir2(), "ccv-git-"));
5515
4668
  try {
5516
4669
  await this.#run(["init", "--bare", "--quiet", dir]);
5517
4670
  return await this.#soft([`--git-dir=${dir}`, `--work-tree=${this.cwd}`, ...args]);
@@ -5557,7 +4710,7 @@ var GitRepo = class {
5557
4710
  * исключил. Повторы отсеиваются, чтобы файл не рос от каждой публикации.
5558
4711
  */
5559
4712
  async #appendGitignore(paths) {
5560
- const file = path10.join(this.cwd, ".gitignore");
4713
+ const file = path9.join(this.cwd, ".gitignore");
5561
4714
  const existing = await readFile5(file, "utf8").catch(() => "");
5562
4715
  const known = new Set(existing.split(/\r?\n/).map((line) => line.trim()));
5563
4716
  const lines = paths.map(ignorePattern).filter((line) => !known.has(line));
@@ -5582,7 +4735,7 @@ var GitRepo = class {
5582
4735
  #run(args, options2 = {}) {
5583
4736
  const token = options2.token ?? "";
5584
4737
  return new Promise((resolve, reject) => {
5585
- const child = execFile5(
4738
+ const child = execFile4(
5586
4739
  "git",
5587
4740
  // core.quotepath=false — иначе кириллические пути приезжают в виде
5588
4741
  // «\320\277\321\200…» и в панели читаются как мусор.
@@ -5763,9 +4916,9 @@ function parsePatch(raw) {
5763
4916
  body = "";
5764
4917
  }
5765
4918
  total += body.length;
5766
- const path26 = status === "deleted" ? oldPath : newPath || oldPath;
4919
+ const path25 = status === "deleted" ? oldPath : newPath || oldPath;
5767
4920
  files.push({
5768
- path: path26,
4921
+ path: path25,
5769
4922
  oldPath: status === "renamed" ? oldPath : "",
5770
4923
  status,
5771
4924
  added: count(body, "+"),
@@ -5777,10 +4930,10 @@ function parsePatch(raw) {
5777
4930
  return { files, truncated };
5778
4931
  }
5779
4932
  function stripPrefix(value) {
5780
- const path26 = unquote(value.trim());
5781
- if (path26 === "/dev/null")
4933
+ const path25 = unquote(value.trim());
4934
+ if (path25 === "/dev/null")
5782
4935
  return "";
5783
- return path26.replace(/^[ab]\//, "");
4936
+ return path25.replace(/^[ab]\//, "");
5784
4937
  }
5785
4938
  function count(body, mark) {
5786
4939
  let n = 0;
@@ -5792,9 +4945,9 @@ function count(body, mark) {
5792
4945
  }
5793
4946
 
5794
4947
  // ../host/dist/github.js
5795
- import { execFile as execFile6 } from "node:child_process";
4948
+ import { execFile as execFile5 } from "node:child_process";
5796
4949
  import { mkdir as mkdir4, readFile as readFile6, writeFile as writeFile5 } from "node:fs/promises";
5797
- import path11 from "node:path";
4950
+ import path10 from "node:path";
5798
4951
  var API = "https://api.github.com";
5799
4952
  var API_VERSION = "2022-11-28";
5800
4953
  var API_TIMEOUT_MS = 2e4;
@@ -5815,7 +4968,7 @@ var GitHubAccount = class {
5815
4968
  */
5816
4969
  #ghInstalled = null;
5817
4970
  constructor(dataDir) {
5818
- this.#storePath = path11.join(dataDir, "github.json");
4971
+ this.#storePath = path10.join(dataDir, "github.json");
5819
4972
  }
5820
4973
  async load() {
5821
4974
  try {
@@ -5829,7 +4982,7 @@ var GitHubAccount = class {
5829
4982
  /** Сохранить токен или стереть его пустой строкой. */
5830
4983
  async setToken(token) {
5831
4984
  this.#token = token.trim();
5832
- await mkdir4(path11.dirname(this.#storePath), { recursive: true });
4985
+ await mkdir4(path10.dirname(this.#storePath), { recursive: true });
5833
4986
  await writeFile5(this.#storePath, JSON.stringify({ token: this.#token }, null, 2), {
5834
4987
  encoding: "utf8",
5835
4988
  mode: 384
@@ -5981,7 +5134,7 @@ var GitHubAccount = class {
5981
5134
  };
5982
5135
  function gh(args) {
5983
5136
  return new Promise((resolve, reject) => {
5984
- execFile6("gh", args, { timeout: GH_TIMEOUT_MS, windowsHide: true, encoding: "utf8" }, (error, stdout, stderr) => {
5137
+ execFile5("gh", args, { timeout: GH_TIMEOUT_MS, windowsHide: true, encoding: "utf8" }, (error, stdout, stderr) => {
5985
5138
  if (error)
5986
5139
  return reject(new Error(stderr.trim() || error.message));
5987
5140
  resolve(stdout);
@@ -6022,10 +5175,10 @@ function describe4(error) {
6022
5175
  }
6023
5176
 
6024
5177
  // ../host/dist/finder.js
6025
- import { existsSync as existsSync3, statSync as statSync2 } from "node:fs";
5178
+ import { existsSync as existsSync2, statSync } from "node:fs";
6026
5179
  import { readdir as readdir2 } from "node:fs/promises";
6027
5180
  import os2 from "node:os";
6028
- import path12 from "node:path";
5181
+ import path11 from "node:path";
6029
5182
  import { listSessions } from "@anthropic-ai/claude-agent-sdk";
6030
5183
  var CACHE_TTL = 6e4;
6031
5184
  var FIND_LIMIT = 50;
@@ -6064,7 +5217,7 @@ var ProjectFinder = class {
6064
5217
  if (needles.length === 0)
6065
5218
  return { candidates: [], truncated: false };
6066
5219
  const open = new Map(this.registry.list().map((workspace) => [workspace.path.toLowerCase(), workspace]));
6067
- const byName = this.#dirs.filter((dir) => matches(path12.basename(dir.path), needles));
5220
+ const byName = this.#dirs.filter((dir) => matches(path11.basename(dir.path), needles));
6068
5221
  const matched = byName.length > 0 ? byName : this.#dirs.filter((dir) => matches(dir.path, needles));
6069
5222
  const sorted = [...matched].sort((a, b) => {
6070
5223
  const aOpen = open.has(a.path.toLowerCase());
@@ -6075,7 +5228,7 @@ var ProjectFinder = class {
6075
5228
  return a.sessions > 0 ? -1 : 1;
6076
5229
  if (a.lastUsedAt !== b.lastUsedAt)
6077
5230
  return b.lastUsedAt - a.lastUsedAt;
6078
- return path12.basename(a.path).localeCompare(path12.basename(b.path), void 0, {
5231
+ return path11.basename(a.path).localeCompare(path11.basename(b.path), void 0, {
6079
5232
  numeric: true,
6080
5233
  sensitivity: "base"
6081
5234
  });
@@ -6083,7 +5236,7 @@ var ProjectFinder = class {
6083
5236
  return {
6084
5237
  candidates: sorted.slice(0, FIND_LIMIT).map((dir) => ({
6085
5238
  path: dir.path,
6086
- name: path12.basename(dir.path) || dir.path,
5239
+ name: path11.basename(dir.path) || dir.path,
6087
5240
  sessions: dir.sessions,
6088
5241
  lastUsedAt: dir.lastUsedAt || null,
6089
5242
  open: open.has(dir.path.toLowerCase()),
@@ -6107,7 +5260,7 @@ var ProjectFinder = class {
6107
5260
  const candidates = [];
6108
5261
  for (const entry of named) {
6109
5262
  const absolute = entry.path.trim();
6110
- if (!absolute || !path12.isAbsolute(absolute))
5263
+ if (!absolute || !path11.isAbsolute(absolute))
6111
5264
  continue;
6112
5265
  const key = absolute.toLowerCase();
6113
5266
  if (seen.has(key))
@@ -6118,7 +5271,7 @@ var ProjectFinder = class {
6118
5271
  const record = known.get(key);
6119
5272
  candidates.push({
6120
5273
  path: record?.path ?? absolute,
6121
- name: path12.basename(absolute) || absolute,
5274
+ name: path11.basename(absolute) || absolute,
6122
5275
  sessions: record?.sessions ?? 0,
6123
5276
  lastUsedAt: record?.lastUsedAt || null,
6124
5277
  open: open.has(key),
@@ -6175,7 +5328,7 @@ var ProjectFinder = class {
6175
5328
  if (!dirent.isDirectory() || SKIP_NAMES.has(dirent.name) || dirent.name.startsWith(".")) {
6176
5329
  continue;
6177
5330
  }
6178
- const full = path12.join(parent, dirent.name);
5331
+ const full = path11.join(parent, dirent.name);
6179
5332
  const key = full.toLowerCase();
6180
5333
  if (dirs.has(key))
6181
5334
  continue;
@@ -6196,7 +5349,7 @@ var ProjectFinder = class {
6196
5349
  #parents(dirs) {
6197
5350
  const counted = /* @__PURE__ */ new Map();
6198
5351
  for (const dir of dirs) {
6199
- const parent = path12.dirname(dir.path);
5352
+ const parent = path11.dirname(dir.path);
6200
5353
  if (parent === dir.path || !usable(parent))
6201
5354
  continue;
6202
5355
  const key = parent.toLowerCase();
@@ -6210,7 +5363,7 @@ var ProjectFinder = class {
6210
5363
  }
6211
5364
  };
6212
5365
  function usable(dir) {
6213
- return !contains(os2.tmpdir(), dir) && existsSync3(dir);
5366
+ return !contains(os2.tmpdir(), dir) && existsSync2(dir);
6214
5367
  }
6215
5368
  function tokens(query2) {
6216
5369
  return query2.toLowerCase().split(/[^a-z0-9а-яё]+/i).filter(Boolean);
@@ -6221,7 +5374,7 @@ function matches(value, needles) {
6221
5374
  }
6222
5375
  function isDirectory(dir) {
6223
5376
  try {
6224
- return statSync2(dir).isDirectory();
5377
+ return statSync(dir).isDirectory();
6225
5378
  } catch {
6226
5379
  return false;
6227
5380
  }
@@ -6307,15 +5460,15 @@ function fromText(text) {
6307
5460
  }
6308
5461
 
6309
5462
  // ../host/dist/workspaces.js
6310
- import { existsSync as existsSync4, statSync as statSync3 } from "node:fs";
5463
+ import { existsSync as existsSync3, statSync as statSync2 } from "node:fs";
6311
5464
  import { mkdir as mkdir5, readFile as readFile7, writeFile as writeFile6 } from "node:fs/promises";
6312
- import path13 from "node:path";
5465
+ import path12 from "node:path";
6313
5466
  import { listSessions as listSessions2 } from "@anthropic-ai/claude-agent-sdk";
6314
5467
  var WorkspaceRegistry = class {
6315
5468
  #entries = [];
6316
5469
  #storePath;
6317
5470
  constructor(dataDir) {
6318
- this.#storePath = path13.join(dataDir, "workspaces.json");
5471
+ this.#storePath = path12.join(dataDir, "workspaces.json");
6319
5472
  }
6320
5473
  async load() {
6321
5474
  try {
@@ -6331,13 +5484,13 @@ var WorkspaceRegistry = class {
6331
5484
  if (isEntry(item))
6332
5485
  return item;
6333
5486
  return null;
6334
- }).filter((e) => e !== null && existsSync4(e.path));
5487
+ }).filter((e) => e !== null && existsSync3(e.path));
6335
5488
  } catch {
6336
5489
  this.#entries = [];
6337
5490
  }
6338
5491
  }
6339
5492
  async #persist() {
6340
- await mkdir5(path13.dirname(this.#storePath), { recursive: true });
5493
+ await mkdir5(path12.dirname(this.#storePath), { recursive: true });
6341
5494
  await writeFile6(this.#storePath, JSON.stringify(this.#entries, null, 2), "utf8");
6342
5495
  }
6343
5496
  /** Активные проекты. */
@@ -6357,8 +5510,8 @@ var WorkspaceRegistry = class {
6357
5510
  return entry ? toInfo(entry) : void 0;
6358
5511
  }
6359
5512
  async open(rawPath) {
6360
- const absolute = path13.resolve(rawPath);
6361
- if (!existsSync4(absolute)) {
5513
+ const absolute = path12.resolve(rawPath);
5514
+ if (!existsSync3(absolute)) {
6362
5515
  throw new Error(`\u041A\u0430\u0442\u0430\u043B\u043E\u0433 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D: ${absolute}`);
6363
5516
  }
6364
5517
  const existing = this.#entries.find((e) => e.path === absolute);
@@ -6424,24 +5577,24 @@ var WorkspaceRegistry = class {
6424
5577
  async create(parentRaw, nameRaw, init) {
6425
5578
  const name = nameRaw.trim();
6426
5579
  requireName(name);
6427
- const parent = path13.resolve(parentRaw.trim());
6428
- if (!existsSync4(parent)) {
5580
+ const parent = path12.resolve(parentRaw.trim());
5581
+ if (!existsSync3(parent)) {
6429
5582
  throw new Error(`\u041A\u0430\u0442\u0430\u043B\u043E\u0433 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D: ${parent}`);
6430
5583
  }
6431
- if (!statSync3(parent).isDirectory()) {
5584
+ if (!statSync2(parent).isDirectory()) {
6432
5585
  throw new Error(`\u042D\u0442\u043E \u043D\u0435 \u043A\u0430\u0442\u0430\u043B\u043E\u0433: ${parent}`);
6433
5586
  }
6434
- const target = path13.join(parent, name);
6435
- if (existsSync4(target)) {
5587
+ const target = path12.join(parent, name);
5588
+ if (existsSync3(target)) {
6436
5589
  throw new Error(`\u0423\u0436\u0435 \u0441\u0443\u0449\u0435\u0441\u0442\u0432\u0443\u0435\u0442: ${target} \u2014 \u043E\u0442\u043A\u0440\u043E\u0439\u0442\u0435 \u0435\u0433\u043E \u043A\u0430\u043A \u043F\u0440\u043E\u0435\u043A\u0442`);
6437
5590
  }
6438
5591
  await mkdir5(target);
6439
5592
  const warnings = [];
6440
5593
  if (init.claudeMd) {
6441
- await step(warnings, "CLAUDE.md", () => writeFile6(path13.join(target, "CLAUDE.md"), claudeMdStub(name), "utf8"));
5594
+ await step(warnings, "CLAUDE.md", () => writeFile6(path12.join(target, "CLAUDE.md"), claudeMdStub(name), "utf8"));
6442
5595
  }
6443
5596
  if (init.readme) {
6444
- await step(warnings, "README.md", () => writeFile6(path13.join(target, "README.md"), readmeStub(name), "utf8"));
5597
+ await step(warnings, "README.md", () => writeFile6(path12.join(target, "README.md"), readmeStub(name), "utf8"));
6445
5598
  }
6446
5599
  if (init.git) {
6447
5600
  await step(warnings, "git init", () => new GitRepo(target).init());
@@ -6513,8 +5666,8 @@ function toInfo(entry) {
6513
5666
  return {
6514
5667
  id: workspaceIdFromPath(absolute),
6515
5668
  path: absolute,
6516
- name: path13.basename(absolute) || absolute,
6517
- hasClaudeMd: existsSync4(path13.join(absolute, "CLAUDE.md")),
5669
+ name: path12.basename(absolute) || absolute,
5670
+ hasClaudeMd: existsSync3(path12.join(absolute, "CLAUDE.md")),
6518
5671
  ...archivedAt ? { archivedAt } : {}
6519
5672
  };
6520
5673
  }
@@ -6524,13 +5677,13 @@ function isEntry(value) {
6524
5677
 
6525
5678
  // ../host/dist/archive.js
6526
5679
  import { mkdir as mkdir6, readFile as readFile8, writeFile as writeFile7 } from "node:fs/promises";
6527
- import path14 from "node:path";
5680
+ import path13 from "node:path";
6528
5681
  var SessionArchive = class {
6529
5682
  #archived = /* @__PURE__ */ new Map();
6530
5683
  #restored = /* @__PURE__ */ new Map();
6531
5684
  #storePath;
6532
5685
  constructor(dataDir) {
6533
- this.#storePath = path14.join(dataDir, "session-archive.json");
5686
+ this.#storePath = path13.join(dataDir, "session-archive.json");
6534
5687
  }
6535
5688
  async load() {
6536
5689
  try {
@@ -6642,7 +5795,7 @@ var SessionArchive = class {
6642
5795
  archived: Object.fromEntries(this.#archived),
6643
5796
  restored: Object.fromEntries(this.#restored)
6644
5797
  };
6645
- await mkdir6(path14.dirname(this.#storePath), { recursive: true });
5798
+ await mkdir6(path13.dirname(this.#storePath), { recursive: true });
6646
5799
  await writeFile7(this.#storePath, JSON.stringify(file, null, 2), "utf8");
6647
5800
  }
6648
5801
  };
@@ -6652,7 +5805,7 @@ function isRecord(value) {
6652
5805
 
6653
5806
  // ../host/dist/pins.js
6654
5807
  import { mkdir as mkdir7, readFile as readFile9, writeFile as writeFile8 } from "node:fs/promises";
6655
- import path15 from "node:path";
5808
+ import path14 from "node:path";
6656
5809
  var SessionPins = class {
6657
5810
  #pinned = /* @__PURE__ */ new Map();
6658
5811
  /**
@@ -6667,7 +5820,7 @@ var SessionPins = class {
6667
5820
  #moved = /* @__PURE__ */ new Map();
6668
5821
  #storePath;
6669
5822
  constructor(dataDir) {
6670
- this.#storePath = path15.join(dataDir, "session-pins.json");
5823
+ this.#storePath = path14.join(dataDir, "session-pins.json");
6671
5824
  }
6672
5825
  async load() {
6673
5826
  try {
@@ -6824,7 +5977,7 @@ var SessionPins = class {
6824
5977
  pinned: Object.fromEntries(this.#pinned),
6825
5978
  ...this.#moved.size > 0 ? { moved: Object.fromEntries(this.#moved) } : {}
6826
5979
  };
6827
- await mkdir7(path15.dirname(this.#storePath), { recursive: true });
5980
+ await mkdir7(path14.dirname(this.#storePath), { recursive: true });
6828
5981
  await writeFile8(this.#storePath, JSON.stringify(file, null, 2), "utf8");
6829
5982
  }
6830
5983
  };
@@ -6834,12 +5987,12 @@ function isRecord2(value) {
6834
5987
 
6835
5988
  // ../host/dist/order.js
6836
5989
  import { mkdir as mkdir8, readFile as readFile10, writeFile as writeFile9 } from "node:fs/promises";
6837
- import path16 from "node:path";
5990
+ import path15 from "node:path";
6838
5991
  var ListOrderStore = class {
6839
5992
  #order = emptyOrder();
6840
5993
  #storePath;
6841
5994
  constructor(dataDir) {
6842
- this.#storePath = path16.join(dataDir, "list-order.json");
5995
+ this.#storePath = path15.join(dataDir, "list-order.json");
6843
5996
  }
6844
5997
  async load() {
6845
5998
  try {
@@ -6915,7 +6068,7 @@ var ListOrderStore = class {
6915
6068
  return changed;
6916
6069
  }
6917
6070
  async #persist() {
6918
- await mkdir8(path16.dirname(this.#storePath), { recursive: true });
6071
+ await mkdir8(path15.dirname(this.#storePath), { recursive: true });
6919
6072
  await writeFile9(this.#storePath, JSON.stringify(this.#order, null, 2), "utf8");
6920
6073
  }
6921
6074
  };
@@ -6946,8 +6099,8 @@ function sanitize(value) {
6946
6099
 
6947
6100
  // ../host/dist/folders.js
6948
6101
  import { mkdir as mkdir9, readFile as readFile11, writeFile as writeFile10 } from "node:fs/promises";
6949
- import path17 from "node:path";
6950
- import { randomUUID as randomUUID4 } from "node:crypto";
6102
+ import path16 from "node:path";
6103
+ import { randomUUID as randomUUID3 } from "node:crypto";
6951
6104
  var COLOR_PATTERN = /^#[0-9a-f]{6}$/i;
6952
6105
  var Folders = class {
6953
6106
  #workspaceFolders = /* @__PURE__ */ new Map();
@@ -6958,7 +6111,7 @@ var Folders = class {
6958
6111
  #pinnedAssignments = /* @__PURE__ */ new Map();
6959
6112
  #storePath;
6960
6113
  constructor(dataDir) {
6961
- this.#storePath = path17.join(dataDir, "folders.json");
6114
+ this.#storePath = path16.join(dataDir, "folders.json");
6962
6115
  }
6963
6116
  async load() {
6964
6117
  try {
@@ -7047,19 +6200,19 @@ var Folders = class {
7047
6200
  };
7048
6201
  }
7049
6202
  async createWorkspaceFolder(name) {
7050
- const id = randomUUID4();
6203
+ const id = randomUUID3();
7051
6204
  this.#workspaceFolders.set(id, { name });
7052
6205
  await this.#persist();
7053
6206
  return id;
7054
6207
  }
7055
6208
  async createSessionFolder(workspaceId, name) {
7056
- const id = randomUUID4();
6209
+ const id = randomUUID3();
7057
6210
  this.#sessionFolders.set(id, { name, workspaceId });
7058
6211
  await this.#persist();
7059
6212
  return id;
7060
6213
  }
7061
6214
  async createPinnedFolder(name) {
7062
- const id = randomUUID4();
6215
+ const id = randomUUID3();
7063
6216
  this.#pinnedFolders.set(id, { name });
7064
6217
  await this.#persist();
7065
6218
  return id;
@@ -7239,7 +6392,7 @@ var Folders = class {
7239
6392
  sessionAssignments: Object.fromEntries(this.#sessionAssignments),
7240
6393
  pinnedAssignments: Object.fromEntries(this.#pinnedAssignments)
7241
6394
  };
7242
- await mkdir9(path17.dirname(this.#storePath), { recursive: true });
6395
+ await mkdir9(path16.dirname(this.#storePath), { recursive: true });
7243
6396
  await writeFile10(this.#storePath, JSON.stringify(file, null, 2), "utf8");
7244
6397
  }
7245
6398
  };
@@ -7262,8 +6415,8 @@ function isPinnedFolder(value) {
7262
6415
 
7263
6416
  // ../host/dist/app-settings.js
7264
6417
  import { mkdir as mkdir10, readFile as readFile12, writeFile as writeFile11 } from "node:fs/promises";
7265
- import { homedir as homedir5 } from "node:os";
7266
- import path18 from "node:path";
6418
+ import { homedir as homedir4 } from "node:os";
6419
+ import path17 from "node:path";
7267
6420
  var DEFAULT_AUTO_ARCHIVE_AFTER_MS = 2 * 24 * 60 * 60 * 1e3;
7268
6421
  var MIN_AUTO_ARCHIVE_AFTER_MS = 60 * 60 * 1e3;
7269
6422
  var DEFAULT_AUTO_STOP_AFTER_MS = 10 * 60 * 1e3;
@@ -7271,7 +6424,7 @@ var MIN_AUTO_STOP_AFTER_MS = 60 * 1e3;
7271
6424
  var MIN_AUTO_SAVE_AFTER_PAUSE_MS = 500;
7272
6425
  var DEFAULT_BLOCKED_COUNTRIES = ["RU", "BY", "CN", "IR", "KP", "SY", "CU"];
7273
6426
  var FOLDER_ACCESS = ["all", "projects", "project"];
7274
- var PROVIDERS = ["claude", "antigravity", "codex"];
6427
+ var PROVIDERS = ["claude", "antigravity"];
7275
6428
  var PERMISSION_MODES = [
7276
6429
  "default",
7277
6430
  "acceptEdits",
@@ -7306,7 +6459,7 @@ var DEFAULT_APP_SETTINGS = {
7306
6459
  limitStopFiveHourPct: 95,
7307
6460
  limitStopSevenDayPct: 99,
7308
6461
  // Оба: до появления настройки приложение предлагало обоих агентов.
7309
- enabledProviders: ["claude", "antigravity", "codex"],
6462
+ enabledProviders: ["claude", "antigravity"],
7310
6463
  // Включено: запрос без VPN может стоить аккаунта, а тому, у кого маршрут и
7311
6464
  // так из разрешённой страны, защита ничем не мешает.
7312
6465
  networkGuardEnabled: true,
@@ -7316,7 +6469,7 @@ var AppSettingsStore = class {
7316
6469
  #settings = { ...DEFAULT_APP_SETTINGS };
7317
6470
  #storePath;
7318
6471
  constructor(dataDir) {
7319
- this.#storePath = path18.join(dataDir, "app-settings.json");
6472
+ this.#storePath = path17.join(dataDir, "app-settings.json");
7320
6473
  }
7321
6474
  async load() {
7322
6475
  try {
@@ -7340,7 +6493,7 @@ var AppSettingsStore = class {
7340
6493
  async update(patch) {
7341
6494
  const next = sanitize2(patch, this.#settings);
7342
6495
  this.#settings = next;
7343
- await mkdir10(path18.dirname(this.#storePath), { recursive: true });
6496
+ await mkdir10(path17.dirname(this.#storePath), { recursive: true });
7344
6497
  await writeFile11(this.#storePath, JSON.stringify(next, null, 2), "utf8");
7345
6498
  return this.current;
7346
6499
  }
@@ -7407,7 +6560,7 @@ function sanitize2(value, fallback) {
7407
6560
  return result;
7408
6561
  }
7409
6562
  function claudeHome() {
7410
- return path18.join(homedir5(), ".claude");
6563
+ return path17.join(homedir4(), ".claude");
7411
6564
  }
7412
6565
  function writableRoots(mode, cwd, workspacePaths) {
7413
6566
  if (mode === "all")
@@ -7417,7 +6570,7 @@ function writableRoots(mode, cwd, workspacePaths) {
7417
6570
  return [...roots];
7418
6571
  for (const workspace of [cwd, ...workspacePaths]) {
7419
6572
  roots.add(workspace);
7420
- const parent = path18.dirname(workspace);
6573
+ const parent = path17.dirname(workspace);
7421
6574
  if (parent !== workspace)
7422
6575
  roots.add(parent);
7423
6576
  }
@@ -7426,11 +6579,11 @@ function writableRoots(mode, cwd, workspacePaths) {
7426
6579
 
7427
6580
  // ../host/dist/handoff-store.js
7428
6581
  import { mkdir as mkdir11, readFile as readFile13, readdir as readdir3, rm as rm4, writeFile as writeFile12 } from "node:fs/promises";
7429
- import path19 from "node:path";
6582
+ import path18 from "node:path";
7430
6583
  var HandoffStore = class {
7431
6584
  #dir;
7432
6585
  constructor(dataDir) {
7433
- this.#dir = path19.join(dataDir, "handoffs");
6586
+ this.#dir = path18.join(dataDir, "handoffs");
7434
6587
  }
7435
6588
  async get(sessionId) {
7436
6589
  const file = this.#file(sessionId);
@@ -7467,7 +6620,7 @@ var HandoffStore = class {
7467
6620
  #file(sessionId) {
7468
6621
  if (!/^[\w-]{1,128}$/.test(sessionId))
7469
6622
  return null;
7470
- return path19.join(this.#dir, `${sessionId}.json`);
6623
+ return path18.join(this.#dir, `${sessionId}.json`);
7471
6624
  }
7472
6625
  };
7473
6626
  var SAME_WINDOW_MS = 5 * 6e4;
@@ -7475,7 +6628,7 @@ var LimitStopState = class {
7475
6628
  #fired = {};
7476
6629
  #storePath;
7477
6630
  constructor(dataDir) {
7478
- this.#storePath = path19.join(dataDir, "limit-stop.json");
6631
+ this.#storePath = path18.join(dataDir, "limit-stop.json");
7479
6632
  }
7480
6633
  async load() {
7481
6634
  try {
@@ -7511,7 +6664,7 @@ var LimitStopState = class {
7511
6664
  /** Запомнить срабатывание до `until` (момент сброса окна). */
7512
6665
  async mark(limit, until) {
7513
6666
  this.#fired[limit] = until;
7514
- await mkdir11(path19.dirname(this.#storePath), { recursive: true });
6667
+ await mkdir11(path18.dirname(this.#storePath), { recursive: true });
7515
6668
  await writeFile12(this.#storePath, JSON.stringify(this.#fired, null, 2), "utf8");
7516
6669
  }
7517
6670
  };
@@ -7617,8 +6770,8 @@ function capitalize(text) {
7617
6770
 
7618
6771
  // ../host/dist/plugins.js
7619
6772
  import { readFile as readFile14 } from "node:fs/promises";
7620
- import { homedir as homedir6 } from "node:os";
7621
- import path20 from "node:path";
6773
+ import { homedir as homedir5 } from "node:os";
6774
+ import path19 from "node:path";
7622
6775
  var TIMEOUT_MS2 = 12e4;
7623
6776
  var SAFE_ARG = /^[A-Za-z0-9][A-Za-z0-9._@/-]*$/;
7624
6777
  var PluginCli = class {
@@ -7717,10 +6870,10 @@ async function readCatalog(markets, installed) {
7717
6870
  return lists.flat().sort((a, b) => a.name.localeCompare(b.name));
7718
6871
  }
7719
6872
  async function readMarketplace(market, installed) {
7720
- const root = market.installLocation || path20.join(homedir6(), ".claude", "plugins", "marketplaces", market.name);
6873
+ const root = market.installLocation || path19.join(homedir5(), ".claude", "plugins", "marketplaces", market.name);
7721
6874
  let manifest;
7722
6875
  try {
7723
- const text = await readFile14(path20.join(root, ".claude-plugin", "marketplace.json"), "utf8");
6876
+ const text = await readFile14(path19.join(root, ".claude-plugin", "marketplace.json"), "utf8");
7724
6877
  manifest = JSON.parse(text);
7725
6878
  } catch {
7726
6879
  return [];
@@ -7763,7 +6916,7 @@ function authorName(raw) {
7763
6916
  }
7764
6917
 
7765
6918
  // ../host/dist/auth.js
7766
- import { EventEmitter as EventEmitter6 } from "node:events";
6919
+ import { EventEmitter as EventEmitter4 } from "node:events";
7767
6920
  var QUICK_TIMEOUT_MS = 3e4;
7768
6921
  var LOGIN_TIMEOUT_MS = 10 * 6e4;
7769
6922
  var URL_RE = /https:\/\/\S*\/oauth\/authorize\S*/;
@@ -7775,7 +6928,7 @@ var IDLE = {
7775
6928
  output: "",
7776
6929
  error: null
7777
6930
  };
7778
- var AuthCli = class extends EventEmitter6 {
6931
+ var AuthCli = class extends EventEmitter4 {
7779
6932
  #child = null;
7780
6933
  #state = IDLE;
7781
6934
  #timer = null;
@@ -7960,9 +7113,9 @@ function describe5(error) {
7960
7113
  }
7961
7114
 
7962
7115
  // ../host/dist/relay-link.js
7963
- import { EventEmitter as EventEmitter7 } from "node:events";
7116
+ import { EventEmitter as EventEmitter5 } from "node:events";
7964
7117
  import { readFile as readFile15, writeFile as writeFile13, rm as rm5, mkdir as mkdir12 } from "node:fs/promises";
7965
- import path21 from "node:path";
7118
+ import path20 from "node:path";
7966
7119
  import { hostname } from "node:os";
7967
7120
  import WebSocket from "ws";
7968
7121
 
@@ -7979,7 +7132,7 @@ var SILENCE_TIMEOUT_MS = 95e3;
7979
7132
  function jitter(delay2) {
7980
7133
  return Math.round(delay2 * (0.8 + Math.random() * 0.4));
7981
7134
  }
7982
- var RelayLink = class extends EventEmitter7 {
7135
+ var RelayLink = class extends EventEmitter5 {
7983
7136
  #credentials = null;
7984
7137
  #socket = null;
7985
7138
  #retry = RETRY_MIN_MS;
@@ -8017,7 +7170,7 @@ var RelayLink = class extends EventEmitter7 {
8017
7170
  #log;
8018
7171
  constructor(options2) {
8019
7172
  super();
8020
- this.#file = path21.join(options2.dataDir, "relay.json");
7173
+ this.#file = path20.join(options2.dataDir, "relay.json");
8021
7174
  this.#defaultUrl = options2.defaultUrl.replace(/\/+$/, "");
8022
7175
  this.#log = options2.log ?? ((msg) => console.log(`[relay] ${msg}`));
8023
7176
  }
@@ -8111,7 +7264,7 @@ var RelayLink = class extends EventEmitter7 {
8111
7264
  }
8112
7265
  }
8113
7266
  async #write(credentials) {
8114
- await mkdir12(path21.dirname(this.#file), { recursive: true });
7267
+ await mkdir12(path20.dirname(this.#file), { recursive: true });
8115
7268
  await writeFile13(this.#file, `${JSON.stringify(credentials, null, 2)}
8116
7269
  `, {
8117
7270
  encoding: "utf8",
@@ -8367,14 +7520,14 @@ function humanize(error) {
8367
7520
  }
8368
7521
 
8369
7522
  // ../host/dist/terminal.js
8370
- import { EventEmitter as EventEmitter8 } from "node:events";
8371
- import { access as access2, constants as constants3 } from "node:fs/promises";
8372
- import path22 from "node:path";
8373
- import { randomUUID as randomUUID5 } from "node:crypto";
7523
+ import { EventEmitter as EventEmitter6 } from "node:events";
7524
+ import { access as access2, constants as constants2 } from "node:fs/promises";
7525
+ import path21 from "node:path";
7526
+ import { randomUUID as randomUUID4 } from "node:crypto";
8374
7527
  var SCROLLBACK_BYTES = 256 * 1024;
8375
7528
  var FLUSH_MS = 12;
8376
7529
  var MAX_TERMINALS = 24;
8377
- var TerminalHub = class extends EventEmitter8 {
7530
+ var TerminalHub = class extends EventEmitter6 {
8378
7531
  #terminals = /* @__PURE__ */ new Map();
8379
7532
  #module = null;
8380
7533
  list(workspaceId) {
@@ -8407,7 +7560,7 @@ var TerminalHub = class extends EventEmitter8 {
8407
7560
  env: environment()
8408
7561
  });
8409
7562
  const info = {
8410
- id: randomUUID5(),
7563
+ id: randomUUID4(),
8411
7564
  workspaceId: options2.workspaceId,
8412
7565
  title: shell.title,
8413
7566
  shell: shell.file,
@@ -8539,36 +7692,36 @@ async function defaultShell() {
8539
7692
  if (pwsh)
8540
7693
  return { file: pwsh, args: [], title: "pwsh" };
8541
7694
  const system = process.env.SystemRoot ?? "C:\\Windows";
8542
- const powershell = path22.join(system, "System32/WindowsPowerShell/v1.0/powershell.exe");
7695
+ const powershell = path21.join(system, "System32/WindowsPowerShell/v1.0/powershell.exe");
8543
7696
  if (await exists2(powershell))
8544
7697
  return { file: powershell, args: [], title: "powershell" };
8545
7698
  return { file: process.env.COMSPEC ?? "cmd.exe", args: [], title: "cmd" };
8546
7699
  }
8547
7700
  const shell = process.env.SHELL;
8548
7701
  if (shell && await exists2(shell))
8549
- return { file: shell, args: [], title: path22.basename(shell) };
7702
+ return { file: shell, args: [], title: path21.basename(shell) };
8550
7703
  if (await exists2("/bin/bash"))
8551
7704
  return { file: "/bin/bash", args: [], title: "bash" };
8552
7705
  return { file: "/bin/sh", args: [], title: "sh" };
8553
7706
  }
8554
7707
  async function findOnPath(name) {
8555
- const dirs = (process.env.PATH ?? "").split(path22.delimiter).filter(Boolean);
7708
+ const dirs = (process.env.PATH ?? "").split(path21.delimiter).filter(Boolean);
8556
7709
  for (const dir of dirs) {
8557
- const candidate = path22.join(dir, name);
7710
+ const candidate = path21.join(dir, name);
8558
7711
  if (await exists2(candidate))
8559
7712
  return candidate;
8560
7713
  }
8561
7714
  return null;
8562
7715
  }
8563
7716
  function exists2(file) {
8564
- return access2(file, constants3.X_OK).then(() => true, () => false);
7717
+ return access2(file, constants2.X_OK).then(() => true, () => false);
8565
7718
  }
8566
7719
 
8567
7720
  // ../host/dist/mcp-config.js
8568
7721
  import { readFile as readFile16, writeFile as writeFile14, mkdir as mkdir13 } from "node:fs/promises";
8569
- import path23 from "node:path";
7722
+ import path22 from "node:path";
8570
7723
  var MCP_FILE = ".mcp.json";
8571
- var LOCAL_SETTINGS2 = path23.join(".claude", "settings.local.json");
7724
+ var LOCAL_SETTINGS2 = path22.join(".claude", "settings.local.json");
8572
7725
  var queues = /* @__PURE__ */ new Map();
8573
7726
  function serialize(cwd, work) {
8574
7727
  const previous = queues.get(cwd) ?? Promise.resolve();
@@ -8577,7 +7730,7 @@ function serialize(cwd, work) {
8577
7730
  return next;
8578
7731
  }
8579
7732
  async function readProjectServers(cwd) {
8580
- const file = await readJson(path23.join(cwd, MCP_FILE));
7733
+ const file = await readJson(path22.join(cwd, MCP_FILE));
8581
7734
  const servers = file?.mcpServers;
8582
7735
  if (!servers || typeof servers !== "object")
8583
7736
  return {};
@@ -8585,23 +7738,23 @@ async function readProjectServers(cwd) {
8585
7738
  }
8586
7739
  function addProjectServer(cwd, name, config) {
8587
7740
  return serialize(cwd, async () => {
8588
- const file = await readJson(path23.join(cwd, MCP_FILE)) ?? {};
7741
+ const file = await readJson(path22.join(cwd, MCP_FILE)) ?? {};
8589
7742
  const servers = file.mcpServers ?? {};
8590
7743
  servers[name] = config;
8591
7744
  file.mcpServers = servers;
8592
- await writeJson(path23.join(cwd, MCP_FILE), file);
7745
+ await writeJson(path22.join(cwd, MCP_FILE), file);
8593
7746
  await approve(cwd, name);
8594
7747
  });
8595
7748
  }
8596
7749
  function removeProjectServer(cwd, name) {
8597
7750
  return serialize(cwd, async () => {
8598
- const file = await readJson(path23.join(cwd, MCP_FILE));
7751
+ const file = await readJson(path22.join(cwd, MCP_FILE));
8599
7752
  const servers = file?.mcpServers;
8600
7753
  if (!servers || !(name in servers))
8601
7754
  return false;
8602
7755
  delete servers[name];
8603
- await writeJson(path23.join(cwd, MCP_FILE), file);
8604
- const settingsPath = path23.join(cwd, LOCAL_SETTINGS2);
7756
+ await writeJson(path22.join(cwd, MCP_FILE), file);
7757
+ const settingsPath = path22.join(cwd, LOCAL_SETTINGS2);
8605
7758
  const settings = await readJson(settingsPath);
8606
7759
  const enabled = settings?.enabledMcpjsonServers;
8607
7760
  if (settings && Array.isArray(enabled) && enabled.includes(name)) {
@@ -8612,7 +7765,7 @@ function removeProjectServer(cwd, name) {
8612
7765
  });
8613
7766
  }
8614
7767
  async function approve(cwd, name) {
8615
- const file = path23.join(cwd, LOCAL_SETTINGS2);
7768
+ const file = path22.join(cwd, LOCAL_SETTINGS2);
8616
7769
  const settings = await readJson(file) ?? {};
8617
7770
  const enabled = Array.isArray(settings.enabledMcpjsonServers) ? settings.enabledMcpjsonServers : [];
8618
7771
  if (!enabled.includes(name))
@@ -8658,13 +7811,13 @@ async function readJson(file) {
8658
7811
  if (error.code === "ENOENT")
8659
7812
  return null;
8660
7813
  if (error instanceof SyntaxError) {
8661
- throw new Error(`\u041D\u0435 \u0443\u0434\u0430\u043B\u043E\u0441\u044C \u0440\u0430\u0437\u043E\u0431\u0440\u0430\u0442\u044C ${path23.basename(file)}: ${error.message}`);
7814
+ throw new Error(`\u041D\u0435 \u0443\u0434\u0430\u043B\u043E\u0441\u044C \u0440\u0430\u0437\u043E\u0431\u0440\u0430\u0442\u044C ${path22.basename(file)}: ${error.message}`);
8662
7815
  }
8663
7816
  throw error;
8664
7817
  }
8665
7818
  }
8666
7819
  async function writeJson(file, data) {
8667
- await mkdir13(path23.dirname(file), { recursive: true });
7820
+ await mkdir13(path22.dirname(file), { recursive: true });
8668
7821
  await writeFile14(file, `${JSON.stringify(data, null, 2)}
8669
7822
  `, "utf8");
8670
7823
  }
@@ -8683,8 +7836,6 @@ var BUSY_STATES2 = /* @__PURE__ */ new Set([
8683
7836
  "reconnecting"
8684
7837
  ]);
8685
7838
  var HostServer = class {
8686
- #httpServer = null;
8687
- #webSockets = null;
8688
7839
  #options;
8689
7840
  #workspaces;
8690
7841
  #archive;
@@ -8697,7 +7848,6 @@ var HostServer = class {
8697
7848
  /** Опросы статуса для идущих OAuth-входов MCP, ключ — сессия и сервер. */
8698
7849
  #mcpAuthWatch = /* @__PURE__ */ new Map();
8699
7850
  #antigravity;
8700
- #codex;
8701
7851
  /** Боковые сессии («вопрос на полях») по id родителя — не больше одной на разговор. */
8702
7852
  #sides = /* @__PURE__ */ new Map();
8703
7853
  /**
@@ -8745,7 +7895,7 @@ var HostServer = class {
8745
7895
  #limitHandoffBusy = /* @__PURE__ */ new Set();
8746
7896
  /** Живые id сессий, у которых сейчас пишется ручной хэндофф. */
8747
7897
  #handoffBusy = /* @__PURE__ */ new Set();
8748
- #hostId = randomUUID6();
7898
+ #hostId = randomUUID5();
8749
7899
  #plugins = new PluginCli();
8750
7900
  #auth = new AuthCli();
8751
7901
  #relay;
@@ -8769,7 +7919,6 @@ var HostServer = class {
8769
7919
  this.#folders = new Folders(options2.dataDir);
8770
7920
  this.#settings = new AppSettingsStore(options2.dataDir);
8771
7921
  this.#antigravity = new AntigravityStore(options2.dataDir);
8772
- this.#codex = new AntigravityStore(options2.dataDir, "codex");
8773
7922
  this.#handoffs = new HandoffStore(options2.dataDir);
8774
7923
  this.#limitStop = new LimitStopState(options2.dataDir);
8775
7924
  this.#finder = new ProjectFinder(this.#workspaces);
@@ -8796,11 +7945,9 @@ var HostServer = class {
8796
7945
  const id = workspaceIdFromPath(dir);
8797
7946
  const onDisk = await this.#workspaces.sessionsOnDisk(id);
8798
7947
  const antigravity = await this.#antigravity.list(id);
8799
- const codex = await this.#codex.list(id);
8800
- return [...onDisk.map((s) => s.sessionId), ...antigravity.map((r) => r.id), ...codex.map((r) => r.id)];
7948
+ return [...onDisk.map((s) => s.sessionId), ...antigravity.map((r) => r.id)];
8801
7949
  });
8802
7950
  await this.#antigravity.remapWorkspaceIds(remap);
8803
- await this.#codex.remapWorkspaceIds(remap);
8804
7951
  await this.#archive.remapWorkspaceIds(remap);
8805
7952
  await this.#pins.remapWorkspaceIds(remap);
8806
7953
  await this.#order.remapWorkspaceIds(remap);
@@ -8835,8 +7982,6 @@ var HostServer = class {
8835
7982
  resolve();
8836
7983
  });
8837
7984
  });
8838
- this.#httpServer = httpServer;
8839
- this.#webSockets = wss;
8840
7985
  await this.#relay.start().catch((error) => {
8841
7986
  console.error("[relay]", error instanceof Error ? error.message : String(error));
8842
7987
  });
@@ -8875,16 +8020,6 @@ var HostServer = class {
8875
8020
  await this.#relay.close();
8876
8021
  await Promise.all([...this.#sessions.values()].map((s) => s.close("host shutdown")));
8877
8022
  this.#sessions.clear();
8878
- const wss = this.#webSockets;
8879
- const http = this.#httpServer;
8880
- this.#webSockets = null;
8881
- this.#httpServer = null;
8882
- for (const socket of wss?.clients ?? [])
8883
- socket.terminate();
8884
- await Promise.all([
8885
- ...wss ? [new Promise((resolve) => wss.close(() => resolve()))] : [],
8886
- ...http ? [new Promise((resolve) => http.close(() => resolve()))] : []
8887
- ]);
8888
8023
  }
8889
8024
  // -------------------------------------------------------------------------
8890
8025
  // WebSocket
@@ -10284,31 +9419,7 @@ var HostServer = class {
10284
9419
  throw new Error(`\u0412\u043E\u0440\u043A\u0441\u043F\u0435\u0439\u0441 \u043D\u0435 \u043D\u0430\u0439\u0434\u0435\u043D: ${frame.workspaceId}`);
10285
9420
  const provider = frame.provider ?? "claude";
10286
9421
  if (!frame.resume && !this.#settings.current.enabledProviders.includes(provider)) {
10287
- throw new Error(`${provider === "antigravity" ? "Antigravity" : provider === "codex" ? "Codex" : "Claude"} \u0432\u044B\u043A\u043B\u044E\u0447\u0435\u043D \u0432 \u043D\u0430\u0441\u0442\u0440\u043E\u0439\u043A\u0430\u0445`);
10288
- }
10289
- const codexRecord = frame.resume ? await this.#codex.find(frame.resume) : null;
10290
- if (codexRecord || !frame.resume && provider === "codex") {
10291
- if (frame.fork)
10292
- throw new Error("\u0412\u0435\u0442\u0432\u043B\u0435\u043D\u0438\u0435 \u0441\u0435\u0441\u0441\u0438\u0439 Codex \u043F\u043E\u043A\u0430 \u043D\u0435 \u043F\u043E\u0434\u0434\u0435\u0440\u0436\u0438\u0432\u0430\u0435\u0442\u0441\u044F");
10293
- if (codexRecord && codexRecord.workspaceId !== workspace.id)
10294
- throw new Error("\u0421\u0435\u0441\u0441\u0438\u044F Codex \u043F\u0440\u0438\u043D\u0430\u0434\u043B\u0435\u0436\u0438\u0442 \u0434\u0440\u0443\u0433\u043E\u043C\u0443 \u043F\u0440\u043E\u0435\u043A\u0442\u0443");
10295
- if (codexRecord)
10296
- await this.#archive.unarchive([codexRecord.id]);
10297
- const session2 = new CodexSession({
10298
- workspaceId: workspace.id,
10299
- cwd: codexRecord?.cwd ?? workspace.path,
10300
- store: this.#codex,
10301
- ...codexRecord ? { record: codexRecord } : {},
10302
- ...frame.permissionMode ? { permissionMode: frame.permissionMode } : {},
10303
- ...frame.model ? { model: frame.model } : {},
10304
- defaultTitle: workspace.name
10305
- });
10306
- this.#wire(session2);
10307
- this.#sessions.set(session2.id, session2);
10308
- session2.start();
10309
- this.#sendLive();
10310
- this.#send(socket, { type: "session.summary", session: session2.summary() });
10311
- return;
9422
+ throw new Error(`${provider === "antigravity" ? "Antigravity" : "Claude"} \u0432\u044B\u043A\u043B\u044E\u0447\u0435\u043D \u0432 \u043D\u0430\u0441\u0442\u0440\u043E\u0439\u043A\u0430\u0445`);
10312
9423
  }
10313
9424
  const agyRecord = frame.resume ? await this.#antigravity.find(frame.resume) : null;
10314
9425
  if (agyRecord || !frame.resume && frame.provider === "antigravity") {
@@ -10472,7 +9583,7 @@ var HostServer = class {
10472
9583
  this.#broadcast({ type: "context.state", sessionId: session.id, context });
10473
9584
  });
10474
9585
  session.on("stderr", (data) => {
10475
- const tag = session instanceof AntigravitySession ? "agy" : session instanceof CodexSession ? "codex" : "claude";
9586
+ const tag = session instanceof AntigravitySession ? "agy" : "claude";
10476
9587
  process.stderr.write(`[${tag} ${session.id.slice(0, 8)}] ${data}`);
10477
9588
  });
10478
9589
  }
@@ -10492,7 +9603,7 @@ var HostServer = class {
10492
9603
  * разговора пока и не было.
10493
9604
  */
10494
9605
  #ensureSide(parent) {
10495
- if (!(parent instanceof ClaudeSession)) {
9606
+ if (parent instanceof AntigravitySession) {
10496
9607
  throw new Error("\u0412\u043E\u043F\u0440\u043E\u0441 \u043D\u0430 \u043F\u043E\u043B\u044F\u0445 \u0434\u043E\u0441\u0442\u0443\u043F\u0435\u043D \u0442\u043E\u043B\u044C\u043A\u043E \u0432 \u0441\u0435\u0441\u0441\u0438\u044F\u0445 Claude");
10497
9608
  }
10498
9609
  const existing = this.#sides.get(parent.id);
@@ -10550,7 +9661,7 @@ var HostServer = class {
10550
9661
  */
10551
9662
  #roots() {
10552
9663
  const roots = this.#finder.roots();
10553
- return roots.length > 0 ? roots : [homedir7()];
9664
+ return roots.length > 0 ? roots : [homedir6()];
10554
9665
  }
10555
9666
  /**
10556
9667
  * Где сессии этого каталога разрешено писать без вопроса.
@@ -10792,7 +9903,7 @@ var HostServer = class {
10792
9903
  live.setTitle(title);
10793
9904
  return;
10794
9905
  }
10795
- if (await this.#antigravity.rename(sessionId, title) || await this.#codex.rename(sessionId, title)) {
9906
+ if (await this.#antigravity.rename(sessionId, title)) {
10796
9907
  if (workspaceId)
10797
9908
  await this.#sendSessionList(workspaceId);
10798
9909
  return;
@@ -10849,11 +9960,6 @@ var HostServer = class {
10849
9960
  continue;
10850
9961
  historical.push(antigravitySummary(record));
10851
9962
  }
10852
- for (const record of await this.#codex.list(workspaceId)) {
10853
- if (liveIds.has(record.id))
10854
- continue;
10855
- historical.push({ ...antigravitySummary(record), provider: "codex", switchModelsOnFlag: false });
10856
- }
10857
9963
  const known = /* @__PURE__ */ new Set([...liveIds, ...historical.map((s) => s.id)]);
10858
9964
  await this.#archive.sweep(workspaceId, historical.filter((s) => !this.#pins.has(s.id)).map((s) => ({ id: s.id, updatedAt: s.updatedAt })), known, this.#settings.current.autoArchiveAfterMs);
10859
9965
  await this.#pins.sweep(workspaceId, known);
@@ -10900,15 +10006,15 @@ var HostServer = class {
10900
10006
  }
10901
10007
  #serveStatic(req, res) {
10902
10008
  const webRoot = this.#options.webRoot;
10903
- if (!webRoot || !existsSync5(webRoot)) {
10009
+ if (!webRoot || !existsSync4(webRoot)) {
10904
10010
  res.writeHead(200, { "content-type": "text/plain; charset=utf-8" });
10905
10011
  res.end("CCV host is running. UI is served by the Vite dev server.\n");
10906
10012
  return;
10907
10013
  }
10908
10014
  const url2 = new URL(req.url ?? "/", "http://localhost");
10909
- const requested = path24.join(webRoot, path24.normalize(url2.pathname));
10910
- const target = requested.startsWith(webRoot) && existsSync5(requested) && statSync4(requested).isFile() ? requested : path24.join(webRoot, "index.html");
10911
- if (!existsSync5(target)) {
10015
+ const requested = path23.join(webRoot, path23.normalize(url2.pathname));
10016
+ const target = requested.startsWith(webRoot) && existsSync4(requested) && statSync3(requested).isFile() ? requested : path23.join(webRoot, "index.html");
10017
+ if (!existsSync4(target)) {
10912
10018
  res.writeHead(404).end("not found");
10913
10019
  return;
10914
10020
  }
@@ -10933,7 +10039,7 @@ function contentType(file) {
10933
10039
  ".svg": "image/svg+xml",
10934
10040
  ".woff2": "font/woff2"
10935
10041
  };
10936
- return types[path24.extname(file)] ?? "application/octet-stream";
10042
+ return types[path23.extname(file)] ?? "application/octet-stream";
10937
10043
  }
10938
10044
  function antigravitySummary(record) {
10939
10045
  return {
@@ -10962,9 +10068,9 @@ function antigravitySummary(record) {
10962
10068
  }
10963
10069
 
10964
10070
  // dist/ccv.js
10965
- var HERE = path25.dirname(fileURLToPath(import.meta.url));
10966
- var PACKAGE_ROOT = path25.resolve(HERE, "..");
10967
- var USAGE = `ccv \u2014 Claude Code Visual: \u0438\u043D\u0442\u0435\u0440\u0444\u0435\u0439\u0441 \u043A Claude Code, Codex \u0438 Antigravity \u0432 \u0431\u0440\u0430\u0443\u0437\u0435\u0440\u0435.
10071
+ var HERE = path24.dirname(fileURLToPath(import.meta.url));
10072
+ var PACKAGE_ROOT = path24.resolve(HERE, "..");
10073
+ var USAGE = `ccv \u2014 Claude Code Visual: \u043B\u043E\u043A\u0430\u043B\u044C\u043D\u044B\u0439 \u0445\u043E\u0441\u0442 Claude Code \u0441 \u0438\u043D\u0442\u0435\u0440\u0444\u0435\u0439\u0441\u043E\u043C \u0432 \u0431\u0440\u0430\u0443\u0437\u0435\u0440\u0435.
10968
10074
 
10969
10075
  \u0418\u0441\u043F\u043E\u043B\u044C\u0437\u043E\u0432\u0430\u043D\u0438\u0435:
10970
10076
  ccv [\u043E\u043F\u0446\u0438\u0438]
@@ -10973,12 +10079,12 @@ var USAGE = `ccv \u2014 Claude Code Visual: \u0438\u043D\u0442\u0435\u0440\u0444
10973
10079
  -p, --port <\u043F\u043E\u0440\u0442> \u043F\u043E\u0440\u0442 \u0445\u043E\u0441\u0442\u0430 (\u043F\u043E \u0443\u043C\u043E\u043B\u0447\u0430\u043D\u0438\u044E 8787)
10974
10080
  --host <\u0430\u0434\u0440\u0435\u0441> \u0430\u0434\u0440\u0435\u0441 \u043F\u0440\u043E\u0441\u043B\u0443\u0448\u0438\u0432\u0430\u043D\u0438\u044F (\u043F\u043E \u0443\u043C\u043E\u043B\u0447\u0430\u043D\u0438\u044E 127.0.0.1)
10975
10081
  --no-open \u043D\u0435 \u043E\u0442\u043A\u0440\u044B\u0432\u0430\u0442\u044C \u0431\u0440\u0430\u0443\u0437\u0435\u0440
10976
- --claude \u0447\u0435\u043C \u0431\u0443\u0434\u0443\u0442 \u043F\u043E\u0434\u043D\u0438\u043C\u0430\u0442\u044C\u0441\u044F \u0441\u0435\u0441\u0441\u0438\u0438 Claude, \u0438 \u0432\u044B\u0439\u0442\u0438
10082
+ --claude \u0447\u0435\u043C \u0431\u0443\u0434\u0443\u0442 \u043F\u043E\u0434\u043D\u0438\u043C\u0430\u0442\u044C\u0441\u044F \u0441\u0435\u0441\u0441\u0438\u0438, \u0438 \u0432\u044B\u0439\u0442\u0438
10977
10083
  -v, --version \u0432\u0435\u0440\u0441\u0438\u044F
10978
10084
  -h, --help \u044D\u0442\u0430 \u0441\u043F\u0440\u0430\u0432\u043A\u0430
10979
10085
 
10980
10086
  \u041E\u043A\u0440\u0443\u0436\u0435\u043D\u0438\u0435: CCV_PORT, CCV_HOST, CCV_DATA_DIR, CCV_WEB_ROOT, CCV_RELAY_URL,
10981
- CCV_CLAUDE_PATH, CCV_BUNDLED_CLAUDE, CCV_CODEX_PATH, CCV_AGY_PATH.
10087
+ CCV_CLAUDE_PATH, CCV_BUNDLED_CLAUDE.
10982
10088
  \u0424\u043B\u0430\u0433 \u0432\u0430\u0436\u043D\u0435\u0435 \u043F\u0435\u0440\u0435\u043C\u0435\u043D\u043D\u043E\u0439 \u043E\u043A\u0440\u0443\u0436\u0435\u043D\u0438\u044F, \u043F\u0435\u0440\u0435\u043C\u0435\u043D\u043D\u0430\u044F \u0432\u0430\u0436\u043D\u0435\u0435 \u0437\u043D\u0430\u0447\u0435\u043D\u0438\u044F \u043F\u043E \u0443\u043C\u043E\u043B\u0447\u0430\u043D\u0438\u044E.`;
10983
10089
  var options = {
10984
10090
  port: { type: "string", short: "p" },
@@ -11030,7 +10136,7 @@ var server = new HostServer({
11030
10136
  dataDir: defaults.dataDir,
11031
10137
  // UI лежит в пакете рядом с бандлом — это и есть разница между установленной
11032
10138
  // утилитой и запуском из репозитория, где сборка живёт в `apps/web/dist`.
11033
- webRoot: process.env.CCV_WEB_ROOT ?? path25.join(PACKAGE_ROOT, "web"),
10139
+ webRoot: process.env.CCV_WEB_ROOT ?? path24.join(PACKAGE_ROOT, "web"),
11034
10140
  version,
11035
10141
  relayUrl: defaults.relayUrl
11036
10142
  });
@@ -11059,7 +10165,7 @@ for (const signal of ["SIGINT", "SIGTERM"]) {
11059
10165
  }
11060
10166
  async function packageVersion() {
11061
10167
  try {
11062
- const text = await readFile17(path25.join(PACKAGE_ROOT, "package.json"), "utf8");
10168
+ const text = await readFile17(path24.join(PACKAGE_ROOT, "package.json"), "utf8");
11063
10169
  return JSON.parse(text).version ?? "0.0.0";
11064
10170
  } catch {
11065
10171
  return "0.0.0";
@@ -11103,7 +10209,7 @@ function openBrowser(target) {
11103
10209
  return;
11104
10210
  }
11105
10211
  const command = process.platform === "win32" ? { file: "cmd", args: ["/c", "start", "", target] } : process.platform === "darwin" ? { file: "open", args: [target] } : { file: "xdg-open", args: [target] };
11106
- const child = spawn4(command.file, command.args, {
10212
+ const child = spawn3(command.file, command.args, {
11107
10213
  stdio: "ignore",
11108
10214
  detached: true,
11109
10215
  windowsHide: true