codex-overleaf-link 2.4.1 → 2.5.1

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 (397) hide show
  1. package/README.md +275 -305
  2. package/README.zh-CN.md +290 -320
  3. package/extension/bootstrap/background.js +99 -19
  4. package/extension/bootstrap/manifest.template.json +9 -4
  5. package/extension/bootstrap/popup.html +11 -16
  6. package/extension/bootstrap/popupFallback.js +55 -0
  7. package/extension/bootstrap/update.js +25 -2
  8. package/extension/bootstrap/updateStatus.js +1 -0
  9. package/extension/runtime-manifest.json +3 -1
  10. package/extension/src/background.js +234 -56
  11. package/extension/src/backgroundBootstrapMigration.js +181 -0
  12. package/extension/src/backgroundSharedSessions.js +440 -0
  13. package/extension/src/backgroundUpdateCoordinator.js +541 -381
  14. package/extension/src/backgroundUpdateSafety.js +173 -0
  15. package/extension/src/content/activeTurnControl.js +16 -2
  16. package/extension/src/content/applyResultFormatters.js +46 -73
  17. package/extension/src/content/assetTransferBroker.js +244 -12
  18. package/extension/src/content/changeHistoryView.js +175 -0
  19. package/extension/src/content/composerAttachments.js +117 -67
  20. package/extension/src/content/composerPanel.js +41 -8
  21. package/extension/src/content/contentRuntime.js +1084 -1099
  22. package/extension/src/content/diagnosticsController.js +122 -97
  23. package/extension/src/content/diagnosticsExport.js +236 -0
  24. package/extension/src/content/diagnosticsPanel.js +78 -19
  25. package/extension/src/content/diffReviewPanel.js +8 -5
  26. package/extension/src/content/directoryCleanupRecovery.js +54 -0
  27. package/extension/src/content/generated/content.bundle.js +14680 -3606
  28. package/extension/src/content/generated/content.bundle.meta.json +30 -3
  29. package/extension/src/content/globalPreferencesController.js +1 -1
  30. package/extension/src/content/legacyGlobalRegistry.js +25 -1
  31. package/extension/src/content/localSkillsPanel.js +141 -16
  32. package/extension/src/content/markdownDomRenderer.js +9 -4
  33. package/extension/src/content/markdownText.js +5 -6
  34. package/extension/src/content/modelPicker.js +8 -5
  35. package/extension/src/content/nativeCompatibilityController.js +45 -20
  36. package/extension/src/content/otWarmMirror.js +4 -5
  37. package/extension/src/content/otWarmMirrorController.js +17 -20
  38. package/extension/src/content/pageBridgeClient.js +33 -5
  39. package/extension/src/content/panelMaintenance.js +87 -132
  40. package/extension/src/content/panelRenderer.js +10 -0
  41. package/extension/src/content/pendingInputView.js +109 -76
  42. package/extension/src/content/projectProviderSelection.js +13 -4
  43. package/extension/src/content/projectSessionCleanup.js +109 -62
  44. package/extension/src/content/projectSettingsCoordinator.js +39 -2
  45. package/extension/src/content/providerSettingsCoordinator.js +63 -14
  46. package/extension/src/content/providerSettingsDialog.js +724 -113
  47. package/extension/src/content/recentProjects.js +21 -6
  48. package/extension/src/content/runActivitySummary.js +665 -0
  49. package/extension/src/content/runCompletionMeta.js +344 -0
  50. package/extension/src/content/runController.js +40 -15
  51. package/extension/src/content/runFailureNotice.js +34 -12
  52. package/extension/src/content/runGuidanceController.js +76 -30
  53. package/extension/src/content/runGuidanceView.js +59 -10
  54. package/extension/src/content/runPresence.js +306 -0
  55. package/extension/src/content/runQueueScheduler.js +150 -43
  56. package/extension/src/content/runRecoveryActions.js +146 -0
  57. package/extension/src/content/runResultActions.js +11 -8
  58. package/extension/src/content/runReviewController.js +574 -0
  59. package/extension/src/content/runScrollLayout.js +21 -2
  60. package/extension/src/content/runTimelineView.js +315 -290
  61. package/extension/src/content/scopedPersistencePanelState.js +51 -6
  62. package/extension/src/content/selectionContextView.js +300 -0
  63. package/extension/src/content/sensitivePreflight.js +140 -0
  64. package/extension/src/content/sessionForkController.js +80 -17
  65. package/extension/src/content/sessionManager.js +1 -1
  66. package/extension/src/content/sessionPersistence.js +6 -1
  67. package/extension/src/content/settingsPanel.js +84 -55
  68. package/extension/src/content/settingsWorkbench.js +379 -0
  69. package/extension/src/content/sharedSessionViewSync.js +109 -0
  70. package/extension/src/content/subagentActivityView.js +195 -0
  71. package/extension/src/content/trackedChangeCaptureController.js +7 -3
  72. package/extension/src/content/updateIdle.js +4 -1
  73. package/extension/src/content/updateNotice.js +179 -56
  74. package/extension/src/content/updateSafetyReceiver.js +58 -0
  75. package/extension/src/content/writebackController.js +308 -2
  76. package/extension/src/content/writebackOrchestrator.js +213 -199
  77. package/extension/src/content/writebackPlan.js +231 -0
  78. package/extension/src/content/writebackRecovery.js +122 -0
  79. package/extension/src/content/writingStyleSettings.js +600 -0
  80. package/extension/src/content/writtenChangesView.js +152 -0
  81. package/extension/src/page/binaryAssetUploader.js +223 -23
  82. package/extension/src/page/fileMover.js +256 -0
  83. package/extension/src/page/overleafProjectSnapshot.js +1 -0
  84. package/extension/src/page/ownedDirectoryCleanup.js +94 -0
  85. package/extension/src/page/referenceProjects.js +149 -0
  86. package/extension/src/page/reviewContext.js +113 -0
  87. package/extension/src/page/saveState.js +20 -6
  88. package/extension/src/page/snapshotRouter.js +124 -48
  89. package/extension/src/page/textCoordinates.js +102 -0
  90. package/extension/src/page/textFileCreator.js +442 -71
  91. package/extension/src/page/trackedChangeCapture.js +53 -57
  92. package/extension/src/page/trackedChangeOwnership.js +216 -0
  93. package/extension/src/page/trackedChangeReplay.js +184 -0
  94. package/extension/src/page/trackedChangesLifecycle.js +343 -339
  95. package/extension/src/page/treeOperations.js +33 -12
  96. package/extension/src/page/updateSafetyProbe.js +41 -0
  97. package/extension/src/page/writebackReceiptJournal.js +114 -0
  98. package/extension/src/page/writebackRouter.js +242 -201
  99. package/extension/src/pageBridge.js +73 -102
  100. package/extension/src/popup.js +261 -65
  101. package/extension/src/shared/agentTranscript.js +41 -4
  102. package/extension/src/shared/auditRecords.js +73 -0
  103. package/extension/src/shared/changeHistoryModel.js +94 -0
  104. package/extension/src/shared/compatibility.js +22 -6
  105. package/extension/src/shared/compileAdapter.js +101 -37
  106. package/extension/src/shared/composerAttachmentDraft.js +151 -0
  107. package/extension/src/shared/directoryCleanupProof.js +43 -0
  108. package/extension/src/shared/failureReasons.js +329 -3
  109. package/extension/src/shared/globalPreferences.js +31 -14
  110. package/extension/src/shared/governanceRules.js +4 -37
  111. package/extension/src/shared/i18n.js +389 -25
  112. package/extension/src/shared/managedUpdateProjection.js +8 -5
  113. package/extension/src/shared/nativeRequestIdentity.js +1 -0
  114. package/extension/src/shared/pageRpcContract.js +9 -2
  115. package/extension/src/shared/projectFiles.js +21 -44
  116. package/extension/src/shared/providerProfiles.js +114 -3
  117. package/extension/src/shared/runActivityModel.js +361 -0
  118. package/extension/src/shared/runExecutionSnapshot.js +8 -2
  119. package/extension/src/shared/runExecutionSnapshotCodec.js +16 -4
  120. package/extension/src/shared/runInputQueue.js +48 -5
  121. package/extension/src/shared/scopedPersistenceBrowserAdapter.js +6 -3
  122. package/extension/src/shared/selectionContext.js +37 -0
  123. package/extension/src/shared/sessionState.js +166 -30
  124. package/extension/src/shared/settlementFacts.js +10 -2
  125. package/extension/src/shared/sharedSessionBridge.js +311 -0
  126. package/extension/src/shared/sharedSessionTransfer.js +140 -0
  127. package/extension/src/shared/staleGuard.js +118 -13
  128. package/extension/src/shared/storageDb.js +77 -78
  129. package/extension/src/shared/storageMigration.js +74 -111
  130. package/extension/src/shared/storageRunActions.js +211 -22
  131. package/extension/src/shared/storageValuePruning.js +40 -0
  132. package/extension/src/shared/subagentActivityModel.js +174 -0
  133. package/extension/src/shared/undoOperations.js +216 -6
  134. package/extension/src/shared/updateConsent.js +42 -11
  135. package/extension/src/shared/updateRuntimeIdentity.js +1 -1
  136. package/extension/src/shared/writebackIntent.js +78 -0
  137. package/extension/src/shared/writebackOperationEvidence.js +4 -15
  138. package/extension/src/shared/writebackSettlement.js +67 -48
  139. package/extension/src/shared/writingStyle.js +33 -0
  140. package/extension/styles/panel.css +1987 -385
  141. package/extension/styles/popup.css +110 -0
  142. package/native-host/src/anthropicBridgeRequest.js +6 -3
  143. package/native-host/src/anthropicBridgeResponse.js +6 -2
  144. package/native-host/src/anthropicMessagesBridge.js +24 -16
  145. package/native-host/src/bootstrapMigration.js +296 -0
  146. package/native-host/src/bootstrapMigrationContract.js +101 -0
  147. package/native-host/src/bootstrapUpdate.js +233 -0
  148. package/native-host/src/bootstrapUpdateWatchdog.js +44 -0
  149. package/native-host/src/chatBridgeResponse.js +10 -0
  150. package/native-host/src/chatCompletionsBridge.js +21 -15
  151. package/native-host/src/codexConfigPaths.js +106 -0
  152. package/native-host/src/codexHome.js +66 -73
  153. package/native-host/src/codexHomeScope.js +124 -0
  154. package/native-host/src/codexInheritedAuth.js +90 -0
  155. package/native-host/src/codexLocalSkills.js +301 -0
  156. package/native-host/src/codexModelRecovery.js +107 -0
  157. package/native-host/src/codexPromptAssembly.js +33 -12
  158. package/native-host/src/codexProviderLaunch.js +3 -3
  159. package/native-host/src/codexProviderTest.js +24 -26
  160. package/native-host/src/codexRuntimeIdentity.js +1 -0
  161. package/native-host/src/codexSessionRunner.js +211 -318
  162. package/native-host/src/codexSessionTiming.js +21 -8
  163. package/native-host/src/codexSkillIsolation.js +170 -0
  164. package/native-host/src/codexThreadFork.js +19 -3
  165. package/native-host/src/index.js +19 -7
  166. package/native-host/src/managedInstall.js +115 -39
  167. package/native-host/src/managedInstallRecovery.js +140 -0
  168. package/native-host/src/managedRuntimeEvidence.js +57 -0
  169. package/native-host/src/mirrorWorkspace.js +92 -22
  170. package/native-host/src/nativeDoctor.js +15 -0
  171. package/native-host/src/nativeEnvironment.js +70 -0
  172. package/native-host/src/nativeHelperLifecycle.js +21 -0
  173. package/native-host/src/nativeHostRegistration.js +33 -0
  174. package/native-host/src/nativeQuotas.js +15 -8
  175. package/native-host/src/nativeRunLifecycle.js +71 -0
  176. package/native-host/src/overleafWorkspaceRules.js +16 -0
  177. package/native-host/src/processStopBarrier.js +115 -0
  178. package/native-host/src/projectPathPlatform.js +30 -0
  179. package/native-host/src/providerHttp.js +80 -0
  180. package/native-host/src/providerModelCatalog.js +4 -3
  181. package/native-host/src/providerProfile.js +17 -3
  182. package/native-host/src/providerReasoning.js +10 -11
  183. package/native-host/src/providerRuntime.js +1 -0
  184. package/native-host/src/providerStore.js +76 -14
  185. package/native-host/src/releaseTransport.js +14 -5
  186. package/native-host/src/responsesPassthroughBridge.js +266 -52
  187. package/native-host/src/runtimeInstaller.js +21 -1
  188. package/native-host/src/selectionScope.js +86 -0
  189. package/native-host/src/skills/parallel-subagents/SKILL.md +31 -3
  190. package/native-host/src/skills/writing-style-builder/SKILL.md +146 -0
  191. package/native-host/src/subagentAdmission.js +26 -0
  192. package/native-host/src/subagentBroker.js +176 -159
  193. package/native-host/src/subagentTelemetry.js +325 -0
  194. package/native-host/src/subagentWorkspace.js +103 -0
  195. package/native-host/src/subagentWorkspacePath.js +34 -0
  196. package/native-host/src/taskRunnerRuntime.js +130 -57
  197. package/native-host/src/tomlStatements.js +140 -0
  198. package/native-host/src/turnAttachments.js +113 -0
  199. package/native-host/src/updateManager.js +406 -38
  200. package/native-host/src/updateNetworkControl.js +75 -0
  201. package/native-host/src/updateTrust.js +21 -2
  202. package/native-host/src/vendor/pdfjs/LICENSE +177 -0
  203. package/native-host/src/vendor/pdfjs/SOURCE.txt +3 -0
  204. package/native-host/src/vendor/pdfjs/cmaps/78-EUC-H.bcmap +0 -0
  205. package/native-host/src/vendor/pdfjs/cmaps/78-EUC-V.bcmap +0 -0
  206. package/native-host/src/vendor/pdfjs/cmaps/78-H.bcmap +0 -0
  207. package/native-host/src/vendor/pdfjs/cmaps/78-RKSJ-H.bcmap +0 -0
  208. package/native-host/src/vendor/pdfjs/cmaps/78-RKSJ-V.bcmap +0 -0
  209. package/native-host/src/vendor/pdfjs/cmaps/78-V.bcmap +0 -0
  210. package/native-host/src/vendor/pdfjs/cmaps/78ms-RKSJ-H.bcmap +0 -0
  211. package/native-host/src/vendor/pdfjs/cmaps/78ms-RKSJ-V.bcmap +0 -0
  212. package/native-host/src/vendor/pdfjs/cmaps/83pv-RKSJ-H.bcmap +0 -0
  213. package/native-host/src/vendor/pdfjs/cmaps/90ms-RKSJ-H.bcmap +0 -0
  214. package/native-host/src/vendor/pdfjs/cmaps/90ms-RKSJ-V.bcmap +0 -0
  215. package/native-host/src/vendor/pdfjs/cmaps/90msp-RKSJ-H.bcmap +0 -0
  216. package/native-host/src/vendor/pdfjs/cmaps/90msp-RKSJ-V.bcmap +0 -0
  217. package/native-host/src/vendor/pdfjs/cmaps/90pv-RKSJ-H.bcmap +0 -0
  218. package/native-host/src/vendor/pdfjs/cmaps/90pv-RKSJ-V.bcmap +0 -0
  219. package/native-host/src/vendor/pdfjs/cmaps/Add-H.bcmap +0 -0
  220. package/native-host/src/vendor/pdfjs/cmaps/Add-RKSJ-H.bcmap +0 -0
  221. package/native-host/src/vendor/pdfjs/cmaps/Add-RKSJ-V.bcmap +0 -0
  222. package/native-host/src/vendor/pdfjs/cmaps/Add-V.bcmap +0 -0
  223. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-0.bcmap +0 -0
  224. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-1.bcmap +0 -0
  225. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-2.bcmap +0 -0
  226. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-3.bcmap +0 -0
  227. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-4.bcmap +0 -0
  228. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-5.bcmap +0 -0
  229. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-6.bcmap +0 -0
  230. package/native-host/src/vendor/pdfjs/cmaps/Adobe-CNS1-UCS2.bcmap +0 -0
  231. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-0.bcmap +0 -0
  232. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-1.bcmap +0 -0
  233. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-2.bcmap +0 -0
  234. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-3.bcmap +0 -0
  235. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-4.bcmap +0 -0
  236. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-5.bcmap +0 -0
  237. package/native-host/src/vendor/pdfjs/cmaps/Adobe-GB1-UCS2.bcmap +0 -0
  238. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-0.bcmap +0 -0
  239. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-1.bcmap +0 -0
  240. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-2.bcmap +0 -0
  241. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-3.bcmap +0 -0
  242. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-4.bcmap +0 -0
  243. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-5.bcmap +0 -0
  244. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-6.bcmap +0 -0
  245. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Japan1-UCS2.bcmap +0 -0
  246. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Korea1-0.bcmap +0 -0
  247. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Korea1-1.bcmap +0 -0
  248. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Korea1-2.bcmap +0 -0
  249. package/native-host/src/vendor/pdfjs/cmaps/Adobe-Korea1-UCS2.bcmap +0 -0
  250. package/native-host/src/vendor/pdfjs/cmaps/B5-H.bcmap +0 -0
  251. package/native-host/src/vendor/pdfjs/cmaps/B5-V.bcmap +0 -0
  252. package/native-host/src/vendor/pdfjs/cmaps/B5pc-H.bcmap +0 -0
  253. package/native-host/src/vendor/pdfjs/cmaps/B5pc-V.bcmap +0 -0
  254. package/native-host/src/vendor/pdfjs/cmaps/CNS-EUC-H.bcmap +0 -0
  255. package/native-host/src/vendor/pdfjs/cmaps/CNS-EUC-V.bcmap +0 -0
  256. package/native-host/src/vendor/pdfjs/cmaps/CNS1-H.bcmap +0 -0
  257. package/native-host/src/vendor/pdfjs/cmaps/CNS1-V.bcmap +0 -0
  258. package/native-host/src/vendor/pdfjs/cmaps/CNS2-H.bcmap +0 -0
  259. package/native-host/src/vendor/pdfjs/cmaps/CNS2-V.bcmap +3 -0
  260. package/native-host/src/vendor/pdfjs/cmaps/ETHK-B5-H.bcmap +0 -0
  261. package/native-host/src/vendor/pdfjs/cmaps/ETHK-B5-V.bcmap +0 -0
  262. package/native-host/src/vendor/pdfjs/cmaps/ETen-B5-H.bcmap +0 -0
  263. package/native-host/src/vendor/pdfjs/cmaps/ETen-B5-V.bcmap +0 -0
  264. package/native-host/src/vendor/pdfjs/cmaps/ETenms-B5-H.bcmap +3 -0
  265. package/native-host/src/vendor/pdfjs/cmaps/ETenms-B5-V.bcmap +0 -0
  266. package/native-host/src/vendor/pdfjs/cmaps/EUC-H.bcmap +0 -0
  267. package/native-host/src/vendor/pdfjs/cmaps/EUC-V.bcmap +0 -0
  268. package/native-host/src/vendor/pdfjs/cmaps/Ext-H.bcmap +0 -0
  269. package/native-host/src/vendor/pdfjs/cmaps/Ext-RKSJ-H.bcmap +0 -0
  270. package/native-host/src/vendor/pdfjs/cmaps/Ext-RKSJ-V.bcmap +0 -0
  271. package/native-host/src/vendor/pdfjs/cmaps/Ext-V.bcmap +0 -0
  272. package/native-host/src/vendor/pdfjs/cmaps/GB-EUC-H.bcmap +0 -0
  273. package/native-host/src/vendor/pdfjs/cmaps/GB-EUC-V.bcmap +0 -0
  274. package/native-host/src/vendor/pdfjs/cmaps/GB-H.bcmap +4 -0
  275. package/native-host/src/vendor/pdfjs/cmaps/GB-V.bcmap +0 -0
  276. package/native-host/src/vendor/pdfjs/cmaps/GBK-EUC-H.bcmap +0 -0
  277. package/native-host/src/vendor/pdfjs/cmaps/GBK-EUC-V.bcmap +0 -0
  278. package/native-host/src/vendor/pdfjs/cmaps/GBK2K-H.bcmap +0 -0
  279. package/native-host/src/vendor/pdfjs/cmaps/GBK2K-V.bcmap +0 -0
  280. package/native-host/src/vendor/pdfjs/cmaps/GBKp-EUC-H.bcmap +0 -0
  281. package/native-host/src/vendor/pdfjs/cmaps/GBKp-EUC-V.bcmap +0 -0
  282. package/native-host/src/vendor/pdfjs/cmaps/GBT-EUC-H.bcmap +0 -0
  283. package/native-host/src/vendor/pdfjs/cmaps/GBT-EUC-V.bcmap +0 -0
  284. package/native-host/src/vendor/pdfjs/cmaps/GBT-H.bcmap +0 -0
  285. package/native-host/src/vendor/pdfjs/cmaps/GBT-V.bcmap +0 -0
  286. package/native-host/src/vendor/pdfjs/cmaps/GBTpc-EUC-H.bcmap +0 -0
  287. package/native-host/src/vendor/pdfjs/cmaps/GBTpc-EUC-V.bcmap +0 -0
  288. package/native-host/src/vendor/pdfjs/cmaps/GBpc-EUC-H.bcmap +0 -0
  289. package/native-host/src/vendor/pdfjs/cmaps/GBpc-EUC-V.bcmap +0 -0
  290. package/native-host/src/vendor/pdfjs/cmaps/H.bcmap +0 -0
  291. package/native-host/src/vendor/pdfjs/cmaps/HKdla-B5-H.bcmap +0 -0
  292. package/native-host/src/vendor/pdfjs/cmaps/HKdla-B5-V.bcmap +0 -0
  293. package/native-host/src/vendor/pdfjs/cmaps/HKdlb-B5-H.bcmap +0 -0
  294. package/native-host/src/vendor/pdfjs/cmaps/HKdlb-B5-V.bcmap +0 -0
  295. package/native-host/src/vendor/pdfjs/cmaps/HKgccs-B5-H.bcmap +0 -0
  296. package/native-host/src/vendor/pdfjs/cmaps/HKgccs-B5-V.bcmap +0 -0
  297. package/native-host/src/vendor/pdfjs/cmaps/HKm314-B5-H.bcmap +0 -0
  298. package/native-host/src/vendor/pdfjs/cmaps/HKm314-B5-V.bcmap +0 -0
  299. package/native-host/src/vendor/pdfjs/cmaps/HKm471-B5-H.bcmap +0 -0
  300. package/native-host/src/vendor/pdfjs/cmaps/HKm471-B5-V.bcmap +0 -0
  301. package/native-host/src/vendor/pdfjs/cmaps/HKscs-B5-H.bcmap +0 -0
  302. package/native-host/src/vendor/pdfjs/cmaps/HKscs-B5-V.bcmap +0 -0
  303. package/native-host/src/vendor/pdfjs/cmaps/Hankaku.bcmap +0 -0
  304. package/native-host/src/vendor/pdfjs/cmaps/Hiragana.bcmap +0 -0
  305. package/native-host/src/vendor/pdfjs/cmaps/KSC-EUC-H.bcmap +0 -0
  306. package/native-host/src/vendor/pdfjs/cmaps/KSC-EUC-V.bcmap +0 -0
  307. package/native-host/src/vendor/pdfjs/cmaps/KSC-H.bcmap +0 -0
  308. package/native-host/src/vendor/pdfjs/cmaps/KSC-Johab-H.bcmap +0 -0
  309. package/native-host/src/vendor/pdfjs/cmaps/KSC-Johab-V.bcmap +0 -0
  310. package/native-host/src/vendor/pdfjs/cmaps/KSC-V.bcmap +0 -0
  311. package/native-host/src/vendor/pdfjs/cmaps/KSCms-UHC-H.bcmap +0 -0
  312. package/native-host/src/vendor/pdfjs/cmaps/KSCms-UHC-HW-H.bcmap +0 -0
  313. package/native-host/src/vendor/pdfjs/cmaps/KSCms-UHC-HW-V.bcmap +0 -0
  314. package/native-host/src/vendor/pdfjs/cmaps/KSCms-UHC-V.bcmap +0 -0
  315. package/native-host/src/vendor/pdfjs/cmaps/KSCpc-EUC-H.bcmap +0 -0
  316. package/native-host/src/vendor/pdfjs/cmaps/KSCpc-EUC-V.bcmap +0 -0
  317. package/native-host/src/vendor/pdfjs/cmaps/Katakana.bcmap +0 -0
  318. package/native-host/src/vendor/pdfjs/cmaps/LICENSE +36 -0
  319. package/native-host/src/vendor/pdfjs/cmaps/NWP-H.bcmap +0 -0
  320. package/native-host/src/vendor/pdfjs/cmaps/NWP-V.bcmap +0 -0
  321. package/native-host/src/vendor/pdfjs/cmaps/RKSJ-H.bcmap +0 -0
  322. package/native-host/src/vendor/pdfjs/cmaps/RKSJ-V.bcmap +0 -0
  323. package/native-host/src/vendor/pdfjs/cmaps/Roman.bcmap +0 -0
  324. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UCS2-H.bcmap +0 -0
  325. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UCS2-V.bcmap +0 -0
  326. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UTF16-H.bcmap +0 -0
  327. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UTF16-V.bcmap +0 -0
  328. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UTF32-H.bcmap +0 -0
  329. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UTF32-V.bcmap +0 -0
  330. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UTF8-H.bcmap +0 -0
  331. package/native-host/src/vendor/pdfjs/cmaps/UniCNS-UTF8-V.bcmap +0 -0
  332. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UCS2-H.bcmap +0 -0
  333. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UCS2-V.bcmap +0 -0
  334. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UTF16-H.bcmap +0 -0
  335. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UTF16-V.bcmap +0 -0
  336. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UTF32-H.bcmap +0 -0
  337. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UTF32-V.bcmap +0 -0
  338. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UTF8-H.bcmap +0 -0
  339. package/native-host/src/vendor/pdfjs/cmaps/UniGB-UTF8-V.bcmap +0 -0
  340. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UCS2-H.bcmap +0 -0
  341. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UCS2-HW-H.bcmap +0 -0
  342. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UCS2-HW-V.bcmap +0 -0
  343. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UCS2-V.bcmap +0 -0
  344. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UTF16-H.bcmap +0 -0
  345. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UTF16-V.bcmap +0 -0
  346. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UTF32-H.bcmap +0 -0
  347. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UTF32-V.bcmap +0 -0
  348. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UTF8-H.bcmap +0 -0
  349. package/native-host/src/vendor/pdfjs/cmaps/UniJIS-UTF8-V.bcmap +0 -0
  350. package/native-host/src/vendor/pdfjs/cmaps/UniJIS2004-UTF16-H.bcmap +0 -0
  351. package/native-host/src/vendor/pdfjs/cmaps/UniJIS2004-UTF16-V.bcmap +0 -0
  352. package/native-host/src/vendor/pdfjs/cmaps/UniJIS2004-UTF32-H.bcmap +0 -0
  353. package/native-host/src/vendor/pdfjs/cmaps/UniJIS2004-UTF32-V.bcmap +0 -0
  354. package/native-host/src/vendor/pdfjs/cmaps/UniJIS2004-UTF8-H.bcmap +0 -0
  355. package/native-host/src/vendor/pdfjs/cmaps/UniJIS2004-UTF8-V.bcmap +0 -0
  356. package/native-host/src/vendor/pdfjs/cmaps/UniJISPro-UCS2-HW-V.bcmap +0 -0
  357. package/native-host/src/vendor/pdfjs/cmaps/UniJISPro-UCS2-V.bcmap +0 -0
  358. package/native-host/src/vendor/pdfjs/cmaps/UniJISPro-UTF8-V.bcmap +0 -0
  359. package/native-host/src/vendor/pdfjs/cmaps/UniJISX0213-UTF32-H.bcmap +0 -0
  360. package/native-host/src/vendor/pdfjs/cmaps/UniJISX0213-UTF32-V.bcmap +0 -0
  361. package/native-host/src/vendor/pdfjs/cmaps/UniJISX02132004-UTF32-H.bcmap +0 -0
  362. package/native-host/src/vendor/pdfjs/cmaps/UniJISX02132004-UTF32-V.bcmap +0 -0
  363. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UCS2-H.bcmap +0 -0
  364. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UCS2-V.bcmap +0 -0
  365. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UTF16-H.bcmap +0 -0
  366. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UTF16-V.bcmap +0 -0
  367. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UTF32-H.bcmap +0 -0
  368. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UTF32-V.bcmap +0 -0
  369. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UTF8-H.bcmap +0 -0
  370. package/native-host/src/vendor/pdfjs/cmaps/UniKS-UTF8-V.bcmap +0 -0
  371. package/native-host/src/vendor/pdfjs/cmaps/V.bcmap +0 -0
  372. package/native-host/src/vendor/pdfjs/cmaps/WP-Symbol.bcmap +0 -0
  373. package/native-host/src/vendor/pdfjs/pdf.mjs +26740 -0
  374. package/native-host/src/vendor/pdfjs/pdf.worker.mjs +62201 -0
  375. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitDingbats.pfb +0 -0
  376. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitFixed.pfb +0 -0
  377. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitFixedBold.pfb +0 -0
  378. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitFixedBoldItalic.pfb +0 -0
  379. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitFixedItalic.pfb +0 -0
  380. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitSerif.pfb +0 -0
  381. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitSerifBold.pfb +0 -0
  382. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitSerifBoldItalic.pfb +0 -0
  383. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitSerifItalic.pfb +0 -0
  384. package/native-host/src/vendor/pdfjs/standard_fonts/FoxitSymbol.pfb +0 -0
  385. package/native-host/src/vendor/pdfjs/standard_fonts/LICENSE_FOXIT +27 -0
  386. package/native-host/src/vendor/pdfjs/standard_fonts/LICENSE_LIBERATION +102 -0
  387. package/native-host/src/vendor/pdfjs/standard_fonts/LiberationSans-Bold.ttf +0 -0
  388. package/native-host/src/vendor/pdfjs/standard_fonts/LiberationSans-BoldItalic.ttf +0 -0
  389. package/native-host/src/vendor/pdfjs/standard_fonts/LiberationSans-Italic.ttf +0 -0
  390. package/native-host/src/vendor/pdfjs/standard_fonts/LiberationSans-Regular.ttf +0 -0
  391. package/native-host/src/writingStyleEvidence.js +102 -0
  392. package/native-host/src/writingStylePdfWorker.js +35 -0
  393. package/native-host/src/writingStyleProfile.js +165 -0
  394. package/native-host/src/writingStyleRuntime.js +475 -0
  395. package/native-host/src/writingStyleStore.js +73 -0
  396. package/package.json +1 -1
  397. package/scripts/install-managed.mjs +1 -0
