codex-overleaf-link 2.3.2 → 2.3.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -3,7 +3,7 @@
3
3
  <h1>Codex Overleaf Link</h1>
4
4
  <p><strong>Empower Overleaf with Codex.</strong></p>
5
5
  <p>
6
- <img src="https://img.shields.io/badge/version-2.3.2-blue" alt="version">
6
+ <img src="https://img.shields.io/badge/version-2.3.3-blue" alt="version">
7
7
  <img src="https://img.shields.io/badge/platform-macOS%20%2F%20Windows%20%2F%20Linux-lightgrey" alt="platform">
8
8
  <img src="https://img.shields.io/badge/chrome-MV3-green" alt="chrome manifest v3">
9
9
  <img src="https://img.shields.io/badge/node-%3E%3D20-brightgreen" alt="node version">
@@ -38,14 +38,14 @@ One command installs the managed native host **and** managed extension runtime.
38
38
  macOS / Linux:
39
39
 
40
40
  ```bash
41
- CODEX_OVERLEAF_REF=v2.3.2 bash -c "$(curl -fsSL https://raw.githubusercontent.com/Ghqqqq/codex-overleaf-link/v2.3.2/install.sh)"
41
+ CODEX_OVERLEAF_REF=v2.3.3 bash -c "$(curl -fsSL https://raw.githubusercontent.com/Ghqqqq/codex-overleaf-link/v2.3.3/install.sh)"
42
42
  ```
43
43
 
44
44
  Windows PowerShell:
45
45
 
46
46
  ```powershell
47
- iwr https://raw.githubusercontent.com/Ghqqqq/codex-overleaf-link/v2.3.2/install.ps1 -OutFile install.ps1
48
- $env:CODEX_OVERLEAF_REF='v2.3.2'
47
+ iwr https://raw.githubusercontent.com/Ghqqqq/codex-overleaf-link/v2.3.3/install.ps1 -OutFile install.ps1
48
+ $env:CODEX_OVERLEAF_REF='v2.3.3'
49
49
  powershell -ExecutionPolicy Bypass -File install.ps1
50
50
  ```
51
51
 
@@ -56,7 +56,7 @@ Then, in the `chrome://extensions` tab the script opened: enable **Developer mod
56
56
  `npm exec` installs the same managed native host and extension runtime without keeping a source checkout. Use it if you prefer a pinned npm package.
57
57
 
58
58
  ```bash
59
- npm exec --yes codex-overleaf-link@2.3.2 -- install-managed
59
+ npm exec --yes codex-overleaf-link@2.3.3 -- install-managed
60
60
  ```
61
61
 
62
62
  Then, in `chrome://extensions`, enable **Developer mode**, click **Load unpacked**, and select the managed extension path printed by the command. The Release extension zip remains available for explicitly unmanaged/manual installations.
@@ -88,9 +88,9 @@ npm installs, updates, and uninstalls the coordinated managed extension/native p
88
88
 
89
89
  | Action | Command |
90
90
  |--------|---------|
91
- | Install / update | `npm exec --yes codex-overleaf-link@2.3.2 -- install-managed` |
92
- | Diagnose | `npm exec --yes codex-overleaf-link@2.3.2 -- doctor` |
93
- | Uninstall | `npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed` |
91
+ | Install / update | `npm exec --yes codex-overleaf-link@2.3.3 -- install-managed` |
92
+ | Diagnose | `npm exec --yes codex-overleaf-link@2.3.3 -- doctor` |
93
+ | Uninstall | `npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed` |
94
94
 
95
95
  Use `--extension-id <chrome-extension-id>` only for a custom/dev unpacked extension id that differs from the official bundled id.
96
96
 
@@ -104,13 +104,13 @@ Managed installations discover signed stable updates automatically and apply the
104
104
 
105
105
  v2.2.0 introduces Bootstrap protocol 2. Existing v2.1.x managed installations must run the pinned `install-managed` command once, then reload the extension and Overleaf. Later protocol-2 releases use the in-product signed updater for ordinary runtime, style, vendor, and Native Host feature changes.
106
106
 
107
- The v2.3.2 GitHub Release contains:
107
+ The v2.3.3 GitHub Release contains:
108
108
 
