codexuse-cli 5.1.1 → 5.1.5

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -4327,9 +4327,19 @@ async function requestGumroadVerify(licenseKey, mode) {
4327
4327
  clearTimeout(timeout);
4328
4328
  }
4329
4329
  }
4330
- function normalizeVerificationResult(response) {
4330
+ function isExplicitRevocationMessage(message) {
4331
+ if (!message) {
4332
+ return false;
4333
+ }
4334
+ const normalized = message.toLowerCase();
4335
+ return normalized.includes("revoked") || normalized.includes("refunded") || normalized.includes("chargeback") || normalized.includes("disabled") || normalized.includes("subscription") || normalized.includes("no longer active");
4336
+ }
4337
+ function normalizeVerificationResult(response, mode) {
4331
4338
  if (!response.success) {
4332
4339
  const message = response.message ?? "License key is invalid.";
4340
+ if (mode === "refresh" && !isExplicitRevocationMessage(message)) {
4341
+ throw new LicenseError(message, "network");
4342
+ }
4333
4343
  throw new LicenseError(message, "invalid");
4334
4344
  }
4335
4345
  if (!response.purchase) {
@@ -4502,7 +4512,7 @@ var LicenseService = class {
4502
4512
  try {
4503
4513
  const result = await requestGumroadVerify(workingStored.licenseKey, "refresh");
4504
4514
  ensureWithinUseLimit(result);
4505
- const normalized = normalizeVerificationResult(result);
4515
+ const normalized = normalizeVerificationResult(result, "refresh");
4506
4516
  const updated = {
4507
4517
  licenseKey: workingStored.licenseKey,
4508
4518
  purchaseEmail: normalized.email,
@@ -4561,7 +4571,7 @@ var LicenseService = class {
4561
4571
  const digest = import_node_crypto5.default.createHash("sha256").update(trimmed).digest("hex");
4562
4572
  const result = await requestGumroadVerify(trimmed, "activation");
4563
4573
  ensureWithinUseLimit(result);
4564
- const normalized = normalizeVerificationResult(result);
4574
+ const normalized = normalizeVerificationResult(result, "activation");
4565
4575
  const stored = {
4566
4576
  licenseKey: trimmed,
4567
4577
  purchaseEmail: normalized.email,
@@ -4670,6 +4680,10 @@ function resolveProfileIdentityKey(profile) {
4670
4680
  return profileName ? `profile:${profileName}` : null;
4671
4681
  }
4672
4682
  function resolveProfileIdentityKeyFromProfile(profile) {
4683
+ const rateLimitKey = normalizeValue(profile.rateLimitKey);
4684
+ if (rateLimitKey) {
4685
+ return rateLimitKey;
4686
+ }
4673
4687
  return resolveProfileIdentityKey(profile) ?? `profile:${profile.name}`;
4674
4688
  }
4675
4689
 
@@ -4873,6 +4887,17 @@ function buildCodexCommand(binaryPath, args, env) {
4873
4887
  };
4874
4888
  }
4875
4889
 
4890
+ // ../../packages/runtime-codex/src/cli/env.ts
4891
+ function buildCodexChildEnv(overrides = {}) {
4892
+ const env = { ...process.env };
4893
+ for (const key of Object.keys(env)) {
4894
+ if (key.startsWith("OPENAI_")) {
4895
+ delete env[key];
4896
+ }
4897
+ }
4898
+ return { ...env, ...overrides };
4899
+ }
4900
+
4876
4901
  // ../../packages/shared/src/core/logger.ts
4877
4902
  var isTestEnv = process.env.NODE_ENV === "test" || process.env.VITEST === "true" || process.env.VITEST === "1";
4878
4903
  function isMocked(fn) {
@@ -5715,14 +5740,13 @@ async function fetchRateLimitsViaRpc(envOverride, options = {}) {
5715
5740
  });
5716
5741
  return null;
5717
5742
  }
5718
- const childEnv = {
5719
- ...process.env,
5743
+ const childEnv = buildCodexChildEnv({
5720
5744
  ...envOverride ?? {},
5721
5745
  HOME: tempHome,
5722
5746
  CODEX_HOME: tempHome,
5723
5747
  CODEX_TELEMETRY_LABEL: "codex-rpc",
5724
5748
  ELECTRON_RUN_AS_NODE: "1"
5725
- };
5749
+ });
5726
5750
  const command = buildCodexCommand(
5727
5751
  binaryPath,
5728
5752
  ["-s", "read-only", "-a", "untrusted", "app-server"],
@@ -5825,14 +5849,13 @@ async function activateResetWindowViaRpc(envOverride, options = {}) {
5825
5849
  });
5826
5850
  return { status: "skipped", reason: "auth-missing" };
5827
5851
  }
5828
- const childEnv = {
5829
- ...process.env,
5852
+ const childEnv = buildCodexChildEnv({
5830
5853
  ...envOverride ?? {},
5831
5854
  HOME: tempHome,
5832
5855
  CODEX_HOME: tempHome,
5833
5856
  CODEX_TELEMETRY_LABEL: "codex-reset-activation",
5834
5857
  ELECTRON_RUN_AS_NODE: "1"
5835
- };
5858
+ });
5836
5859
  const command = buildCodexCommand(
5837
5860
  binaryPath,
5838
5861
  ["-s", "read-only", "-a", "untrusted", "app-server"],
@@ -6155,6 +6178,7 @@ var ProfileManager = class {
6155
6178
  displayName: record.displayName ?? null,
6156
6179
  data: record.data,
6157
6180
  metadata: record.metadata,
6181
+ rateLimitKey: record.rateLimitKey ?? null,
6158
6182
  accountId: record.accountId ?? null,
6159
6183
  workspaceId: record.workspaceId ?? null,
6160
6184
  workspaceName: record.workspaceName ?? null,
@@ -6172,11 +6196,14 @@ var ProfileManager = class {
6172
6196
  if (!dataRaw || typeof dataRaw !== "object") {
6173
6197
  return null;
6174
6198
  }
6175
- return {
6199
+ const data = cloneJson(dataRaw);
6200
+ const metadata = raw.metadata ? cloneJson(raw.metadata) : void 0;
6201
+ const fallbackRecord = {
6176
6202
  name: profileName,
6177
6203
  displayName: typeof raw.displayName === "string" ? raw.displayName : null,
6178
- data: cloneJson(dataRaw),
6179
- metadata: raw.metadata ? cloneJson(raw.metadata) : void 0,
6204
+ data,
6205
+ metadata,
6206
+ rateLimitKey: typeof raw.rateLimitKey === "string" ? raw.rateLimitKey : null,
6180
6207
  accountId: typeof raw.accountId === "string" ? raw.accountId : null,
6181
6208
  workspaceId: typeof raw.workspaceId === "string" ? raw.workspaceId : null,
6182
6209
  workspaceName: typeof raw.workspaceName === "string" ? raw.workspaceName : null,
@@ -6185,6 +6212,10 @@ var ProfileManager = class {
6185
6212
  createdAt: typeof raw.createdAt === "string" ? raw.createdAt : null,
6186
6213
  updatedAt: typeof raw.updatedAt === "string" ? raw.updatedAt : null
6187
6214
  };
6215
+ return {
6216
+ ...fallbackRecord,
6217
+ rateLimitKey: fallbackRecord.rateLimitKey ?? this.resolveProfileIdentityFromRecord(fallbackRecord)
6218
+ };
6188
6219
  }
6189
6220
  async readProfilesStateSource() {
6190
6221
  const state = await getAppState();
@@ -6234,10 +6265,11 @@ var ProfileManager = class {
6234
6265
  }
6235
6266
  rateLimitSnapshotKeysForRecord(record) {
6236
6267
  return Array.from(
6237
- /* @__PURE__ */ new Set([
6268
+ new Set([
6238
6269
  this.resolveProfileIdentityFromRecord(record),
6270
+ record.rateLimitKey,
6239
6271
  resolveFallbackAccountKey(record.name)
6240
- ])
6272
+ ].filter((key) => Boolean(key)))
6241
6273
  );
6242
6274
  }
6243
6275
  rateLimitSnapshotKeysForStateMap(map) {
@@ -6950,6 +6982,7 @@ var ProfileManager = class {
6950
6982
  displayName,
6951
6983
  data,
6952
6984
  metadata: resolvedMetadata,
6985
+ rateLimitKey: existingRecord?.rateLimitKey ?? this.resolveProfileIdentityFromData(resolvedName, data, resolvedMetadata),
6953
6986
  accountId,
6954
6987
  workspaceId: data.workspace_id ?? workspaceId,
6955
6988
  workspaceName: data.workspace_name ?? workspaceName,
@@ -6968,6 +7001,7 @@ var ProfileManager = class {
6968
7001
  createdAt: row.createdAt ?? void 0,
6969
7002
  authMethod: row.authMethod ?? void 0,
6970
7003
  accountId: row.accountId ?? void 0,
7004
+ rateLimitKey: row.rateLimitKey ?? void 0,
6971
7005
  workspaceId: row.workspaceId ?? void 0,
6972
7006
  workspaceName: row.workspaceName ?? void 0,
6973
7007
  metadata: row.metadata
@@ -7004,6 +7038,7 @@ var ProfileManager = class {
7004
7038
  name,
7005
7039
  displayName: fallback?.displayName ?? name,
7006
7040
  isValid: Boolean(data && Object.keys(data).length > 0),
7041
+ rateLimitKey: fallback?.rateLimitKey,
7007
7042
  accountId,
7008
7043
  workspaceId,
7009
7044
  workspaceName,
@@ -7395,11 +7430,10 @@ var ProfileManager = class {
7395
7430
  const codexFormat = this.convertToCodexFormat(profileData);
7396
7431
  const profileHome = await this.prepareProfileHome(profileName, codexFormat);
7397
7432
  const authPath = import_path.default.join(profileHome, "auth.json");
7398
- const envOverrides = {
7399
- ...process.env,
7433
+ const envOverrides = buildCodexChildEnv({
7400
7434
  HOME: profileHome,
7401
7435
  CODEX_HOME: profileHome
7402
- };
7436
+ });
7403
7437
  try {
7404
7438
  return await action(envOverrides);
7405
7439
  } finally {
@@ -7449,11 +7483,10 @@ var ProfileManager = class {
7449
7483
  const profileHome = await this.prepareProfileHome(profileName, codexFormat);
7450
7484
  return {
7451
7485
  profileHome,
7452
- env: {
7453
- ...process.env,
7486
+ env: buildCodexChildEnv({
7454
7487
  HOME: profileHome,
7455
7488
  CODEX_HOME: profileHome
7456
- }
7489
+ })
7457
7490
  };
7458
7491
  })
7459
7492
  );
@@ -7698,13 +7731,13 @@ var ProfileManager = class {
7698
7731
  profileName,
7699
7732
  async (env) => {
7700
7733
  try {
7701
- const oauthSnapshot = await fetchRateLimitsViaOAuth(env);
7702
- if (oauthSnapshot) {
7703
- return oauthSnapshot;
7734
+ const rpcSnapshot = await fetchRateLimitsViaRpc(env, { codexPath: options.codexPath });
7735
+ if (rpcSnapshot) {
7736
+ return rpcSnapshot;
7704
7737
  }
7705
7738
  } catch {
7706
7739
  }
7707
- return fetchRateLimitsViaRpc(env, { codexPath: options.codexPath });
7740
+ return fetchRateLimitsViaOAuth(env);
7708
7741
  },
7709
7742
  { syncFromActiveAuthBeforeAction: false }
7710
7743
  )
@@ -8049,6 +8082,7 @@ var ProfileManager = class {
8049
8082
  displayName: typeof candidate.displayName === "string" ? candidate.displayName : null,
8050
8083
  data,
8051
8084
  metadata,
8085
+ rateLimitKey: this.resolveProfileIdentityFromData(name, data, metadata),
8052
8086
  accountId: typeof candidate.accountId === "string" ? candidate.accountId : null,
8053
8087
  workspaceId: typeof candidate.workspaceId === "string" ? candidate.workspaceId : null,
8054
8088
  workspaceName: typeof candidate.workspaceName === "string" ? candidate.workspaceName : null,
@@ -9611,6 +9645,7 @@ var import_node_path10 = __toESM(require("path"), 1);
9611
9645
  var import_node_fs6 = require("fs");
9612
9646
  var import_node_path9 = __toESM(require("path"), 1);
9613
9647
  var ROLLOUT_DIRS = ["sessions", "archived_sessions"];
9648
+ var SQLITE_EXTENSIONS = /* @__PURE__ */ new Set([".db", ".sqlite", ".sqlite3"]);
9614
9649
  function isRecord5(value) {
9615
9650
  return Boolean(value) && typeof value === "object" && !Array.isArray(value);
9616
9651
  }
@@ -9729,8 +9764,91 @@ function resolveRolloutPath(profileHome, rolloutPath) {
9729
9764
  }
9730
9765
  return import_node_path9.default.isAbsolute(rolloutPath) ? rolloutPath : import_node_path9.default.join(profileHome, rolloutPath);
9731
9766
  }
9732
- async function readThreadRecordFromStateDb(profileHome, threadId) {
9733
- const dbPath = import_node_path9.default.join(profileHome, "state_5.sqlite");
9767
+ async function collectSessionDatabasePaths(profileHome) {
9768
+ const paths = [];
9769
+ const sqliteDir = import_node_path9.default.join(profileHome, "sqlite");
9770
+ try {
9771
+ const entries = await import_node_fs6.promises.readdir(sqliteDir, {
9772
+ withFileTypes: true,
9773
+ encoding: "utf8"
9774
+ });
9775
+ for (const entry of entries) {
9776
+ if (!entry.isFile()) {
9777
+ continue;
9778
+ }
9779
+ const entryName = String(entry.name);
9780
+ if (SQLITE_EXTENSIONS.has(import_node_path9.default.extname(entryName))) {
9781
+ paths.push(import_node_path9.default.join(sqliteDir, entryName));
9782
+ }
9783
+ }
9784
+ } catch {
9785
+ }
9786
+ paths.sort((left, right) => {
9787
+ const leftName = import_node_path9.default.basename(left);
9788
+ const rightName = import_node_path9.default.basename(right);
9789
+ if (leftName === "codex-dev.db" && rightName !== "codex-dev.db") return -1;
9790
+ if (rightName === "codex-dev.db" && leftName !== "codex-dev.db") return 1;
9791
+ return leftName.localeCompare(rightName);
9792
+ });
9793
+ const legacy = import_node_path9.default.join(profileHome, "state_5.sqlite");
9794
+ if (!paths.includes(legacy)) {
9795
+ paths.push(legacy);
9796
+ }
9797
+ return paths;
9798
+ }
9799
+ function tableColumns(db, table) {
9800
+ try {
9801
+ return new Set(
9802
+ db.prepare(`PRAGMA table_info(${table})`).all().map((row) => isRecord5(row) ? recordString(row.name) : null).filter((name) => Boolean(name))
9803
+ );
9804
+ } catch {
9805
+ return /* @__PURE__ */ new Set();
9806
+ }
9807
+ }
9808
+ function firstColumn(columns, names) {
9809
+ return names.find((name) => columns.has(name)) ?? null;
9810
+ }
9811
+ function sqlColumnOrNull(column, alias) {
9812
+ return column ? `${column} AS ${alias}` : `NULL AS ${alias}`;
9813
+ }
9814
+ function queryThreadRecordFromTable(db, profileHome, threadId, config) {
9815
+ const columns = tableColumns(db, config.table);
9816
+ const idColumn = firstColumn(columns, config.id);
9817
+ if (!idColumn) {
9818
+ return null;
9819
+ }
9820
+ const variants = threadIdVariants(threadId);
9821
+ const placeholders = variants.map(() => "?").join(", ");
9822
+ const orderByColumn = firstColumn(columns, [
9823
+ "updated_at_ms",
9824
+ "updated_at",
9825
+ "created_at_ms",
9826
+ "created_at"
9827
+ ]);
9828
+ const select = [
9829
+ sqlColumnOrNull(firstColumn(columns, config.rolloutPath), "rollout_path"),
9830
+ sqlColumnOrNull(firstColumn(columns, config.title), "title"),
9831
+ sqlColumnOrNull(firstColumn(columns, config.cwd), "cwd"),
9832
+ sqlColumnOrNull(firstColumn(columns, ["updated_at"]), "updated_at"),
9833
+ sqlColumnOrNull(firstColumn(columns, ["updated_at_ms"]), "updated_at_ms"),
9834
+ sqlColumnOrNull(firstColumn(columns, ["created_at_ms", "created_at"]), "created_at_ms")
9835
+ ].join(", ");
9836
+ const orderBy = orderByColumn ? ` ORDER BY ${orderByColumn} DESC, ${idColumn} DESC` : ` ORDER BY ${idColumn} DESC`;
9837
+ const row = db.prepare(
9838
+ `SELECT ${select} FROM ${config.table} WHERE ${idColumn} IN (${placeholders})${orderBy} LIMIT 1`
9839
+ ).all(...variants).find(isRecord5);
9840
+ if (!row) {
9841
+ return null;
9842
+ }
9843
+ return {
9844
+ rolloutPath: resolveRolloutPath(profileHome, recordString(row.rollout_path)),
9845
+ title: recordString(row.title),
9846
+ cwd: recordString(row.cwd),
9847
+ updatedAt: recordString(row.updated_at),
9848
+ updatedAtMs: normalizeTimestampMs(row.updated_at_ms) ?? normalizeTimestampMs(row.updated_at) ?? normalizeTimestampMs(row.created_at_ms)
9849
+ };
9850
+ }
9851
+ async function readThreadRecordFromDb(profileHome, dbPath, threadId) {
9734
9852
  try {
9735
9853
  await import_node_fs6.promises.access(dbPath);
9736
9854
  } catch {
@@ -9739,42 +9857,28 @@ async function readThreadRecordFromStateDb(profileHome, threadId) {
9739
9857
  let db = null;
9740
9858
  try {
9741
9859
  db = await openReadonlyDatabase(dbPath);
9742
- const columns = new Set(
9743
- db.prepare("PRAGMA table_info(threads)").all().map((row2) => isRecord5(row2) ? recordString(row2.name) : null).filter((name) => Boolean(name))
9744
- );
9745
- const idColumn = columns.has("id") ? "id" : columns.has("thread_id") ? "thread_id" : null;
9746
- if (!idColumn) {
9747
- return null;
9748
- }
9749
- const variants = threadIdVariants(threadId);
9750
- const placeholders = variants.map(() => "?").join(", ");
9751
- const select = [
9752
- columns.has("rollout_path") ? "rollout_path AS rollout_path" : "NULL AS rollout_path",
9753
- columns.has("title") ? "title AS title" : "NULL AS title",
9754
- columns.has("cwd") ? "cwd AS cwd" : "NULL AS cwd",
9755
- columns.has("updated_at") ? "updated_at AS updated_at" : "NULL AS updated_at",
9756
- columns.has("updated_at_ms") ? "updated_at_ms AS updated_at_ms" : "NULL AS updated_at_ms",
9757
- columns.has("created_at_ms") ? "created_at_ms AS created_at_ms" : "NULL AS created_at_ms"
9758
- ].join(", ");
9759
- const orderByColumn = columns.has("updated_at_ms") ? "updated_at_ms" : columns.has("updated_at") ? "updated_at" : columns.has("created_at_ms") ? "created_at_ms" : null;
9760
- const orderBy = orderByColumn ? ` ORDER BY ${orderByColumn} DESC, ${idColumn} DESC` : ` ORDER BY ${idColumn} DESC`;
9761
- const rows = db.prepare(
9762
- `SELECT ${select} FROM threads WHERE ${idColumn} IN (${placeholders})${orderBy} LIMIT 1`
9763
- ).all(...variants);
9764
- const row = rows.find(isRecord5);
9765
- if (!row) {
9766
- return null;
9860
+ for (const config of [
9861
+ {
9862
+ table: "threads",
9863
+ id: ["id", "thread_id"],
9864
+ title: ["title", "thread_title"],
9865
+ cwd: ["cwd", "source_cwd"],
9866
+ rolloutPath: ["rollout_path"]
9867
+ },
9868
+ {
9869
+ table: "automation_runs",
9870
+ id: ["thread_id", "id"],
9871
+ title: ["thread_title", "title", "inbox_title"],
9872
+ cwd: ["source_cwd", "cwd"],
9873
+ rolloutPath: []
9874
+ }
9875
+ ]) {
9876
+ const record = queryThreadRecordFromTable(db, profileHome, threadId, config);
9877
+ if (record) {
9878
+ return record;
9879
+ }
9767
9880
  }
9768
- return {
9769
- rolloutPath: resolveRolloutPath(
9770
- profileHome,
9771
- recordString(row.rollout_path)
9772
- ),
9773
- title: recordString(row.title),
9774
- cwd: recordString(row.cwd),
9775
- updatedAt: recordString(row.updated_at),
9776
- updatedAtMs: normalizeTimestampMs(row.updated_at_ms) ?? normalizeTimestampMs(row.updated_at) ?? normalizeTimestampMs(row.created_at_ms)
9777
- };
9881
+ return null;
9778
9882
  } catch {
9779
9883
  return null;
9780
9884
  } finally {
@@ -9782,9 +9886,16 @@ async function readThreadRecordFromStateDb(profileHome, threadId) {
9782
9886
  }
9783
9887
  }
9784
9888
  async function findOfficialCodexThreadRecord(profileHome, threadId) {
9785
- const stateRecord = await readThreadRecordFromStateDb(profileHome, threadId);
9786
- if (stateRecord) {
9787
- return stateRecord;
9889
+ const records = [];
9890
+ for (const dbPath of await collectSessionDatabasePaths(profileHome)) {
9891
+ const stateRecord = await readThreadRecordFromDb(profileHome, dbPath, threadId);
9892
+ if (stateRecord) {
9893
+ records.push(stateRecord);
9894
+ }
9895
+ }
9896
+ if (records.length > 0) {
9897
+ records.sort((left, right) => (right.updatedAtMs ?? 0) - (left.updatedAtMs ?? 0));
9898
+ return records[0] ?? null;
9788
9899
  }
9789
9900
  const rolloutMatch = await findRolloutFileByScan(profileHome, threadId);
9790
9901
  if (!rolloutMatch) {
@@ -10150,13 +10261,14 @@ async function readCdpTargets(port) {
10150
10261
  }
10151
10262
  throw lastError instanceof Error ? lastError : new Error("cdp-list-failed");
10152
10263
  }
10153
- function pickCodexCdpTarget(targets) {
10264
+ function pickCodexCdpTarget(targets, options = {}) {
10154
10265
  const pages = targets.filter(
10155
10266
  (target) => target.webSocketDebuggerUrl && (target.type === "page" || target.type === "webview" || !target.type)
10156
10267
  );
10157
- return pages.find(
10268
+ const codexPage = pages.find(
10158
10269
  (target) => `${target.title ?? ""} ${target.url ?? ""}`.toLowerCase().includes("codex")
10159
- ) ?? pages[0] ?? null;
10270
+ ) ?? null;
10271
+ return codexPage ?? (options.allowAnyPage === true ? pages[0] ?? null : null);
10160
10272
  }
10161
10273
  function buildCdpDevToolsUrl(port, target) {
10162
10274
  const frontendUrl = target.devtoolsFrontendUrl?.trim();
@@ -10500,6 +10612,8 @@ function buildInCodexStatusOverlayCssRules() {
10500
10612
  `${chip} .codexuse-handoff-hide{display:inline-flex;width:20px;height:20px;align-items:center;justify-content:center;margin-right:3px;border-radius:50%;color:var(--cu-muted);cursor:pointer;font-size:12px;line-height:1;}`,
10501
10613
  `${chip} .codexuse-handoff-hide:hover{background:var(--cu-border);color:var(--cu-fg,#ececf1);}`,
10502
10614
  `body>[data-radix-popper-content-wrapper],body>[data-floating-ui-portal]{z-index:2147483004!important;}`,
10615
+ // Official Codex marks its titlebar draggable; injected controls must opt out.
10616
+ `${id},${id} *,${chip},${chip} *,${picker},${picker} *{-webkit-app-region:no-drag;}`,
10503
10617
  // Hand-off account picker is a standalone body child (not inside the pill),
10504
10618
  // so the pill-scoped popover rules don't reach it — give it its own palette
10505
10619
  // + popover styling, mirroring the chip.
@@ -10881,6 +10995,7 @@ function createBridgeApplyQolExpression(settings) {
10881
10995
  const overlayPosKey = "codexuse:overlay:pos";
10882
10996
  const handoffHiddenKey = "codexuse:handoff:hidden";
10883
10997
  const handoffPosKey = "codexuse:handoff:pos:v2";
10998
+ const defaultPosKey = "codexuse:overlay:top-default:v1";
10884
10999
  const readOverlayStore = (key) => {
10885
11000
  try {
10886
11001
  return window.localStorage.getItem(key);
@@ -10975,8 +11090,8 @@ function createBridgeApplyQolExpression(settings) {
10975
11090
  };
10976
11091
  const placeInitialOverlayPosition = (pill) => {
10977
11092
  const rect = pill.getBoundingClientRect();
10978
- const x = Math.round((window.innerWidth - rect.width) / 2);
10979
- const y = Math.max(72, Math.min(140, Math.round(window.innerHeight * 0.16)));
11093
+ const x = Math.max(8, window.innerWidth - rect.width - 32);
11094
+ const y = Math.max(96, Math.min(132, Math.round(window.innerHeight * 0.12)));
10980
11095
  placeOverlay(pill, x, y);
10981
11096
  };
10982
11097
  const rectsOverlap = (a, b, gap = 0) =>
@@ -10990,30 +11105,17 @@ function createBridgeApplyQolExpression(settings) {
10990
11105
  right: pos.x + rect.width,
10991
11106
  bottom: pos.y + rect.height
10992
11107
  });
10993
- const placeInitialHandoffPosition = (chip, anchorRect = null) => {
11108
+ const placeInitialHandoffPosition = (chip) => {
10994
11109
  const rect = chip.getBoundingClientRect();
10995
- if (anchorRect && rect.width > 0 && rect.height > 0) {
10996
- const gap = 8;
10997
- const middleY = Math.round(anchorRect.top + (anchorRect.height - rect.height) / 2);
10998
- const candidates = [
10999
- { x: anchorRect.right + gap, y: middleY },
11000
- { x: anchorRect.left - rect.width - gap, y: middleY },
11001
- { x: anchorRect.right - rect.width, y: anchorRect.top - rect.height - gap },
11002
- { x: anchorRect.left, y: anchorRect.top - rect.height - gap },
11003
- { x: anchorRect.right - rect.width, y: anchorRect.bottom + gap }
11004
- ];
11005
- for (const candidate of candidates) {
11006
- const next = clampOverlayXY(chip, candidate.x, candidate.y);
11007
- if (!rectsOverlap(positionedRect(rect, next), anchorRect, 6)) {
11008
- placeOverlay(chip, next.x, next.y);
11009
- return;
11010
- }
11011
- }
11012
- }
11013
- const x = Math.max(8, window.innerWidth - rect.width - 16);
11014
- const y = Math.max(64, Math.min(128, Math.round(window.innerHeight * 0.14)));
11110
+ const x = Math.round((window.innerWidth - rect.width) / 2);
11111
+ const y = 14;
11015
11112
  placeOverlay(chip, x, y);
11016
11113
  };
11114
+ if (readOverlayStore(defaultPosKey) !== "1") {
11115
+ writeOverlayStore(overlayPosKey, null);
11116
+ writeOverlayStore(handoffPosKey, null);
11117
+ writeOverlayStore(defaultPosKey, "1");
11118
+ }
11017
11119
  const setOverlayMessage = (value) => {
11018
11120
  const node = document.querySelector("#" + statusId + " [data-codexuse-action-status]");
11019
11121
  if (node) node.textContent = value || "";
@@ -11143,7 +11245,8 @@ function createBridgeApplyQolExpression(settings) {
11143
11245
  renderHandoff();
11144
11246
  }, true);
11145
11247
  document.body.appendChild(pill);
11146
- applyStoredOverlayPosition(pill);
11248
+ if (hasStoredPosition) applyStoredOverlayPosition(pill);
11249
+ else placeInitialOverlayPosition(pill);
11147
11250
  return true;
11148
11251
  }
11149
11252
  pill.dataset.open = currentAutoRollDecision || wasOpen || shouldShowIntro ? "true" : "false";
@@ -11448,6 +11551,8 @@ function createBridgeApplyQolExpression(settings) {
11448
11551
  if (shouldShowIntro) {
11449
11552
  placeInitialOverlayPosition(pill);
11450
11553
  writeOverlayStore(overlayIntroKey, "1");
11554
+ } else if (!hasStoredPosition) {
11555
+ placeInitialOverlayPosition(pill);
11451
11556
  } else {
11452
11557
  applyStoredOverlayPosition(pill);
11453
11558
  }
@@ -11692,18 +11797,18 @@ function createBridgeApplyQolExpression(settings) {
11692
11797
  const next = clampOverlayXY(chip, pos.x, pos.y);
11693
11798
  const chipRect = chip.getBoundingClientRect();
11694
11799
  if (rectsOverlap(positionedRect(chipRect, next), rect, 6)) {
11695
- placeInitialHandoffPosition(chip, rect);
11800
+ placeInitialHandoffPosition(chip);
11696
11801
  } else {
11697
11802
  placeOverlay(chip, next.x, next.y);
11698
11803
  }
11699
11804
  } else {
11700
- placeInitialHandoffPosition(chip, rect);
11805
+ placeInitialHandoffPosition(chip);
11701
11806
  }
11702
11807
  } catch {
11703
- placeInitialHandoffPosition(chip, rect);
11808
+ placeInitialHandoffPosition(chip);
11704
11809
  }
11705
11810
  } else {
11706
- placeInitialHandoffPosition(chip, rect);
11811
+ placeInitialHandoffPosition(chip);
11707
11812
  }
11708
11813
  if (wasOpen) openPicker();
11709
11814
  reportHandoff("rendered");
@@ -12055,11 +12160,23 @@ function createBridgeApplyPowerExpression(settings, settingsExpression) {
12055
12160
  || typeof item.name === "string"
12056
12161
  )
12057
12162
  );
12058
- const patchModelArray = (items, allowEmpty = false) => {
12163
+ const modelLabelLooksKnown = (value) =>
12164
+ typeof value === "string" && /(?:gpt|codex|chatgpt|claude|gemini|llama|mistral|qwen|deepseek|grok|davinci|\\bo[1-9]\\b)/i.test(value);
12165
+ const objectArrayLooksModelLike = (items) =>
12166
+ objectArrayLooksPatchable(items)
12167
+ && items.some((item) =>
12168
+ modelLabelLooksKnown(item.model)
12169
+ || modelLabelLooksKnown(item.id)
12170
+ || modelLabelLooksKnown(item.slug)
12171
+ || modelLabelLooksKnown(item.name)
12172
+ || modelLabelLooksKnown(item.displayName)
12173
+ || modelLabelLooksKnown(item.title)
12174
+ );
12175
+ const patchModelArray = (items, allowEmpty = false, requireModelLike = false) => {
12059
12176
  if (!Array.isArray(items)) return false;
12060
12177
  let localChanged = false;
12061
- unhideArray(items);
12062
12178
  if (stringArrayLooksPatchable(items)) {
12179
+ if (requireModelLike && !items.some(modelLabelLooksKnown)) return false;
12063
12180
  for (const model of modelWhitelistModels) {
12064
12181
  if (!items.includes(model)) {
12065
12182
  items.push(model);
@@ -12068,7 +12185,8 @@ function createBridgeApplyPowerExpression(settings, settingsExpression) {
12068
12185
  }
12069
12186
  return localChanged;
12070
12187
  }
12071
- if (objectArrayLooksPatchable(items, allowEmpty)) {
12188
+ if (objectArrayLooksPatchable(items, allowEmpty) && (!requireModelLike || allowEmpty || objectArrayLooksModelLike(items))) {
12189
+ unhideArray(items);
12072
12190
  const existing = new Set();
12073
12191
  for (const item of items) {
12074
12192
  existing.add(String(item.model || item.id || item.slug || item.name || ""));
@@ -12083,8 +12201,8 @@ function createBridgeApplyPowerExpression(settings, settingsExpression) {
12083
12201
  return localChanged;
12084
12202
  };
12085
12203
  if (patchModelArray(value.models, "defaultModel" in value || "availableModels" in value)) changed = true;
12086
- if (patchModelArray(value.data)) changed = true;
12087
- if (patchModelArray(value.result)) changed = true;
12204
+ if (patchModelArray(value.data, false, true)) changed = true;
12205
+ if (patchModelArray(value.result, false, true)) changed = true;
12088
12206
  if (patchModelArray(value.availableModels, true)) changed = true;
12089
12207
  if (patchModelArray(value.available_models, true)) changed = true;
12090
12208
  if (value.available_models instanceof Set) {
@@ -12201,11 +12319,23 @@ function createBridgeApplyPowerExpression(settings, settingsExpression) {
12201
12319
  return changed;
12202
12320
  };
12203
12321
  const reactFiberKeys = (element) => Object.keys(element || {}).filter((key) => key.startsWith("__reactFiber") || key.startsWith("__reactInternalInstance") || key.startsWith("__reactProps"));
12322
+ const reactModelStatePatchSelector = "[role='menu'],[role='dialog'],[role='listbox'],[data-radix-popper-content-wrapper],[data-floating-ui-portal]";
12323
+ const isWorkspaceChromeNode = (node) => {
12324
+ if (!node || node.nodeType !== 1) return false;
12325
+ if (node.closest?.("[data-app-action-sidebar-section-heading='Chats'],[data-app-action-sidebar-section-heading='Projects'],[data-app-action-sidebar-thread-id],[data-app-action-sidebar-project-row],[data-app-action-sidebar-project-id]")) {
12326
+ return true;
12327
+ }
12328
+ return Boolean(node.closest?.("main aside"));
12329
+ };
12330
+ const reactModelStatePatchNodes = () => {
12331
+ return Array.from(document.querySelectorAll(reactModelStatePatchSelector))
12332
+ .filter((node) => node && !isWorkspaceChromeNode(node));
12333
+ };
12204
12334
  const patchReactModelState = () => {
12205
12335
  if (!enabled.modelWhitelistUnlock) return false;
12206
12336
  try {
12207
12337
  const visited = new WeakSet();
12208
- const nodes = [document.body, ...Array.from(document.querySelectorAll("button,[role='menu'],[role='dialog'],[data-radix-popper-content-wrapper]"))].filter(Boolean);
12338
+ const nodes = reactModelStatePatchNodes();
12209
12339
  let changed = false;
12210
12340
  for (const node of nodes.slice(0, 220)) {
12211
12341
  for (const key of reactFiberKeys(node)) {
@@ -12220,6 +12350,39 @@ function createBridgeApplyPowerExpression(settings, settingsExpression) {
12220
12350
  return false;
12221
12351
  }
12222
12352
  };
12353
+ const installModelReactStateObserver = () => {
12354
+ if (typeof state.cleanupModelReactStateObserver === "function") {
12355
+ state.cleanupModelReactStateObserver();
12356
+ state.cleanupModelReactStateObserver = null;
12357
+ }
12358
+ if (!enabled.modelWhitelistUnlock) return false;
12359
+ let frame = 0;
12360
+ const schedulePatch = () => {
12361
+ if (frame) return;
12362
+ frame = requestAnimationFrame(() => {
12363
+ frame = 0;
12364
+ patchReactModelState();
12365
+ });
12366
+ };
12367
+ const isPatchableMutationNode = (node) => {
12368
+ const element = node?.nodeType === 1 ? node : node?.parentElement;
12369
+ return Boolean(
12370
+ element?.matches?.(reactModelStatePatchSelector)
12371
+ || element?.querySelector?.(reactModelStatePatchSelector)
12372
+ );
12373
+ };
12374
+ const observer = new MutationObserver((mutations) => {
12375
+ if (mutations.some((mutation) => Array.from(mutation.addedNodes).some(isPatchableMutationNode))) {
12376
+ schedulePatch();
12377
+ }
12378
+ });
12379
+ observer.observe(document.body, { childList: true, subtree: true });
12380
+ state.cleanupModelReactStateObserver = () => {
12381
+ observer.disconnect();
12382
+ if (frame) cancelAnimationFrame(frame);
12383
+ };
12384
+ return true;
12385
+ };
12223
12386
  const patchPluginContainer = (value, visited = new WeakSet(), depth = 0, inheritedMarketplaceName = null) => {
12224
12387
  if (!enabled.pluginMarketplaceUnlock || !value || typeof value !== "object" || visited.has(value) || depth > 4) return false;
12225
12388
  visited.add(value);
@@ -12763,6 +12926,7 @@ function createBridgeApplyPowerExpression(settings, settingsExpression) {
12763
12926
  const modelStatsigPatchApplied = enabled.modelWhitelistUnlock
12764
12927
  ? patchStatsigModelWhitelist()
12765
12928
  : false;
12929
+ installModelReactStateObserver();
12766
12930
  const modelReactStatePatched = enabled.modelWhitelistUnlock
12767
12931
  ? patchReactModelState()
12768
12932
  : false;
@@ -13939,14 +14103,16 @@ async function reloadOfficialCodexBridgePage(debuggerUrl) {
13939
14103
  return false;
13940
14104
  }
13941
14105
  }
13942
- async function probeOfficialCodexBridge(instance, forceInstall = false) {
14106
+ async function probeOfficialCodexBridge(instance, forceInstall = false, allowAnyPageTarget = false) {
13943
14107
  const checkedAt = Date.now();
13944
14108
  if (!instance.cdpPort) {
13945
14109
  return bridgeStateUnavailable();
13946
14110
  }
13947
14111
  try {
13948
14112
  const targets = await readCdpTargets(instance.cdpPort);
13949
- const target = pickCodexCdpTarget(targets);
14113
+ const target = pickCodexCdpTarget(targets, {
14114
+ allowAnyPage: allowAnyPageTarget
14115
+ });
13950
14116
  if (!target?.webSocketDebuggerUrl) {
13951
14117
  return bridgeStateUnhealthy(
13952
14118
  instance.cdpPort,
@@ -14016,14 +14182,16 @@ async function probeOfficialCodexBridge(instance, forceInstall = false) {
14016
14182
  );
14017
14183
  }
14018
14184
  }
14019
- async function reapplyDesiredBridgeSettings(instance, bridge) {
14185
+ async function reapplyDesiredBridgeSettings(instance, bridge, allowAnyPageTarget = false) {
14020
14186
  const shouldClearPowerRuntime = !instance.desiredPowerSettings && hasEnabledBridgePowerRuntime(bridge.bridgePower);
14021
14187
  if (bridge.bridgeStatus !== "healthy" || !instance.cdpPort || !instance.desiredQolSettings && !instance.desiredPowerSettings && !shouldClearPowerRuntime) {
14022
14188
  return bridge;
14023
14189
  }
14024
14190
  try {
14025
14191
  const targets = await readCdpTargets(instance.cdpPort);
14026
- const target = pickCodexCdpTarget(targets);
14192
+ const target = pickCodexCdpTarget(targets, {
14193
+ allowAnyPage: allowAnyPageTarget
14194
+ });
14027
14195
  if (!target?.webSocketDebuggerUrl) {
14028
14196
  return bridge;
14029
14197
  }
@@ -14109,7 +14277,7 @@ async function reapplyDesiredBridgeSettings(instance, bridge) {
14109
14277
  };
14110
14278
  }
14111
14279
  }
14112
- async function refreshBridgeStateIfNeeded(instance, running, force = false, reapplyDesired = false) {
14280
+ async function refreshBridgeStateIfNeeded(instance, running, force = false, reapplyDesired = false, allowAnyPageTarget = false) {
14113
14281
  if (!running || !instance.cdpPort) {
14114
14282
  return bridgeStateUnavailable();
14115
14283
  }
@@ -14117,12 +14285,16 @@ async function refreshBridgeStateIfNeeded(instance, running, force = false, reap
14117
14285
  if (!force && checkedAt && Date.now() - checkedAt < CODEX_BRIDGE_PROBE_TTL_MS) {
14118
14286
  return bridgeStateForStoredInstance(instance, true);
14119
14287
  }
14120
- const bridge = await probeOfficialCodexBridge(instance, force);
14121
- return reapplyDesired ? await reapplyDesiredBridgeSettings(instance, bridge) : bridge;
14288
+ const bridge = await probeOfficialCodexBridge(
14289
+ instance,
14290
+ force,
14291
+ allowAnyPageTarget
14292
+ );
14293
+ return reapplyDesired ? await reapplyDesiredBridgeSettings(instance, bridge, allowAnyPageTarget) : bridge;
14122
14294
  }
14123
14295
  async function waitForBridgeStateAfterLaunch(instance) {
14124
14296
  const deadline = Date.now() + CODEX_BRIDGE_LAUNCH_WAIT_MS;
14125
- let latest = await refreshBridgeStateIfNeeded(instance, true, true, true);
14297
+ let latest = await refreshBridgeStateIfNeeded(instance, true, true, true, true);
14126
14298
  while (latest.bridgeStatus !== "healthy" && Date.now() < deadline) {
14127
14299
  await new Promise((resolve) => setTimeout(resolve, POLL_INTERVAL_MS));
14128
14300
  latest = await refreshBridgeStateIfNeeded(
@@ -14132,6 +14304,7 @@ async function waitForBridgeStateAfterLaunch(instance) {
14132
14304
  },
14133
14305
  true,
14134
14306
  true,
14307
+ true,
14135
14308
  true
14136
14309
  );
14137
14310
  }
@@ -14140,7 +14313,7 @@ async function waitForBridgeStateAfterLaunch(instance) {
14140
14313
  async function waitForBridgeStateAfterReload(instance) {
14141
14314
  const deadline = Date.now() + CODEX_BRIDGE_LAUNCH_WAIT_MS;
14142
14315
  await new Promise((resolve) => setTimeout(resolve, POLL_INTERVAL_MS));
14143
- let latest = await refreshBridgeStateIfNeeded(instance, true, true, true);
14316
+ let latest = await refreshBridgeStateIfNeeded(instance, true, true, true, true);
14144
14317
  while (latest.bridgeStatus !== "healthy" && Date.now() < deadline) {
14145
14318
  await new Promise((resolve) => setTimeout(resolve, POLL_INTERVAL_MS));
14146
14319
  latest = await refreshBridgeStateIfNeeded(
@@ -14150,6 +14323,7 @@ async function waitForBridgeStateAfterReload(instance) {
14150
14323
  },
14151
14324
  true,
14152
14325
  true,
14326
+ true,
14153
14327
  true
14154
14328
  );
14155
14329
  }
@@ -14519,7 +14693,7 @@ async function openCodexWithProfileHome(candidate, profileHome, profileName, cdp
14519
14693
  ],
14520
14694
  {
14521
14695
  detached: true,
14522
- env: process.env,
14696
+ env: buildCodexChildEnv(),
14523
14697
  stdio: "ignore"
14524
14698
  }
14525
14699
  );
@@ -16577,7 +16751,7 @@ async function runCommand3(command, args, timeoutMs = 3e3) {
16577
16751
  return new Promise((resolve, reject) => {
16578
16752
  const child = (0, import_node_child_process8.spawn)(command, args, {
16579
16753
  stdio: ["ignore", "pipe", "pipe"],
16580
- env: process.env
16754
+ env: buildCodexChildEnv()
16581
16755
  });
16582
16756
  let stdout = "";
16583
16757
  let stderr = "";
@@ -18138,7 +18312,7 @@ async function ensureCliStorageReady() {
18138
18312
  }
18139
18313
 
18140
18314
  // src/app/main.ts
18141
- var VERSION = true ? "5.1.1" : "0.0.0";
18315
+ var VERSION = true ? "5.1.5" : "0.0.0";
18142
18316
  async function runCli() {
18143
18317
  const args = process.argv.slice(2);
18144
18318
  if (args.length === 0) {