@@ -1,11 +1,8 @@
1
1
  (function initCodexOverleafDiagnosticsController() {
2
2
  'use strict';
3
3
 
4
- // Diagnostics controller — the check runners (inspect*) and result formatters
5
- // carved out of contentRuntime.js (v1.4.5 structural-debt phase 1). The code
6
- // below moved verbatim (original indentation kept); runtime collaborators are
7
- // factory-injected so behavior is unchanged. Mutable runtime state (panel
8
- // state, OT status) is read through injected getters.
4
+ // Check runners own observations; result formatters project those observations
5
+ // into the current UI language. Runtime collaborators are factory-injected.
9
6
  function create(deps = {}) {
10
7
  const {
11
8
  Compatibility: CodexOverleafCompatibility,
@@ -23,12 +20,12 @@
23
20
  otWarmMirrorController,
24
21
  getActiveFocusFiles,
25
22
  getCurrentProjectId,
23
+ getScope,
26
24
  isExperimentalOtEnabled,
27
25
  readOtBridgeStatus,
28
26
  formatOtStatusLabel,
29
27
  normalizeOtStatus,
30
28
  formatProbeStatusBar,
31
- getProbeRunReadiness,
32
29
  getMirrorFreshness,
33
30
  formatProjectSnapshotLog,
34
31
  formatProjectSnapshotWarning,
@@ -38,6 +35,48 @@
38
35
  RUN_SNAPSHOT_ZIP_TIMEOUT_MS
39
36
  } = deps;
40
37
 
38
+ // All visible checks share one request owner. Aggregate collectOnly calls
39
+ // must not supersede their own parent, and a later single check supersedes
40
+ // an older aggregate just as a later aggregate does.
41
+ let requestGeneration = 0;
42
+ let currentProjection = null;
43
+ const resultProjections = new WeakMap();
44
+ // Preserve the observed status and raw technical evidence across UI refreshes.
45
+ function projectableResult(project) {
46
+ const result = project();
47
+ resultProjections.set(result, () => ({ ...project(), status: result.status, technical: result.technical }));
48
+ return result;
49
+ }
50
+ function refreshLocale() {
51
+ return currentProjection && isCurrentDiagnosticsRequest(currentProjection.request)
52
+ ? currentProjection.project() : null;
53
+ }
54
+ function captureDiagnosticsScope() {
55
+ const scope = getScope?.() || { projectId: getCurrentProjectId?.() };
56
+ return { accountScopeId: scope.accountScopeId, projectId: scope.projectId, generation: scope.generation };
57
+ }
58
+
59
+ function beginDiagnostics(title, subtitle) {
60
+ const request = { generation: ++requestGeneration, scope: captureDiagnosticsScope() };
61
+ currentProjection = { request, project: () => ({ title: tr(title), subtitle: tr(subtitle),
62
+ status: 'running', summary: tr('diagnosticsLoadingSummary') }) };
63
+ showDiagnosticsLoading(tr(title), tr(subtitle));
64
+ return request;
65
+ }
66
+
67
+ function isCurrentDiagnosticsRequest(request) {
68
+ if (!request || request.generation !== requestGeneration) return false;
69
+ const scope = captureDiagnosticsScope();
70
+ return ['accountScopeId', 'projectId', 'generation'].every(key => scope[key] === request.scope[key]);
71
+ }
72
+
73
+ function showCurrentDiagnosticsResult(request, result) {
74
+ if (isCurrentDiagnosticsRequest(request)) {
75
+ currentProjection = { request, project: resultProjections.get(result) || (() => result) };
76
+ showDiagnosticsResult(result);
77
+ }
78
+ }
79
+
41
80
  // Reduce a result status to a health bucket. 'completed' is a pass; a hard
42
81
  // failure is fail; everything else (warning, partial, info) is attention.
43
82
  function diagnosticsHealthBucket(status) {
@@ -50,12 +89,12 @@
50
89
  // report (a status row per check) instead of four separate result screens.
51
90
  // The overall bucket also updates the trigger dot.
52
91
  async function runAllDiagnostics() {
53
- showDiagnosticsLoading(tr('diagnosticsHealthTitle'), tr('diagnosticsRunningAll'));
92
+ const request = beginDiagnostics('diagnosticsHealthTitle', 'diagnosticsRunningAll');
54
93
  const specs = [
55
- { label: tr('diagnosticsNativeShort'), run: inspectNativeEnvironment },
56
- { label: tr('diagnosticsPageShort'), run: inspectPageStateDiagnostics },
57
- { label: tr('diagnosticsSnapshotShort'), run: inspectProjectSnapshot },
58
- { label: tr('diagnosticsOtShort'), run: inspectOtWarmMirrorDiagnostics }
94
+ { label: 'diagnosticsNativeShort', run: inspectNativeEnvironment },
95
+ { label: 'diagnosticsPageShort', run: inspectPageStateDiagnostics },
96
+ { label: 'diagnosticsSnapshotShort', run: inspectProjectSnapshot },
97
+ { label: 'diagnosticsOtShort', run: inspectOtWarmMirrorDiagnostics }
59
98
  ];
60
99
  const checks = [];
61
100
  let worst = 'ok';
@@ -64,7 +103,7 @@
64
103
  try {
65
104
  result = await spec.run({ collectOnly: true });
66
105
  } catch (error) {
67
- result = { status: 'failed', summary: tr('diagnosticsCheckErrored'), technical: error?.message || String(error) };
106
+ result = projectableResult(() => ({ status: 'failed', summary: tr('diagnosticsCheckErrored'), technical: error?.message || String(error) }));
68
107
  }
69
108
  const bucket = diagnosticsHealthBucket(result?.status);
70
109
  if (bucket === 'fail') {
@@ -72,35 +111,32 @@
72
111
  } else if (bucket === 'warn' && worst !== 'fail') {
73
112
  worst = 'warn';
74
113
  }
75
- checks.push({
76
- status: result?.status || 'info',
77
- title: spec.label,
78
- summary: result?.summary || result?.subtitle || '',
79
- nextStep: bucket === 'ok' ? '' : (result?.nextStep || '')
114
+ const project = resultProjections.get(result) || (() => result);
115
+ checks.push(() => {
116
+ const translated = project();
117
+ return {
118
+ status: result?.status || 'info',
119
+ title: tr(spec.label),
120
+ summary: translated?.summary || translated?.subtitle || '',
121
+ nextStep: bucket === 'ok' ? '' : (translated?.nextStep || '')
122
+ };
80
123
  });
81
124
  }
82
125
  const overallSubtitleKey = worst === 'ok'
83
126
  ? 'diagnosticsHealthOk'
84
127
  : worst === 'fail' ? 'diagnosticsHealthFail' : 'diagnosticsHealthWarn';
85
- showDiagnosticsResult({
128
+ showCurrentDiagnosticsResult(request, projectableResult(() => ({
86
129
  title: tr('diagnosticsHealthTitle'),
87
130
  subtitle: tr(overallSubtitleKey),
88
131
  status: worst === 'ok' ? 'completed' : worst === 'fail' ? 'failed' : 'warning',
89
- checks,
90
- technical: checks.map(check => `${check.title}: ${check.status}`).join('\n')
91
- });
92
- setDiagnosticsHealth(worst);
132
+ checks: checks.map(project => project())
133
+ })));
134
+ if (isCurrentDiagnosticsRequest(request)) setDiagnosticsHealth(worst);
93
135
  }
94
136
 
95
-
96
-
97
-
98
-
99
-
100
137
  async function inspectProjectSnapshot(options = {}) {
101
- if (!options.collectOnly) {
102
- showDiagnosticsLoading(tr('diagnosticsSnapshotTitle'), tr('diagnosticsSnapshotLoading'));
103
- }
138
+ const request = options.collectOnly ? null
139
+ : beginDiagnostics('diagnosticsSnapshotTitle', 'diagnosticsSnapshotLoading');
104
140
  let result;
105
141
  try {
106
142
  const project = await callPageBridge('getProjectSnapshot', {
@@ -112,36 +148,35 @@
112
148
  zipOnly: true,
113
149
  zipTimeoutMs: RUN_SNAPSHOT_ZIP_TIMEOUT_MS
114
150
  });
115
- result = formatProjectSnapshotDiagnosticsResult(project);
151
+ result = projectableResult(() => formatProjectSnapshotDiagnosticsResult(project));
116
152
  } catch (error) {
117
- result = {
153
+ result = projectableResult(() => ({
118
154
  title: tx('Project Read Failed', '项目读取失败'),
119
155
  subtitle: tx('The extension did not receive Overleaf project content.', '插件没有拿到 Overleaf 项目内容。'),
120
156
  status: 'failed',
121
157
  summary: tr('diagnosticsSnapshotErrorSummary'),
122
158
  nextStep: tx('Reload Overleaf, wait for the left file tree to finish loading, then retry.', '刷新 Overleaf 页面,等左侧文件树加载完成后重试。'),
123
159
  technical: error?.stack || error?.message || String(error)
124
- };
160
+ }));
125
161
  }
126
162
  if (options.collectOnly) {
127
163
  return result;
128
164
  }
129
- showDiagnosticsResult(result);
165
+ showCurrentDiagnosticsResult(request, result);
130
166
  }
131
167
 
132
168
  async function inspectNativeEnvironment(options = {}) {
133
- if (!options.collectOnly) {
134
- showDiagnosticsLoading(tr('diagnosticsNativeTitle'), tr('diagnosticsNativeLoading'));
135
- }
169
+ const request = options.collectOnly ? null
170
+ : beginDiagnostics('diagnosticsNativeTitle', 'diagnosticsNativeLoading');
136
171
  const params = CodexOverleafCompatibility?.buildBridgePingParams
137
172
  ? CodexOverleafCompatibility.buildBridgePingParams(getExtensionCompatibilityMetadata())
138
173
  : {};
139
174
  const response = await sendBackgroundNative({ method: 'bridge.ping', params });
140
- const result = formatNativeEnvironmentResult(response);
175
+ const result = projectableResult(() => formatNativeEnvironmentResult(response));
141
176
  if (options.collectOnly) {
142
177
  return result;
143
178
  }
144
- showDiagnosticsResult(result);
179
+ showCurrentDiagnosticsResult(request, result);
145
180
  }
146
181
 
147
182
  function formatNativeEnvironmentResult(response) {
@@ -151,7 +186,6 @@
151
186
  if (compatibility.status !== 'ok' && compatibility.status !== 'native_unhealthy') {
152
187
  return formatNativeCompatibilityResult(compatibility, response);
153
188
  }
154
-
155
189
  if (!response?.ok) {
156
190
  return {
157
191
  title: tx('Local Connection Problem', '本机连接异常'),
@@ -159,11 +193,10 @@
159
193
  status: 'failed',
160
194
  summary: tx('The extension is not connected to the local service, so it cannot run local Codex or sync the local workspace yet.', '插件没有连上本机服务,所以暂时不能调用本地 Codex 或同步本地 workspace。'),
161
195
  nextStep: tx('Make sure the native host is installed, reload the Chrome extension, then try again.', '确认 native host 已安装,并重新加载 Chrome 扩展后再试。'),
162
- installCommand: INSTALL_COMMAND,
196
+ installCommand: compatibility.installCommand ?? INSTALL_COMMAND,
163
197
  technical: response?.error?.message || tx('native host did not respond', 'native host 没有响应')
164
198
  };
165
199
  }
166
-
167
200
  const environment = response.result?.environment;
168
201
  if (!environment) {
169
202
  return {
@@ -175,7 +208,6 @@
175
208
  technical: JSON.stringify(response.result || {}, null, 2)
176
209
  };
177
210
  }
178
-
179
211
  const codexOk = environment.codex?.ok === true;
180
212
  const latexTools = environment.latex?.available || [];
181
213
  const latexOk = latexTools.length > 0;
@@ -187,7 +219,6 @@
187
219
  ? tx(`LaTeX tools available: ${latexTools.join(', ')}`, `LaTeX 工具可用:${latexTools.join(', ')}`)
188
220
  : tx('LaTeX tools were not found: text editing works, but local compile checks are limited.', 'LaTeX 工具没有找到:可以编辑文本,但不能在本地编译验证。')
189
221
  ];
190
-
191
222
  if (codexOk && latexOk) {
192
223
  return {
193
224
  title: tx('Local Connection OK', '本机连接正常'),
@@ -198,7 +229,6 @@
198
229
  technical: JSON.stringify(environment, null, 2)
199
230
  };
200
231
  }
201
-
202
232
  return {
203
233
  title: codexOk ? tx('Local Connection Partially Available', '本机连接部分可用') : tx('Codex Unavailable', 'Codex 不可用'),
204
234
  subtitle: codexOk ? tx('Codex is available, but compile tools are incomplete.', 'Codex 可用,但编译工具不完整。') : tx('Local Codex was not found.', '没有找到本机 Codex。'),
@@ -213,7 +243,6 @@
213
243
  technical: JSON.stringify(environment, null, 2)
214
244
  };
215
245
  }
216
-
217
246
  function fallbackNativeCompatibility(response) {
218
247
  return response?.ok
219
248
  ? { status: 'ok', classification: 'compatible', native: response.result, installCommand: INSTALL_COMMAND }
@@ -239,12 +268,13 @@
239
268
  subtitle: tx('The extension could not connect to the local service.', '插件没有连上本机服务。'),
240
269
  status: 'failed',
241
270
  summary: tx('The extension is not connected to the local service, so it cannot run local Codex or sync the local workspace yet.', '插件没有连上本机服务,所以暂时不能调用本地 Codex 或同步本地 workspace。'),
242
- nextStep: tx('Make sure the native host is installed, reload the Chrome extension, then try again.', '确认 native host 已安装,并重新加载 Chrome 扩展后再试。'),
243
- installCommand: INSTALL_COMMAND,
271
+ nextStep: compatibility.installIdentity?.managed && !compatibility.installCommand
272
+ ? tx('Repair Managed using the original managed root, browser and extension ID with install-managed.', '请使用原管理根目录、浏览器及扩展 ID,通过 install-managed 修复托管安装。')
273
+ : tx('Make sure the native host is installed, reload the Chrome extension, then try again.', '确认 native host 已安装,并重新加载 Chrome 扩展后再试。'),
274
+ installCommand: compatibility.installCommand ?? INSTALL_COMMAND,
244
275
  technical: response?.error?.message || tx('native host did not respond', 'native host 没有响应')
245
276
  };
246
277
  }
247
-
248
278
  const messages = getNativeCompatibilityMessages(statusValue);
249
279
  return {
250
280
  title: messages.title,
@@ -257,7 +287,6 @@
257
287
  technical: formatNativeCompatibilityTechnicalDetails(compatibility, response)
258
288
  };
259
289
  }
260
-
261
290
  function getNativeCompatibilityMessages(statusValue) {
262
291
  switch (statusValue) {
263
292
  case 'native_too_old':
@@ -330,62 +359,59 @@
330
359
  }
331
360
 
332
361
  async function inspectPageStateDiagnostics(options = {}) {
333
- if (!options.collectOnly) {
334
- showDiagnosticsLoading(tr('diagnosticsPageTitle'), tr('diagnosticsPageLoading'));
335
- }
362
+ const request = options.collectOnly ? null
363
+ : beginDiagnostics('diagnosticsPageTitle', 'diagnosticsPageLoading');
336
364
  let result;
337
365
  try {
338
366
  const probe = await callPageBridge('probe', {
339
367
  manualOverride: getState()?.requireReviewing === false
340
368
  });
341
- result = formatPageStateDiagnosticsResult(probe);
369
+ const mode = getState()?.mode;
370
+ result = projectableResult(() => formatPageStateDiagnosticsResult(probe, mode));
342
371
  } catch (error) {
343
- result = {
372
+ result = projectableResult(() => ({
344
373
  title: tx('Overleaf Page Check Failed', 'Overleaf 页面检查失败'),
345
374
  subtitle: tx('The extension did not read the current page state.', '插件没有读到当前页面状态。'),
346
375
  status: 'failed',
347
376
  summary: tx('This usually means Overleaf is still loading, or the page script is temporarily unavailable.', '这通常表示 Overleaf 页面还在加载,或者页面脚本暂时不可用。'),
348
377
  nextStep: tx('Reload Overleaf, open the .tex file you want to work on, then try again.', '刷新 Overleaf 页面,点开要处理的 .tex 文件后再试。'),
349
378
  technical: error?.stack || error?.message || String(error)
350
- };
379
+ }));
351
380
  }
352
381
  if (options.collectOnly) {
353
382
  return result;
354
383
  }
355
- showDiagnosticsResult(result);
384
+ showCurrentDiagnosticsResult(request, result);
356
385
  }
357
386
 
358
387
  async function inspectOtWarmMirrorDiagnostics(options = {}) {
359
- if (!options.collectOnly) {
360
- showDiagnosticsLoading(tr('diagnosticsOtTitle'), tr('diagnosticsLoading'));
361
- }
388
+ const request = options.collectOnly ? null
389
+ : beginDiagnostics('diagnosticsOtTitle', 'diagnosticsLoading');
362
390
  // OT warm mirror is opt-in and off by default. When it is disabled
363
391
  // there is nothing live to probe, so report a clean, healthy "disabled"
364
392
  // state instead of querying (then warning about) absent OT metadata — or
365
393
  // degrading to the generic "could not run" error if a probe throws. A
366
394
  // turned-off feature must never read as a failure.
367
395
  if (!isExperimentalOtEnabled()) {
368
- const disabledResult = {
369
- title: tr('diagnosticsOtTitle'),
370
- subtitle: tr('diagnosticsOtSubtitle'),
371
- status: 'completed',
372
- summary: tr('diagnosticsOtSummaryDisabled'),
373
- bullets: [],
374
- nextStep: '',
375
- technical: ''
376
- };
377
396
  const mirrorState = getOtWarmMirrorState?.() || {};
378
- if (mirrorState.failureActive && mirrorState.lastFailure) {
379
- const failure = mirrorState.lastFailure;
380
- disabledResult.status = 'warning';
381
- disabledResult.summary = tr(otWarmMirrorController.getFailureMessageKey(failure.code));
382
- disabledResult.nextStep = tr('otFailureNextStep');
383
- disabledResult.technical = `lastErrorCode: ${failure.code}\nphase: ${failure.phase}\nfailedAt: ${new Date(failure.at).toISOString()}`;
384
- }
397
+ const failure = mirrorState.failureActive && mirrorState.lastFailure ? { ...mirrorState.lastFailure } : null;
398
+ const disabledResult = projectableResult(() => {
399
+ const result = {
400
+ title: tr('diagnosticsOtTitle'), subtitle: tr('diagnosticsOtSubtitle'), status: 'completed',
401
+ summary: tr('diagnosticsOtSummaryDisabled'), bullets: [], nextStep: '', technical: ''
402
+ };
403
+ if (failure) {
404
+ result.status = 'warning';
405
+ result.summary = tr(otWarmMirrorController.getFailureMessageKey(failure.code));
406
+ result.nextStep = tr('otFailureNextStep');
407
+ result.technical = `lastErrorCode: ${failure.code}\nphase: ${failure.phase}\nfailedAt: ${new Date(failure.at).toISOString()}`;
408
+ }
409
+ return result;
410
+ });
385
411
  if (options.collectOnly) {
386
412
  return disabledResult;
387
413
  }
388
- showDiagnosticsResult(disabledResult);
414
+ showCurrentDiagnosticsResult(request, disabledResult);
389
415
  return;
390
416
  }
391
417
  const projectId = getCurrentProjectId();
@@ -422,26 +448,30 @@
422
448
  mirrorStatus = { lastOtErrorCode: 'mirror_status_failed' };
423
449
  }
424
450
 
425
- const baseResult = formatOtDiagnosticsResult({ otStatus, mirrorStatus });
426
- const result = metadataWarning
427
- ? {
451
+ const context = { enabled: isExperimentalOtEnabled(), status: getCurrentOtStatus(),
452
+ warmMirrorState: { ...(getOtWarmMirrorState() || {}) }, focusFiles: getActiveFocusFiles() };
453
+ context.warmStart = otWarmMirrorController?.canUseOtWarmStart?.({ enabled: context.enabled, focusFiles: context.focusFiles, mirrorStatus }) || { ok: false };
454
+ const result = projectableResult(() => {
455
+ const baseResult = formatOtDiagnosticsResult({ otStatus, mirrorStatus, context });
456
+ return metadataWarning ? {
428
457
  ...baseResult,
429
458
  status: 'warning',
430
459
  summary: `${baseResult.summary} ${tx('Some OT diagnostic metadata is unavailable.', '部分 OT 诊断元数据暂时不可用。')}`
431
460
  }
432
- : baseResult;
461
+ : baseResult;
462
+ });
433
463
  if (options.collectOnly) {
434
464
  return result;
435
465
  }
436
- showDiagnosticsResult(result);
466
+ showCurrentDiagnosticsResult(request, result);
437
467
  }
438
468
 
439
- function formatOtDiagnosticsResult({ otStatus, mirrorStatus }) {
440
- const enabled = isExperimentalOtEnabled();
441
- const statusValue = normalizeOtStatus(otStatus ? readOtBridgeStatus(otStatus) : getCurrentOtStatus());
469
+ function formatOtDiagnosticsResult({ otStatus, mirrorStatus, context = {} }) {
470
+ const enabled = context.enabled ?? isExperimentalOtEnabled();
471
+ const statusValue = normalizeOtStatus(otStatus ? readOtBridgeStatus(otStatus) : context.status ?? getCurrentOtStatus());
442
472
  const queuedEventCount = normalizeOtDiagnosticsCount(otStatus?.queuedEventCount);
443
473
  const lastEventAt = formatOtDiagnosticValue(otStatus?.lastEventAt, tr('noneValue'));
444
- const warmMirrorState = getOtWarmMirrorState() || {};
474
+ const warmMirrorState = context.warmMirrorState || getOtWarmMirrorState() || {};
445
475
  const failureActive = warmMirrorState.failureActive === true;
446
476
  const lastOtPatchAt = formatOtDiagnosticValue(mirrorStatus?.lastOtPatchAt || warmMirrorState.lastPatchAt, tr('noneValue'));
447
477
  const lastOtErrorCode = formatOtDiagnosticValue(mirrorStatus?.lastOtErrorCode || warmMirrorState.lastErrorCode, tr('noneValue'));
@@ -452,10 +482,9 @@
452
482
  Array.isArray(mirrorStatus?.otFreshFiles) ? mirrorStatus.otFreshFiles.length : 0
453
483
  );
454
484
  const bridgeFailed = otStatus?.ok === false;
455
- const focusFiles = getActiveFocusFiles();
456
- const otWarmStart = otWarmMirrorController?.canUseOtWarmStart?.({ enabled, focusFiles, mirrorStatus }) || { ok: false };
485
+ const focusFiles = context.focusFiles || getActiveFocusFiles();
486
+ const otWarmStart = context.warmStart || otWarmMirrorController?.canUseOtWarmStart?.({ enabled, focusFiles, mirrorStatus }) || { ok: false };
457
487
  const fallback = !enabled || failureActive || statusValue !== 'observing' || bridgeFailed || otWarmStart?.ok !== true;
458
-
459
488
  return {
460
489
  title: tr('diagnosticsOtTitle'),
461
490
  subtitle: tr('diagnosticsOtSubtitle'),
@@ -479,7 +508,6 @@
479
508
  })
480
509
  };
481
510
  }
482
-
483
511
  function formatOtDiagnosticsTechnicalDetails(metadata = {}) {
484
512
  const lines = [
485
513
  `strategy: ${metadata.strategy || 'unknown'}`,
@@ -531,8 +559,7 @@
531
559
  return text.length > 160 ? `${text.slice(0, 157)}...` : text;
532
560
  }
533
561
 
534
- function formatPageStateDiagnosticsResult(probe) {
535
- const readiness = getProbeRunReadiness(probe || {});
562
+ function formatPageStateDiagnosticsResult(probe, mode = getState()?.mode) {
536
563
  const reviewingOk = probe?.reviewing?.ok === true;
537
564
  const writable = probe?.capabilities?.editor?.write !== false;
538
565
  const readable = probe?.editor?.ok === true;
@@ -546,10 +573,10 @@
546
573
  return {
547
574
  title: tx('Overleaf Page Ready', 'Overleaf 页面可用'),
548
575
  subtitle: formatProbeStatusBar(probe),
549
- status: reviewingOk || getState()?.mode === 'ask' ? 'completed' : 'warning',
576
+ status: reviewingOk || mode === 'ask' ? 'completed' : 'warning',
550
577
  summary: tx('The current Overleaf file can be read and written. The extension still verifies before writing to avoid overwriting new user or collaborator edits.', '当前 Overleaf 文件可以读取和写入。写入前插件仍会再次验证,避免覆盖用户或协作者的新改动。'),
551
578
  bullets,
552
- nextStep: reviewingOk || getState()?.mode === 'ask' ? '' : tx('If you need tracked writes, turn on Overleaf Reviewing/Track Changes first.', '如果需要留痕写入,请先在 Overleaf 开启 Reviewing/Track Changes。'),
579
+ nextStep: reviewingOk || mode === 'ask' ? '' : tx('If you need tracked writes, turn on Overleaf Reviewing/Track Changes first.', '如果需要留痕写入,请先在 Overleaf 开启 Reviewing/Track Changes。'),
553
580
  technical: formatPageDiagnosticsTechnicalDetails(probe)
554
581
  };
555
582
  }
@@ -580,7 +607,6 @@
580
607
  tx(`Asset files: ${binaryCount}`, `资源文件:${binaryCount} 个`),
581
608
  project?.activePath ? tx(`Current file: ${project.activePath}`, `当前文件:${project.activePath}`) : tx('Current file: not detected', '当前文件:未识别')
582
609
  ];
583
-
584
610
  if (fullProject && files.length) {
585
611
  return {
586
612
  title: tx('Project Read OK', '项目读取正常'),
@@ -594,7 +620,6 @@
594
620
  technical: formatProjectSnapshotLog(project)
595
621
  };
596
622
  }
597
-
598
623
  return {
599
624
  title: files.length ? tx('Full Project Not Read', '没有读到完整项目') : tx('No Project Files Read', '没有读到项目文件'),
600
625
  subtitle: tx(`Read source: ${source}`, `读取来源:${source}`),
@@ -610,7 +635,6 @@
610
635
  technical: formatProjectSnapshotLog(project)
611
636
  };
612
637
  }
613
-
614
638
  function formatPageDiagnosticsTechnicalDetails(probe) {
615
639
  const lines = [];
616
640
  lines.push(tx(`Status: ${formatProbeStatusBar(probe || {})}`, `状态:${formatProbeStatusBar(probe || {})}`));
@@ -657,6 +681,7 @@
657
681
 
658
682
 
659
683
  return {
684
+ refreshLocale,
660
685
  runAllDiagnostics,
661
686
  inspectProjectSnapshot,
662
687
  inspectNativeEnvironment,