109
- - `codex-overleaf-link-extension-v2.3.2.zip`: loadable Chrome extension package for manual unpacked installation.
110
- - `codex-overleaf-native-host-v2.3.2.tar.gz`: native host runtime files used by the installer and release verification.
111
- - `codex-overleaf-link-2.3.2.tgz`: npm native host CLI package for pinned install, doctor, and uninstall flows.
112
- - `install.sh`: release-pinned macOS / Linux installer that defaults to `v2.3.2` when run directly from the release artifact.
113
- - `install.ps1`: release-pinned Windows PowerShell installer that defaults to `v2.3.2` when run directly from the release artifact.
109
+ - `codex-overleaf-link-extension-v2.3.3.zip`: loadable Chrome extension package for manual unpacked installation.
110
+ - `codex-overleaf-native-host-v2.3.3.tar.gz`: native host runtime files used by the installer and release verification.
111
+ - `codex-overleaf-link-2.3.3.tgz`: npm native host CLI package for pinned install, doctor, and uninstall flows.
112
+ - `install.sh`: release-pinned macOS / Linux installer that defaults to `v2.3.3` when run directly from the release artifact.
113
+ - `install.ps1`: release-pinned Windows PowerShell installer that defaults to `v2.3.3` when run directly from the release artifact.
114
114
  - `uninstall-native-host.mjs`: native host uninstaller that removes the Chrome Native Messaging manifest, bridge executable, and runtime copy.
115
115
  - `nativeHostPlatform.js`, `manifest.js`, `runtimeInstaller.js`: helper files required by the loose uninstaller asset.
116
116
  - `SHA256SUMS` and `release-manifest.json`: checksum and artifact metadata for release verification.
@@ -121,7 +121,7 @@ The v2.3.2 GitHub Release contains:
121
121
  Remove the native host (use `--browser chromium` on Linux Chromium):
122
122
 
123
123
  ```bash
124
- npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed
124
+ npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed
125
125
  ```
126
126
 
127
127
  The same command works on Windows PowerShell. If you installed from a manual checkout or source installer, you can also run `npm run uninstall:native` inside the repo, use `node ~/.codex-overleaf/source/scripts/uninstall-native-host.mjs` on macOS / Linux, or use `node $env:LOCALAPPDATA\CodexOverleaf\source\scripts\uninstall-native-host.mjs` on Windows PowerShell.
@@ -156,13 +156,13 @@ Then remove the extension from `chrome://extensions`. To delete local data: on m
156
156
  Linux Chromium install or update:
157
157
 
158
158
  ```bash
159
- CODEX_OVERLEAF_REF=v2.3.2 bash -c "$(curl -fsSL https://raw.githubusercontent.com/Ghqqqq/codex-overleaf-link/v2.3.2/install.sh)" -- --browser chromium
159
+ CODEX_OVERLEAF_REF=v2.3.3 bash -c "$(curl -fsSL https://raw.githubusercontent.com/Ghqqqq/codex-overleaf-link/v2.3.3/install.sh)" -- --browser chromium
160
160
  ```
161
161
 
162
162
  Linux Chromium uninstall:
163
163
 
164
164
  ```bash
165
- npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed --browser chromium
165
+ npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed --browser chromium
166
166
  ```
167
167
 
168
168
  ## Features
