specrails-desktop 2.29.0 → 2.29.2
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/client/dist/assets/ActivityFeedPage-ClpD5CFj.js +1 -0
- package/client/dist/assets/AgentBrowserCapture-CSPs9Ofc.js +1 -0
- package/client/dist/assets/AgentModeCodePane-DwcyklA5.js +2 -0
- package/client/dist/assets/AgentModeJobsPane-C69bqlMa.js +1 -0
- package/client/dist/assets/AgentsPage-pRiRr9-W.js +86 -0
- package/client/dist/assets/AnalyticsPage-C14exKsC.js +1 -0
- package/client/dist/assets/BarChart-nBOMNfiy.js +33 -0
- package/client/dist/assets/CodePage-CK76JKm9.js +2 -0
- package/client/dist/assets/DesktopAnalyticsPage-Cnv0f3XQ.js +1 -0
- package/client/dist/assets/DocsDialog-CHUm_Ym0.js +11 -0
- package/client/dist/assets/DocsPage-COI-oDok.js +11 -0
- package/client/dist/assets/ExportDropdown-BrtfWzEG.js +1 -0
- package/client/dist/assets/IntegrationsPage-Bs00_tl4.js +1 -0
- package/client/dist/assets/InteractiveJobComposer-CypM7R1F.js +19 -0
- package/client/dist/assets/JobDetailModal-B_W0H9dw.js +1 -0
- package/client/dist/assets/JobDetailPage-CeeXOoKS.js +1 -0
- package/client/dist/assets/JobsPage-CwhJG9jw.js +1 -0
- package/client/dist/assets/LoopBuilderPage-C51t1WOM.js +7 -0
- package/client/dist/assets/LoopPreviewModal-Y2HgtIJu.js +1 -0
- package/client/dist/assets/LoopsPage-Bvn1Kw5V.js +1 -0
- package/client/dist/assets/MinimizedChatsContext-DiFvZDPW.js +1 -0
- package/client/dist/assets/PluginsPage-BGPRJpdf.js +2 -0
- package/client/dist/assets/ProjectSettingsDialog-D_GTyGLc.js +1 -0
- package/client/dist/assets/TemplatePreviewModal-szwBhd7h.js +1 -0
- package/client/dist/assets/TicketDetailModal-9UEyK974.js +14 -0
- package/client/dist/assets/Trans-B_vKZ-Hb.js +1 -0
- package/client/dist/assets/activity-DiyjsgQV.js +1 -0
- package/client/dist/assets/addon-image-BRmmRHgQ.js +1 -0
- package/client/dist/assets/addon-ligatures-qIZUPvRV.js +2 -0
- package/client/dist/assets/{addon-webgl-DMbGeI_u.js → addon-webgl-C2d7lriQ.js} +3 -3
- package/client/dist/assets/addspec-Rw8uVBC1.js +1 -0
- package/client/dist/assets/agent-4rmXoo_p.js +1 -0
- package/client/dist/assets/agent-BxZuNGih.js +1 -0
- package/client/dist/assets/agent-C3uXOYv_.js +1 -0
- package/client/dist/assets/agent-CA8Y4wbw.js +1 -0
- package/client/dist/assets/agent-CASKrhG12.js +1 -0
- package/client/dist/assets/agent-Cv-jud5n2.js +1 -0
- package/client/dist/assets/agent-DitUxYh2.js +1 -0
- package/client/dist/assets/agent-Doow4X7o.js +1 -0
- package/client/dist/assets/agents-DhG7mg6-.js +1 -0
- package/client/dist/assets/agentstudio-BIUe1Im2.js +1 -0
- package/client/dist/assets/aiedit-iIjz2_Qk.js +1 -0
- package/client/dist/assets/analytics-DZ8Aoq3I.js +1 -0
- package/client/dist/assets/api-B2M7CtDw.js +1 -0
- package/client/dist/assets/arrow-left-CpIR4j7G.js +1 -0
- package/client/dist/assets/arrow-up-right-9DoMn7fD.js +1 -0
- package/client/dist/assets/attachments-B53PG733.js +1 -0
- package/client/dist/assets/brain-DI9lHkKY.js +1 -0
- package/client/dist/assets/browser-CXUcnTMI.js +1 -0
- package/client/dist/assets/button-BUIIBQPT.js +1 -0
- package/client/dist/assets/chat-BGD7MXAy.js +1 -0
- package/client/dist/assets/chevron-right-CViMxucY.js +1 -0
- package/client/dist/assets/chunk-KS7C4IRE-Cx5sqopX.js +3 -0
- package/client/dist/assets/circle-x-CMYsN4ZH.js +1 -0
- package/client/dist/assets/code-BDXEM4ml.js +1 -0
- package/client/dist/assets/commands-DyUZQ1FI.js +1 -0
- package/client/dist/assets/common-CD1QHriA2.js +1 -0
- package/client/dist/assets/common-CwwPaRxx.js +1 -0
- package/client/dist/assets/common-DVQuhs-m.js +1 -0
- package/client/dist/assets/common-Dg2jaX7d.js +1 -0
- package/client/dist/assets/common-DuBwj6tK.js +1 -0
- package/client/dist/assets/common-MRj9MHcc.js +1 -0
- package/client/dist/assets/common-O4ZpnMLp.js +1 -0
- package/client/dist/assets/common-fyeF0v7C2.js +1 -0
- package/client/dist/assets/createLucideIcon-Bjbbp_KS.js +1 -0
- package/client/dist/assets/{css.worker-Wv5dxAWO.js → css.worker-yKcq13f2.js} +13 -13
- package/client/dist/assets/{cssMode-DBHbkBvI.js → cssMode-BM4z9OX0.js} +1 -1
- package/client/dist/assets/dashboard-B_NkSHYm.js +1 -0
- package/client/dist/assets/dashboard-ClBb_3pq.js +1 -0
- package/client/dist/assets/dashboard-CpCmJvMB.js +1 -0
- package/client/dist/assets/dashboard-Czohu35O2.js +1 -0
- package/client/dist/assets/dashboard-DcjbD0UK.js +1 -0
- package/client/dist/assets/dashboard-Dvx5F3we.js +1 -0
- package/client/dist/assets/dashboard-R1bOPjBh2.js +1 -0
- package/client/dist/assets/dashboard-owcDucDi.js +1 -0
- package/client/dist/assets/dialog-CzIekCw0.js +45 -0
- package/client/dist/assets/dist-Cez5CRkX.js +1 -0
- package/client/dist/assets/dist-bVqfYmby.js +1 -0
- package/client/dist/assets/{dist-js-UjXbEWhN.js → dist-js-CcBCbb32.js} +1 -1
- package/client/dist/assets/{dist-js-BTAcxhPb.js → dist-js-VwztRkGj.js} +1 -1
- package/client/dist/assets/download-CFHyyHcw.js +1 -0
- package/client/dist/assets/editor.api2-4ndOupAA.js +872 -0
- package/client/dist/assets/{editor.main-C9J2ikJK.js → editor.main-DxrmGfoq.js} +2 -2
- package/client/dist/assets/editor.worker-tytyn86m.js +26 -0
- package/client/dist/assets/explore-DgBACn39.js +1 -0
- package/client/dist/assets/external-link-BcU5EWZp.js +1 -0
- package/client/dist/assets/file-text-CFT-xXKN.js +1 -0
- package/client/dist/assets/formatDistanceToNow-ByHIauTQ.js +1 -0
- package/client/dist/assets/{freemarker2-J5iIIIK-.js → freemarker2-CELlTDJ2.js} +1 -1
- package/client/dist/assets/getTimezoneOffsetInMilliseconds-BxHAksaU.js +1 -0
- package/client/dist/assets/git-branch-BRM0F5GN.js +1 -0
- package/client/dist/assets/{handlebars-DSw1l_tw.js → handlebars-NEjHJ7o_.js} +1 -1
- package/client/dist/assets/{html-h2-wE1Lj.js → html-CA10zN5A.js} +1 -1
- package/client/dist/assets/{html.worker-CQP8QQsS.js → html.worker-DSJ9zmd7.js} +12 -12
- package/client/dist/assets/{htmlMode-Cc_ij7lW.js → htmlMode-89rPYiyq.js} +1 -1
- package/client/dist/assets/i18n-CgaRxpII.js +2 -0
- package/client/dist/assets/index-BflYQpWm.css +2 -0
- package/client/dist/assets/index-C1_-BTXy.js +72 -0
- package/client/dist/assets/integrations-mB-7zoyT.js +1 -0
- package/client/dist/assets/{javascript-C1q3xv6N.js → javascript-B1gDmwzS.js} +1 -1
- package/client/dist/assets/jira-CmKWERE0.js +1 -0
- package/client/dist/assets/jira-api-BgFIr8eD.js +1 -0
- package/client/dist/assets/job-time-BCL7wee9.js +1 -0
- package/client/dist/assets/jobs-B-sDHEay2.js +1 -0
- package/client/dist/assets/jobs-BCtGfgUA.js +1 -0
- package/client/dist/assets/jobs-BHR_EnDI.js +1 -0
- package/client/dist/assets/jobs-BMbZJjJJ.js +1 -0
- package/client/dist/assets/jobs-CVFD8rar.js +1 -0
- package/client/dist/assets/jobs-DoSaFzAa.js +1 -0
- package/client/dist/assets/jobs-DzSIR8V62.js +1 -0
- package/client/dist/assets/jobs-lk1_Dq1U.js +1 -0
- package/client/dist/assets/json.worker-Oa9UrkKE.js +58 -0
- package/client/dist/assets/{jsonMode-CeaCdEhr.js → jsonMode-xHLMfzhF.js} +1 -1
- package/client/dist/assets/jsx-runtime-zu2_FqZY.js +1 -0
- package/client/dist/assets/lib-C7Mhm-gT.js +7 -0
- package/client/dist/assets/lib-CGdyxIWg.js +29 -0
- package/client/dist/assets/{liquid-eFsVK0V-.js → liquid-BY6hCUXG.js} +1 -1
- package/client/dist/assets/loader-circle-DcygOQpC.js +1 -0
- package/client/dist/assets/loops-BzfXWEwO.js +1 -0
- package/client/dist/assets/{lspLanguageFeatures-DT3-bbhn.js → lspLanguageFeatures-ira2aEJh.js} +1 -1
- package/client/dist/assets/mcp-uDkXYu4L.js +1 -0
- package/client/dist/assets/{mdx-Fuwnh1cX.js → mdx-BNx0xr3N.js} +1 -1
- package/client/dist/assets/monaco.contribution-Bt92R3Vw.js +2 -0
- package/client/dist/assets/nav-myFaXRHD.js +1 -0
- package/client/dist/assets/pencil-C9RkrIPZ.js +1 -0
- package/client/dist/assets/play-DNlrawbS.js +1 -0
- package/client/dist/assets/plus-CsnjfkmX.js +1 -0
- package/client/dist/assets/preload-helper-Czpn1I53.js +1 -0
- package/client/dist/assets/{python-BgoEs6Cj.js → python-DLdbtmNw.js} +1 -1
- package/client/dist/assets/{razor-CM1sPMMq.js → razor-B9gdhAbR.js} +1 -1
- package/client/dist/assets/react-dom-DiWzBDP9.js +1 -0
- package/client/dist/assets/rolldown-runtime-CNC7AqOf.js +1 -0
- package/client/dist/assets/save-28sIlCdr.js +1 -0
- package/client/dist/assets/search-Cq_gE3Ik.js +1 -0
- package/client/dist/assets/settings-B0ypw9uw.js +1 -0
- package/client/dist/assets/{settings-Bp24JHlv2.js → settings-B9ilOSYO.js} +1 -1
- package/client/dist/assets/{settings-Bx2ObkTR2.js → settings-BqlWHRHA.js} +1 -1
- package/client/dist/assets/{settings-C_T0-j9d.js → settings-D8dlqt4d.js} +1 -1
- package/client/dist/assets/{settings-DhaFKpcw2.js → settings-DAZqjX2a2.js} +1 -1
- package/client/dist/assets/{settings-B_v3zgJf.js → settings-DRh39v1S2.js} +1 -1
- package/client/dist/assets/{settings-BemR_e3F.js → settings-Mj1OJbfd2.js} +1 -1
- package/client/dist/assets/{settings-BvIwQ3A1.js → settings-lRReaSYm.js} +1 -1
- package/client/dist/assets/setup-CmK87LuS.js +1 -0
- package/client/dist/assets/sparkles-DrY8hb0X.js +1 -0
- package/client/dist/assets/specs-DII0C8gw.js +1 -0
- package/client/dist/assets/spending-C4p06nen.js +1 -0
- package/client/dist/assets/terminal-BFRZnMPP.js +1 -0
- package/client/dist/assets/tickets-B8BuAaj5.js +1 -0
- package/client/dist/assets/tickets-B_yh4qQk.js +1 -0
- package/client/dist/assets/tickets-Bs37scwY2.js +1 -0
- package/client/dist/assets/tickets-CFk2n2Or.js +1 -0
- package/client/dist/assets/tickets-DQp7JS2R2.js +1 -0
- package/client/dist/assets/tickets-D_yDquEw.js +1 -0
- package/client/dist/assets/tickets-DpmdE8tv2.js +1 -0
- package/client/dist/assets/tickets-pAUJkDTu.js +1 -0
- package/client/dist/assets/trash-2-BOU3WdZZ.js +1 -0
- package/client/dist/assets/triangle-alert-H9T4jAmh.js +1 -0
- package/client/dist/assets/{ts.worker-METxwbDZ.js → ts.worker-BtjBFNHX.js} +48 -33
- package/client/dist/assets/{tsMode-BmT8WogI.js → tsMode-DEjSThU9.js} +1 -1
- package/client/dist/assets/{typescript-CQrQPsoW.js → typescript-CRRnD2Ts.js} +1 -1
- package/client/dist/assets/upload-DYMjAQ6M.js +1 -0
- package/client/dist/assets/useBrowserCaptureSession-2OqX0vap.js +1 -0
- package/client/dist/assets/useDesktop-X8YB9xzv.js +1 -0
- package/client/dist/assets/useSharedWebSocket-DaPh7QBL.js +1 -0
- package/client/dist/assets/utils-BC4DHlz2.js +1 -0
- package/client/dist/assets/value-s-gzBeyF.js +1 -0
- package/client/dist/assets/{workers-U0UXyLUf.js → workers-uOo7WLaa.js} +1 -1
- package/client/dist/assets/x-CBMI9ejn.js +1 -0
- package/client/dist/assets/{xml-WRxJs8_I.js → xml-EDREH2X7.js} +1 -1
- package/client/dist/assets/{yaml-CjpSTjJU.js → yaml-BjaDVX1E.js} +1 -1
- package/client/dist/assets/zap-CHo3aCD1.js +1 -0
- package/client/dist/index.html +73 -32
- package/docs/guide/en/integrations/5-mcp-server.md +2 -2
- package/docs/internals/safe-pr-review-flow.md +190 -132
- package/docs/mcp.md +15 -5
- package/package.json +11 -7
- package/server/dist/active-pr-continuation.js +16 -1
- package/server/dist/agent-chat-manager.js +360 -181
- package/server/dist/agent-cwd-manager.js +52 -8
- package/server/dist/agent-generator.js +90 -48
- package/server/dist/agent-mcp-config.js +69 -36
- package/server/dist/agent-operator-prompt.js +3 -2
- package/server/dist/agent-refine-manager.js +47 -6
- package/server/dist/agent-tier.js +13 -11
- package/server/dist/artifact-registry.js +33 -2
- package/server/dist/auth.js +5 -4
- package/server/dist/browser-capture-manager.js +92 -29
- package/server/dist/chat-manager.js +302 -46
- package/server/dist/contract-refine-runner.js +19 -6
- package/server/dist/db.js +665 -8
- package/server/dist/desktop-router.js +1 -2
- package/server/dist/headroom-manager.js +1310 -121
- package/server/dist/headroom-routing.js +120 -2
- package/server/dist/index.js +48 -13
- package/server/dist/interactive-job-session.js +237 -82
- package/server/dist/jira/jira-adf.js +10 -0
- package/server/dist/jira/jira-db.js +15 -3
- package/server/dist/jira/jira-sync-manager.js +182 -13
- package/server/dist/job-listing.js +140 -0
- package/server/dist/job-spawn-idempotency.js +67 -0
- package/server/dist/loop-run-manager.js +508 -98
- package/server/dist/loop-runs-store.js +266 -13
- package/server/dist/mcp/agent-capability.js +71 -0
- package/server/dist/mcp/guide.js +5 -2
- package/server/dist/mcp/mcp-server.js +5 -10
- package/server/dist/mcp/mcp-token.js +5 -5
- package/server/dist/mcp/tools/jobs.js +20 -13
- package/server/dist/mcp/tools/types.js +20 -42
- package/server/dist/mobile/mobile-router.js +1 -1
- package/server/dist/pr-lifecycle.js +77 -0
- package/server/dist/pr-publisher.js +94 -27
- package/server/dist/process-admission.js +82 -0
- package/server/dist/project-registry.js +572 -174
- package/server/dist/project-router-git.js +13 -2
- package/server/dist/project-router-jobs.js +111 -55
- package/server/dist/project-router-tickets.js +32 -2
- package/server/dist/providers/claude-adapter.js +21 -13
- package/server/dist/queue-manager.js +2332 -623
- package/server/dist/rail-isolated-launch.js +1141 -280
- package/server/dist/rail-isolation.js +4 -2
- package/server/dist/rail-pr-decision.js +756 -270
- package/server/dist/rail-pr-delivery.js +2 -1
- package/server/dist/rail-pr-store.js +317 -18
- package/server/dist/rail-pr-ticket-effects.js +328 -0
- package/server/dist/rail-worktree-release.js +28 -6
- package/server/dist/rails-router.js +149 -112
- package/server/dist/rails-store.js +106 -3
- package/server/dist/ticket-store.js +23 -1
- package/server/dist/transient-children.js +13 -0
- package/server/dist/util/cli-prompt.js +42 -8
- package/server/dist/util/secure-token-file.js +84 -0
- package/server/dist/worktree-manager.js +70 -21
- package/client/dist/assets/ActivityFeedPage-Be-6L0Ld.js +0 -1
- package/client/dist/assets/AgentBrowserCapture-CpZ-dd8O.js +0 -1
- package/client/dist/assets/AgentIntegrationsModal-DO1pN_Ez.js +0 -1
- package/client/dist/assets/AgentModeCodePane-DLltTOqp.js +0 -2
- package/client/dist/assets/AgentModeJobsPane-Dp5YvmW0.js +0 -1
- package/client/dist/assets/AgentsPage-ehHuVUds.js +0 -86
- package/client/dist/assets/AnalyticsPage-C4Ik95FX.js +0 -1
- package/client/dist/assets/BarChart-DVZgrhJd.js +0 -33
- package/client/dist/assets/CodePage-D4OCMfxL.js +0 -2
- package/client/dist/assets/DesktopAnalyticsPage-2Xf-52x2.js +0 -1
- package/client/dist/assets/DocsDialog-CHihLjWd.js +0 -11
- package/client/dist/assets/DocsPage-1vEk7XbH.js +0 -11
- package/client/dist/assets/ExportDropdown-DLHFQxVn.js +0 -1
- package/client/dist/assets/IntegrationsPage-CCb2YuyJ.js +0 -1
- package/client/dist/assets/InteractiveJobComposer-CxJJEnjw.js +0 -19
- package/client/dist/assets/JobDetailModal-CJI7qRkm.js +0 -1
- package/client/dist/assets/JobDetailPage-DwA9bbwx.js +0 -1
- package/client/dist/assets/JobsPage-BDIyFfd5.js +0 -1
- package/client/dist/assets/LoopBuilderPage-CpBaW59t.js +0 -7
- package/client/dist/assets/LoopPreviewModal-CwpKcv0Y.js +0 -1
- package/client/dist/assets/LoopsPage-BO0Pa8oz.js +0 -1
- package/client/dist/assets/PluginsPage-BBGTBpGh.js +0 -2
- package/client/dist/assets/ProjectSettingsDialog-M9zGQo0l.js +0 -1
- package/client/dist/assets/TemplatePreviewModal-eBI0zL5P.js +0 -1
- package/client/dist/assets/activity-Dbl71S-E.js +0 -1
- package/client/dist/assets/addon-image-CwoZj17F.js +0 -1
- package/client/dist/assets/addon-ligatures-CWDrED80.js +0 -2
- package/client/dist/assets/addspec-DrXqP8ip.js +0 -1
- package/client/dist/assets/agent-BEXYxDbs.js +0 -1
- package/client/dist/assets/agent-BoXSzaBk2.js +0 -1
- package/client/dist/assets/agent-C2-rROL52.js +0 -1
- package/client/dist/assets/agent-CeRTdGT12.js +0 -1
- package/client/dist/assets/agent-DZ8zTrQT.js +0 -1
- package/client/dist/assets/agent-DqyzT33X.js +0 -1
- package/client/dist/assets/agent-fQI_6tsA.js +0 -1
- package/client/dist/assets/agent-tJdAobaM.js +0 -1
- package/client/dist/assets/agents-CGDn_3kB.js +0 -1
- package/client/dist/assets/agentstudio-Dxe_94PK.js +0 -1
- package/client/dist/assets/aiedit-DrfHQnlz.js +0 -1
- package/client/dist/assets/analytics-CxDYcBl9.js +0 -1
- package/client/dist/assets/attachments-DvxQbBTC.js +0 -1
- package/client/dist/assets/brain-DecvjjPU.js +0 -1
- package/client/dist/assets/browser-DM8G151q.js +0 -1
- package/client/dist/assets/chat-0dg5hOo_.js +0 -1
- package/client/dist/assets/chunk-BNv3lrIs.js +0 -1
- package/client/dist/assets/code-B62fClk-.js +0 -1
- package/client/dist/assets/commands-DCJ-R9E4.js +0 -1
- package/client/dist/assets/common-BfQD173j.js +0 -1
- package/client/dist/assets/common-CF8iGXrG.js +0 -1
- package/client/dist/assets/common-Cfmwcrl52.js +0 -1
- package/client/dist/assets/common-D2cimsul.js +0 -1
- package/client/dist/assets/common-DH7fjyL1.js +0 -1
- package/client/dist/assets/common-DXrmj6WD.js +0 -1
- package/client/dist/assets/common-DZbXlmq72.js +0 -1
- package/client/dist/assets/common-DtXmzX2o2.js +0 -1
- package/client/dist/assets/dashboard-5C2FOZQX.js +0 -1
- package/client/dist/assets/dashboard-B6iQ-IL_.js +0 -1
- package/client/dist/assets/dashboard-BFfnCtq52.js +0 -1
- package/client/dist/assets/dashboard-BIC8KtRf2.js +0 -1
- package/client/dist/assets/dashboard-CEgg9NAr.js +0 -1
- package/client/dist/assets/dashboard-CiOyDh9L.js +0 -1
- package/client/dist/assets/dashboard-D6x5OnNj2.js +0 -1
- package/client/dist/assets/dashboard-DBuLfWo9.js +0 -1
- package/client/dist/assets/editor.api2-C3B0tp2x.js +0 -872
- package/client/dist/assets/editor.worker-Bd9IXS8d.js +0 -26
- package/client/dist/assets/explore-_XyU5e7R.js +0 -1
- package/client/dist/assets/index-BVbgKXUu.css +0 -2
- package/client/dist/assets/index-OBDI7bHm.js +0 -158
- package/client/dist/assets/integrations-By80EBkf.js +0 -1
- package/client/dist/assets/jira-DeIjwCK3.js +0 -1
- package/client/dist/assets/jobs-BFIdeDTw.js +0 -1
- package/client/dist/assets/jobs-BJ-Gcao22.js +0 -1
- package/client/dist/assets/jobs-DAGiPVIS2.js +0 -1
- package/client/dist/assets/jobs-DAU8C_tZ.js +0 -1
- package/client/dist/assets/jobs-Da0GaaSc.js +0 -1
- package/client/dist/assets/jobs-DrYmsKy5.js +0 -1
- package/client/dist/assets/jobs-P3unxtxo2.js +0 -1
- package/client/dist/assets/jobs-p360zdf1.js +0 -1
- package/client/dist/assets/json.worker-DzV-CpCQ.js +0 -58
- package/client/dist/assets/lib-C5ZxrPSR.js +0 -7
- package/client/dist/assets/loops-CO6q75W8.js +0 -1
- package/client/dist/assets/mcp-HwBbQDk0.js +0 -1
- package/client/dist/assets/monaco.contribution-Desq7oq4.js +0 -2
- package/client/dist/assets/nav-BTg8s-cD.js +0 -1
- package/client/dist/assets/preload-helper-DSXbuxSR.js +0 -1
- package/client/dist/assets/settings-BYCMtxOz.js +0 -1
- package/client/dist/assets/setup-D2CmgAro.js +0 -1
- package/client/dist/assets/specs-PGIOzMtc.js +0 -1
- package/client/dist/assets/terminal-CFt56A5f.js +0 -1
- package/client/dist/assets/tickets-BHv3ewvq.js +0 -1
- package/client/dist/assets/tickets-BIxU86j12.js +0 -1
- package/client/dist/assets/tickets-C2BhwzwR.js +0 -1
- package/client/dist/assets/tickets-D1IeX2EW.js +0 -1
- package/client/dist/assets/tickets-DZut8Ryt.js +0 -1
- package/client/dist/assets/tickets-LfK6LzKl2.js +0 -1
- package/client/dist/assets/tickets-dQfsc7Ph.js +0 -1
- package/client/dist/assets/tickets-sVun0I6v.js +0 -1
- package/client/dist/assets/upload-lgjKJgrl.js +0 -1
- package/client/dist/assets/value-Bc0_jlJA.js +0 -1
- /package/client/dist/assets/{abap-D0E4FfVW.js → abap-08VXUWAP.js} +0 -0
- /package/client/dist/assets/{activity-BbWiDfn-2.js → activity-B-rp4h_v.js} +0 -0
- /package/client/dist/assets/{activity-DvECTYGt.js → activity-C6kJpm9q2.js} +0 -0
- /package/client/dist/assets/{activity-D3Ic-HTS.js → activity-CGx4kb_j.js} +0 -0
- /package/client/dist/assets/{activity-BZZlEG3a.js → activity-CnoX2bH7.js} +0 -0
- /package/client/dist/assets/{activity-DtzRy92x.js → activity-DAyekdlt2.js} +0 -0
- /package/client/dist/assets/{activity-FleOlK0l2.js → activity-DCxtpT7j.js} +0 -0
- /package/client/dist/assets/{activity-DFbvNqhE2.js → activity-JzwRaWPD.js} +0 -0
- /package/client/dist/assets/{addspec-CFxGvmJR2.js → addspec-BXjvkh5q.js} +0 -0
- /package/client/dist/assets/{addspec-NBbcTbLc.js → addspec-C4bwrmpi.js} +0 -0
- /package/client/dist/assets/{addspec-BKrH2Ucz.js → addspec-CArHXUDM.js} +0 -0
- /package/client/dist/assets/{addspec-CR8MB5Fr2.js → addspec-DTKJcXiR.js} +0 -0
- /package/client/dist/assets/{addspec-B_LQMHW3.js → addspec-DbNBbrha2.js} +0 -0
- /package/client/dist/assets/{addspec-DaA-CbTt.js → addspec-htHGZHOe2.js} +0 -0
- /package/client/dist/assets/{addspec-Bw_YQwo62.js → addspec-lr_LP6jk.js} +0 -0
- /package/client/dist/assets/{agents-BHgn--3j.js → agents-6ZOJXWVk2.js} +0 -0
- /package/client/dist/assets/{agents-VsyFhGOS2.js → agents-BZ0XQKjg.js} +0 -0
- /package/client/dist/assets/{agents-HFCqQH0Z.js → agents-BqWklnHR.js} +0 -0
- /package/client/dist/assets/{agents-B_qGaB0F.js → agents-Bz-thHkB2.js} +0 -0
- /package/client/dist/assets/{agents-CP8_ezYG.js → agents-CJclElx6.js} +0 -0
- /package/client/dist/assets/{agents-B9pFSJQI2.js → agents-D_l9L0VA.js} +0 -0
- /package/client/dist/assets/{agents-CV-_xBvX2.js → agents-u_C0jPB5.js} +0 -0
- /package/client/dist/assets/{agentstudio-BEp7Sb46.js → agentstudio-BF19hbXj.js} +0 -0
- /package/client/dist/assets/{agentstudio-Br3WD7Xs.js → agentstudio-BLGvxWBx2.js} +0 -0
- /package/client/dist/assets/{agentstudio-BOjG6tgJ.js → agentstudio-D9UKiWTj2.js} +0 -0
- /package/client/dist/assets/{agentstudio-D2A5peWV2.js → agentstudio-Drs37nIM.js} +0 -0
- /package/client/dist/assets/{agentstudio-CuTt3ZGe2.js → agentstudio-nEnKkcXM.js} +0 -0
- /package/client/dist/assets/{agentstudio-RsxnZtUA.js → agentstudio-pyFcSBKy.js} +0 -0
- /package/client/dist/assets/{agentstudio-RfZavULt2.js → agentstudio-zfTzQh3U.js} +0 -0
- /package/client/dist/assets/{aiedit-DnBzjlVz2.js → aiedit-B0KUbpB6.js} +0 -0
- /package/client/dist/assets/{aiedit-D0Syl-mC.js → aiedit-BoG24nlg2.js} +0 -0
- /package/client/dist/assets/{aiedit-CcugGPbS.js → aiedit-CjlSRQVP.js} +0 -0
- /package/client/dist/assets/{aiedit-DrIjSojo.js → aiedit-DCjA7jLJ.js} +0 -0
- /package/client/dist/assets/{aiedit-CV520D4W2.js → aiedit-DNXxq_Dr.js} +0 -0
- /package/client/dist/assets/{aiedit-26p5A_HY2.js → aiedit-DQ-0_pvE.js} +0 -0
- /package/client/dist/assets/{aiedit-a-Z-g5iC.js → aiedit-olnv3QSt2.js} +0 -0
- /package/client/dist/assets/{analytics-DEe5BMz8.js → analytics-BC7mwR4s.js} +0 -0
- /package/client/dist/assets/{analytics-4HvXb0Vn2.js → analytics-BiNg8edP.js} +0 -0
- /package/client/dist/assets/{analytics-CpSTNfui.js → analytics-C0s_T2GN.js} +0 -0
- /package/client/dist/assets/{analytics-4-eskbtX.js → analytics-CdsAPAwZ2.js} +0 -0
- /package/client/dist/assets/{analytics-Bpe41fnX2.js → analytics-Cr1_q-lC.js} +0 -0
- /package/client/dist/assets/{analytics-DcOITHla2.js → analytics-IEsKZvpW2.js} +0 -0
- /package/client/dist/assets/{analytics-Bd9rHGjV.js → analytics-SRPf84OT.js} +0 -0
- /package/client/dist/assets/{apex-D_X_8J4d.js → apex-BWPQTe0t.js} +0 -0
- /package/client/dist/assets/{atom-one-dark-BMDPFwRZ.js → atom-one-dark-qiGhVQxg.js} +0 -0
- /package/client/dist/assets/{attachments-CgOQ9K-6.js → attachments-D0wXXt9T2.js} +0 -0
- /package/client/dist/assets/{attachments-DlEQu56g2.js → attachments-DenIjuVI.js} +0 -0
- /package/client/dist/assets/{attachments-CA2f3qL3.js → attachments-DhO7LPfy.js} +0 -0
- /package/client/dist/assets/{attachments-D2jwJXQ42.js → attachments-DoH5w0x4.js} +0 -0
- /package/client/dist/assets/{attachments-CHDbhKeH.js → attachments-Q9yNtiEM.js} +0 -0
- /package/client/dist/assets/{attachments-CKAY5aYG2.js → attachments-V_WZAYXx2.js} +0 -0
- /package/client/dist/assets/{attachments-jVdKzAXn.js → attachments-eaeScpjM.js} +0 -0
- /package/client/dist/assets/{auth-DpZq5p1e.js → auth-D_5bQv5W.js} +0 -0
- /package/client/dist/assets/{azcli-PZLnZ3jH.js → azcli-Bc_sGQ0U.js} +0 -0
- /package/client/dist/assets/{bat-KlBOxpO4.js → bat-i0X4ZdIN.js} +0 -0
- /package/client/dist/assets/{bicep-CgG9oF3V.js → bicep-B5-_aFwp.js} +0 -0
- /package/client/dist/assets/{browser-Cl-FwPXs.js → browser-C25DkQiO.js} +0 -0
- /package/client/dist/assets/{browser-JsiohNmW.js → browser-CiJ7-L32.js} +0 -0
- /package/client/dist/assets/{browser-BbJ_q_OT2.js → browser-CvgDySd9.js} +0 -0
- /package/client/dist/assets/{browser-BQFDxrRq.js → browser-CyR1Kp3m2.js} +0 -0
- /package/client/dist/assets/{browser-Do2jf8_N.js → browser-DwZljcRh2.js} +0 -0
- /package/client/dist/assets/{browser-C4VJ5CW12.js → browser-DxP-alBK.js} +0 -0
- /package/client/dist/assets/{browser-kA31eYhu2.js → browser-rRCwi7Y7.js} +0 -0
- /package/client/dist/assets/{cameligo-6R45j6Ph.js → cameligo-DMUM7wLl.js} +0 -0
- /package/client/dist/assets/{chat-BalviUAD.js → chat-2rIB8HhT.js} +0 -0
- /package/client/dist/assets/{chat-Ds8GvCnv.js → chat-BR8oe53x2.js} +0 -0
- /package/client/dist/assets/{chat-D5xEtsf3.js → chat-Bua03tty.js} +0 -0
- /package/client/dist/assets/{chat-SaG-ng1x2.js → chat-CZpAQan1.js} +0 -0
- /package/client/dist/assets/{chat-CJddjN3D2.js → chat-CdY5SGvS.js} +0 -0
- /package/client/dist/assets/{chat-n43nZGvn.js → chat-DZyu3ImY2.js} +0 -0
- /package/client/dist/assets/{chat-BMWD_Rx12.js → chat-D_I7nU5K.js} +0 -0
- /package/client/dist/assets/{clojure-CLAAMO7J.js → clojure-Cm7r79vr.js} +0 -0
- /package/client/dist/assets/{clsx-CNmW0Nip.js → clsx-CjueKrWZ.js} +0 -0
- /package/client/dist/assets/{code-C9U6M5-e2.js → code-76gS0IdL.js} +0 -0
- /package/client/dist/assets/{code-BotxM43N2.js → code-C1VwxlML.js} +0 -0
- /package/client/dist/assets/{code-HDK4P6Rx.js → code-CnMZyJpr.js} +0 -0
- /package/client/dist/assets/{code-DUe1Bouz.js → code-D20ef9Cf2.js} +0 -0
- /package/client/dist/assets/{code-Bit_z2Xd2.js → code-DdOXaWRY.js} +0 -0
- /package/client/dist/assets/{code-F_KjccGf.js → code-Duohuf9l.js} +0 -0
- /package/client/dist/assets/{code-CIPmDEd0.js → code-geHmknB92.js} +0 -0
- /package/client/dist/assets/{coffee-AruSygo-.js → coffee-Ba7i2nA0.js} +0 -0
- /package/client/dist/assets/{commands-BFQZc9AG.js → commands-B9RZO4qS.js} +0 -0
- /package/client/dist/assets/{commands-BMkC5-ki.js → commands-BEwbAjtD2.js} +0 -0
- /package/client/dist/assets/{commands-KBbhsnw8.js → commands-Bbxu8kLU.js} +0 -0
- /package/client/dist/assets/{commands-CzFSoIiq2.js → commands-CDU3qv68.js} +0 -0
- /package/client/dist/assets/{commands-CWX9WmDX2.js → commands-CzezgtQj.js} +0 -0
- /package/client/dist/assets/{commands-BllkJauO.js → commands-DTQBF_q52.js} +0 -0
- /package/client/dist/assets/{commands-cKTaLwwV2.js → commands-hOtKuOXc.js} +0 -0
- /package/client/dist/assets/{cpp-DEE5r4Pw.js → cpp-C7h46wYY.js} +0 -0
- /package/client/dist/assets/{csharp-BVXJUvbK.js → csharp-BKxtCVv1.js} +0 -0
- /package/client/dist/assets/{csp-cXOF0JoV.js → csp-bTuwJoIa.js} +0 -0
- /package/client/dist/assets/{css-C_zQuAoy.js → css-DIMkf-bt.js} +0 -0
- /package/client/dist/assets/{cypher-t95m_Q-O.js → cypher-CVaqCwHa.js} +0 -0
- /package/client/dist/assets/{dart-B4r1Tg-e.js → dart-onAF5SnQ.js} +0 -0
- /package/client/dist/assets/{dockerfile-6mt7zHQw.js → dockerfile-DZFCIeNp.js} +0 -0
- /package/client/dist/assets/{ecl-DEY_Fz_Q.js → ecl-D05T4iGw.js} +0 -0
- /package/client/dist/assets/{elixir-R6-q1c5t.js → elixir-6RTg0lbw.js} +0 -0
- /package/client/dist/assets/{explore-CAc8Qzu32.js → explore-BG99VGpL.js} +0 -0
- /package/client/dist/assets/{explore-BO_OinBD.js → explore-C0TjprJW2.js} +0 -0
- /package/client/dist/assets/{explore-Bhy7WWXv.js → explore-C2dgEo7q.js} +0 -0
- /package/client/dist/assets/{explore-ELbrSZyQ2.js → explore-C8NDHbob.js} +0 -0
- /package/client/dist/assets/{explore-DW_YTkQh.js → explore-CWWgzQGR.js} +0 -0
- /package/client/dist/assets/{explore-DCZL9gRN2.js → explore-CcQXpdtS.js} +0 -0
- /package/client/dist/assets/{explore-BEpIs343.js → explore-DsXAgnmJ2.js} +0 -0
- /package/client/dist/assets/{flow9-CNQvHBOt.js → flow9-C5_-GSwl.js} +0 -0
- /package/client/dist/assets/{format-command-Db1viey1.js → format-command-Dfa1o2d-.js} +0 -0
- /package/client/dist/assets/{fsharp-vPZkFXwv.js → fsharp-C8Ef5oNN.js} +0 -0
- /package/client/dist/assets/{go-KUzBMYJ_.js → go-C-y9NEjX.js} +0 -0
- /package/client/dist/assets/{graphql-C3W0rCsD.js → graphql-fmXr3nnJ.js} +0 -0
- /package/client/dist/assets/{hcl-BOOMFSNX.js → hcl-CpzslTdj.js} +0 -0
- /package/client/dist/assets/{ini-CFat1WJr.js → ini-sBoK_t0W.js} +0 -0
- /package/client/dist/assets/{integrations-CG2dp3Kd.js → integrations-CH0zy1Mw2.js} +0 -0
- /package/client/dist/assets/{integrations-CUNe3t9l2.js → integrations-CIAjhd7L.js} +0 -0
- /package/client/dist/assets/{integrations-CWjh5VRk.js → integrations-CZdwOe8A.js} +0 -0
- /package/client/dist/assets/{integrations-RJfzXkPx2.js → integrations-Ct7omMld.js} +0 -0
- /package/client/dist/assets/{integrations-CAjq5tdW2.js → integrations-D6MSxy3-.js} +0 -0
- /package/client/dist/assets/{integrations-JOHSCvB3.js → integrations-DbZa-Zyc.js} +0 -0
- /package/client/dist/assets/{integrations-CP_aiV_8.js → integrations-b8pH-vfl2.js} +0 -0
- /package/client/dist/assets/{java-Dee-CNAM.js → java-BEtHBSE6.js} +0 -0
- /package/client/dist/assets/{jira-CQ7mrZde.js → jira-BySfUuQZ.js} +0 -0
- /package/client/dist/assets/{jira-DIRkZk9U.js → jira-Byw2C0F8.js} +0 -0
- /package/client/dist/assets/{jira-C5UjxHE4.js → jira-CNeYi06w2.js} +0 -0
- /package/client/dist/assets/{jira-ZdKb-50F2.js → jira-D11gPhxz.js} +0 -0
- /package/client/dist/assets/{jira-DTYu3hJi2.js → jira-D38Gj7AT.js} +0 -0
- /package/client/dist/assets/{jira-B5wszJ1-2.js → jira-gAvOyije.js} +0 -0
- /package/client/dist/assets/{jira-DtZpokjJ.js → jira-pRaL7JQo2.js} +0 -0
- /package/client/dist/assets/{julia-CGNlLYuU.js → julia-Bri6UV-V.js} +0 -0
- /package/client/dist/assets/{kotlin-CY7lhknJ.js → kotlin-BOotOW0E.js} +0 -0
- /package/client/dist/assets/{less-D0KN7hfJ.js → less-B9JPFI3C.js} +0 -0
- /package/client/dist/assets/{lexon-CuRJufPs.js → lexon-CfSJPG6W.js} +0 -0
- /package/client/dist/assets/{loops-DKzYFcq6.js → loops-CPpgMapU.js} +0 -0
- /package/client/dist/assets/{loops-Du-bNVpc2.js → loops-CWWbKuVL.js} +0 -0
- /package/client/dist/assets/{loops-DDs4KPu_.js → loops-Crc9It8o2.js} +0 -0
- /package/client/dist/assets/{loops-Bi4ywYGn.js → loops-DH2hZcbK2.js} +0 -0
- /package/client/dist/assets/{loops-DvGbSfxw2.js → loops-DS5TmvIU2.js} +0 -0
- /package/client/dist/assets/{loops-D3wdUkZV.js → loops-P2f0cN8-.js} +0 -0
- /package/client/dist/assets/{loops-BjK8lmoZ2.js → loops-fJV-9hH7.js} +0 -0
- /package/client/dist/assets/{lua-DHvH62Zf.js → lua-CsQS60Ue.js} +0 -0
- /package/client/dist/assets/{m3-tlthQ8Fo.js → m3-D-oSqn_W.js} +0 -0
- /package/client/dist/assets/{markdown-Dbx1LgUZ.js → markdown-Cimd5fb3.js} +0 -0
- /package/client/dist/assets/{mcp-DfmzoT5t.js → mcp-Czd_iyp02.js} +0 -0
- /package/client/dist/assets/{mcp-BG-OCJca2.js → mcp-D2pc5GGx.js} +0 -0
- /package/client/dist/assets/{mcp-CrWdq5db.js → mcp-D4ZjtIx32.js} +0 -0
- /package/client/dist/assets/{mcp-CbJ04oFS2.js → mcp-DIfBUv2D2.js} +0 -0
- /package/client/dist/assets/{mcp-Dd844F5_.js → mcp-DsTwmjST.js} +0 -0
- /package/client/dist/assets/{mcp-zSJ2TsJj.js → mcp-SMkn8boG.js} +0 -0
- /package/client/dist/assets/{mcp-DyULurYS2.js → mcp-fSfiVYAc.js} +0 -0
- /package/client/dist/assets/{mips-D_O3IUz_.js → mips-CIPQ_RoX.js} +0 -0
- /package/client/dist/assets/{msdax-C_ZmCnRt.js → msdax-DauUninz.js} +0 -0
- /package/client/dist/assets/{mysql-C-dCEYSX.js → mysql-SOo6toE5.js} +0 -0
- /package/client/dist/assets/{nav-DUuw9VIU2.js → nav-BRJBxaGt2.js} +0 -0
- /package/client/dist/assets/{nav-D0Erv9ZJ2.js → nav-CAGKv3_F.js} +0 -0
- /package/client/dist/assets/{nav-BY_4EWRv.js → nav-CNskRJKQ2.js} +0 -0
- /package/client/dist/assets/{nav-CVXtv0wX2.js → nav-DY93irBL.js} +0 -0
- /package/client/dist/assets/{nav-B2_ToNqS.js → nav-DhjvYgqt.js} +0 -0
- /package/client/dist/assets/{nav-S4HM94vW.js → nav-Gb-r4wop.js} +0 -0
- /package/client/dist/assets/{nav-BAMkVEId.js → nav-TvumAFD22.js} +0 -0
- /package/client/dist/assets/{objective-c-DZY9Aqxd.js → objective-c-FvmIjYaQ.js} +0 -0
- /package/client/dist/assets/{pascal-BVHLXoor.js → pascal-DrH0SRf2.js} +0 -0
- /package/client/dist/assets/{pascaligo-XdG_6u3k.js → pascaligo-D-ptJ9y-.js} +0 -0
- /package/client/dist/assets/{perl-b9QV0BcD.js → perl-oz_6vUea.js} +0 -0
- /package/client/dist/assets/{pgsql-Du5FDOgT.js → pgsql-DTj74zXo.js} +0 -0
- /package/client/dist/assets/{php-WJD0z2Z_.js → php-nr791fC2.js} +0 -0
- /package/client/dist/assets/{pla-CbciTf2w.js → pla-CopQ2nXW.js} +0 -0
- /package/client/dist/assets/{postiats-C1QxmvVq.js → postiats-43DmfD33.js} +0 -0
- /package/client/dist/assets/{powerquery-BEYDhPLZ.js → powerquery-D3hlyOfw.js} +0 -0
- /package/client/dist/assets/{powershell-CfaYw4XL.js → powershell-DmHpPYUd.js} +0 -0
- /package/client/dist/assets/{protobuf-pwZEDOYa.js → protobuf-C531GsRP.js} +0 -0
- /package/client/dist/assets/{pug-5ftqSPVe.js → pug-Z5eAx3Zn.js} +0 -0
- /package/client/dist/assets/{qsharp-uI6qZMq4.js → qsharp-DkqhCAOL.js} +0 -0
- /package/client/dist/assets/{r-BK54P1EG.js → r-BwWrilGY.js} +0 -0
- /package/client/dist/assets/{redis-DI0yd7kN.js → redis-ClamHrr6.js} +0 -0
- /package/client/dist/assets/{redshift-Dov26eyI.js → redshift-DT7zqm-g.js} +0 -0
- /package/client/dist/assets/{restructuredtext-QqJ_1dC-.js → restructuredtext-BYgofb2h.js} +0 -0
- /package/client/dist/assets/{ruby-5WjveeVb.js → ruby-DezsRK8O.js} +0 -0
- /package/client/dist/assets/{rust-BzVSfqFH.js → rust-DdL9SqIa.js} +0 -0
- /package/client/dist/assets/{sb-DMIUfT-3.js → sb-CcwsVR0C.js} +0 -0
- /package/client/dist/assets/{scala-CSKA7lqt.js → scala-DHpiXF5c.js} +0 -0
- /package/client/dist/assets/{scheme-CojOP2Qc.js → scheme-BeGwcela.js} +0 -0
- /package/client/dist/assets/{scss-DoBZGJG6.js → scss-gp-XZpBa.js} +0 -0
- /package/client/dist/assets/{setup-JeBwoXoM.js → setup-CGZjy2IF2.js} +0 -0
- /package/client/dist/assets/{setup-1vN48B-m2.js → setup-CXa0Sx16.js} +0 -0
- /package/client/dist/assets/{setup-BmJ0Kx16.js → setup-D2ktKKMF2.js} +0 -0
- /package/client/dist/assets/{setup-T_ApeQDV2.js → setup-DG2H7ha5.js} +0 -0
- /package/client/dist/assets/{setup-DQWsu2TR.js → setup-DK5bHDUq2.js} +0 -0
- /package/client/dist/assets/{setup-q0wRHUp1.js → setup-DrWlIQTZ.js} +0 -0
- /package/client/dist/assets/{setup-mXnzww4f.js → setup-rzHUVgAu.js} +0 -0
- /package/client/dist/assets/{shell-YOaE4udl.js → shell-CC2rA5mh.js} +0 -0
- /package/client/dist/assets/{solidity-l3jSyVLu.js → solidity-BEEn4gHE.js} +0 -0
- /package/client/dist/assets/{sophia-BhSGTaQJ.js → sophia-CRfGWb83.js} +0 -0
- /package/client/dist/assets/{sparql-qhk6QD9w.js → sparql-D_Lu-MrJ.js} +0 -0
- /package/client/dist/assets/{specs-BGRKhM8t.js → specs-BcyxaCwf2.js} +0 -0
- /package/client/dist/assets/{specs-GkiL-snY.js → specs-C1q9geAi.js} +0 -0
- /package/client/dist/assets/{specs-DbtIzV8a.js → specs-CLZKysq-2.js} +0 -0
- /package/client/dist/assets/{specs-Ce5y2iFc2.js → specs-DZMS9o54.js} +0 -0
- /package/client/dist/assets/{specs-CT8exGOy2.js → specs-Dm6zUI-R.js} +0 -0
- /package/client/dist/assets/{specs-C6J2zrLM.js → specs-V3TvhKLX.js} +0 -0
- /package/client/dist/assets/{specs-DZDoZsDq.js → specs-dV3Mq5Mu2.js} +0 -0
- /package/client/dist/assets/{sql-DoO3y21-.js → sql-NEE52Syq.js} +0 -0
- /package/client/dist/assets/{st-ChZAY8oG.js → st-DbInun42.js} +0 -0
- /package/client/dist/assets/{swift-D290Tr7_.js → swift-Bxkupp3x.js} +0 -0
- /package/client/dist/assets/{systemverilog-DsxzgJ-o.js → systemverilog-Bz4Y3fRF.js} +0 -0
- /package/client/dist/assets/{tcl-BKDUHAAR.js → tcl-DISqw1ZD.js} +0 -0
- /package/client/dist/assets/{terminal-BTpE7iki.js → terminal-BZiIu3rf.js} +0 -0
- /package/client/dist/assets/{terminal-DEyt0prF.js → terminal-C2NAd7BW2.js} +0 -0
- /package/client/dist/assets/{terminal-a6Uq8B0p.js → terminal-IahE4LW92.js} +0 -0
- /package/client/dist/assets/{terminal-DDk_bTw0.js → terminal-QpXZU2Bn2.js} +0 -0
- /package/client/dist/assets/{terminal-BNSg2lR7.js → terminal-ScjyXNxQ.js} +0 -0
- /package/client/dist/assets/{terminal-Cvabyzm42.js → terminal-d7GadXbN.js} +0 -0
- /package/client/dist/assets/{terminal-D0z12_sJ2.js → terminal-tITa81iz.js} +0 -0
- /package/client/dist/assets/{twig-UpZQaM8G.js → twig-De2hgUGE.js} +0 -0
- /package/client/dist/assets/{typespec-DzaKvN8i.js → typespec-B8J7ngcE.js} +0 -0
- /package/client/dist/assets/{vb-CZpbb7tk.js → vb-DV3o63ZY.js} +0 -0
- /package/client/dist/assets/{wgsl-CNt3OIvl.js → wgsl-DpFanUEy.js} +0 -0
|
@@ -6,7 +6,8 @@
|
|
|
6
6
|
// classification → retry / dead-letter / auth-pause),
|
|
7
7
|
// - the write-back hooks: onRailLaunch (todo→In Progress), onJobOutcome
|
|
8
8
|
// (Done / revert + completion comment), onRailReview (ask-first PR delivery
|
|
9
|
-
// settle → on_review) and
|
|
9
|
+
// settle → on_review) and the merged/completed/refined/discarded decision
|
|
10
|
+
// outcomes (each with truthful, idempotent Jira semantics),
|
|
10
11
|
// and stays completely inert until the project configures a Jira connection.
|
|
11
12
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
13
|
exports.JiraSyncManager = void 0;
|
|
@@ -15,6 +16,8 @@ exports.formatJqlDate = formatJqlDate;
|
|
|
15
16
|
exports.buildCompletionComment = buildCompletionComment;
|
|
16
17
|
exports.buildRailReviewComment = buildRailReviewComment;
|
|
17
18
|
exports.buildPrMergedComment = buildPrMergedComment;
|
|
19
|
+
exports.buildRailCompletedComment = buildRailCompletedComment;
|
|
20
|
+
exports.buildRailRefinedComment = buildRailRefinedComment;
|
|
18
21
|
const node_crypto_1 = require("node:crypto");
|
|
19
22
|
const ticket_store_1 = require("../ticket-store");
|
|
20
23
|
const jira_client_1 = require("./jira-client");
|
|
@@ -49,6 +52,8 @@ class JiraSyncManager {
|
|
|
49
52
|
notifyLocalWriteCb;
|
|
50
53
|
pollTimer = null;
|
|
51
54
|
drainTimer = null;
|
|
55
|
+
/** Exactly one outbox drain loop may claim work for this project at a time. */
|
|
56
|
+
drainPromise = null;
|
|
52
57
|
/** When set, the outbox is paused pending re-auth (401). */
|
|
53
58
|
authPaused = false;
|
|
54
59
|
constructor(opts) {
|
|
@@ -722,12 +727,14 @@ class JiraSyncManager {
|
|
|
722
727
|
* known) per Jira-linked ticket. Outbox-only: the local on_review→done cache
|
|
723
728
|
* write is the caller's job (the decision endpoint mutates the ticket store
|
|
724
729
|
* itself). NOT onJobOutcome — its completion comment assumes job cost/duration
|
|
725
|
-
* that a merge poll does not have. Never throws.
|
|
730
|
+
* that a merge poll does not have. Never throws. Returns false only when the
|
|
731
|
+
* durable Jira-outbox handoff itself failed; callers that do not need the
|
|
732
|
+
* acknowledgement may continue to ignore the return value.
|
|
726
733
|
*/
|
|
727
734
|
onRailMerged(ticketIds, refId, prUrl) {
|
|
728
735
|
try {
|
|
729
736
|
if (!this.isActive())
|
|
730
|
-
return;
|
|
737
|
+
return true;
|
|
731
738
|
const text = buildPrMergedComment(prUrl);
|
|
732
739
|
const ops = [];
|
|
733
740
|
for (const localId of ticketIds) {
|
|
@@ -749,13 +756,138 @@ class JiraSyncManager {
|
|
|
749
756
|
});
|
|
750
757
|
}
|
|
751
758
|
if (ops.length === 0)
|
|
752
|
-
return;
|
|
759
|
+
return true;
|
|
753
760
|
(0, jira_db_1.enqueueMany)(this.db, ops);
|
|
754
761
|
this.broadcastOutboxState();
|
|
755
762
|
void this.drainOnce().catch(() => undefined);
|
|
763
|
+
return true;
|
|
756
764
|
}
|
|
757
765
|
catch (err) {
|
|
758
766
|
console.error('[jira-sync] onRailMerged failed:', err);
|
|
767
|
+
return false;
|
|
768
|
+
}
|
|
769
|
+
}
|
|
770
|
+
/**
|
|
771
|
+
* Called when a fresh no-change result is explicitly accepted as complete.
|
|
772
|
+
* This is not a merge: enqueue a truthful no-PR comment plus Done transition,
|
|
773
|
+
* with action-specific keys so crash replay cannot duplicate either effect.
|
|
774
|
+
*/
|
|
775
|
+
onRailCompleted(ticketIds, refId) {
|
|
776
|
+
try {
|
|
777
|
+
if (!this.isActive())
|
|
778
|
+
return true;
|
|
779
|
+
const text = buildRailCompletedComment();
|
|
780
|
+
const ops = [];
|
|
781
|
+
for (const localId of ticketIds) {
|
|
782
|
+
const link = (0, jira_db_1.getLinkByLocalId)(this.db, localId);
|
|
783
|
+
if (!link || link.tombstoned)
|
|
784
|
+
continue;
|
|
785
|
+
ops.push({
|
|
786
|
+
jiraIssueId: link.jiraIssueId,
|
|
787
|
+
opType: 'comment',
|
|
788
|
+
idempotencyKey: `${refId}:${localId}:comment:completed`,
|
|
789
|
+
payload: {
|
|
790
|
+
jiraIssueId: link.jiraIssueId,
|
|
791
|
+
text,
|
|
792
|
+
marker: (0, jira_adf_1.railCompletedCommentMarker)(refId, localId),
|
|
793
|
+
},
|
|
794
|
+
});
|
|
795
|
+
ops.push({
|
|
796
|
+
jiraIssueId: link.jiraIssueId,
|
|
797
|
+
opType: 'transition',
|
|
798
|
+
idempotencyKey: `${refId}:${localId}:transition:completed`,
|
|
799
|
+
payload: { localId, jiraIssueId: link.jiraIssueId, logicalState: 'done' },
|
|
800
|
+
});
|
|
801
|
+
}
|
|
802
|
+
if (ops.length === 0)
|
|
803
|
+
return true;
|
|
804
|
+
(0, jira_db_1.enqueueMany)(this.db, ops);
|
|
805
|
+
this.broadcastOutboxState();
|
|
806
|
+
void this.drainOnce().catch(() => undefined);
|
|
807
|
+
return true;
|
|
808
|
+
}
|
|
809
|
+
catch (err) {
|
|
810
|
+
console.error('[jira-sync] onRailCompleted failed:', err);
|
|
811
|
+
return false;
|
|
812
|
+
}
|
|
813
|
+
}
|
|
814
|
+
/**
|
|
815
|
+
* Called when a fresh no-change result is returned for refinement. Refine is
|
|
816
|
+
* deliberately distinct from discard: it always goes to logical todo and
|
|
817
|
+
* never consults the configured discard/cancelled status.
|
|
818
|
+
*/
|
|
819
|
+
onRailRefined(ticketIds, refId) {
|
|
820
|
+
try {
|
|
821
|
+
if (!this.isActive())
|
|
822
|
+
return true;
|
|
823
|
+
const text = buildRailRefinedComment();
|
|
824
|
+
const ops = [];
|
|
825
|
+
for (const localId of ticketIds) {
|
|
826
|
+
const link = (0, jira_db_1.getLinkByLocalId)(this.db, localId);
|
|
827
|
+
if (!link || link.tombstoned)
|
|
828
|
+
continue;
|
|
829
|
+
ops.push({
|
|
830
|
+
jiraIssueId: link.jiraIssueId,
|
|
831
|
+
opType: 'comment',
|
|
832
|
+
idempotencyKey: `${refId}:${localId}:comment:refine`,
|
|
833
|
+
payload: {
|
|
834
|
+
jiraIssueId: link.jiraIssueId,
|
|
835
|
+
text,
|
|
836
|
+
marker: (0, jira_adf_1.railRefinedCommentMarker)(refId, localId),
|
|
837
|
+
},
|
|
838
|
+
});
|
|
839
|
+
ops.push({
|
|
840
|
+
jiraIssueId: link.jiraIssueId,
|
|
841
|
+
opType: 'transition',
|
|
842
|
+
idempotencyKey: `${refId}:${localId}:transition:refine`,
|
|
843
|
+
payload: { localId, jiraIssueId: link.jiraIssueId, logicalState: 'todo' },
|
|
844
|
+
});
|
|
845
|
+
}
|
|
846
|
+
if (ops.length === 0)
|
|
847
|
+
return true;
|
|
848
|
+
(0, jira_db_1.enqueueMany)(this.db, ops);
|
|
849
|
+
this.broadcastOutboxState();
|
|
850
|
+
void this.drainOnce().catch(() => undefined);
|
|
851
|
+
return true;
|
|
852
|
+
}
|
|
853
|
+
catch (err) {
|
|
854
|
+
console.error('[jira-sync] onRailRefined failed:', err);
|
|
855
|
+
return false;
|
|
856
|
+
}
|
|
857
|
+
}
|
|
858
|
+
/**
|
|
859
|
+
* Migration-only recovery for an ambiguous historical fresh discard. The
|
|
860
|
+
* only safe fact is that its local tickets must leave on_review for todo.
|
|
861
|
+
* Enqueue that transition without a causal comment and without consulting
|
|
862
|
+
* discardStatus, because v49 did not retain whether the user chose Refine or
|
|
863
|
+
* discarded a real delivery.
|
|
864
|
+
*/
|
|
865
|
+
onRailBacklog(ticketIds, refId) {
|
|
866
|
+
try {
|
|
867
|
+
if (!this.isActive())
|
|
868
|
+
return true;
|
|
869
|
+
const ops = [];
|
|
870
|
+
for (const localId of ticketIds) {
|
|
871
|
+
const link = (0, jira_db_1.getLinkByLocalId)(this.db, localId);
|
|
872
|
+
if (!link || link.tombstoned)
|
|
873
|
+
continue;
|
|
874
|
+
ops.push({
|
|
875
|
+
jiraIssueId: link.jiraIssueId,
|
|
876
|
+
opType: 'transition',
|
|
877
|
+
idempotencyKey: `${refId}:${localId}:transition:backlog`,
|
|
878
|
+
payload: { localId, jiraIssueId: link.jiraIssueId, logicalState: 'todo' },
|
|
879
|
+
});
|
|
880
|
+
}
|
|
881
|
+
if (ops.length === 0)
|
|
882
|
+
return true;
|
|
883
|
+
(0, jira_db_1.enqueueMany)(this.db, ops);
|
|
884
|
+
this.broadcastOutboxState();
|
|
885
|
+
void this.drainOnce().catch(() => undefined);
|
|
886
|
+
return true;
|
|
887
|
+
}
|
|
888
|
+
catch (err) {
|
|
889
|
+
console.error('[jira-sync] onRailBacklog failed:', err);
|
|
890
|
+
return false;
|
|
759
891
|
}
|
|
760
892
|
}
|
|
761
893
|
/**
|
|
@@ -764,12 +896,13 @@ class JiraSyncManager {
|
|
|
764
896
|
* (mirroring discardSpec's transition payload), else reverts it to the backlog
|
|
765
897
|
* via a plain `todo` transition — a missing configuration is never an error.
|
|
766
898
|
* Outbox-only like onRailMerged: local cache writes belong to the caller.
|
|
767
|
-
* Never throws.
|
|
899
|
+
* Never throws. Returns false only when the durable Jira-outbox handoff
|
|
900
|
+
* failed; existing fire-and-forget callers may ignore the acknowledgement.
|
|
768
901
|
*/
|
|
769
902
|
onRailDiscard(ticketIds, refId) {
|
|
770
903
|
try {
|
|
771
904
|
if (!this.isActive())
|
|
772
|
-
return;
|
|
905
|
+
return true;
|
|
773
906
|
const conn = (0, jira_db_1.getConnection)(this.db, this.projectId);
|
|
774
907
|
const target = conn?.discardStatus ?? null;
|
|
775
908
|
const ops = [];
|
|
@@ -789,17 +922,30 @@ class JiraSyncManager {
|
|
|
789
922
|
});
|
|
790
923
|
}
|
|
791
924
|
if (ops.length === 0)
|
|
792
|
-
return;
|
|
925
|
+
return true;
|
|
793
926
|
(0, jira_db_1.enqueueMany)(this.db, ops);
|
|
794
927
|
this.broadcastOutboxState();
|
|
795
928
|
void this.drainOnce().catch(() => undefined);
|
|
929
|
+
return true;
|
|
796
930
|
}
|
|
797
931
|
catch (err) {
|
|
798
932
|
console.error('[jira-sync] onRailDiscard failed:', err);
|
|
933
|
+
return false;
|
|
799
934
|
}
|
|
800
935
|
}
|
|
801
936
|
// ─── Outbox drain ──────────────────────────────────────────────────────────
|
|
802
|
-
|
|
937
|
+
drainOnce() {
|
|
938
|
+
if (this.drainPromise)
|
|
939
|
+
return this.drainPromise;
|
|
940
|
+
const running = this.drainUntilBlocked();
|
|
941
|
+
this.drainPromise = running;
|
|
942
|
+
void running.finally(() => {
|
|
943
|
+
if (this.drainPromise === running)
|
|
944
|
+
this.drainPromise = null;
|
|
945
|
+
}).catch(() => undefined);
|
|
946
|
+
return running;
|
|
947
|
+
}
|
|
948
|
+
async drainUntilBlocked() {
|
|
803
949
|
if (this.authPaused)
|
|
804
950
|
return;
|
|
805
951
|
const conn = (0, jira_db_1.getConnection)(this.db, this.projectId);
|
|
@@ -808,11 +954,16 @@ class JiraSyncManager {
|
|
|
808
954
|
const client = this.buildClient();
|
|
809
955
|
if (!client)
|
|
810
956
|
return;
|
|
811
|
-
|
|
812
|
-
|
|
813
|
-
|
|
814
|
-
|
|
815
|
-
|
|
957
|
+
let changed = false;
|
|
958
|
+
while (!this.authPaused) {
|
|
959
|
+
const batch = (0, jira_db_1.claimDrainable)(this.db, MAX_DRAIN_BATCH);
|
|
960
|
+
if (batch.length === 0)
|
|
961
|
+
break;
|
|
962
|
+
changed = true;
|
|
963
|
+
await Promise.all(batch.map((op) => this.executeOp(client, conn, op)));
|
|
964
|
+
}
|
|
965
|
+
if (changed)
|
|
966
|
+
this.broadcastOutboxState();
|
|
816
967
|
}
|
|
817
968
|
async executeOp(client, conn, op) {
|
|
818
969
|
try {
|
|
@@ -1209,6 +1360,24 @@ function buildPrMergedComment(prUrl) {
|
|
|
1209
1360
|
parts.push(`PR: ${prUrl}`);
|
|
1210
1361
|
return parts.join('\n');
|
|
1211
1362
|
}
|
|
1363
|
+
/** Comment posted when the user accepts a fresh no-change result as complete. */
|
|
1364
|
+
function buildRailCompletedComment() {
|
|
1365
|
+
return [
|
|
1366
|
+
'Specrails delivery accepted.',
|
|
1367
|
+
'Result: no code changes were required.',
|
|
1368
|
+
'No pull request was created.',
|
|
1369
|
+
'Jira status: moving to Done.',
|
|
1370
|
+
].join('\n');
|
|
1371
|
+
}
|
|
1372
|
+
/** Comment posted when the user returns a fresh no-change result to refinement. */
|
|
1373
|
+
function buildRailRefinedComment() {
|
|
1374
|
+
return [
|
|
1375
|
+
'Specrails delivery returned for refinement.',
|
|
1376
|
+
'Result: no code changes were accepted as complete.',
|
|
1377
|
+
'No pull request was created.',
|
|
1378
|
+
'Jira status: returning to the backlog.',
|
|
1379
|
+
].join('\n');
|
|
1380
|
+
}
|
|
1212
1381
|
function formatDuration(ms) {
|
|
1213
1382
|
const s = Math.round(ms / 1000);
|
|
1214
1383
|
if (s < 60)
|
|
@@ -0,0 +1,140 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.listUnifiedJobs = listUnifiedJobs;
|
|
4
|
+
exports.getQueuedJobForListing = getQueuedJobForListing;
|
|
5
|
+
const QUEUED_SOURCE = `
|
|
6
|
+
WITH queued_source AS (
|
|
7
|
+
SELECT
|
|
8
|
+
q.id, q.command, q.queue_position, q.priority,
|
|
9
|
+
q.depends_on_job_id, q.pipeline_id, q.enqueued_at
|
|
10
|
+
FROM queued_jobs q
|
|
11
|
+
UNION ALL
|
|
12
|
+
SELECT
|
|
13
|
+
j.id, j.command, j.queue_position, j.priority,
|
|
14
|
+
j.depends_on_job_id, j.pipeline_id, j.started_at AS enqueued_at
|
|
15
|
+
FROM jobs j
|
|
16
|
+
WHERE j.status = 'queued'
|
|
17
|
+
AND NOT EXISTS (SELECT 1 FROM queued_jobs q WHERE q.id = j.id)
|
|
18
|
+
)
|
|
19
|
+
`;
|
|
20
|
+
function queuedConditions(opts) {
|
|
21
|
+
const conditions = [];
|
|
22
|
+
const params = [];
|
|
23
|
+
if (opts.from) {
|
|
24
|
+
conditions.push('datetime(enqueued_at) >= datetime(?)');
|
|
25
|
+
params.push(opts.from);
|
|
26
|
+
}
|
|
27
|
+
if (opts.to) {
|
|
28
|
+
conditions.push('datetime(enqueued_at) <= datetime(?)');
|
|
29
|
+
params.push(opts.to);
|
|
30
|
+
}
|
|
31
|
+
return {
|
|
32
|
+
sql: conditions.length > 0 ? `WHERE ${conditions.join(' AND ')}` : '',
|
|
33
|
+
params,
|
|
34
|
+
};
|
|
35
|
+
}
|
|
36
|
+
function historyConditions(opts) {
|
|
37
|
+
const conditions = ["jobs.status <> 'queued'"];
|
|
38
|
+
const params = [];
|
|
39
|
+
if (opts.status) {
|
|
40
|
+
conditions.push('jobs.status = ?');
|
|
41
|
+
params.push(opts.status);
|
|
42
|
+
}
|
|
43
|
+
if (opts.from) {
|
|
44
|
+
conditions.push('jobs.started_at >= ?');
|
|
45
|
+
params.push(opts.from);
|
|
46
|
+
}
|
|
47
|
+
if (opts.to) {
|
|
48
|
+
conditions.push('jobs.started_at <= ?');
|
|
49
|
+
params.push(opts.to);
|
|
50
|
+
}
|
|
51
|
+
return { sql: `WHERE ${conditions.join(' AND ')}`, params };
|
|
52
|
+
}
|
|
53
|
+
function toQueuedJobRow(row) {
|
|
54
|
+
return {
|
|
55
|
+
id: row.id,
|
|
56
|
+
command: row.command,
|
|
57
|
+
started_at: null,
|
|
58
|
+
enqueued_at: row.enqueued_at,
|
|
59
|
+
finished_at: null,
|
|
60
|
+
status: 'queued',
|
|
61
|
+
exit_code: null,
|
|
62
|
+
queue_position: row.queue_position,
|
|
63
|
+
priority: row.priority,
|
|
64
|
+
tokens_in: null,
|
|
65
|
+
tokens_out: null,
|
|
66
|
+
tokens_cache_read: null,
|
|
67
|
+
tokens_cache_create: null,
|
|
68
|
+
total_cost_usd: null,
|
|
69
|
+
total_cost_usd_estimated: null,
|
|
70
|
+
num_turns: null,
|
|
71
|
+
model: null,
|
|
72
|
+
duration_ms: null,
|
|
73
|
+
duration_api_ms: null,
|
|
74
|
+
session_id: null,
|
|
75
|
+
depends_on_job_id: row.depends_on_job_id,
|
|
76
|
+
pipeline_id: row.pipeline_id,
|
|
77
|
+
skip_reason: null,
|
|
78
|
+
profile_name: null,
|
|
79
|
+
interactive: 0,
|
|
80
|
+
provider: null,
|
|
81
|
+
owner: 'queue',
|
|
82
|
+
};
|
|
83
|
+
}
|
|
84
|
+
/**
|
|
85
|
+
* Page queued admissions and execution history as one stable sequence. Queued
|
|
86
|
+
* work remains first (in durable queue order), followed by history newest-first.
|
|
87
|
+
* Both total and offset apply to that combined sequence; no in-memory prepend
|
|
88
|
+
* can amplify the requested limit.
|
|
89
|
+
*/
|
|
90
|
+
function listUnifiedJobs(db, opts) {
|
|
91
|
+
const limit = Math.max(1, Math.min(opts.limit, 200));
|
|
92
|
+
const offset = Math.max(0, opts.offset);
|
|
93
|
+
const includeQueued = !opts.status || opts.status === 'queued';
|
|
94
|
+
const includeHistory = opts.status !== 'queued';
|
|
95
|
+
let queuedTotal = 0;
|
|
96
|
+
let queuedRows = [];
|
|
97
|
+
if (includeQueued) {
|
|
98
|
+
const queued = queuedConditions(opts);
|
|
99
|
+
queuedTotal = db.prepare(`${QUEUED_SOURCE} SELECT COUNT(*) AS count FROM queued_source ${queued.sql}`).get(...queued.params).count;
|
|
100
|
+
const queuedOffset = Math.min(offset, queuedTotal);
|
|
101
|
+
const queuedLimit = Math.min(limit, Math.max(0, queuedTotal - offset));
|
|
102
|
+
if (queuedLimit > 0) {
|
|
103
|
+
const rows = db.prepare(`
|
|
104
|
+
${QUEUED_SOURCE}
|
|
105
|
+
SELECT * FROM queued_source
|
|
106
|
+
${queued.sql}
|
|
107
|
+
ORDER BY queue_position ASC, id ASC
|
|
108
|
+
LIMIT ? OFFSET ?
|
|
109
|
+
`).all(...queued.params, queuedLimit, queuedOffset);
|
|
110
|
+
queuedRows = rows.map(toQueuedJobRow);
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
let historyTotal = 0;
|
|
114
|
+
let historyRows = [];
|
|
115
|
+
if (includeHistory) {
|
|
116
|
+
const history = historyConditions(opts);
|
|
117
|
+
historyTotal = db.prepare(`SELECT COUNT(*) AS count FROM jobs ${history.sql}`).get(...history.params).count;
|
|
118
|
+
const remaining = limit - queuedRows.length;
|
|
119
|
+
const historyOffset = Math.max(0, offset - queuedTotal);
|
|
120
|
+
if (remaining > 0 && historyOffset < historyTotal) {
|
|
121
|
+
historyRows = db.prepare(`
|
|
122
|
+
SELECT jobs.*, jp.profile_name AS profile_name, NULL AS enqueued_at
|
|
123
|
+
FROM jobs
|
|
124
|
+
LEFT JOIN job_profiles jp ON jp.job_id = jobs.id
|
|
125
|
+
${history.sql}
|
|
126
|
+
ORDER BY jobs.started_at DESC, jobs.id ASC
|
|
127
|
+
LIMIT ? OFFSET ?
|
|
128
|
+
`).all(...history.params, remaining, historyOffset);
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
return { jobs: [...queuedRows, ...historyRows], total: queuedTotal + historyTotal };
|
|
132
|
+
}
|
|
133
|
+
/** Durable queued detail lookup used before execution creates a jobs row. */
|
|
134
|
+
function getQueuedJobForListing(db, jobId) {
|
|
135
|
+
const row = db.prepare(`
|
|
136
|
+
${QUEUED_SOURCE}
|
|
137
|
+
SELECT * FROM queued_source WHERE id = ?
|
|
138
|
+
`).get(jobId);
|
|
139
|
+
return row ? toQueuedJobRow(row) : undefined;
|
|
140
|
+
}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.JobSpawnIdempotencyReplayError = exports.JobSpawnIdempotencyConflictError = exports.JOB_SPAWN_IDEMPOTENCY_TTL_MS = void 0;
|
|
4
|
+
exports.fingerprintJobSpawn = fingerprintJobSpawn;
|
|
5
|
+
exports.findIdempotentJob = findIdempotentJob;
|
|
6
|
+
exports.rememberIdempotentJob = rememberIdempotentJob;
|
|
7
|
+
exports.claimIdempotentJob = claimIdempotentJob;
|
|
8
|
+
const crypto_1 = require("crypto");
|
|
9
|
+
exports.JOB_SPAWN_IDEMPOTENCY_TTL_MS = 10 * 60 * 1000;
|
|
10
|
+
class JobSpawnIdempotencyConflictError extends Error {
|
|
11
|
+
constructor() {
|
|
12
|
+
super('Idempotency-Key was already used for a different spawn request');
|
|
13
|
+
this.name = 'JobSpawnIdempotencyConflictError';
|
|
14
|
+
}
|
|
15
|
+
}
|
|
16
|
+
exports.JobSpawnIdempotencyConflictError = JobSpawnIdempotencyConflictError;
|
|
17
|
+
/** Internal control-flow signal: another request already committed the exact
|
|
18
|
+
* same logical spawn. Throwing from QueueManager's outer admission transaction
|
|
19
|
+
* rolls the speculative queued_jobs row and in-memory job back before the route
|
|
20
|
+
* returns the original id. */
|
|
21
|
+
class JobSpawnIdempotencyReplayError extends Error {
|
|
22
|
+
jobId;
|
|
23
|
+
constructor(jobId) {
|
|
24
|
+
super('Idempotent spawn already admitted');
|
|
25
|
+
this.jobId = jobId;
|
|
26
|
+
this.name = 'JobSpawnIdempotencyReplayError';
|
|
27
|
+
}
|
|
28
|
+
}
|
|
29
|
+
exports.JobSpawnIdempotencyReplayError = JobSpawnIdempotencyReplayError;
|
|
30
|
+
/** Hash a canonical, route-owned payload so the ledger never has to duplicate
|
|
31
|
+
* the command text already stored in jobs. Callers must construct object keys
|
|
32
|
+
* in a stable order. */
|
|
33
|
+
function fingerprintJobSpawn(payload) {
|
|
34
|
+
return (0, crypto_1.createHash)('sha256').update(JSON.stringify(payload)).digest('hex');
|
|
35
|
+
}
|
|
36
|
+
/** Return the original job for an unexpired matching request. Reusing a key
|
|
37
|
+
* with different semantics is a client error, never permission to enqueue. */
|
|
38
|
+
function findIdempotentJob(db, key, fingerprint, nowMs = Date.now()) {
|
|
39
|
+
return db.transaction(() => {
|
|
40
|
+
db.prepare('DELETE FROM job_spawn_requests WHERE expires_at_ms <= ?').run(nowMs);
|
|
41
|
+
const row = db.prepare('SELECT fingerprint, job_id FROM job_spawn_requests WHERE idempotency_key = ?').get(key);
|
|
42
|
+
if (!row)
|
|
43
|
+
return null;
|
|
44
|
+
if (row.fingerprint !== fingerprint)
|
|
45
|
+
throw new JobSpawnIdempotencyConflictError();
|
|
46
|
+
return row.job_id;
|
|
47
|
+
})();
|
|
48
|
+
}
|
|
49
|
+
function rememberIdempotentJob(db, key, fingerprint, jobId, nowMs = Date.now()) {
|
|
50
|
+
db.prepare(`INSERT INTO job_spawn_requests
|
|
51
|
+
(idempotency_key, fingerprint, job_id, created_at_ms, expires_at_ms)
|
|
52
|
+
VALUES (?, ?, ?, ?, ?)`).run(key, fingerprint, jobId, nowMs, nowMs + exports.JOB_SPAWN_IDEMPOTENCY_TTL_MS);
|
|
53
|
+
}
|
|
54
|
+
/** Claim a key from INSIDE QueueManager's durable-admission transaction.
|
|
55
|
+
* Existing matching keys throw Replay so the speculative queue admission rolls
|
|
56
|
+
* back; mismatched keys throw Conflict; a new key is inserted atomically beside
|
|
57
|
+
* queued_jobs before QueueManager is allowed to drain. */
|
|
58
|
+
function claimIdempotentJob(db, key, fingerprint, jobId, nowMs = Date.now()) {
|
|
59
|
+
db.prepare('DELETE FROM job_spawn_requests WHERE expires_at_ms <= ?').run(nowMs);
|
|
60
|
+
const row = db.prepare('SELECT fingerprint, job_id FROM job_spawn_requests WHERE idempotency_key = ?').get(key);
|
|
61
|
+
if (row) {
|
|
62
|
+
if (row.fingerprint !== fingerprint)
|
|
63
|
+
throw new JobSpawnIdempotencyConflictError();
|
|
64
|
+
throw new JobSpawnIdempotencyReplayError(row.job_id);
|
|
65
|
+
}
|
|
66
|
+
rememberIdempotentJob(db, key, fingerprint, jobId, nowMs);
|
|
67
|
+
}
|