@@ -298,7 +298,7 @@ Composer attachments are turn-scoped Codex context. Limits are 8 attachments per
298
298
  Re-run any [native host installer](#install), reload the extension in `chrome://extensions`, then refresh the Overleaf tab. This also fixes extension/native version mismatch and native protocol mismatch.
299
299
 
300
300
  ```bash
301
- npm exec --yes codex-overleaf-link@2.3.2 -- install-managed
301
+ npm exec --yes codex-overleaf-link@2.3.3 -- install-managed
302
302
  ```
303
303
 
304
304
  **The Windows popup or panel shows a Bash recovery command**
@@ -347,8 +347,8 @@ Use this matrix for release-candidate signoff and compatibility reports. Record
347
347
  | Browser/channel/version | Google Chrome channel and version. | Google Chrome channel and version. | Google Chrome channel and version. | Chromium channel/package and version. |
348
348
  | Install mode | Manual unpacked extension from GitHub Release zip or checkout. | Manual unpacked extension from GitHub Release zip or checkout. | Manual unpacked extension from GitHub Release zip or checkout. | Manual unpacked extension from GitHub Release zip or checkout; native host installed with `--browser chromium`. |
349
349
  | Extension id | Bundled id `illdpneeeopfffmiepaejglgmhpmdhdc`, or actual custom id passed with `--extension-id`. | Bundled id `illdpneeeopfffmiepaejglgmhpmdhdc`, or actual custom id passed with `--extension-id`. | Bundled id `illdpneeeopfffmiepaejglgmhpmdhdc`, or actual custom id passed with `--extension-id`. | Bundled id `illdpneeeopfffmiepaejglgmhpmdhdc`, or actual custom id passed with `--extension-id`. |
350
- | Installer/update command | `npm exec --yes codex-overleaf-link@2.3.2 -- install-managed` | `npm exec --yes codex-overleaf-link@2.3.2 -- install-managed` | `npm exec --yes codex-overleaf-link@2.3.2 -- install-managed` | `npm exec --yes codex-overleaf-link@2.3.2 -- install-managed --browser chromium` |
351
- | Uninstall command | `npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed` | `npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed` | `npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed` | `npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-managed --browser chromium` |
350
+ | Installer/update command | `npm exec --yes codex-overleaf-link@2.3.3 -- install-managed` | `npm exec --yes codex-overleaf-link@2.3.3 -- install-managed` | `npm exec --yes codex-overleaf-link@2.3.3 -- install-managed` | `npm exec --yes codex-overleaf-link@2.3.3 -- install-managed --browser chromium` |
351
+ | Uninstall command | `npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed` | `npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed` | `npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed` | `npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-managed --browser chromium` |
352
352
  | Manifest/registry path | `~/Library/Application Support/Google/Chrome/NativeMessagingHosts/com.codex.overleaf.json` | `HKCU\Software\Google\Chrome\NativeMessagingHosts\com.codex.overleaf` -> `%LOCALAPPDATA%\CodexOverleaf\native-host-runtime\com.codex.overleaf.json` | `~/.config/google-chrome/NativeMessagingHosts/com.codex.overleaf.json` | `~/.config/chromium/NativeMessagingHosts/com.codex.overleaf.json` |
353
353
  | Bridge/runtime/source path | Bridge `~/.codex-overleaf/codex-overleaf-bridge`; runtime `~/.codex-overleaf/native-host-runtime`; source `~/.codex-overleaf/source`. | Bridge `%LOCALAPPDATA%\CodexOverleaf\codex-overleaf-bridge.cmd`; runtime `%LOCALAPPDATA%\CodexOverleaf\native-host-runtime`; source `%LOCALAPPDATA%\CodexOverleaf\source`. | Bridge `~/.codex-overleaf/codex-overleaf-bridge`; runtime `~/.codex-overleaf/native-host-runtime`; source `~/.codex-overleaf/source`. | Bridge `~/.codex-overleaf/codex-overleaf-bridge`; runtime `~/.codex-overleaf/native-host-runtime`; source `~/.codex-overleaf/source`. |
354
354
  | Node/Git/Codex/TeX | Node.js >= 20; Git; Codex CLI installed and logged in; TeX optional. | Node.js >= 20; Git; Codex CLI installed and logged in; TeX optional. | Node.js >= 20; Git; Codex CLI installed and logged in; TeX optional. | Node.js >= 20; Git; Codex CLI installed and logged in; TeX optional. |
@@ -384,7 +384,7 @@ Contributions are welcome. Please open an issue before submitting large changes
384
384
  The recommended v1.9 installation owns one stable unpacked-extension directory and a versioned native-host directory:
385
385
 
386
386
  ```bash
387
- npm exec --yes codex-overleaf-link@2.3.2 -- install-managed
387
+ npm exec --yes codex-overleaf-link@2.3.3 -- install-managed
388
388
  ```
389
389
 
390
390
  Load the printed extension path once from `chrome://extensions`. Starting with the next signed stable release, Codex Overleaf Link checks GitHub Releases automatically, downloads and verifies the coordinated extension/native-host bundle, waits until every connected Overleaf tab is saved and idle, and then updates both components together. A failed health check restores the previous version automatically.
@@ -394,11 +394,11 @@ The stable updater ignores drafts and prereleases, performs no telemetry, and ca
394
394
  The legacy native-only installer remains available for source or unmanaged extension directories:
395
395
 
396
396
  ```bash
397
- npm exec --yes codex-overleaf-link@2.3.2 -- install-native
397
+ npm exec --yes codex-overleaf-link@2.3.3 -- install-native
398
398
  ```
399
399
 
400
400
  Legacy native-only installations can be removed with:
401
401
 
402
402
  ```bash
403
- npm exec --yes codex-overleaf-link@2.3.2 -- uninstall-native
403
+ npm exec --yes codex-overleaf-link@2.3.3 -- uninstall-native
404
404
  ```
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "manifest_version": 3,
3
3
  "name": "Codex Overleaf Link",
4
- "version": "2.3.2",
4
+ "version": "2.3.3",
5
5
  "description": "Connect the active Overleaf project to a local Codex bridge.",
6
6
  "icons": {
7
7
  "16": "assets/icons/icon16.png",
@@ -432,6 +432,7 @@
432
432
  cssEscape,
433
433
  renderMarkdownInlineText,
434
434
  renderMarkdownBlockText,
435
+ decorateCompletionReport: Modules.MarkdownDomRenderer.decorateCompletionReport,
435
436
  sanitizeAssistantVisibleText,
436
437
  sanitizeAssistantVisibleValue,
437
438
  buildMarkdownInlineNodes,
@@ -11368,7 +11368,7 @@ ${block}`;
11368
11368
  const MIN_NATIVE_VERSION = "1.0.0";
11369
11369
  const MIN_COMPATIBLE_NATIVE_VERSION = "1.0.0";
11370
11370
  const MIN_COMPATIBLE_EXTENSION_VERSION = "1.0.0";
11371
- const BUILD_TARGET_VERSION = "2.3.2";
11371
+ const BUILD_TARGET_VERSION = "2.3.3";
11372
11372
  const DEFAULT_CHROME_EXTENSION_ID = "illdpneeeopfffmiepaejglgmhpmdhdc";
11373
11373
  const REQUIRED_CAPABILITIES = Object.freeze([
11374
11374
  "bridgePing",
@@ -18735,6 +18735,7 @@ ${block}`;
18735
18735
  return;
18736
18736
  }
18737
18737
  const style = instance.document.defaultView.getComputedStyle(panel);
18738
+ instance.root.dataset.theme = panel.dataset.theme === "light" ? "light" : "dark";
18738
18739
  instance.root.style.setProperty("--provider-panel-bg", style.backgroundColor || "#151716");
18739
18740
  instance.root.style.setProperty("--provider-panel-color", style.color || "#eceeea");
18740
18741
  }
@@ -20687,10 +20688,17 @@ ${block}`;
20687
20688
  }
20688
20689
  container.replaceChildren();
20689
20690
  container.hidden = !items.length;
20691
+ if (!items.length) {
20692
+ return;
20693
+ }
20690
20694
  for (const item of items) {
20691
20695
  const row = document.createElement("article");
20692
20696
  row.className = "codex-pending-input";
20693
20697
  row.dataset.status = item.status || "queued";
20698
+ const marker = document.createElement("span");
20699
+ marker.className = "codex-pending-input-marker";
20700
+ marker.setAttribute("aria-hidden", "true");
20701
+ marker.append(createIcon("queue"));
20694
20702
  const copy = document.createElement("div");
20695
20703
  copy.className = "codex-pending-input-copy";
20696
20704
  const status = document.createElement("span");
@@ -20699,7 +20707,10 @@ ${block}`;
20699
20707
  const text = document.createElement("span");
20700
20708
  text.className = "codex-pending-input-text";
20701
20709
  text.textContent = item.text;
20702
- copy.append(status, text);
20710
+ copy.append(text);
20711
+ if (item.status && item.status !== "queued") {
20712
+ copy.append(status);
20713
+ }
20703
20714
  const actions = document.createElement("div");
20704
20715
  actions.className = "codex-pending-input-actions";
20705
20716
  if (item.status === "paused") {
@@ -20723,7 +20734,8 @@ ${block}`;
20723
20734
  remove.disabled = item.status === "steering" || item.status === "executing";
20724
20735
  text.title = item.text;
20725
20736
  actions.append(remove);
20726
- row.append(copy, actions);
20737
+ row.setAttribute("aria-label", `${status.textContent || options2.tr?.("queuedInputQueued") || "Queued"}: ${item.text}`);
20738
+ row.append(marker, copy, actions);
20727
20739
  container.append(row);
20728
20740
  }
20729
20741
  }
@@ -20750,7 +20762,7 @@ ${block}`;
20750
20762
  svg.setAttribute("viewBox", "0 0 20 20");
20751
20763
  svg.setAttribute("aria-hidden", "true");
20752
20764
  svg.setAttribute("focusable", "false");
20753
- const paths = icon === "guide" ? ["M4 4.5v4a4 4 0 0 0 4 4h7", "m12 9 3.5 3.5L12 16"] : ["M6 6h8", "M8 6V4.5h4V6", "m7.2 8 0.6 7.5h4.4l.6-7.5"];
20765
+ const paths = icon === "guide" ? ["M4 4.5v4a4 4 0 0 0 4 4h7", "m12 9 3.5 3.5L12 16"] : icon === "queue" ? ["M4 5.5h12", "M4 10h12", "M4 14.5h8"] : ["M6 6h8", "M8 6V4.5h4V6", "m7.2 8 0.6 7.5h4.4l.6-7.5"];
20754
20766
  for (const value of paths) {
20755
20767
  const path = document.createElementNS("http://www.w3.org/2000/svg", "path");
20756
20768
  path.setAttribute("d", value);
@@ -27385,9 +27397,69 @@ ${block}`;
27385
27397
  error.code = code;
27386
27398
  return error;
27387
27399
  }
27400
+ function decorateCompletionReport(container, options2 = {}) {
27401
+ const tx = typeof options2.tx === "function" ? options2.tx : (en) => en;
27402
+ const document2 = container?.ownerDocument || globalThis.document;
27403
+ if (!container || !document2) return;
27404
+ for (const block of Array.from(container.children || [])) {
27405
+ const textNode = Array.from(block.childNodes || []).find((node) => node?.nodeType === 3 && String(node.textContent || "").trim());
27406
+ if (!textNode) continue;
27407
+ const text = String(textNode.textContent || "");
27408
+ const match = text.match(/^(\s*)(Conclusion:|结论:|Changes:|修改:)(\s*)/);
27409
+ if (!match || !textNode.parentNode) continue;
27410
+ const label = document2.createElement("span");
27411
+ label.className = "run-system-label";
27412
+ label.dataset.systemLabel = ["Conclusion:", "\u7ED3\u8BBA\uFF1A"].includes(match[2]) ? "conclusion" : "changes";
27413
+ label.textContent = `${match[2]}${match[3]}`;
27414
+ textNode.textContent = `${match[1]}${text.slice(match[0].length)}`;
27415
+ textNode.parentNode.insertBefore(label, textNode);
27416
+ }
27417
+ decorateChangeReceipts(container, document2, tx);
27418
+ }
27419
+ function decorateChangeReceipts(container, document2, tx) {
27420
+ const label = container.querySelector?.('.run-system-label[data-system-label="changes"]');
27421
+ const list = label?.closest?.("p")?.nextElementSibling;
27422
+ if (!list || !["UL", "OL"].includes(list.tagName)) return;
27423
+ const receipts = [];
27424
+ for (const item of Array.from(list.children || [])) {
27425
+ const original = String(item.textContent || "").trim();
27426
+ const match = original.match(/^(.+?):\s+(edit|create|rename|move|delete)(?:\s+\((.+)\))?$/i) || original.match(/^(.+?):\s*(编辑|新建|重命名|移动|删除)(?:((.+)))?$/);
27427
+ if (!match) return;
27428
+ receipts.push({ item, original, file: match[1], operation: match[2] });
27429
+ }
27430
+ if (!receipts.length) return;
27431
+ const syncedFiles = new Set(receipts.map((receipt) => receipt.file)).size;
27432
+ const summary = document2.createElement("div");
27433
+ summary.className = "run-change-summary";
27434
+ const check = document2.createElement("span");
27435
+ check.className = "run-change-summary__check";
27436
+ check.setAttribute("aria-hidden", "true");
27437
+ check.textContent = "\u2713";
27438
+ const text = document2.createElement("span");
27439
+ text.textContent = tx(
27440
+ `${syncedFiles} ${syncedFiles === 1 ? "file" : "files"} synced`,
27441
+ `\u5DF2\u540C\u6B65 ${syncedFiles} \u4E2A\u6587\u4EF6`
27442
+ );
27443
+ summary.append(check, text);
27444
+ list.parentNode?.insertBefore(summary, list);
27445
+ list.classList.add("run-change-receipts");
27446
+ for (const receipt of receipts) {
27447
+ const file = document2.createElement("span");
27448
+ file.className = "run-change-receipt__file";
27449
+ file.textContent = receipt.file;
27450
+ const operation = document2.createElement("span");
27451
+ operation.className = "run-change-receipt__operation";
27452
+ operation.textContent = receipt.operation;
27453
+ receipt.item.classList.add("run-change-receipt");
27454
+ receipt.item.setAttribute("aria-label", receipt.original);
27455
+ receipt.item.title = receipt.original;
27456
+ receipt.item.replaceChildren(file, operation);
27457
+ }
27458
+ }
27388
27459
  return {
27389
27460
  DEFAULT_LIMITS,
27390
27461
  countTokens,
27462
+ decorateCompletionReport,
27391
27463
  renderMarkdown,
27392
27464
  stripEmptyHtmlComments
27393
27465
  };
@@ -28820,6 +28892,7 @@ ${block}`;
28820
28892
  cssEscape,
28821
28893
  renderMarkdownInlineText,
28822
28894
  renderMarkdownBlockText,
28895
+ decorateCompletionReport,
28823
28896
  sanitizeAssistantVisibleText,
28824
28897
  sanitizeAssistantVisibleValue,
28825
28898
  stripEmptyHtmlCommentPlaceholders = (value) => value,
@@ -29400,6 +29473,7 @@ ${lines}`
29400
29473
  }
29401
29474
  if (mainSections.length) {
29402
29475
  renderMarkdownBlockText(main, mainSections.join("\n\n"));
29476
+ decorateCompletionReport(main, { tx });
29403
29477
  report.append(main);
29404
29478
  }
29405
29479
  appendCompletionMetaBlock(report, structured.meta);
@@ -29413,6 +29487,7 @@ ${lines}`
29413
29487
  const body = document.createElement("div");
29414
29488
  body.className = "run-final-answer";
29415
29489
  renderMarkdownBlockText(body, split.body || flatText);
29490
+ decorateCompletionReport(body, { tx });
29416
29491
  report.append(body);
29417
29492
  appendCompileFix(report);
29418
29493
  appendRejectedRedo(report);
@@ -35593,6 +35668,7 @@ ${tx("Writeback note: Codex could not confirm any Overleaf write result entries,
35593
35668
  cssEscape,
35594
35669
  renderMarkdownInlineText,
35595
35670
  renderMarkdownBlockText,
35671
+ decorateCompletionReport: Modules.MarkdownDomRenderer.decorateCompletionReport,
35596
35672
  sanitizeAssistantVisibleText,
35597
35673
  sanitizeAssistantVisibleValue,
35598
35674
  buildMarkdownInlineNodes,
@@ -2,9 +2,9 @@
2
2
  "schemaVersion": 1,
3
3
  "entry": "extension/entries/content-entry.mjs",
4
4
  "output": "extension/src/content/generated/content.bundle.js",
5
- "sourceDigest": "d2167fca49721d0ef5e477dc76b11a0cedb33c9f51b920b55ea666ab4668dc4c",
6
- "outputDigest": "87cbcf7d9877860b7c1d047cd3fa6e985e28812c8df81c9105ec9312a5e45ea6",
7
- "byteLength": 2309285,
5
+ "sourceDigest": "4b5c2f7a7653947ac71ae42a3301c7547f789c2ca33e25f99f6781f31d1147be",
6
+ "outputDigest": "4e32bcf7d8be72541bb39508e38335ad0e32e41844afa45d7f0d34c9481a1cec",
7
+ "byteLength": 2313648,
8
8
  "inputs": [
9
9
  "extension/entries/content-entry.mjs",
10
10
  "extension/src/content/activeTurnControl.js",
@@ -442,9 +442,79 @@
442
442
  return error;
443
443
  }
444
444
 
445
+ function decorateCompletionReport(container, options = {}) {
446
+ const tx = typeof options.tx === 'function' ? options.tx : en => en;
447
+ const document = container?.ownerDocument || globalThis.document;
448
+ if (!container || !document) return;
449
+
450
+ for (const block of Array.from(container.children || [])) {
451
+ const textNode = Array.from(block.childNodes || [])
452
+ .find(node => node?.nodeType === 3 && String(node.textContent || '').trim());
453
+ if (!textNode) continue;
454
+ const text = String(textNode.textContent || '');
455
+ const match = text.match(/^(\s*)(Conclusion:|结论:|Changes:|修改:)(\s*)/);
456
+ if (!match || !textNode.parentNode) continue;
457
+ const label = document.createElement('span');
458
+ label.className = 'run-system-label';
459
+ label.dataset.systemLabel = ['Conclusion:', '结论:'].includes(match[2])
460
+ ? 'conclusion'
461
+ : 'changes';
462
+ label.textContent = `${match[2]}${match[3]}`;
463
+ textNode.textContent = `${match[1]}${text.slice(match[0].length)}`;
464
+ textNode.parentNode.insertBefore(label, textNode);
465
+ }
466
+ decorateChangeReceipts(container, document, tx);
467
+ }
468
+
469
+ function decorateChangeReceipts(container, document, tx) {
470
+ const label = container.querySelector?.('.run-system-label[data-system-label="changes"]');
471
+ const list = label?.closest?.('p')?.nextElementSibling;
472
+ if (!list || !['UL', 'OL'].includes(list.tagName)) return;
473
+
474
+ const receipts = [];
475
+ for (const item of Array.from(list.children || [])) {
476
+ const original = String(item.textContent || '').trim();
477
+ const match = original.match(/^(.+?):\s+(edit|create|rename|move|delete)(?:\s+\((.+)\))?$/i)
478
+ || original.match(/^(.+?):\s*(编辑|新建|重命名|移动|删除)(?:((.+)))?$/);
479
+ if (!match) return;
480
+ receipts.push({ item, original, file: match[1], operation: match[2] });
481
+ }
482
+ if (!receipts.length) return;
483
+
484
+ const syncedFiles = new Set(receipts.map(receipt => receipt.file)).size;
485
+ const summary = document.createElement('div');
486
+ summary.className = 'run-change-summary';
487
+ const check = document.createElement('span');
488
+ check.className = 'run-change-summary__check';
489
+ check.setAttribute('aria-hidden', 'true');
490
+ check.textContent = '✓';
491
+ const text = document.createElement('span');
492
+ text.textContent = tx(
493
+ `${syncedFiles} ${syncedFiles === 1 ? 'file' : 'files'} synced`,
494
+ `已同步 ${syncedFiles} 个文件`
495
+ );
496
+ summary.append(check, text);
497
+ list.parentNode?.insertBefore(summary, list);
498
+ list.classList.add('run-change-receipts');
499
+
500
+ for (const receipt of receipts) {
501
+ const file = document.createElement('span');
502
+ file.className = 'run-change-receipt__file';
503
+ file.textContent = receipt.file;
504
+ const operation = document.createElement('span');
505
+ operation.className = 'run-change-receipt__operation';
506
+ operation.textContent = receipt.operation;
507
+ receipt.item.classList.add('run-change-receipt');
508
+ receipt.item.setAttribute('aria-label', receipt.original);
509
+ receipt.item.title = receipt.original;
510
+ receipt.item.replaceChildren(file, operation);
511
+ }
512
+ }
513
+
445
514
  return {
446
515
  DEFAULT_LIMITS,
447
516
  countTokens,
517
+ decorateCompletionReport,
448
518
  renderMarkdown,
449
519
  stripEmptyHtmlComments
450
520
  };
@@ -16,10 +16,17 @@
16
16
  }
17
17
  container.replaceChildren();
18
18
  container.hidden = !items.length;
19
+ if (!items.length) {
20
+ return;
21
+ }
19
22
  for (const item of items) {
20
23
  const row = document.createElement('article');
21
24
  row.className = 'codex-pending-input';
22
25
  row.dataset.status = item.status || 'queued';
26
+ const marker = document.createElement('span');
27
+ marker.className = 'codex-pending-input-marker';
28
+ marker.setAttribute('aria-hidden', 'true');
29
+ marker.append(createIcon('queue'));
23
30
  const copy = document.createElement('div');
24
31
  copy.className = 'codex-pending-input-copy';
25
32
  const status = document.createElement('span');
@@ -34,7 +41,10 @@
34
41
  const text = document.createElement('span');
35
42
  text.className = 'codex-pending-input-text';
36
43
  text.textContent = item.text;
37
- copy.append(status, text);
44
+ copy.append(text);
45
+ if (item.status && item.status !== 'queued') {
46
+ copy.append(status);
47
+ }
38
48
  const actions = document.createElement('div');
39
49
  actions.className = 'codex-pending-input-actions';
40
50
  if (item.status === 'paused') {
@@ -60,7 +70,8 @@
60
70
  remove.disabled = item.status === 'steering' || item.status === 'executing';
61
71
  text.title = item.text;
62
72
  actions.append(remove);
63
- row.append(copy, actions);
73
+ row.setAttribute('aria-label', `${status.textContent || options.tr?.('queuedInputQueued') || 'Queued'}: ${item.text}`);
74
+ row.append(marker, copy, actions);
64
75
  container.append(row);
65
76
  }
66
77
  }
@@ -93,7 +104,9 @@
93
104
  svg.setAttribute('focusable', 'false');
94
105
  const paths = icon === 'guide'
95
106
  ? ['M4 4.5v4a4 4 0 0 0 4 4h7', 'm12 9 3.5 3.5L12 16']
96
- : ['M6 6h8', 'M8 6V4.5h4V6', 'm7.2 8 0.6 7.5h4.4l.6-7.5'];
107
+ : icon === 'queue'
108
+ ? ['M4 5.5h12', 'M4 10h12', 'M4 14.5h8']
109
+ : ['M6 6h8', 'M8 6V4.5h4V6', 'm7.2 8 0.6 7.5h4.4l.6-7.5'];
97
110
  for (const value of paths) {
98
111
  const path = document.createElementNS('http://www.w3.org/2000/svg', 'path');
99
112
  path.setAttribute('d', value);
@@ -985,6 +985,7 @@
985
985
  return;
986
986
  }
987
987
  const style = instance.document.defaultView.getComputedStyle(panel);
988
+ instance.root.dataset.theme = panel.dataset.theme === 'light' ? 'light' : 'dark';
988
989
  instance.root.style.setProperty('--provider-panel-bg', style.backgroundColor || '#151716');
989
990
  instance.root.style.setProperty('--provider-panel-color', style.color || '#eceeea');
990
991
  }
@@ -30,6 +30,7 @@
30
30
  cssEscape,
31
31
  renderMarkdownInlineText,
32
32
  renderMarkdownBlockText,
33
+ decorateCompletionReport,
33
34
  sanitizeAssistantVisibleText,
34
35
  sanitizeAssistantVisibleValue,
35
36
  stripEmptyHtmlCommentPlaceholders = value => value,
@@ -709,6 +710,7 @@
709
710
  }
710
711
  if (mainSections.length) {
711
712
  renderMarkdownBlockText(main, mainSections.join('\n\n'));
713
+ decorateCompletionReport(main, { tx });
712
714
  report.append(main);
713
715
  }
714
716
 
@@ -729,6 +731,7 @@
729
731
  const body = document.createElement('div');
730
732
  body.className = 'run-final-answer';
731
733
  renderMarkdownBlockText(body, split.body || flatText);
734
+ decorateCompletionReport(body, { tx });
732
735
  report.append(body);
733
736
  appendCompileFix(report);
734
737
  appendRejectedRedo(report);
@@ -12,7 +12,7 @@
12
12
  const MIN_NATIVE_VERSION = '1.0.0';
13
13
  const MIN_COMPATIBLE_NATIVE_VERSION = '1.0.0';
14
14
  const MIN_COMPATIBLE_EXTENSION_VERSION = '1.0.0';
15
- const BUILD_TARGET_VERSION = '2.3.2';
15
+ const BUILD_TARGET_VERSION = '2.3.3';
16
16
  const DEFAULT_CHROME_EXTENSION_ID = 'illdpneeeopfffmiepaejglgmhpmdhdc';
17
17
  const REQUIRED_CAPABILITIES = Object.freeze([
18
18
  'bridgePing',