shadow-claw 1.59.6 → 1.59.7

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 (324) hide show
  1. package/.well-known/mcp/server-card.json +12 -4
  2. package/.well-known/mcp.json +12 -4
  3. package/dist/cli/build/build.js +1 -1
  4. package/dist/cli/{chunk-DM4xsTry.js → chunk-3vNYrs_L.js} +1 -1
  5. package/dist/cli/{chunk-Ctg5L55n.js → chunk-66BvqAV0.js} +1 -1
  6. package/dist/cli/{chunk-Bq38OubR.js → chunk-B0qusANw.js} +1 -1
  7. package/dist/cli/{chunk-yiVdvGCJ.js → chunk-B3TrWbca.js} +7 -7
  8. package/dist/cli/{chunk-C8DBACtx.js → chunk-B88Z8T_9.js} +1 -1
  9. package/dist/cli/chunk-BCjL0JXf.js +1 -0
  10. package/dist/cli/chunk-BNcu1oiT.js +1 -0
  11. package/dist/cli/{chunk-gvNsvav0.js → chunk-C5ypckWC.js} +7 -7
  12. package/dist/cli/{chunk-Dw8GndPD.js → chunk-CAAeGOdy.js} +1 -1
  13. package/dist/cli/chunk-CFxww5Yz.js +1 -0
  14. package/dist/cli/chunk-CGIgtL6R.js +1 -0
  15. package/dist/cli/{chunk-DJqHK-qS.js → chunk-CQaCgswD.js} +7 -7
  16. package/dist/cli/chunk-CZdCRqNe.js +7 -0
  17. package/dist/cli/chunk-CafdvLx-.js +1 -0
  18. package/dist/cli/{chunk-Bc_weULz.js → chunk-CncW6_WL.js} +1 -1
  19. package/dist/cli/chunk-DDvuLVfW.js +1 -0
  20. package/dist/cli/{chunk-Cq_kQohv.js → chunk-DMs7kREC.js} +1 -1
  21. package/dist/cli/{chunk-CX2itile.js → chunk-D_te8ufL.js} +1 -1
  22. package/dist/cli/{chunk-3wTukVof.js → chunk-DhOU6GYX.js} +1 -1
  23. package/dist/cli/chunk-Dhap1VwA.js +1 -0
  24. package/dist/cli/chunk-DwvavohW.js +1 -0
  25. package/dist/cli/{chunk-DLde6nuO.js → chunk-SRBRVorc.js} +1 -1
  26. package/dist/cli/{chunk-D3y7h9Xe.js → chunk-SxK79JmB.js} +1 -1
  27. package/dist/cli/chunk-_a0CkUNS.js +139 -0
  28. package/dist/cli/{chunk-C9o6lXP3.js → chunk-hVf839t7.js} +1 -1
  29. package/dist/cli/chunk-iB8OoMmW.js +7 -0
  30. package/dist/cli/cli.js +1 -1
  31. package/dist/headless-agent.js +1 -1
  32. package/dist/lib/{app-routes-DJdIjp2V.js → app-routes-BXiRvlNl.js} +7 -25
  33. package/dist/lib/{app-routes-DJdIjp2V.js.map → app-routes-BXiRvlNl.js.map} +1 -1
  34. package/dist/lib/{attachment-capabilities-Dbb-4ZP5.js → attachment-capabilities-BjkEPip8.js} +2 -2
  35. package/dist/lib/{attachment-capabilities-Dbb-4ZP5.js.map → attachment-capabilities-BjkEPip8.js.map} +1 -1
  36. package/dist/lib/{channel-Dlru5ofR.js → channel-mmdGzPkT.js} +3 -3
  37. package/dist/lib/{channel-Dlru5ofR.js.map → channel-mmdGzPkT.js.map} +1 -1
  38. package/dist/lib/{chat-template-BuuLY8l7.js → chat-template-DPEKGJhB.js} +2 -2
  39. package/dist/lib/{chat-template-BuuLY8l7.js.map → chat-template-DPEKGJhB.js.map} +1 -1
  40. package/dist/lib/{compact-context-BtR55YPU.js → compact-context-CY9BBlUQ.js} +19 -19
  41. package/dist/lib/{compact-context-BtR55YPU.js.map → compact-context-CY9BBlUQ.js.map} +1 -1
  42. package/dist/lib/components/common/shadow-claw-provider-model-picker.js +1 -1
  43. package/dist/lib/components/index.js +27 -27
  44. package/dist/lib/components/settings/shadow-claw-accounts.js +1 -1
  45. package/dist/lib/components/settings/shadow-claw-channel-config.js +1 -1
  46. package/dist/lib/components/settings/shadow-claw-control-plane.js +1 -1
  47. package/dist/lib/components/settings/shadow-claw-git.js +1 -1
  48. package/dist/lib/components/settings/shadow-claw-integrations.js +1 -1
  49. package/dist/lib/components/settings/shadow-claw-llm.js +1 -1
  50. package/dist/lib/components/settings/shadow-claw-mcp-remote.js +1 -1
  51. package/dist/lib/components/settings/shadow-claw-networking.js +1 -1
  52. package/dist/lib/components/settings/shadow-claw-notifications.js +1 -1
  53. package/dist/lib/components/settings/shadow-claw-peerjs.js +1 -1
  54. package/dist/lib/components/settings/shadow-claw-storage.js +1 -1
  55. package/dist/lib/components/settings/shadow-claw-task-server.js +1 -1
  56. package/dist/lib/components/settings/shadow-claw-webvm.js +1 -1
  57. package/dist/lib/components/shadow-claw-a2ui.js +1 -1
  58. package/dist/lib/components/shadow-claw-accounts.js +1 -1
  59. package/dist/lib/components/shadow-claw-channel-config.js +1 -1
  60. package/dist/lib/components/shadow-claw-channels.js +1 -1
  61. package/dist/lib/components/shadow-claw-chat.js +1 -1
  62. package/dist/lib/components/shadow-claw-control-plane.js +1 -1
  63. package/dist/lib/components/shadow-claw-conversations.js +1 -1
  64. package/dist/lib/components/shadow-claw-file-viewer.js +1 -1
  65. package/dist/lib/components/shadow-claw-files.js +1 -1
  66. package/dist/lib/components/shadow-claw-git.js +1 -1
  67. package/dist/lib/components/shadow-claw-integrations.js +1 -1
  68. package/dist/lib/components/shadow-claw-llm.js +1 -1
  69. package/dist/lib/components/shadow-claw-mcp-remote.js +1 -1
  70. package/dist/lib/components/shadow-claw-networking.js +1 -1
  71. package/dist/lib/components/shadow-claw-notifications.js +1 -1
  72. package/dist/lib/components/shadow-claw-page-header.js +1 -1
  73. package/dist/lib/components/shadow-claw-pages.js +1 -1
  74. package/dist/lib/components/shadow-claw-peerjs.js +1 -1
  75. package/dist/lib/components/shadow-claw-provider-model-picker.js +1 -1
  76. package/dist/lib/components/shadow-claw-settings.js +1 -1
  77. package/dist/lib/components/shadow-claw-storage.js +1 -1
  78. package/dist/lib/components/shadow-claw-task-server.js +1 -1
  79. package/dist/lib/components/shadow-claw-tasks.js +1 -1
  80. package/dist/lib/components/shadow-claw-terminal.js +1 -1
  81. package/dist/lib/components/shadow-claw-tools.js +1 -1
  82. package/dist/lib/components/shadow-claw-webvm.js +1 -1
  83. package/dist/lib/components/shadow-claw.js +1 -1
  84. package/dist/lib/{config-DxNI3TlW.js → config-BrHR97zt.js} +2 -2
  85. package/dist/lib/{config-DxNI3TlW.js.map → config-BrHR97zt.js.map} +1 -1
  86. package/dist/lib/{configure-peer-js-ChDhOZU4.js → configure-peer-js-ccNvax2N.js} +3 -3
  87. package/dist/lib/{configure-peer-js-ChDhOZU4.js.map → configure-peer-js-ccNvax2N.js.map} +1 -1
  88. package/dist/lib/{connections-DC4NZkJE.js → connections-C1FWsBsE.js} +2 -2
  89. package/dist/lib/{connections-DC4NZkJE.js.map → connections-C1FWsBsE.js.map} +1 -1
  90. package/dist/lib/{credentials-5vpz0XPk.js → credentials-CZbngHXW.js} +2 -2
  91. package/dist/lib/{credentials-5vpz0XPk.js.map → credentials-CZbngHXW.js.map} +1 -1
  92. package/dist/lib/{discover-skills-CD0sKvAI.js → discover-skills-OwlQ2sXA.js} +13 -13
  93. package/dist/lib/{discover-skills-CD0sKvAI.js.map → discover-skills-OwlQ2sXA.js.map} +1 -1
  94. package/dist/lib/{download-group-file-Dk3qaxhJ.js → download-group-file-D0wgg10Q.js} +2 -2
  95. package/dist/lib/{download-group-file-Dk3qaxhJ.js.map → download-group-file-D0wgg10Q.js.map} +1 -1
  96. package/dist/lib/{file-viewer-B4pRW-_G.js → file-viewer-DOfvX6yy.js} +5 -5
  97. package/dist/lib/{file-viewer-B4pRW-_G.js.map → file-viewer-DOfvX6yy.js.map} +1 -1
  98. package/dist/lib/{get-or-create-subscriber-id-HCcgDEPz.js → get-or-create-subscriber-id-wyzaML7Z.js} +2 -2
  99. package/dist/lib/{get-or-create-subscriber-id-HCcgDEPz.js.map → get-or-create-subscriber-id-wyzaML7Z.js.map} +1 -1
  100. package/dist/lib/{git-B3Q1euc5.js → git-D2J_j9X9.js} +5 -5
  101. package/dist/lib/{git-B3Q1euc5.js.map → git-D2J_j9X9.js.map} +1 -1
  102. package/dist/lib/{iframe-bridge-scripts-D8iuFhUk.js → iframe-bridge-scripts-Dx825LLG.js} +2 -2
  103. package/dist/lib/{iframe-bridge-scripts-D8iuFhUk.js.map → iframe-bridge-scripts-Dx825LLG.js.map} +1 -1
  104. package/dist/lib/index.js +28 -28
  105. package/dist/lib/{init-chat-split-resize-B0ODULx9.js → init-chat-split-resize-Cc0bd2z9.js} +2 -2
  106. package/dist/lib/{init-chat-split-resize-B0ODULx9.js.map → init-chat-split-resize-Cc0bd2z9.js.map} +1 -1
  107. package/dist/lib/{init-control-plane-C1FRRmjC.js → init-control-plane-B7blDVIE.js} +15 -15
  108. package/dist/lib/{init-control-plane-C1FRRmjC.js.map → init-control-plane-B7blDVIE.js.map} +1 -1
  109. package/dist/lib/{invoke-agent-CzN7sVh-.js → invoke-agent-SxvudiDT.js} +11 -11
  110. package/dist/lib/{invoke-agent-CzN7sVh-.js.map → invoke-agent-SxvudiDT.js.map} +1 -1
  111. package/dist/lib/{markdown-mbNo7cV3.js → markdown--6vTAPEH.js} +2 -2
  112. package/dist/lib/{markdown-mbNo7cV3.js.map → markdown--6vTAPEH.js.map} +1 -1
  113. package/dist/lib/{mcp-reconnect-3T7yWGEY.js → mcp-reconnect-BeqQvNWO.js} +3 -3
  114. package/dist/lib/{mcp-reconnect-3T7yWGEY.js.map → mcp-reconnect-BeqQvNWO.js.map} +1 -1
  115. package/dist/lib/{model-ranking-DGNSWYwN.js → model-ranking-BhsJV7vb.js} +2 -2
  116. package/dist/lib/{model-ranking-DGNSWYwN.js.map → model-ranking-BhsJV7vb.js.map} +1 -1
  117. package/dist/lib/{move-group-entry-NMTJ59M9.js → move-group-entry-DDpjxa10.js} +5 -5
  118. package/dist/lib/{move-group-entry-NMTJ59M9.js.map → move-group-entry-DDpjxa10.js.map} +1 -1
  119. package/dist/lib/{orchestrator-B8FV1V7x.js → orchestrator-C7fkh7T7.js} +24 -24
  120. package/dist/lib/{orchestrator-B8FV1V7x.js.map → orchestrator-C7fkh7T7.js.map} +1 -1
  121. package/dist/lib/{orchestrator-i_QJ-o22.js → orchestrator-CCARkxQC.js} +11 -11
  122. package/dist/lib/orchestrator-CCARkxQC.js.map +1 -0
  123. package/dist/lib/{parse-path-DPCn-HwI.js → parse-path-BOHQP_IQ.js} +3 -3
  124. package/dist/lib/{parse-path-DPCn-HwI.js.map → parse-path-BOHQP_IQ.js.map} +1 -1
  125. package/dist/lib/{peerjs-z5zeioPV.js → peerjs-Bfw_FWLB.js} +8 -8
  126. package/dist/lib/{peerjs-z5zeioPV.js.map → peerjs-Bfw_FWLB.js.map} +1 -1
  127. package/dist/lib/{process-peer-query-param-CJp7w7AU.js → process-peer-query-param-BxYiZNdf.js} +5 -5
  128. package/dist/lib/{process-peer-query-param-CJp7w7AU.js.map → process-peer-query-param-BxYiZNdf.js.map} +1 -1
  129. package/dist/lib/{process-pending-shared-payloads-B6_TlBFA.js → process-pending-shared-payloads-DPIbwRb3.js} +4 -4
  130. package/dist/lib/{process-pending-shared-payloads-B6_TlBFA.js.map → process-pending-shared-payloads-DPIbwRb3.js.map} +1 -1
  131. package/dist/lib/{process-room-query-param-C3FFGGn6.js → process-room-query-param-B2_d50nE.js} +4 -4
  132. package/dist/lib/{process-room-query-param-C3FFGGn6.js.map → process-room-query-param-B2_d50nE.js.map} +1 -1
  133. package/dist/lib/{provider-DcQZypu5.js → provider-BC9KPI14.js} +3 -3
  134. package/dist/lib/{provider-DcQZypu5.js.map → provider-BC9KPI14.js.map} +1 -1
  135. package/dist/lib/{push-client-Cx5rMs6J.js → push-client-rrjTdc-U.js} +5 -5
  136. package/dist/lib/{push-client-Cx5rMs6J.js.map → push-client-rrjTdc-U.js.map} +1 -1
  137. package/dist/lib/{read-group-file-bytes-CXOG_YyM.js → read-group-file-bytes-UQIk1eJG.js} +2 -2
  138. package/dist/lib/{read-group-file-bytes-CXOG_YyM.js.map → read-group-file-bytes-UQIk1eJG.js.map} +1 -1
  139. package/dist/lib/{rooms-CwlkYLDU.js → rooms-bwGoYb1q.js} +2 -2
  140. package/dist/lib/{rooms-CwlkYLDU.js.map → rooms-bwGoYb1q.js.map} +1 -1
  141. package/dist/lib/{shadow-claw-DoQ7fgl5.js → shadow-claw-CypGVlVO.js} +17 -20
  142. package/dist/lib/shadow-claw-CypGVlVO.js.map +1 -0
  143. package/dist/lib/{shadow-claw-a2ui-Br6qJMs1.js → shadow-claw-a2ui-lG0vQbW8.js} +2 -2
  144. package/dist/lib/{shadow-claw-a2ui-Br6qJMs1.js.map → shadow-claw-a2ui-lG0vQbW8.js.map} +1 -1
  145. package/dist/lib/{shadow-claw-accounts-BTDILfWw.js → shadow-claw-accounts-CkqyCxwp.js} +3 -3
  146. package/dist/lib/{shadow-claw-accounts-BTDILfWw.js.map → shadow-claw-accounts-CkqyCxwp.js.map} +1 -1
  147. package/dist/lib/{shadow-claw-channel-config-IKiL34tI.js → shadow-claw-channel-config-DJpDovkF.js} +4 -4
  148. package/dist/lib/{shadow-claw-channel-config-IKiL34tI.js.map → shadow-claw-channel-config-DJpDovkF.js.map} +1 -1
  149. package/dist/lib/{shadow-claw-channels-JgEzuHWK.js → shadow-claw-channels-DJLwRovH.js} +3 -3
  150. package/dist/lib/{shadow-claw-channels-JgEzuHWK.js.map → shadow-claw-channels-DJLwRovH.js.map} +1 -1
  151. package/dist/lib/{shadow-claw-chat-SGUDT31r.js → shadow-claw-chat-B92cPaft.js} +15 -15
  152. package/dist/lib/{shadow-claw-chat-SGUDT31r.js.map → shadow-claw-chat-B92cPaft.js.map} +1 -1
  153. package/dist/lib/{shadow-claw-control-plane-CRWFZ3vD.js → shadow-claw-control-plane-fvn-qyHj.js} +7 -7
  154. package/dist/lib/{shadow-claw-control-plane-CRWFZ3vD.js.map → shadow-claw-control-plane-fvn-qyHj.js.map} +1 -1
  155. package/dist/lib/{shadow-claw-conversations-D23GJ7qo.js → shadow-claw-conversations-CsVyDOny.js} +7 -7
  156. package/dist/lib/{shadow-claw-conversations-D23GJ7qo.js.map → shadow-claw-conversations-CsVyDOny.js.map} +1 -1
  157. package/dist/lib/{shadow-claw-file-viewer-C1V8WTiU.js → shadow-claw-file-viewer-DFfyP7s5.js} +10 -10
  158. package/dist/lib/{shadow-claw-file-viewer-C1V8WTiU.js.map → shadow-claw-file-viewer-DFfyP7s5.js.map} +1 -1
  159. package/dist/lib/{shadow-claw-files-DN7irmE1.js → shadow-claw-files-cT6HL7ye.js} +11 -11
  160. package/dist/lib/{shadow-claw-files-DN7irmE1.js.map → shadow-claw-files-cT6HL7ye.js.map} +1 -1
  161. package/dist/lib/{shadow-claw-git-D-1oIh65.js → shadow-claw-git-Cv9mQgTx.js} +6 -6
  162. package/dist/lib/{shadow-claw-git-D-1oIh65.js.map → shadow-claw-git-Cv9mQgTx.js.map} +1 -1
  163. package/dist/lib/{shadow-claw-integrations-CZjnm7cM.js → shadow-claw-integrations-RZZ-m-Id.js} +4 -4
  164. package/dist/lib/{shadow-claw-integrations-CZjnm7cM.js.map → shadow-claw-integrations-RZZ-m-Id.js.map} +1 -1
  165. package/dist/lib/{shadow-claw-llm-4Gefh5FN.js → shadow-claw-llm-CKOYzPDp.js} +9 -9
  166. package/dist/lib/{shadow-claw-llm-4Gefh5FN.js.map → shadow-claw-llm-CKOYzPDp.js.map} +1 -1
  167. package/dist/lib/{shadow-claw-mcp-remote-B9ssb3YV.js → shadow-claw-mcp-remote-BKFROurv.js} +4 -4
  168. package/dist/lib/{shadow-claw-mcp-remote-B9ssb3YV.js.map → shadow-claw-mcp-remote-BKFROurv.js.map} +1 -1
  169. package/dist/lib/{shadow-claw-networking-BN5BB4hb.js → shadow-claw-networking-DYfiUQaH.js} +2 -2
  170. package/dist/lib/{shadow-claw-networking-BN5BB4hb.js.map → shadow-claw-networking-DYfiUQaH.js.map} +1 -1
  171. package/dist/lib/{shadow-claw-notifications-71KARtkY.js → shadow-claw-notifications-JJlzriuX.js} +3 -3
  172. package/dist/lib/{shadow-claw-notifications-71KARtkY.js.map → shadow-claw-notifications-JJlzriuX.js.map} +1 -1
  173. package/dist/lib/{shadow-claw-page-header-DMGO-TSe.js → shadow-claw-page-header-C_Qr3xZM.js} +2 -2
  174. package/dist/lib/{shadow-claw-page-header-DMGO-TSe.js.map → shadow-claw-page-header-C_Qr3xZM.js.map} +1 -1
  175. package/dist/lib/{shadow-claw-pages-BiRM6qiA.js → shadow-claw-pages-BCo3ihZI.js} +11 -11
  176. package/dist/lib/{shadow-claw-pages-BiRM6qiA.js.map → shadow-claw-pages-BCo3ihZI.js.map} +1 -1
  177. package/dist/lib/{shadow-claw-peerjs-BZu7jNSe.js → shadow-claw-peerjs-CFNjfrY5.js} +6 -6
  178. package/dist/lib/{shadow-claw-peerjs-BZu7jNSe.js.map → shadow-claw-peerjs-CFNjfrY5.js.map} +1 -1
  179. package/dist/lib/{shadow-claw-provider-model-picker-BXYXEobD.js → shadow-claw-provider-model-picker-B-Ct4yW-.js} +2 -2
  180. package/dist/lib/{shadow-claw-provider-model-picker-BXYXEobD.js.map → shadow-claw-provider-model-picker-B-Ct4yW-.js.map} +1 -1
  181. package/dist/lib/{shadow-claw-settings-CcT5EK08.js → shadow-claw-settings-BMwne0bh.js} +7 -7
  182. package/dist/lib/{shadow-claw-settings-CcT5EK08.js.map → shadow-claw-settings-BMwne0bh.js.map} +1 -1
  183. package/dist/lib/{shadow-claw-storage-eTOpbvpi.js → shadow-claw-storage-DUY8B9m-.js} +5 -5
  184. package/dist/lib/{shadow-claw-storage-eTOpbvpi.js.map → shadow-claw-storage-DUY8B9m-.js.map} +1 -1
  185. package/dist/lib/{shadow-claw-task-server-DFImTUbw.js → shadow-claw-task-server-yWeoA3eL.js} +2 -2
  186. package/dist/lib/{shadow-claw-task-server-DFImTUbw.js.map → shadow-claw-task-server-yWeoA3eL.js.map} +1 -1
  187. package/dist/lib/{shadow-claw-tasks-BjaxsmUx.js → shadow-claw-tasks-Bg0uM15I.js} +9 -9
  188. package/dist/lib/{shadow-claw-tasks-BjaxsmUx.js.map → shadow-claw-tasks-Bg0uM15I.js.map} +1 -1
  189. package/dist/lib/{shadow-claw-terminal-C-4wreFe.js → shadow-claw-terminal-fyJPppY_.js} +2 -2
  190. package/dist/lib/{shadow-claw-terminal-C-4wreFe.js.map → shadow-claw-terminal-fyJPppY_.js.map} +1 -1
  191. package/dist/lib/{shadow-claw-tools-COdrGZJk.js → shadow-claw-tools-D0T8m3go.js} +7 -7
  192. package/dist/lib/{shadow-claw-tools-COdrGZJk.js.map → shadow-claw-tools-D0T8m3go.js.map} +1 -1
  193. package/dist/lib/{shadow-claw-webvm-sxqVjO0L.js → shadow-claw-webvm-CQvzJwKI.js} +3 -3
  194. package/dist/lib/{shadow-claw-webvm-sxqVjO0L.js.map → shadow-claw-webvm-CQvzJwKI.js.map} +1 -1
  195. package/dist/lib/{sync-web-mcp-registration-D4hdUwtv.js → sync-web-mcp-registration-BFtG_4kx.js} +6 -6
  196. package/dist/lib/{sync-web-mcp-registration-D4hdUwtv.js.map → sync-web-mcp-registration-BFtG_4kx.js.map} +1 -1
  197. package/dist/lib/{system-prompt-DT_KeYaL.js → system-prompt-bhGRLoL2.js} +7 -7
  198. package/dist/lib/{system-prompt-DT_KeYaL.js.map → system-prompt-bhGRLoL2.js.map} +1 -1
  199. package/dist/lib/{tools-Beuyh8y1.js → tools-B8OJ4sMF.js} +4 -4
  200. package/dist/lib/{tools-Beuyh8y1.js.map → tools-B8OJ4sMF.js.map} +1 -1
  201. package/dist/lib/{transformers-DydnReu4.js → transformers-BMURofG6.js} +2 -2
  202. package/dist/lib/{transformers-DydnReu4.js.map → transformers-BMURofG6.js.map} +1 -1
  203. package/dist/lib/{trusted-types-CfwZl_rr.js → trusted-types-HwsGS5Nj.js} +19 -17
  204. package/dist/lib/{trusted-types-CfwZl_rr.js.map → trusted-types-HwsGS5Nj.js.map} +1 -1
  205. package/dist/lib/{upload-group-file-BbBzjTcN.js → upload-group-file-CJpoNjEb.js} +3 -3
  206. package/dist/lib/{upload-group-file-BbBzjTcN.js.map → upload-group-file-CJpoNjEb.js.map} +1 -1
  207. package/dist/lib/utils/index.js +1 -1
  208. package/dist/lib/utils/namespaced-storage.js +1 -1
  209. package/dist/lib/utils/runtime-assets.js +1 -1
  210. package/dist/lib/utils/utils.js +1 -1
  211. package/dist/lib/{webmcp-DCfAFiIO.js → webmcp-BoMTvgmX.js} +3 -3
  212. package/dist/lib/{webmcp-DCfAFiIO.js.map → webmcp-BoMTvgmX.js.map} +1 -1
  213. package/dist/lib/{write-group-file-bytes-Ccn-VFUU.js → write-group-file-bytes-CNT7DqOZ.js} +3 -3
  214. package/dist/lib/{write-group-file-bytes-Ccn-VFUU.js.map → write-group-file-bytes-CNT7DqOZ.js.map} +1 -1
  215. package/dist/public/.well-known/mcp/server-card.json +12 -4
  216. package/dist/public/.well-known/mcp.json +12 -4
  217. package/dist/public/agent.worker.js +1 -1
  218. package/dist/public/attachment-capabilities-AdwXt3--.js +1 -0
  219. package/dist/public/{channel-BylT3rJC.js → channel-Dk7wl-Av.js} +1 -1
  220. package/dist/public/{chat-template-DPHJy7tr.js → chat-template-BwAnTFKf.js} +1 -1
  221. package/dist/public/{compact-context-BINQh64w.js → compact-context-fOTqwKF6.js} +2 -2
  222. package/dist/public/config-C16fFWtP.js +1 -0
  223. package/dist/public/{configure-peer-js-DChhcOfe.js → configure-peer-js-BOV0tR6G.js} +1 -1
  224. package/dist/public/{connections-CHaw0VqP.js → connections-Dxwj8yK_.js} +1 -1
  225. package/dist/public/{create-model-cache-fetch-DQebkoPL.js → create-model-cache-fetch-DSAFjOwc.js} +1 -1
  226. package/dist/public/{credentials-CgVqS119.js → credentials-CJUQ5Ep2.js} +1 -1
  227. package/dist/public/{custom-element-security-kiDhPfb8.js → custom-element-security-B2daIE5r.js} +2 -2
  228. package/dist/public/{discover-skills-Cvmx5I9V.js → discover-skills-D1sNTy2r.js} +6 -6
  229. package/dist/public/docs/example/article/index.html +28 -29
  230. package/dist/public/docs/example/article.html +28 -29
  231. package/dist/public/docs/publishing/index.html +28 -29
  232. package/dist/public/docs/publishing.html +28 -29
  233. package/dist/public/docs/skill-creator/index.html +28 -29
  234. package/dist/public/docs/skill-creator.html +28 -29
  235. package/dist/public/{download-group-file-BapoRgfU.js → download-group-file-BkMH-JKi.js} +1 -1
  236. package/dist/public/{e2e-bridge-C0g8vZKr.js → e2e-bridge-Cz95DLlb.js} +1 -1
  237. package/dist/public/get-group-dir-D--BiEyk.js +1 -0
  238. package/dist/public/{get-or-create-subscriber-id-GvRZYXwA.js → get-or-create-subscriber-id-jVHnQfbr.js} +1 -1
  239. package/dist/public/{git-CaAAZfVd.js → git-BmMlwIMP.js} +2 -2
  240. package/dist/public/{iframe-bridge-scripts-BnqtKhE4.js → iframe-bridge-scripts-Cibg0m6A.js} +1 -1
  241. package/dist/public/index.html +28 -29
  242. package/dist/public/index.js +1 -1
  243. package/dist/public/{init-chat-split-resize-Btonoy8u.js → init-chat-split-resize-C8AqCCiK.js} +1 -1
  244. package/dist/public/init-control-plane-Cb31yLTY.js +1 -0
  245. package/dist/public/{invoke-agent-B3Osw6K7.js → invoke-agent-CN7mSV0Z.js} +1 -1
  246. package/dist/public/main/index.html +28 -29
  247. package/dist/public/main/memory/index.html +28 -29
  248. package/dist/public/main/memory.html +28 -29
  249. package/dist/public/main.html +28 -29
  250. package/dist/public/{markdown-CPbU4r1U.js → markdown-CDSb5Hrl.js} +1 -1
  251. package/dist/public/{mcp-reconnect-CzROVsXG.js → mcp-reconnect-iPZPihwX.js} +1 -1
  252. package/dist/public/{memory-storage-BkoMlxOr.js → memory-storage-2m7KZ-aP.js} +1 -1
  253. package/dist/public/{model-ranking-CK0iBo3Z.js → model-ranking-BgOSaNIy.js} +1 -1
  254. package/dist/public/{move-group-entry-CTxoq7lw.js → move-group-entry-CXneuNVa.js} +1 -1
  255. package/dist/public/orchestrator-DBO4NZqd.js +63 -0
  256. package/dist/public/{orchestrator-BrDjQbGf.js → orchestrator-Dyylc8IU.js} +2 -2
  257. package/dist/public/{peerjs-CgF4Iz5W.js → peerjs-l0jiBoh6.js} +1 -1
  258. package/dist/public/{process-peer-query-param-BL2k0Hu-.js → process-peer-query-param-s-aSP1Rq.js} +1 -1
  259. package/dist/public/{process-pending-shared-payloads-C1AgGvn8.js → process-pending-shared-payloads-BN3GigPT.js} +1 -1
  260. package/dist/public/{process-room-query-param-DM0QCq3_.js → process-room-query-param-B2Qe0F0M.js} +1 -1
  261. package/dist/public/provider-YPZmsuHR.js +1 -0
  262. package/dist/public/{push-client-DJEOz7bi.js → push-client-B2LC8Qp9.js} +1 -1
  263. package/dist/public/{rooms-C6LXIJl4.js → rooms-ChCEOvkw.js} +1 -1
  264. package/dist/public/service-worker.js +1 -1
  265. package/dist/public/shadow-claw-Br8mWDUx.js +1176 -0
  266. package/dist/public/{shadow-claw-accounts--4hd_oCz.js → shadow-claw-accounts-Dm6G7KMP.js} +1 -1
  267. package/dist/public/{shadow-claw-card-IbNlZAdK.js → shadow-claw-card-CggS8uSa.js} +1 -1
  268. package/dist/public/{shadow-claw-channels-Vq_pPGa2.js → shadow-claw-channels-088vhuWO.js} +1 -1
  269. package/dist/public/{shadow-claw-chat-D7_GS25e.js → shadow-claw-chat-BRwRlq-n.js} +3 -3
  270. package/dist/public/{shadow-claw-control-plane-WTMEV8_p.js → shadow-claw-control-plane-rhKACK85.js} +2 -2
  271. package/dist/public/{shadow-claw-conversations-CLQgU1IT.js → shadow-claw-conversations-CF_yUfKl.js} +1 -1
  272. package/dist/public/{shadow-claw-empty-state-D4CrFGsN.js → shadow-claw-empty-state-CkpOSXCS.js} +1 -1
  273. package/dist/public/{shadow-claw-file-viewer-BhqiqLWQ.js → shadow-claw-file-viewer-DWCejuY3.js} +4 -4
  274. package/dist/public/{shadow-claw-files-senDiG9l.js → shadow-claw-files-L6_ioyzh.js} +2 -2
  275. package/dist/public/{shadow-claw-git-DOOCqY23.js → shadow-claw-git-DsdkwLqQ.js} +2 -2
  276. package/dist/public/{shadow-claw-integrations-Bsvc3Agq.js → shadow-claw-integrations-CSbRTOm3.js} +1 -1
  277. package/dist/public/{shadow-claw-llm-actYICAk.js → shadow-claw-llm-BitaeAVc.js} +2 -2
  278. package/dist/public/{shadow-claw-mcp-remote-BYUgrK3v.js → shadow-claw-mcp-remote-gSbV5riy.js} +1 -1
  279. package/dist/public/{shadow-claw-networking-Dk3p5Ny_.js → shadow-claw-networking-Dn_y6Cl9.js} +1 -1
  280. package/dist/public/{shadow-claw-notifications-CzPAlay8.js → shadow-claw-notifications-Cj4Lqx8U.js} +1 -1
  281. package/dist/public/{shadow-claw-page-header-CjJpVkyL.js → shadow-claw-page-header-DR4OZFt2.js} +1 -1
  282. package/dist/public/{shadow-claw-page-header-action-button-2DH5O1TD.js → shadow-claw-page-header-action-button-BnCV_2Kb.js} +1 -1
  283. package/dist/public/{shadow-claw-pages-3r5I-wI8.js → shadow-claw-pages-mpDOtNYj.js} +6 -6
  284. package/dist/public/{shadow-claw-pdf-viewer-BiCEwsoY.js → shadow-claw-pdf-viewer-DZ_84qJH.js} +1 -1
  285. package/dist/public/{shadow-claw-settings-DgB9RSZN.js → shadow-claw-settings-CfFTYTEy.js} +2 -2
  286. package/dist/public/{shadow-claw-storage-JB_43nd8.js → shadow-claw-storage-DLmiT4bG.js} +1 -1
  287. package/dist/public/{shadow-claw-task-server-oi5UIxdA.js → shadow-claw-task-server-BoMBCsiS.js} +1 -1
  288. package/dist/public/{shadow-claw-tasks-CnyiOt81.js → shadow-claw-tasks-ChEp1j7x.js} +3 -3
  289. package/dist/public/{shadow-claw-terminal-BC3RynHt.js → shadow-claw-terminal-BaoVbOda.js} +1 -1
  290. package/dist/public/{shadow-claw-toast-YjG--2Za.js → shadow-claw-toast-e8oz7z6Z.js} +1 -1
  291. package/dist/public/{shadow-claw-tools-Bbwk4vlT.js → shadow-claw-tools-BYjUBiJz.js} +1 -1
  292. package/dist/public/{shadow-claw-webvm-HZqzl2H5.js → shadow-claw-webvm-xGb13TME.js} +1 -1
  293. package/dist/public/{sync-web-mcp-registration-BaH2nAP0.js → sync-web-mcp-registration-CQluj-Kz.js} +1 -1
  294. package/dist/public/{system-prompt-Dck3N8T0.js → system-prompt-CTJn0tK-.js} +1 -1
  295. package/dist/public/{tools-DHA1dK2I.js → tools-D-52Zmfc.js} +1 -1
  296. package/dist/public/{transformers-C-DuTM2K.js → transformers-CQ9ss9rD.js} +1 -1
  297. package/dist/public/{upload-group-file-Cejr3zo1.js → upload-group-file-A8kB7lvO.js} +1 -1
  298. package/dist/public/{webmcp-CMRtu57-.js → webmcp-DIUZjVF5.js} +1 -1
  299. package/dist/public/{write-group-file-CmJuVQNO.js → write-group-file-R67DjJ-q.js} +1 -1
  300. package/dist/public/{write-group-file-bytes-Cejr3zo1.js → write-group-file-bytes-A8kB7lvO.js} +1 -1
  301. package/dist/public/{zip-reader-CuQ13eLe.js → zip-reader-DN7FB-Q0.js} +1 -1
  302. package/dist/server.js +1 -1
  303. package/package.json +1 -1
  304. package/dist/cli/chunk-BFziiMKt.js +0 -7
  305. package/dist/cli/chunk-BM3llsxb.js +0 -1
  306. package/dist/cli/chunk-Bj5qFsDi.js +0 -7
  307. package/dist/cli/chunk-Bj95zm-y.js +0 -1
  308. package/dist/cli/chunk-BpyP-esT.js +0 -1
  309. package/dist/cli/chunk-CX696s3_.js +0 -1
  310. package/dist/cli/chunk-DRxCrCAA.js +0 -139
  311. package/dist/cli/chunk-DjbCHa0h.js +0 -1
  312. package/dist/cli/chunk-DsQhAF31.js +0 -1
  313. package/dist/cli/chunk-VM-dECyG.js +0 -1
  314. package/dist/cli/chunk-heu2xRw1.js +0 -1
  315. package/dist/lib/orchestrator-i_QJ-o22.js.map +0 -1
  316. package/dist/lib/shadow-claw-DoQ7fgl5.js.map +0 -1
  317. package/dist/public/app-routes-V_-URXc5.js +0 -1
  318. package/dist/public/attachment-capabilities-B6ibLwQB.js +0 -1
  319. package/dist/public/config-C-YdSFZB.js +0 -1
  320. package/dist/public/get-group-dir-DL44kvqW.js +0 -1
  321. package/dist/public/init-control-plane-BoJijVtf.js +0 -1
  322. package/dist/public/orchestrator-CaUpEVkQ.js +0 -63
  323. package/dist/public/provider-DNIL4-Hw.js +0 -1
  324. package/dist/public/shadow-claw-DdgeYPg5.js +0 -1176
@@ -1,4 +1,4 @@
1
- import { n as applyBasePath } from "./app-routes-DJdIjp2V.js";
1
+ import { t as applyBasePath } from "./app-routes-BXiRvlNl.js";
2
2
  import { getSiteConfig } from "./utils/site-config.js";
3
3
 
4
4
  //#region src/ui/iframe-theme.ts
@@ -367,4 +367,4 @@ function safeInlineScript(code) {
367
367
 
368
368
  //#endregion
369
369
  export { iframeStorageDelete as a, iframeStorageSet as c, getIframeThemeStyleHtml as d, getIframeThemeStylesheetLink as f, iframeStorageClear as i, IframeBroadcastProxy as l, IFRAME_STORAGE_BRIDGE_SCRIPT as n, iframeStorageGet as o, safeInlineScript as r, iframeStorageGetAll as s, FILE_VIEWER_PREVIEW_BRIDGE_SCRIPT as t, getIframeHtmlClass as u };
370
- //# sourceMappingURL=iframe-bridge-scripts-D8iuFhUk.js.map
370
+ //# sourceMappingURL=iframe-bridge-scripts-Dx825LLG.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"iframe-bridge-scripts-D8iuFhUk.js","names":[],"sources":["../../src/ui/iframe-theme.ts","../../src/components/shadow-claw-pages/utils/iframe-broadcast-proxy.ts","../../src/components/shadow-claw-pages/utils/iframe-storage-proxy.ts","../../src/components/shadow-claw-file-viewer/utils/iframe-bridge-scripts.ts"],"sourcesContent":["import { applyBasePath } from \"../core/app-routes.js\";\nimport { getSiteConfig } from \"../utils/site-config.js\";\n\n/**\n * Prefixes whose contents are flattened into the distribution root.\n */\nconst FLATTENED_STYLESHEET_PREFIXES = [\n \"pages/resources/\",\n \"pages/deps/\",\n \"resources/\",\n \"deps/\",\n \"pages/assets/\",\n \"pages/main/assets/\",\n];\n\n/**\n * Resolves a configured theme.stylesheet path to its actual distribution path.\n */\nexport function resolveThemeStylesheetHref(stylesheet: string): string {\n for (const prefix of FLATTENED_STYLESHEET_PREFIXES) {\n if (stylesheet.startsWith(prefix)) {\n return stylesheet.slice(prefix.length).replace(/^\\/+/, \"\");\n }\n }\n return stylesheet.replace(/^\\/+/, \"\");\n}\n\n/**\n * Generates an optional `<style>` or `<link rel=\"stylesheet\">` tag for the preview iframe\n * when an inline theme or theme stylesheet is configured.\n * When neither is configured, returns an empty string to avoid 404 requests.\n */\nexport function getIframeThemeStylesheetLink(siteConfig?: unknown): string {\n let config = siteConfig;\n if (!config && typeof document !== \"undefined\") {\n config = getSiteConfig();\n }\n\n let inlineThemeStyleText: string | undefined;\n if (typeof document !== \"undefined\") {\n let styleElementId = \"shadow-claw-theme\";\n if (config && typeof config === \"object\") {\n const customId = (config as { theme?: { styleElement?: unknown } }).theme\n ?.styleElement;\n if (typeof customId === \"string\" && customId.trim()) {\n styleElementId = customId.trim();\n }\n }\n const inlineStyle =\n document.getElementById(styleElementId) ||\n document.querySelector(\"style[data-shadow-claw-theme]\");\n if (inlineStyle?.textContent) {\n inlineThemeStyleText = inlineStyle.textContent;\n }\n }\n\n let stylesheet: string | undefined;\n if (config && typeof config === \"object\") {\n const rawTheme = (config as { theme?: { stylesheet?: unknown } }).theme;\n if (\n typeof rawTheme?.stylesheet === \"string\" &&\n rawTheme.stylesheet.trim()\n ) {\n stylesheet = rawTheme.stylesheet.trim();\n }\n }\n\n let result = \"\";\n if (inlineThemeStyleText) {\n result += `<style data-theme-style=\"true\">${inlineThemeStyleText}</style>`;\n }\n\n if (!stylesheet) {\n return result;\n }\n\n const isExternal =\n stylesheet.startsWith(\"http://\") ||\n stylesheet.startsWith(\"https://\") ||\n stylesheet.startsWith(\"//\");\n\n if (isExternal) {\n return `${result}<link rel=\"stylesheet\" href=\"${stylesheet}\">`;\n }\n\n // Runtime links must be site-root absolute (with the deployment base path):\n // srcdoc preview iframes set `<base href=\"/<base>/files/<group>/...\">`, so a\n // relative href would resolve under the file route and 404.\n const resolvedHref = resolveThemeStylesheetHref(stylesheet).replace(\n /^\\/+/,\n \"\",\n );\n return `${result}<link rel=\"stylesheet\" href=\"${applyBasePath(`/${resolvedHref}`)}\">`;\n}\n\n/**\n * Generates the CSS style block and html root class for sandboxed preview iframes\n * (file viewer and pages HTML preview) to synchronize theme CSS variables,\n * fonts, link styling, and dark/light mode color-scheme without FOUC.\n */\nexport function getIframeThemeStyleHtml(): string {\n const isDark =\n typeof document !== \"undefined\" &&\n document.documentElement.classList.contains(\"dark-mode\");\n const customProperties: string[] = [];\n\n if (typeof document !== \"undefined\") {\n const styles = getComputedStyle(document.documentElement);\n for (let i = 0; i < styles.length; i++) {\n const prop = styles[i];\n if (prop.startsWith(\"--\")) {\n customProperties.push(`${prop}: ${styles.getPropertyValue(prop)};`);\n }\n }\n }\n\n return [\n \"<style>\",\n \" :root {\",\n ` color-scheme: ${isDark ? \"dark\" : \"light\"};`,\n ` overflow: hidden;`,\n ` line-height: 1.5;`,\n ` ${customProperties.join(\"\\n \")}`,\n \" }\",\n \" * {\",\n \" scrollbar-width: thin;\",\n \" scrollbar-color: var(--shadow-claw-border-color) transparent;\",\n \" }\",\n \" ::-webkit-scrollbar {\",\n \" height: 0.5rem;\",\n \" width: 0.5rem;\",\n \" }\",\n \" ::-webkit-scrollbar-track {\",\n \" background: transparent;\",\n \" }\",\n \" ::-webkit-scrollbar-thumb {\",\n \" background: var(--shadow-claw-border-color);\",\n \" border-radius: 0.25rem;\",\n \" }\",\n \" ::-webkit-scrollbar-thumb:hover {\",\n \" background: var(--shadow-claw-text-tertiary);\",\n \" }\",\n \" body {\",\n \" color: var(--shadow-claw-text-primary);\",\n \" background-color: var(--shadow-claw-bg-primary);\",\n \" font-family: var(--shadow-claw-font-sans);\",\n \" margin: 0;\",\n \" }\",\n \" pre, code, kbd, samp {\",\n \" font-family: var(--shadow-claw-font-mono);\",\n \" }\",\n \" a {\",\n \" color: var(--shadow-claw-link);\",\n \" text-decoration: underline;\",\n \" text-underline-offset: 0.125rem;\",\n \" }\",\n \" a:hover {\",\n \" color: var(--shadow-claw-link-hover);\",\n \" }\",\n \" img {\",\n \" max-width: 100%;\",\n \" height: auto;\",\n \" }\",\n \" ul {\",\n \" line-height: 1.5;\",\n \" }\",\n \" article {\",\n \" padding: 1rem 1.5rem 1rem 1rem;\",\n \" }\",\n \" article > h1, article > h2 {\",\n \" margin-top: 0;\",\n \" }\",\n \"</style>\",\n ].join(\"\\n\");\n}\n\nexport function getIframeHtmlClass(): string {\n const isDark =\n typeof document !== \"undefined\" &&\n document.documentElement.classList.contains(\"dark-mode\");\n\n return isDark ? \"dark-mode\" : \"light-mode\";\n}\n","/**\n * iframe-broadcast-proxy.ts\n *\n * Parent-side BroadcastChannel proxy for sandboxed iframes.\n * When allow-same-origin is omitted from preview iframes, the iframe operates\n * under an opaque (null) origin. Browser BroadcastChannel instances are partitioned\n * by origin, preventing direct communication between parent/worker tools and the iframe.\n *\n * This proxy is completely AGNOSTIC and generic. It dynamically tracks BroadcastChannels\n * instantiated on the parent origin and extracts channel names declaratively from tool\n * definitions registered via site-config/toolsStore.\n */\n\nexport class IframeBroadcastProxy {\n private commandChannels: Map<string, BroadcastChannel> = new Map();\n private originalBroadcastChannel: typeof BroadcastChannel | null = null;\n\n constructor(private getTargetWindow: () => WindowProxy | null) {\n if (typeof BroadcastChannel !== \"undefined\") {\n this.patchParentBroadcastChannel();\n }\n }\n\n /**\n * Automatically intercept BroadcastChannel creation on parent window to\n * dynamically track and forward any channel used by tools or parent scripts.\n */\n private patchParentBroadcastChannel(): void {\n if ((globalThis as any)._shadowClawParentBcPatched) {\n return;\n }\n (globalThis as any)._shadowClawParentBcPatched = true;\n\n const self = this;\n const NativeBc = globalThis.BroadcastChannel;\n this.originalBroadcastChannel = NativeBc;\n\n const WrappedBc = function (this: BroadcastChannel, channelName: string) {\n const instance = new NativeBc(channelName);\n self.registerChannel(channelName);\n return instance;\n } as any;\n\n WrappedBc.prototype = NativeBc.prototype;\n globalThis.BroadcastChannel = WrappedBc;\n }\n\n /**\n * Declaratively scan tool execution code definitions for BroadcastChannel names\n * and register them automatically.\n */\n public registerChannelsFromTools(\n tools: Array<{ execution?: { code?: string }; code?: string }>,\n ): void {\n if (!Array.isArray(tools)) return;\n\n const bcRegex = /new\\s+BroadcastChannel\\s*\\(\\s*['\"`]([^'\"`]+)['\"`]\\s*\\)/g;\n for (const tool of tools) {\n const code = tool.execution?.code || tool.code || \"\";\n if (!code) continue;\n\n let match: RegExpExecArray | null;\n bcRegex.lastIndex = 0;\n while ((match = bcRegex.exec(code)) !== null) {\n if (match[1]) {\n this.registerChannel(match[1]);\n }\n }\n }\n }\n\n /**\n * Register a channel name to forward parent messages to the sandboxed iframe.\n */\n public registerChannel(channelName: string): void {\n if (\n typeof BroadcastChannel === \"undefined\" ||\n !channelName ||\n channelName.endsWith(\"-results\") ||\n this.commandChannels.has(channelName)\n ) {\n return;\n }\n this.listenOnCommandChannel(channelName);\n }\n\n private listenOnCommandChannel(channelName: string): void {\n try {\n const NativeBc =\n this.originalBroadcastChannel || globalThis.BroadcastChannel;\n const bc = new NativeBc(channelName);\n bc.onmessage = (evt) => {\n const target = this.getTargetWindow();\n if (target) {\n target.postMessage(\n {\n type: \"shadow-claw-broadcast-command\",\n channel: channelName,\n payload: evt.data,\n },\n \"*\",\n );\n }\n };\n this.commandChannels.set(channelName, bc);\n } catch (e) {\n console.warn(\n `[IframeBroadcastProxy] Failed to listen on channel ${channelName}:`,\n e,\n );\n }\n }\n\n /**\n * Handle incoming broadcast result/message from the sandboxed iframe and relay it\n * to the parent-origin BroadcastChannel.\n */\n public handleResultFromIframe(\n sourceWindow: WindowProxy,\n channelName: string,\n payload: unknown,\n ): boolean {\n const target = this.getTargetWindow();\n if (target && sourceWindow !== target) {\n return false;\n }\n\n if (channelName) {\n try {\n const NativeBc =\n this.originalBroadcastChannel || globalThis.BroadcastChannel;\n const resBc = new NativeBc(channelName);\n resBc.postMessage(payload);\n resBc.close();\n return true;\n } catch (e) {\n console.warn(\n `[IframeBroadcastProxy] Failed to relay result for channel ${channelName}:`,\n e,\n );\n }\n }\n return false;\n }\n\n public dispose(): void {\n for (const bc of this.commandChannels.values()) {\n try {\n bc.close();\n } catch (e) {}\n }\n this.commandChannels.clear();\n }\n}\n","/**\n * iframe-storage-proxy.ts\n *\n * Parent-side storage implementation for the iframe storage bridge.\n * Provides a namespaced IndexedDB key-value store that the parent frame\n * uses to proxy storage operations on behalf of sandboxed iframes that\n * lack direct storage access due to opaque-origin isolation.\n *\n * Each page gets its own namespace to prevent cross-page data leakage.\n */\n\nconst DB_NAME = \"shadow-claw-iframe-storage\";\nconst DB_VERSION = 1;\nconst STORE_NAME = \"kv\";\n\nlet dbPromise: Promise<IDBDatabase> | null = null;\n\nfunction openDb(): Promise<IDBDatabase> {\n if (dbPromise) {\n return dbPromise;\n }\n\n dbPromise = new Promise<IDBDatabase>((resolve, reject) => {\n const request = indexedDB.open(DB_NAME, DB_VERSION);\n\n request.onupgradeneeded = () => {\n const db = request.result;\n if (!db.objectStoreNames.contains(STORE_NAME)) {\n db.createObjectStore(STORE_NAME);\n }\n };\n\n request.onsuccess = () => resolve(request.result);\n request.onerror = () => {\n dbPromise = null;\n reject(request.error);\n };\n });\n\n return dbPromise;\n}\n\n/**\n * Build a composite key from a namespace and item key.\n */\nfunction compositeKey(namespace: string, key: string): string {\n return `${namespace}\\0${key}`;\n}\n\n/**\n * Set a value in the namespaced store.\n */\nexport async function iframeStorageSet(\n namespace: string,\n key: string,\n value: unknown,\n): Promise<void> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readwrite\");\n tx.objectStore(STORE_NAME).put(value, compositeKey(namespace, key));\n tx.oncomplete = () => resolve();\n tx.onerror = () => reject(tx.error);\n });\n}\n\n/**\n * Get a single value from the namespaced store.\n */\nexport async function iframeStorageGet(\n namespace: string,\n key: string,\n): Promise<unknown> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readonly\");\n const req = tx.objectStore(STORE_NAME).get(compositeKey(namespace, key));\n req.onsuccess = () => resolve(req.result);\n req.onerror = () => reject(req.error);\n });\n}\n\n/**\n * Get all values for a namespace as a key-value object.\n */\nexport async function iframeStorageGetAll(\n namespace: string,\n): Promise<Record<string, unknown>> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readonly\");\n const store = tx.objectStore(STORE_NAME);\n const result: Record<string, unknown> = {};\n const prefix = `${namespace}\\0`;\n const cursorReq = store.openCursor();\n\n cursorReq.onsuccess = () => {\n const cursor = cursorReq.result;\n if (!cursor) {\n resolve(result);\n return;\n }\n const cursorKey =\n typeof cursor.key === \"string\" ? cursor.key : String(cursor.key);\n if (cursorKey.startsWith(prefix)) {\n result[cursorKey.slice(prefix.length)] = cursor.value;\n }\n cursor.continue();\n };\n\n cursorReq.onerror = () => reject(cursorReq.error);\n });\n}\n\n/**\n * Delete a single value from the namespaced store.\n */\nexport async function iframeStorageDelete(\n namespace: string,\n key: string,\n): Promise<void> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readwrite\");\n tx.objectStore(STORE_NAME).delete(compositeKey(namespace, key));\n tx.oncomplete = () => resolve();\n tx.onerror = () => reject(tx.error);\n });\n}\n\n/**\n * Clear all values for a namespace.\n */\nexport async function iframeStorageClear(namespace: string): Promise<void> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readwrite\");\n const store = tx.objectStore(STORE_NAME);\n const prefix = `${namespace}\\0`;\n const cursorReq = store.openCursor();\n\n cursorReq.onsuccess = () => {\n const cursor = cursorReq.result;\n if (!cursor) {\n resolve();\n return;\n }\n const cursorKey =\n typeof cursor.key === \"string\" ? cursor.key : String(cursor.key);\n if (cursorKey.startsWith(prefix)) {\n cursor.delete();\n }\n cursor.continue();\n };\n\n cursorReq.onerror = () => reject(cursorReq.error);\n });\n}\n","/**\n * Auto-generated and bundled inline script sources for sandboxed iframe previews.\n * Inlining these scripts into about:srcdoc with CSP nonces eliminates network roundtrips\n * and prevents browser ad-blockers / Brave Shields from blocking bridge scripts with ERR_BLOCKED_BY_CLIENT.\n */\n\nexport const IFRAME_STORAGE_BRIDGE_SCRIPT: string =\n '/**\\n * iframe-storage-bridge.js\\n *\\n * Injected into sandboxed preview iframes (via nonce-gated CSP) to provide\\n * a transparent storage proxy when the iframe is running in an opaque origin\\n * (i.e. sandbox without allow-same-origin).\\n *\\n * When IndexedDB and localStorage are unavailable due to opaque origin\\n * restrictions, this bridge intercepts storage calls and proxies them to\\n * the parent frame via postMessage. The parent frame performs the actual\\n * storage operations on the iframe\\'s behalf using a namespaced key-value\\n * store.\\n *\\n * SECURITY:\\n * - All messages use a unique type prefix to avoid collision.\\n * - The parent validates message source against the iframe\\'s contentWindow.\\n * - Storage is namespaced per-page to prevent cross-page data leakage.\\n * - This file is served same-origin and loaded with a per-render nonce.\\n */\\n\\n(function () {\\n \"use strict\";\\n\\n // Intercept and prevent unhandled sandboxed serviceWorker SecurityErrors from breaking execution flow\\n try {\\n window.addEventListener(\\n \"error\",\\n function (e) {\\n if (\\n e.message &&\\n (e.message.indexOf(\"serviceWorker\") !== -1 ||\\n e.message.indexOf(\"Service worker\") !== -1)\\n ) {\\n e.preventDefault();\\n e.stopImmediatePropagation();\\n }\\n },\\n true,\\n );\\n window.addEventListener(\\n \"unhandledrejection\",\\n function (e) {\\n if (\\n e.reason &&\\n (String(e.reason).indexOf(\"serviceWorker\") !== -1 ||\\n String(e.reason).indexOf(\"Service worker\") !== -1)\\n ) {\\n e.preventDefault();\\n e.stopImmediatePropagation();\\n }\\n },\\n true,\\n );\\n } catch (e) {}\\n\\n // Safely trap serviceWorker access in sandboxed cross-origin iframes\\n try {\\n var swDesc = {\\n get: function () {\\n return undefined;\\n },\\n configurable: true,\\n enumerable: false,\\n };\\n if (typeof Navigator !== \"undefined\" && Navigator.prototype) {\\n try {\\n Object.defineProperty(Navigator.prototype, \"serviceWorker\", swDesc);\\n } catch (e1) {}\\n }\\n if (typeof navigator !== \"undefined\") {\\n try {\\n Object.defineProperty(navigator, \"serviceWorker\", swDesc);\\n } catch (e2) {}\\n }\\n } catch (e) {\\n // ignore\\n }\\n\\n // Safely trap caches (CacheStorage) access in sandboxed cross-origin iframes\\n try {\\n var cacheDesc = {\\n get: function () {\\n return undefined;\\n },\\n configurable: true,\\n enumerable: false,\\n };\\n if (typeof Window !== \"undefined\" && Window.prototype) {\\n try {\\n Object.defineProperty(Window.prototype, \"caches\", cacheDesc);\\n } catch (e1) {}\\n }\\n if (typeof window !== \"undefined\") {\\n try {\\n Object.defineProperty(window, \"caches\", cacheDesc);\\n } catch (e2) {}\\n }\\n } catch (e) {\\n // ignore\\n }\\n\\n // Polyfill showOpenFilePicker using standard <input type=\"file\"> in sandboxed iframes\\n try {\\n Object.defineProperty(window, \"showOpenFilePicker\", {\\n value: function (options) {\\n return new Promise(function (resolve, reject) {\\n var input = document.createElement(\"input\");\\n input.type = \"file\";\\n if (options && options.multiple) {\\n input.multiple = true;\\n }\\n if (options && options.types && options.types.length > 0) {\\n var accept = [];\\n options.types.forEach(function (t) {\\n if (t.accept) {\\n Object.keys(t.accept).forEach(function (mime) {\\n accept.push(mime);\\n var exts = t.accept[mime];\\n if (Array.isArray(exts)) {\\n exts.forEach(function (ext) {\\n accept.push(ext);\\n });\\n }\\n });\\n }\\n });\\n if (accept.length > 0) {\\n input.accept = accept.join(\",\");\\n }\\n }\\n\\n input.onchange = function () {\\n if (!input.files || input.files.length === 0) {\\n reject(\\n new DOMException(\"The user aborted a request.\", \"AbortError\"),\\n );\\n return;\\n }\\n var handles = Array.from(input.files).map(function (file) {\\n return {\\n kind: \"file\",\\n name: file.name,\\n getFile: function () {\\n return Promise.resolve(file);\\n },\\n };\\n });\\n resolve(handles);\\n };\\n\\n input.oncancel = function () {\\n reject(\\n new DOMException(\"The user aborted a request.\", \"AbortError\"),\\n );\\n };\\n\\n input.click();\\n });\\n },\\n configurable: true,\\n writable: true,\\n });\\n } catch (e) {\\n // ignore\\n }\\n\\n // Polyfill showSaveFilePicker using standard <a download> in sandboxed iframes\\n try {\\n Object.defineProperty(window, \"showSaveFilePicker\", {\\n value: function (options) {\\n var filename = (options && options.suggestedName) || \"download\";\\n var mimeType = \"application/octet-stream\";\\n if (\\n options &&\\n options.types &&\\n options.types.length > 0 &&\\n options.types[0].accept\\n ) {\\n var mimes = Object.keys(options.types[0].accept);\\n if (mimes.length > 0) {\\n mimeType = mimes[0];\\n }\\n }\\n\\n var chunks = [];\\n\\n var writable = {\\n write: function (data) {\\n if (\\n data &&\\n typeof data === \"object\" &&\\n data.type === \"write\" &&\\n data.data\\n ) {\\n chunks.push(data.data);\\n } else if (data !== undefined && data !== null) {\\n chunks.push(data);\\n }\\n return Promise.resolve();\\n },\\n seek: function () {\\n return Promise.resolve();\\n },\\n truncate: function () {\\n return Promise.resolve();\\n },\\n close: function () {\\n return new Promise(function (resolve) {\\n try {\\n var blob = new Blob(chunks, { type: mimeType });\\n var url = URL.createObjectURL(blob);\\n var a = document.createElement(\"a\");\\n a.href = url;\\n a.download = filename;\\n a.style.display = \"none\";\\n document.body.appendChild(a);\\n a.click();\\n setTimeout(function () {\\n if (a.parentNode) {\\n a.parentNode.removeChild(a);\\n }\\n URL.revokeObjectURL(url);\\n }, 1000);\\n } catch (e) {\\n // ignore\\n }\\n resolve();\\n });\\n },\\n };\\n\\n var handle = {\\n kind: \"file\",\\n name: filename,\\n createWritable: function () {\\n return Promise.resolve(writable);\\n },\\n getFile: function () {\\n var blob = new Blob(chunks, { type: mimeType });\\n var file = new File([blob], filename, { type: mimeType });\\n return Promise.resolve(file);\\n },\\n };\\n\\n return Promise.resolve(handle);\\n },\\n configurable: true,\\n writable: true,\\n });\\n } catch (e) {\\n // ignore\\n }\\n\\n // Always install proxy immediately for sandboxed preview iframes.\\n installProxy();\\n\\n // ----------------------------------------------------------------\\n // Pending request tracking\\n // ----------------------------------------------------------------\\n var pendingRequests = {};\\n var requestIdCounter = 0;\\n\\n function sendRequest(method, args) {\\n return new Promise(function (resolve, reject) {\\n var requestId = \"sc-storage-\" + ++requestIdCounter;\\n pendingRequests[requestId] = { resolve: resolve, reject: reject };\\n window.parent.postMessage(\\n {\\n type: \"shadow-claw-storage-proxy\",\\n requestId: requestId,\\n method: method,\\n args: args,\\n },\\n \"*\",\\n );\\n\\n // Timeout after 10 seconds to avoid hanging forever.\\n setTimeout(function () {\\n if (pendingRequests[requestId]) {\\n delete pendingRequests[requestId];\\n reject(new Error(\"Storage proxy request timed out: \" + method));\\n }\\n }, 10000);\\n });\\n }\\n\\n window.addEventListener(\"message\", function (event) {\\n if (!event.data || event.data.type !== \"shadow-claw-storage-proxy-result\") {\\n return;\\n }\\n var requestId = event.data.requestId;\\n var pending = pendingRequests[requestId];\\n if (!pending) {\\n return;\\n }\\n delete pendingRequests[requestId];\\n if (event.data.error) {\\n pending.reject(new Error(event.data.error));\\n } else {\\n pending.resolve(event.data.result);\\n }\\n });\\n\\n // ----------------------------------------------------------------\\n // localStorage shim\\n // ----------------------------------------------------------------\\n function installProxy() {\\n // localStorage shim — backed by parent-proxied key-value store.\\n var localStorageShim = {\\n _cache: {},\\n\\n getItem: function (key) {\\n // Return cached value synchronously (best-effort).\\n // Async warm-up happens in the background.\\n return this._cache[key] !== undefined ? this._cache[key] : null;\\n },\\n\\n setItem: function (key, value) {\\n var stringValue = String(value);\\n this._cache[key] = stringValue;\\n sendRequest(\"setItem\", { key: key, value: stringValue }).catch(\\n function () {\\n // Silently ignore write failures\\n },\\n );\\n },\\n\\n removeItem: function (key) {\\n delete this._cache[key];\\n sendRequest(\"removeItem\", { key: key }).catch(function () {});\\n },\\n\\n clear: function () {\\n this._cache = {};\\n sendRequest(\"clear\", {}).catch(function () {});\\n },\\n\\n key: function (index) {\\n var keys = Object.keys(this._cache);\\n return index >= 0 && index < keys.length ? keys[index] : null;\\n },\\n\\n get length() {\\n return Object.keys(this._cache).length;\\n },\\n };\\n\\n // Warm up the cache from the parent.\\n sendRequest(\"getAllItems\", {})\\n .then(function (items) {\\n if (items && typeof items === \"object\") {\\n for (var k in items) {\\n if (Object.prototype.hasOwnProperty.call(items, k)) {\\n localStorageShim._cache[k] = items[k];\\n }\\n }\\n }\\n })\\n .catch(function () {});\\n\\n try {\\n Object.defineProperty(window, \"localStorage\", {\\n get: function () {\\n return localStorageShim;\\n },\\n configurable: true,\\n });\\n } catch (e) {\\n // If we can\\'t override localStorage, leave the native (broken) one.\\n }\\n\\n // ----------------------------------------------------------------\\n // IndexedDB shim — minimal proxy supporting open / transaction / objectStore CRUD\\n // ----------------------------------------------------------------\\n var IDBShimDatabase = function (name) {\\n this.name = name;\\n this._closed = false;\\n };\\n\\n IDBShimDatabase.prototype.close = function () {\\n this._closed = true;\\n };\\n\\n IDBShimDatabase.prototype.transaction = function (storeNames) {\\n return new IDBShimTransaction(this.name, storeNames);\\n };\\n\\n // Expose objectStoreNames for compatibility (always returns the default store).\\n Object.defineProperty(IDBShimDatabase.prototype, \"objectStoreNames\", {\\n get: function () {\\n return {\\n length: 1,\\n item: function () {\\n return \"__default__\";\\n },\\n contains: function () {\\n return true;\\n },\\n };\\n },\\n });\\n\\n var IDBShimTransaction = function (dbName, storeNames) {\\n this._dbName = dbName;\\n this._storeNames = storeNames;\\n this.oncomplete = null;\\n this.onerror = null;\\n this.onabort = null;\\n\\n // Fire oncomplete asynchronously.\\n var self = this;\\n setTimeout(function () {\\n if (typeof self.oncomplete === \"function\") {\\n self.oncomplete({ target: self });\\n }\\n }, 0);\\n };\\n\\n IDBShimTransaction.prototype.objectStore = function (name) {\\n return new IDBShimObjectStore(this._dbName, name);\\n };\\n\\n var IDBShimObjectStore = function (dbName, storeName) {\\n this._dbName = dbName;\\n this._storeName = storeName;\\n };\\n\\n IDBShimObjectStore.prototype.get = function (key) {\\n return createIDBRequest(\\n sendRequest(\"idb-get\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n key: key,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.getAll = function () {\\n return createIDBRequest(\\n sendRequest(\"idb-getAll\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.put = function (value, key) {\\n return createIDBRequest(\\n sendRequest(\"idb-put\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n key: key,\\n value: value,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.delete = function (key) {\\n return createIDBRequest(\\n sendRequest(\"idb-delete\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n key: key,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.clear = function () {\\n return createIDBRequest(\\n sendRequest(\"idb-clear\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.getAllKeys = function () {\\n return createIDBRequest(\\n sendRequest(\"idb-getAll\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n }).then(function (items) {\\n if (items && typeof items === \"object\") {\\n return Object.keys(items);\\n }\\n return [];\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.openKeyCursor = function () {\\n return this.openCursor();\\n };\\n\\n IDBShimObjectStore.prototype.openCursor = function () {\\n var request = {\\n result: null,\\n error: null,\\n onsuccess: null,\\n onerror: null,\\n readyState: \"pending\",\\n };\\n\\n sendRequest(\"idb-getAll\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n })\\n .then(function (items) {\\n var keys =\\n items && typeof items === \"object\" ? Object.keys(items) : [];\\n var index = 0;\\n\\n function advanceCursor() {\\n if (index >= keys.length) {\\n request.result = null;\\n request.readyState = \"done\";\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n return;\\n }\\n\\n var currentKey = keys[index];\\n var currentValue = items[currentKey];\\n\\n var cursor = {\\n key: currentKey,\\n primaryKey: currentKey,\\n value: currentValue,\\n continue: function () {\\n index++;\\n advanceCursor();\\n },\\n };\\n\\n request.result = cursor;\\n request.readyState = \"done\";\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n }\\n\\n advanceCursor();\\n })\\n .catch(function (err) {\\n request.error = err;\\n request.readyState = \"done\";\\n if (typeof request.onerror === \"function\") {\\n request.onerror({ target: request });\\n }\\n });\\n\\n return request;\\n };\\n\\n function createIDBRequest(promise) {\\n var request = {\\n result: undefined,\\n error: null,\\n onsuccess: null,\\n onerror: null,\\n readyState: \"pending\",\\n };\\n\\n promise\\n .then(function (result) {\\n request.result = result;\\n request.readyState = \"done\";\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n })\\n .catch(function (err) {\\n request.error = err;\\n request.readyState = \"done\";\\n if (typeof request.onerror === \"function\") {\\n request.onerror({ target: request });\\n }\\n });\\n\\n return request;\\n }\\n\\n // indexedDB.open() shim\\n var indexedDBShim = {\\n open: function (name) {\\n var request = {\\n result: null,\\n error: null,\\n onsuccess: null,\\n onerror: null,\\n onupgradeneeded: null,\\n readyState: \"pending\",\\n };\\n\\n // Simulate async open.\\n setTimeout(function () {\\n request.result = new IDBShimDatabase(name);\\n request.readyState = \"done\";\\n\\n // Fire onupgradeneeded first (for initial setup), then onsuccess.\\n if (typeof request.onupgradeneeded === \"function\") {\\n request.onupgradeneeded({\\n target: request,\\n oldVersion: 0,\\n newVersion: 1,\\n });\\n }\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n }, 0);\\n\\n return request;\\n },\\n\\n deleteDatabase: function (name) {\\n var request = createIDBRequest(\\n sendRequest(\"idb-deleteDatabase\", { dbName: name }),\\n );\\n return request;\\n },\\n };\\n\\n try {\\n Object.defineProperty(window, \"indexedDB\", {\\n get: function () {\\n return indexedDBShim;\\n },\\n configurable: true,\\n });\\n } catch (e) {\\n // If we can\\'t override, leave native.\\n }\\n }\\n})();\\n';\n\nexport const FILE_VIEWER_PREVIEW_BRIDGE_SCRIPT: string =\n '/**\\n * file-viewer-preview-bridge.js\\n *\\n * Injected into sandboxed preview iframes (file viewer + pages HTML preview)\\n * via a per-render nonce. Intercepts link clicks and posts them to the parent\\n * so the app can handle workspace-relative navigation.\\n *\\n * SECURITY: This file is served same-origin and loaded with a per-render nonce.\\n * The Trusted Types policy and nonce-gated CSP prevent any other scripts from\\n * running inside the sandboxed srcdoc iframe.\\n */\\n\\n(function () {\\n \"use strict\";\\n\\n // ---------------------------------------------------------------------------\\n // BroadcastChannel Opaque-Origin Proxy Bridge\\n // ---------------------------------------------------------------------------\\n // When allow-same-origin is omitted from sandboxed preview iframes, the iframe\\n // operates under a null (opaque) origin. Native BroadcastChannel instances are\\n // partitioned by origin, preventing direct communication between parent/worker\\n // tools and the iframe.\\n //\\n // This bridge wraps window.BroadcastChannel inside the iframe so that any\\n // message posted by iframe scripts (e.g., tool responses) is automatically\\n // relayed to the parent window via postMessage. It also listens for commands\\n // posted from the parent window and re-emits them to the iframe\\'s BroadcastChannel.\\n // ---------------------------------------------------------------------------\\n var isRelayingCommandFromParent = false;\\n\\n if (\\n typeof BroadcastChannel !== \"undefined\" &&\\n !window._shadowClawBcBridgeInstalled\\n ) {\\n window._shadowClawBcBridgeInstalled = true;\\n var NativeBroadcastChannel = window.BroadcastChannel;\\n var origPostMessage = NativeBroadcastChannel.prototype.postMessage;\\n\\n NativeBroadcastChannel.prototype.postMessage = function (message) {\\n origPostMessage.call(this, message);\\n if (isRelayingCommandFromParent) {\\n return;\\n }\\n try {\\n if (window.parent && window.parent !== window) {\\n window.parent.postMessage(\\n {\\n type: \"shadow-claw-broadcast-result\",\\n channel: this.name,\\n payload: message,\\n },\\n \"*\",\\n );\\n }\\n } catch (e) {\\n // Ignore postMessage transfer errors\\n }\\n };\\n }\\n\\n window.addEventListener(\"message\", function (event) {\\n if (!event.data || typeof event.data !== \"object\") {\\n return;\\n }\\n\\n if (event.data.type === \"shadow-claw-broadcast-command\") {\\n var channelName = event.data.channel;\\n var payload = event.data.payload;\\n if (channelName && typeof NativeBroadcastChannel !== \"undefined\") {\\n try {\\n var bc = new NativeBroadcastChannel(channelName);\\n isRelayingCommandFromParent = true;\\n bc.postMessage(payload);\\n isRelayingCommandFromParent = false;\\n bc.close();\\n } catch (e) {\\n isRelayingCommandFromParent = false;\\n // Ignore command relay errors\\n }\\n }\\n return;\\n }\\n\\n if (event.data.type === \"shadow-claw-theme-update\") {\\n if (event.data.customProperties) {\\n for (var key in event.data.customProperties) {\\n if (\\n Object.prototype.hasOwnProperty.call(\\n event.data.customProperties,\\n key,\\n )\\n ) {\\n document.documentElement.style.setProperty(\\n key,\\n event.data.customProperties[key],\\n );\\n }\\n }\\n }\\n\\n var isDark = event.data.theme === \"dark\";\\n if (isDark) {\\n document.documentElement.classList.add(\"dark-mode\");\\n document.documentElement.classList.remove(\"light-mode\");\\n if (document.body) {\\n document.body.classList.add(\"dark-mode\");\\n document.body.classList.remove(\"light-mode\");\\n }\\n } else {\\n document.documentElement.classList.add(\"light-mode\");\\n document.documentElement.classList.remove(\"dark-mode\");\\n if (document.body) {\\n document.body.classList.add(\"light-mode\");\\n document.body.classList.remove(\"dark-mode\");\\n }\\n }\\n try {\\n document.documentElement.style.colorScheme = isDark ? \"dark\" : \"light\";\\n } catch (e) {}\\n }\\n\\n if (event.data.type === \"shadow-claw-scroll-to-anchor\") {\\n var anchorId = event.data.anchor || \"\";\\n if (anchorId) {\\n var el =\\n document.getElementById(anchorId) ||\\n document.querySelector(\\'a[name=\"\\' + anchorId + \\'\"]\\');\\n if (el && typeof el.scrollIntoView === \"function\") {\\n el.scrollIntoView({ behavior: \"smooth\", block: \"start\" });\\n }\\n }\\n return;\\n }\\n\\n if (event.data.type === \"shadow-claw-update-url-params\") {\\n var searchStr = event.data.search || \"\";\\n if (searchStr) {\\n try {\\n window.history.replaceState(\\n null,\\n \"\",\\n window.location.pathname + searchStr,\\n );\\n } catch (e) {}\\n\\n try {\\n window.dispatchEvent(new Event(\"popstate\"));\\n window.dispatchEvent(new Event(\"locationchange\"));\\n } catch (e) {}\\n\\n var customEls = document.querySelectorAll(\"*\");\\n var retriggered = false;\\n for (var i = 0; i < customEls.length; i++) {\\n var el = customEls[i];\\n if (el.tagName && el.tagName.indexOf(\"-\") !== -1 && el.parentNode) {\\n try {\\n var cb = el.connectedCallback;\\n var clone = el.cloneNode(true);\\n if (typeof cb === \"function\") {\\n clone.connectedCallback = cb;\\n }\\n el.parentNode.replaceChild(clone, el);\\n if (typeof clone.connectedCallback === \"function\") {\\n try {\\n clone.connectedCallback();\\n } catch (e3) {}\\n }\\n retriggered = true;\\n } catch (err) {\\n if (typeof el.connectedCallback === \"function\") {\\n try {\\n el.connectedCallback();\\n retriggered = true;\\n } catch (e2) {}\\n }\\n }\\n }\\n }\\n\\n if (!retriggered) {\\n window.location.reload();\\n }\\n }\\n return;\\n }\\n });\\n\\n function isNavSuppressed(event) {\\n if (!event) return false;\\n var navAttributes = [\\n \"data-no-nav\",\\n \"data-no-swipe\",\\n \"data-no-page-nav\",\\n \"data-prevent-nav\",\\n \"data-prevent-page-nav\",\\n \"data-isolate-input\",\\n \"data-isolate-navigation\",\\n \"data-game-controls\",\\n ];\\n\\n var path =\\n typeof event.composedPath === \"function\" ? event.composedPath() : [];\\n\\n for (var i = 0; i < path.length; i++) {\\n var node = path[i];\\n if (node && node.nodeType === 1) {\\n var tag = (node.tagName || \"\").toLowerCase();\\n if (\\n tag === \"input\" ||\\n tag === \"textarea\" ||\\n tag === \"select\" ||\\n tag === \"option\" ||\\n node.isContentEditable ||\\n node.getAttribute(\"contenteditable\") === \"true\"\\n ) {\\n return true;\\n }\\n\\n for (var j = 0; j < navAttributes.length; j++) {\\n if (node.hasAttribute(navAttributes[j])) {\\n return true;\\n }\\n }\\n }\\n }\\n var target = event.target;\\n if (target && target.nodeType === 3) {\\n target = target.parentNode;\\n }\\n\\n if (target && target instanceof Element) {\\n var targetTag = (target.tagName || \"\").toLowerCase();\\n if (\\n targetTag === \"input\" ||\\n targetTag === \"textarea\" ||\\n targetTag === \"select\" ||\\n targetTag === \"option\" ||\\n target.isContentEditable ||\\n target.getAttribute(\"contenteditable\") === \"true\"\\n ) {\\n return true;\\n }\\n\\n for (var k = 0; k < navAttributes.length; k++) {\\n if (target.closest(\"[\" + navAttributes[k] + \"]\")) {\\n return true;\\n }\\n }\\n }\\n\\n return false;\\n }\\n\\n var touchStartX = 0;\\n var touchStartY = 0;\\n var touchStartTime = 0;\\n\\n document.addEventListener(\\n \"touchstart\",\\n function (event) {\\n if (isNavSuppressed(event)) {\\n touchStartX = 0;\\n touchStartY = 0;\\n touchStartTime = 0;\\n return;\\n }\\n if (event.touches && event.touches.length === 1) {\\n touchStartX = event.touches[0].clientX;\\n touchStartY = event.touches[0].clientY;\\n touchStartTime = Date.now();\\n }\\n },\\n { passive: true },\\n );\\n\\n document.addEventListener(\\n \"touchend\",\\n function (event) {\\n if (!touchStartTime || isNavSuppressed(event)) {\\n touchStartTime = 0;\\n return;\\n }\\n if (event.changedTouches && event.changedTouches.length === 1) {\\n var touchEndX = event.changedTouches[0].clientX;\\n var touchEndY = event.changedTouches[0].clientY;\\n var deltaTime = Date.now() - touchStartTime;\\n\\n var deltaX = touchEndX - touchStartX;\\n var deltaY = touchEndY - touchStartY;\\n\\n if (\\n Math.abs(deltaX) >= 50 &&\\n Math.abs(deltaX) > Math.abs(deltaY) &&\\n deltaTime <= 600\\n ) {\\n var direction = deltaX < 0 ? \"left\" : \"right\";\\n window.parent.postMessage(\\n { type: \"shadow-claw-swipe\", direction: direction },\\n \"*\",\\n );\\n }\\n }\\n touchStartTime = 0;\\n },\\n { passive: true },\\n );\\n\\n var mouseStartX = 0;\\n var mouseStartY = 0;\\n var mouseStartTime = 0;\\n var isMouseDown = false;\\n\\n document.addEventListener(\\n \"mousedown\",\\n function (event) {\\n if (event.button !== 0 || isNavSuppressed(event)) {\\n isMouseDown = false;\\n return;\\n }\\n isMouseDown = true;\\n mouseStartX = event.clientX;\\n mouseStartY = event.clientY;\\n mouseStartTime = Date.now();\\n },\\n { passive: true },\\n );\\n\\n document.addEventListener(\\n \"mouseup\",\\n function (event) {\\n if (!isMouseDown) {\\n return;\\n }\\n isMouseDown = false;\\n if (isNavSuppressed(event)) {\\n return;\\n }\\n\\n var selection = window.getSelection();\\n if (selection && selection.toString().length > 0) {\\n return;\\n }\\n\\n var mouseEndX = event.clientX;\\n var mouseEndY = event.clientY;\\n var deltaTime = Date.now() - mouseStartTime;\\n\\n var deltaX = mouseEndX - mouseStartX;\\n var deltaY = mouseEndY - mouseStartY;\\n\\n if (\\n Math.abs(deltaX) >= 50 &&\\n Math.abs(deltaX) > Math.abs(deltaY) &&\\n deltaTime <= 600\\n ) {\\n var direction = deltaX < 0 ? \"left\" : \"right\";\\n window.parent.postMessage(\\n { type: \"shadow-claw-swipe\", direction: direction },\\n \"*\",\\n );\\n }\\n },\\n { passive: true },\\n );\\n\\n document.addEventListener(\"click\", function (event) {\\n // Only handle unmodified primary clicks.\\n if (event.defaultPrevented || event.button !== 0) {\\n return;\\n }\\n\\n if (event.metaKey || event.ctrlKey || event.shiftKey || event.altKey) {\\n return;\\n }\\n\\n var target = event.target;\\n if (!target) {\\n return;\\n }\\n\\n if (target.nodeType === 3) {\\n {\\n // Node.TEXT_NODE;\\n }\\n\\n target = target.parentNode;\\n }\\n\\n if (!(target instanceof Element)) {\\n return;\\n }\\n\\n var link = target.closest(\"a\");\\n if (!(link instanceof HTMLAnchorElement)) {\\n return;\\n }\\n\\n var href = link.getAttribute(\"href\") || \"\";\\n if (!href) {\\n return;\\n }\\n\\n // Let fragment-only same-page anchors pass through normally.\\n if (\\n href.startsWith(\"#\") &&\\n !href.includes(\"?\") &&\\n !href.includes(\"groupId\")\\n ) {\\n return;\\n }\\n\\n // Intercept all links so sandboxed preview iframes never navigate away from srcdoc.\\n event.preventDefault();\\n\\n window.parent.postMessage(\\n {\\n type: \"shadow-claw-file-viewer-link\",\\n href: href,\\n target: link.getAttribute(\"target\") || \"\",\\n },\\n \"*\",\\n );\\n });\\n\\n var lastReportedHeight = -1;\\n\\n function reportHeight() {\\n var body = document.body;\\n var docEl = document.documentElement;\\n\\n if (!body && !docEl) {\\n return;\\n }\\n\\n // Temporarily collapse documentElement height so that scrollHeight reflects\\n // only the natural content size — not the height the parent previously\\n // injected into the iframe via style.height. Without this reset the\\n // browser keeps scrollHeight equal to the externally-set height, which\\n // creates a feedback loop that leaves a scrollbar on the parent at wide\\n // widths (the iframe reports its own height, the parent honours it, repeat).\\n var prevDocElHeight = docEl ? docEl.style.height : null;\\n if (docEl) {\\n docEl.style.height = \"0\";\\n }\\n\\n var height = Math.max(\\n body ? body.scrollHeight : 0,\\n body ? body.offsetHeight : 0,\\n );\\n\\n if (body && body.lastElementChild) {\\n try {\\n var lastEl = body.lastElementChild;\\n var rect = lastEl.getBoundingClientRect();\\n var bodyRect = body.getBoundingClientRect();\\n var lastElBottom = rect.bottom - bodyRect.top + (window.scrollY || 0);\\n if (lastElBottom > height) {\\n height = Math.ceil(lastElBottom);\\n }\\n } catch (e) {\\n // Fallback if bounding rect computation fails\\n }\\n }\\n\\n // Restore documentElement height.\\n if (docEl) {\\n docEl.style.height = prevDocElHeight || \"\";\\n }\\n\\n if (height > 0 && Math.abs(height - lastReportedHeight) > 1) {\\n lastReportedHeight = height;\\n window.parent.postMessage(\\n { type: \"shadow-claw-iframe-resize\", height: height },\\n \"*\",\\n );\\n }\\n }\\n\\n // Always schedule via rAF so layout is settled before measuring.\\n function scheduleReportHeight() {\\n if (typeof requestAnimationFrame === \"function\") {\\n requestAnimationFrame(reportHeight);\\n } else {\\n reportHeight();\\n }\\n }\\n\\n // First measurement: wait for DOM to be parsed.\\n // If the script runs during \"loading\" (sync <script> in <head>) we listen\\n // for DOMContentLoaded; otherwise the DOM is already ready so measure now.\\n if (document.readyState === \"loading\") {\\n document.addEventListener(\"DOMContentLoaded\", scheduleReportHeight);\\n } else {\\n scheduleReportHeight();\\n }\\n\\n // Re-measure after all sub-resources (images, fonts, etc.) have loaded,\\n // in case they affect the layout height.\\n window.addEventListener(\"load\", scheduleReportHeight);\\n\\n // Re-measure on viewport resize (e.g. window narrowed → text reflows taller).\\n window.addEventListener(\"resize\", scheduleReportHeight);\\n\\n // Ongoing: watch for dynamic content changes after initial load.\\n if (typeof ResizeObserver !== \"undefined\") {\\n var ro = new ResizeObserver(scheduleReportHeight);\\n if (document.documentElement) {\\n ro.observe(document.documentElement);\\n }\\n if (document.body) {\\n ro.observe(document.body);\\n }\\n }\\n})();\\n';\n\n/**\n * Escapes any closing script tags to ensure safe HTML interpolation.\n */\nexport function safeInlineScript(code: string): string {\n return code.replace(/<\\/script/gi, (m) => `<\\\\/${m.slice(2)}`);\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"iframe-bridge-scripts-Dx825LLG.js","names":[],"sources":["../../src/ui/iframe-theme.ts","../../src/components/shadow-claw-pages/utils/iframe-broadcast-proxy.ts","../../src/components/shadow-claw-pages/utils/iframe-storage-proxy.ts","../../src/components/shadow-claw-file-viewer/utils/iframe-bridge-scripts.ts"],"sourcesContent":["import { applyBasePath } from \"../core/app-routes.js\";\nimport { getSiteConfig } from \"../utils/site-config.js\";\n\n/**\n * Prefixes whose contents are flattened into the distribution root.\n */\nconst FLATTENED_STYLESHEET_PREFIXES = [\n \"pages/resources/\",\n \"pages/deps/\",\n \"resources/\",\n \"deps/\",\n \"pages/assets/\",\n \"pages/main/assets/\",\n];\n\n/**\n * Resolves a configured theme.stylesheet path to its actual distribution path.\n */\nexport function resolveThemeStylesheetHref(stylesheet: string): string {\n for (const prefix of FLATTENED_STYLESHEET_PREFIXES) {\n if (stylesheet.startsWith(prefix)) {\n return stylesheet.slice(prefix.length).replace(/^\\/+/, \"\");\n }\n }\n return stylesheet.replace(/^\\/+/, \"\");\n}\n\n/**\n * Generates an optional `<style>` or `<link rel=\"stylesheet\">` tag for the preview iframe\n * when an inline theme or theme stylesheet is configured.\n * When neither is configured, returns an empty string to avoid 404 requests.\n */\nexport function getIframeThemeStylesheetLink(siteConfig?: unknown): string {\n let config = siteConfig;\n if (!config && typeof document !== \"undefined\") {\n config = getSiteConfig();\n }\n\n let inlineThemeStyleText: string | undefined;\n if (typeof document !== \"undefined\") {\n let styleElementId = \"shadow-claw-theme\";\n if (config && typeof config === \"object\") {\n const customId = (config as { theme?: { styleElement?: unknown } }).theme\n ?.styleElement;\n if (typeof customId === \"string\" && customId.trim()) {\n styleElementId = customId.trim();\n }\n }\n const inlineStyle =\n document.getElementById(styleElementId) ||\n document.querySelector(\"style[data-shadow-claw-theme]\");\n if (inlineStyle?.textContent) {\n inlineThemeStyleText = inlineStyle.textContent;\n }\n }\n\n let stylesheet: string | undefined;\n if (config && typeof config === \"object\") {\n const rawTheme = (config as { theme?: { stylesheet?: unknown } }).theme;\n if (\n typeof rawTheme?.stylesheet === \"string\" &&\n rawTheme.stylesheet.trim()\n ) {\n stylesheet = rawTheme.stylesheet.trim();\n }\n }\n\n let result = \"\";\n if (inlineThemeStyleText) {\n result += `<style data-theme-style=\"true\">${inlineThemeStyleText}</style>`;\n }\n\n if (!stylesheet) {\n return result;\n }\n\n const isExternal =\n stylesheet.startsWith(\"http://\") ||\n stylesheet.startsWith(\"https://\") ||\n stylesheet.startsWith(\"//\");\n\n if (isExternal) {\n return `${result}<link rel=\"stylesheet\" href=\"${stylesheet}\">`;\n }\n\n // Runtime links must be site-root absolute (with the deployment base path):\n // srcdoc preview iframes set `<base href=\"/<base>/files/<group>/...\">`, so a\n // relative href would resolve under the file route and 404.\n const resolvedHref = resolveThemeStylesheetHref(stylesheet).replace(\n /^\\/+/,\n \"\",\n );\n return `${result}<link rel=\"stylesheet\" href=\"${applyBasePath(`/${resolvedHref}`)}\">`;\n}\n\n/**\n * Generates the CSS style block and html root class for sandboxed preview iframes\n * (file viewer and pages HTML preview) to synchronize theme CSS variables,\n * fonts, link styling, and dark/light mode color-scheme without FOUC.\n */\nexport function getIframeThemeStyleHtml(): string {\n const isDark =\n typeof document !== \"undefined\" &&\n document.documentElement.classList.contains(\"dark-mode\");\n const customProperties: string[] = [];\n\n if (typeof document !== \"undefined\") {\n const styles = getComputedStyle(document.documentElement);\n for (let i = 0; i < styles.length; i++) {\n const prop = styles[i];\n if (prop.startsWith(\"--\")) {\n customProperties.push(`${prop}: ${styles.getPropertyValue(prop)};`);\n }\n }\n }\n\n return [\n \"<style>\",\n \" :root {\",\n ` color-scheme: ${isDark ? \"dark\" : \"light\"};`,\n ` overflow: hidden;`,\n ` line-height: 1.5;`,\n ` ${customProperties.join(\"\\n \")}`,\n \" }\",\n \" * {\",\n \" scrollbar-width: thin;\",\n \" scrollbar-color: var(--shadow-claw-border-color) transparent;\",\n \" }\",\n \" ::-webkit-scrollbar {\",\n \" height: 0.5rem;\",\n \" width: 0.5rem;\",\n \" }\",\n \" ::-webkit-scrollbar-track {\",\n \" background: transparent;\",\n \" }\",\n \" ::-webkit-scrollbar-thumb {\",\n \" background: var(--shadow-claw-border-color);\",\n \" border-radius: 0.25rem;\",\n \" }\",\n \" ::-webkit-scrollbar-thumb:hover {\",\n \" background: var(--shadow-claw-text-tertiary);\",\n \" }\",\n \" body {\",\n \" color: var(--shadow-claw-text-primary);\",\n \" background-color: var(--shadow-claw-bg-primary);\",\n \" font-family: var(--shadow-claw-font-sans);\",\n \" margin: 0;\",\n \" }\",\n \" pre, code, kbd, samp {\",\n \" font-family: var(--shadow-claw-font-mono);\",\n \" }\",\n \" a {\",\n \" color: var(--shadow-claw-link);\",\n \" text-decoration: underline;\",\n \" text-underline-offset: 0.125rem;\",\n \" }\",\n \" a:hover {\",\n \" color: var(--shadow-claw-link-hover);\",\n \" }\",\n \" img {\",\n \" max-width: 100%;\",\n \" height: auto;\",\n \" }\",\n \" ul {\",\n \" line-height: 1.5;\",\n \" }\",\n \" article {\",\n \" padding: 1rem 1.5rem 1rem 1rem;\",\n \" }\",\n \" article > h1, article > h2 {\",\n \" margin-top: 0;\",\n \" }\",\n \"</style>\",\n ].join(\"\\n\");\n}\n\nexport function getIframeHtmlClass(): string {\n const isDark =\n typeof document !== \"undefined\" &&\n document.documentElement.classList.contains(\"dark-mode\");\n\n return isDark ? \"dark-mode\" : \"light-mode\";\n}\n","/**\n * iframe-broadcast-proxy.ts\n *\n * Parent-side BroadcastChannel proxy for sandboxed iframes.\n * When allow-same-origin is omitted from preview iframes, the iframe operates\n * under an opaque (null) origin. Browser BroadcastChannel instances are partitioned\n * by origin, preventing direct communication between parent/worker tools and the iframe.\n *\n * This proxy is completely AGNOSTIC and generic. It dynamically tracks BroadcastChannels\n * instantiated on the parent origin and extracts channel names declaratively from tool\n * definitions registered via site-config/toolsStore.\n */\n\nexport class IframeBroadcastProxy {\n private commandChannels: Map<string, BroadcastChannel> = new Map();\n private originalBroadcastChannel: typeof BroadcastChannel | null = null;\n\n constructor(private getTargetWindow: () => WindowProxy | null) {\n if (typeof BroadcastChannel !== \"undefined\") {\n this.patchParentBroadcastChannel();\n }\n }\n\n /**\n * Automatically intercept BroadcastChannel creation on parent window to\n * dynamically track and forward any channel used by tools or parent scripts.\n */\n private patchParentBroadcastChannel(): void {\n if ((globalThis as any)._shadowClawParentBcPatched) {\n return;\n }\n (globalThis as any)._shadowClawParentBcPatched = true;\n\n const self = this;\n const NativeBc = globalThis.BroadcastChannel;\n this.originalBroadcastChannel = NativeBc;\n\n const WrappedBc = function (this: BroadcastChannel, channelName: string) {\n const instance = new NativeBc(channelName);\n self.registerChannel(channelName);\n return instance;\n } as any;\n\n WrappedBc.prototype = NativeBc.prototype;\n globalThis.BroadcastChannel = WrappedBc;\n }\n\n /**\n * Declaratively scan tool execution code definitions for BroadcastChannel names\n * and register them automatically.\n */\n public registerChannelsFromTools(\n tools: Array<{ execution?: { code?: string }; code?: string }>,\n ): void {\n if (!Array.isArray(tools)) return;\n\n const bcRegex = /new\\s+BroadcastChannel\\s*\\(\\s*['\"`]([^'\"`]+)['\"`]\\s*\\)/g;\n for (const tool of tools) {\n const code = tool.execution?.code || tool.code || \"\";\n if (!code) continue;\n\n let match: RegExpExecArray | null;\n bcRegex.lastIndex = 0;\n while ((match = bcRegex.exec(code)) !== null) {\n if (match[1]) {\n this.registerChannel(match[1]);\n }\n }\n }\n }\n\n /**\n * Register a channel name to forward parent messages to the sandboxed iframe.\n */\n public registerChannel(channelName: string): void {\n if (\n typeof BroadcastChannel === \"undefined\" ||\n !channelName ||\n channelName.endsWith(\"-results\") ||\n this.commandChannels.has(channelName)\n ) {\n return;\n }\n this.listenOnCommandChannel(channelName);\n }\n\n private listenOnCommandChannel(channelName: string): void {\n try {\n const NativeBc =\n this.originalBroadcastChannel || globalThis.BroadcastChannel;\n const bc = new NativeBc(channelName);\n bc.onmessage = (evt) => {\n const target = this.getTargetWindow();\n if (target) {\n target.postMessage(\n {\n type: \"shadow-claw-broadcast-command\",\n channel: channelName,\n payload: evt.data,\n },\n \"*\",\n );\n }\n };\n this.commandChannels.set(channelName, bc);\n } catch (e) {\n console.warn(\n `[IframeBroadcastProxy] Failed to listen on channel ${channelName}:`,\n e,\n );\n }\n }\n\n /**\n * Handle incoming broadcast result/message from the sandboxed iframe and relay it\n * to the parent-origin BroadcastChannel.\n */\n public handleResultFromIframe(\n sourceWindow: WindowProxy,\n channelName: string,\n payload: unknown,\n ): boolean {\n const target = this.getTargetWindow();\n if (target && sourceWindow !== target) {\n return false;\n }\n\n if (channelName) {\n try {\n const NativeBc =\n this.originalBroadcastChannel || globalThis.BroadcastChannel;\n const resBc = new NativeBc(channelName);\n resBc.postMessage(payload);\n resBc.close();\n return true;\n } catch (e) {\n console.warn(\n `[IframeBroadcastProxy] Failed to relay result for channel ${channelName}:`,\n e,\n );\n }\n }\n return false;\n }\n\n public dispose(): void {\n for (const bc of this.commandChannels.values()) {\n try {\n bc.close();\n } catch (e) {}\n }\n this.commandChannels.clear();\n }\n}\n","/**\n * iframe-storage-proxy.ts\n *\n * Parent-side storage implementation for the iframe storage bridge.\n * Provides a namespaced IndexedDB key-value store that the parent frame\n * uses to proxy storage operations on behalf of sandboxed iframes that\n * lack direct storage access due to opaque-origin isolation.\n *\n * Each page gets its own namespace to prevent cross-page data leakage.\n */\n\nconst DB_NAME = \"shadow-claw-iframe-storage\";\nconst DB_VERSION = 1;\nconst STORE_NAME = \"kv\";\n\nlet dbPromise: Promise<IDBDatabase> | null = null;\n\nfunction openDb(): Promise<IDBDatabase> {\n if (dbPromise) {\n return dbPromise;\n }\n\n dbPromise = new Promise<IDBDatabase>((resolve, reject) => {\n const request = indexedDB.open(DB_NAME, DB_VERSION);\n\n request.onupgradeneeded = () => {\n const db = request.result;\n if (!db.objectStoreNames.contains(STORE_NAME)) {\n db.createObjectStore(STORE_NAME);\n }\n };\n\n request.onsuccess = () => resolve(request.result);\n request.onerror = () => {\n dbPromise = null;\n reject(request.error);\n };\n });\n\n return dbPromise;\n}\n\n/**\n * Build a composite key from a namespace and item key.\n */\nfunction compositeKey(namespace: string, key: string): string {\n return `${namespace}\\0${key}`;\n}\n\n/**\n * Set a value in the namespaced store.\n */\nexport async function iframeStorageSet(\n namespace: string,\n key: string,\n value: unknown,\n): Promise<void> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readwrite\");\n tx.objectStore(STORE_NAME).put(value, compositeKey(namespace, key));\n tx.oncomplete = () => resolve();\n tx.onerror = () => reject(tx.error);\n });\n}\n\n/**\n * Get a single value from the namespaced store.\n */\nexport async function iframeStorageGet(\n namespace: string,\n key: string,\n): Promise<unknown> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readonly\");\n const req = tx.objectStore(STORE_NAME).get(compositeKey(namespace, key));\n req.onsuccess = () => resolve(req.result);\n req.onerror = () => reject(req.error);\n });\n}\n\n/**\n * Get all values for a namespace as a key-value object.\n */\nexport async function iframeStorageGetAll(\n namespace: string,\n): Promise<Record<string, unknown>> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readonly\");\n const store = tx.objectStore(STORE_NAME);\n const result: Record<string, unknown> = {};\n const prefix = `${namespace}\\0`;\n const cursorReq = store.openCursor();\n\n cursorReq.onsuccess = () => {\n const cursor = cursorReq.result;\n if (!cursor) {\n resolve(result);\n return;\n }\n const cursorKey =\n typeof cursor.key === \"string\" ? cursor.key : String(cursor.key);\n if (cursorKey.startsWith(prefix)) {\n result[cursorKey.slice(prefix.length)] = cursor.value;\n }\n cursor.continue();\n };\n\n cursorReq.onerror = () => reject(cursorReq.error);\n });\n}\n\n/**\n * Delete a single value from the namespaced store.\n */\nexport async function iframeStorageDelete(\n namespace: string,\n key: string,\n): Promise<void> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readwrite\");\n tx.objectStore(STORE_NAME).delete(compositeKey(namespace, key));\n tx.oncomplete = () => resolve();\n tx.onerror = () => reject(tx.error);\n });\n}\n\n/**\n * Clear all values for a namespace.\n */\nexport async function iframeStorageClear(namespace: string): Promise<void> {\n const db = await openDb();\n return new Promise((resolve, reject) => {\n const tx = db.transaction(STORE_NAME, \"readwrite\");\n const store = tx.objectStore(STORE_NAME);\n const prefix = `${namespace}\\0`;\n const cursorReq = store.openCursor();\n\n cursorReq.onsuccess = () => {\n const cursor = cursorReq.result;\n if (!cursor) {\n resolve();\n return;\n }\n const cursorKey =\n typeof cursor.key === \"string\" ? cursor.key : String(cursor.key);\n if (cursorKey.startsWith(prefix)) {\n cursor.delete();\n }\n cursor.continue();\n };\n\n cursorReq.onerror = () => reject(cursorReq.error);\n });\n}\n","/**\n * Auto-generated and bundled inline script sources for sandboxed iframe previews.\n * Inlining these scripts into about:srcdoc with CSP nonces eliminates network roundtrips\n * and prevents browser ad-blockers / Brave Shields from blocking bridge scripts with ERR_BLOCKED_BY_CLIENT.\n */\n\nexport const IFRAME_STORAGE_BRIDGE_SCRIPT: string =\n '/**\\n * iframe-storage-bridge.js\\n *\\n * Injected into sandboxed preview iframes (via nonce-gated CSP) to provide\\n * a transparent storage proxy when the iframe is running in an opaque origin\\n * (i.e. sandbox without allow-same-origin).\\n *\\n * When IndexedDB and localStorage are unavailable due to opaque origin\\n * restrictions, this bridge intercepts storage calls and proxies them to\\n * the parent frame via postMessage. The parent frame performs the actual\\n * storage operations on the iframe\\'s behalf using a namespaced key-value\\n * store.\\n *\\n * SECURITY:\\n * - All messages use a unique type prefix to avoid collision.\\n * - The parent validates message source against the iframe\\'s contentWindow.\\n * - Storage is namespaced per-page to prevent cross-page data leakage.\\n * - This file is served same-origin and loaded with a per-render nonce.\\n */\\n\\n(function () {\\n \"use strict\";\\n\\n // Intercept and prevent unhandled sandboxed serviceWorker SecurityErrors from breaking execution flow\\n try {\\n window.addEventListener(\\n \"error\",\\n function (e) {\\n if (\\n e.message &&\\n (e.message.indexOf(\"serviceWorker\") !== -1 ||\\n e.message.indexOf(\"Service worker\") !== -1)\\n ) {\\n e.preventDefault();\\n e.stopImmediatePropagation();\\n }\\n },\\n true,\\n );\\n window.addEventListener(\\n \"unhandledrejection\",\\n function (e) {\\n if (\\n e.reason &&\\n (String(e.reason).indexOf(\"serviceWorker\") !== -1 ||\\n String(e.reason).indexOf(\"Service worker\") !== -1)\\n ) {\\n e.preventDefault();\\n e.stopImmediatePropagation();\\n }\\n },\\n true,\\n );\\n } catch (e) {}\\n\\n // Safely trap serviceWorker access in sandboxed cross-origin iframes\\n try {\\n var swDesc = {\\n get: function () {\\n return undefined;\\n },\\n configurable: true,\\n enumerable: false,\\n };\\n if (typeof Navigator !== \"undefined\" && Navigator.prototype) {\\n try {\\n Object.defineProperty(Navigator.prototype, \"serviceWorker\", swDesc);\\n } catch (e1) {}\\n }\\n if (typeof navigator !== \"undefined\") {\\n try {\\n Object.defineProperty(navigator, \"serviceWorker\", swDesc);\\n } catch (e2) {}\\n }\\n } catch (e) {\\n // ignore\\n }\\n\\n // Safely trap caches (CacheStorage) access in sandboxed cross-origin iframes\\n try {\\n var cacheDesc = {\\n get: function () {\\n return undefined;\\n },\\n configurable: true,\\n enumerable: false,\\n };\\n if (typeof Window !== \"undefined\" && Window.prototype) {\\n try {\\n Object.defineProperty(Window.prototype, \"caches\", cacheDesc);\\n } catch (e1) {}\\n }\\n if (typeof window !== \"undefined\") {\\n try {\\n Object.defineProperty(window, \"caches\", cacheDesc);\\n } catch (e2) {}\\n }\\n } catch (e) {\\n // ignore\\n }\\n\\n // Polyfill showOpenFilePicker using standard <input type=\"file\"> in sandboxed iframes\\n try {\\n Object.defineProperty(window, \"showOpenFilePicker\", {\\n value: function (options) {\\n return new Promise(function (resolve, reject) {\\n var input = document.createElement(\"input\");\\n input.type = \"file\";\\n if (options && options.multiple) {\\n input.multiple = true;\\n }\\n if (options && options.types && options.types.length > 0) {\\n var accept = [];\\n options.types.forEach(function (t) {\\n if (t.accept) {\\n Object.keys(t.accept).forEach(function (mime) {\\n accept.push(mime);\\n var exts = t.accept[mime];\\n if (Array.isArray(exts)) {\\n exts.forEach(function (ext) {\\n accept.push(ext);\\n });\\n }\\n });\\n }\\n });\\n if (accept.length > 0) {\\n input.accept = accept.join(\",\");\\n }\\n }\\n\\n input.onchange = function () {\\n if (!input.files || input.files.length === 0) {\\n reject(\\n new DOMException(\"The user aborted a request.\", \"AbortError\"),\\n );\\n return;\\n }\\n var handles = Array.from(input.files).map(function (file) {\\n return {\\n kind: \"file\",\\n name: file.name,\\n getFile: function () {\\n return Promise.resolve(file);\\n },\\n };\\n });\\n resolve(handles);\\n };\\n\\n input.oncancel = function () {\\n reject(\\n new DOMException(\"The user aborted a request.\", \"AbortError\"),\\n );\\n };\\n\\n input.click();\\n });\\n },\\n configurable: true,\\n writable: true,\\n });\\n } catch (e) {\\n // ignore\\n }\\n\\n // Polyfill showSaveFilePicker using standard <a download> in sandboxed iframes\\n try {\\n Object.defineProperty(window, \"showSaveFilePicker\", {\\n value: function (options) {\\n var filename = (options && options.suggestedName) || \"download\";\\n var mimeType = \"application/octet-stream\";\\n if (\\n options &&\\n options.types &&\\n options.types.length > 0 &&\\n options.types[0].accept\\n ) {\\n var mimes = Object.keys(options.types[0].accept);\\n if (mimes.length > 0) {\\n mimeType = mimes[0];\\n }\\n }\\n\\n var chunks = [];\\n\\n var writable = {\\n write: function (data) {\\n if (\\n data &&\\n typeof data === \"object\" &&\\n data.type === \"write\" &&\\n data.data\\n ) {\\n chunks.push(data.data);\\n } else if (data !== undefined && data !== null) {\\n chunks.push(data);\\n }\\n return Promise.resolve();\\n },\\n seek: function () {\\n return Promise.resolve();\\n },\\n truncate: function () {\\n return Promise.resolve();\\n },\\n close: function () {\\n return new Promise(function (resolve) {\\n try {\\n var blob = new Blob(chunks, { type: mimeType });\\n var url = URL.createObjectURL(blob);\\n var a = document.createElement(\"a\");\\n a.href = url;\\n a.download = filename;\\n a.style.display = \"none\";\\n document.body.appendChild(a);\\n a.click();\\n setTimeout(function () {\\n if (a.parentNode) {\\n a.parentNode.removeChild(a);\\n }\\n URL.revokeObjectURL(url);\\n }, 1000);\\n } catch (e) {\\n // ignore\\n }\\n resolve();\\n });\\n },\\n };\\n\\n var handle = {\\n kind: \"file\",\\n name: filename,\\n createWritable: function () {\\n return Promise.resolve(writable);\\n },\\n getFile: function () {\\n var blob = new Blob(chunks, { type: mimeType });\\n var file = new File([blob], filename, { type: mimeType });\\n return Promise.resolve(file);\\n },\\n };\\n\\n return Promise.resolve(handle);\\n },\\n configurable: true,\\n writable: true,\\n });\\n } catch (e) {\\n // ignore\\n }\\n\\n // Always install proxy immediately for sandboxed preview iframes.\\n installProxy();\\n\\n // ----------------------------------------------------------------\\n // Pending request tracking\\n // ----------------------------------------------------------------\\n var pendingRequests = {};\\n var requestIdCounter = 0;\\n\\n function sendRequest(method, args) {\\n return new Promise(function (resolve, reject) {\\n var requestId = \"sc-storage-\" + ++requestIdCounter;\\n pendingRequests[requestId] = { resolve: resolve, reject: reject };\\n window.parent.postMessage(\\n {\\n type: \"shadow-claw-storage-proxy\",\\n requestId: requestId,\\n method: method,\\n args: args,\\n },\\n \"*\",\\n );\\n\\n // Timeout after 10 seconds to avoid hanging forever.\\n setTimeout(function () {\\n if (pendingRequests[requestId]) {\\n delete pendingRequests[requestId];\\n reject(new Error(\"Storage proxy request timed out: \" + method));\\n }\\n }, 10000);\\n });\\n }\\n\\n window.addEventListener(\"message\", function (event) {\\n if (!event.data || event.data.type !== \"shadow-claw-storage-proxy-result\") {\\n return;\\n }\\n var requestId = event.data.requestId;\\n var pending = pendingRequests[requestId];\\n if (!pending) {\\n return;\\n }\\n delete pendingRequests[requestId];\\n if (event.data.error) {\\n pending.reject(new Error(event.data.error));\\n } else {\\n pending.resolve(event.data.result);\\n }\\n });\\n\\n // ----------------------------------------------------------------\\n // localStorage shim\\n // ----------------------------------------------------------------\\n function installProxy() {\\n // localStorage shim — backed by parent-proxied key-value store.\\n var localStorageShim = {\\n _cache: {},\\n\\n getItem: function (key) {\\n // Return cached value synchronously (best-effort).\\n // Async warm-up happens in the background.\\n return this._cache[key] !== undefined ? this._cache[key] : null;\\n },\\n\\n setItem: function (key, value) {\\n var stringValue = String(value);\\n this._cache[key] = stringValue;\\n sendRequest(\"setItem\", { key: key, value: stringValue }).catch(\\n function () {\\n // Silently ignore write failures\\n },\\n );\\n },\\n\\n removeItem: function (key) {\\n delete this._cache[key];\\n sendRequest(\"removeItem\", { key: key }).catch(function () {});\\n },\\n\\n clear: function () {\\n this._cache = {};\\n sendRequest(\"clear\", {}).catch(function () {});\\n },\\n\\n key: function (index) {\\n var keys = Object.keys(this._cache);\\n return index >= 0 && index < keys.length ? keys[index] : null;\\n },\\n\\n get length() {\\n return Object.keys(this._cache).length;\\n },\\n };\\n\\n // Warm up the cache from the parent.\\n sendRequest(\"getAllItems\", {})\\n .then(function (items) {\\n if (items && typeof items === \"object\") {\\n for (var k in items) {\\n if (Object.prototype.hasOwnProperty.call(items, k)) {\\n localStorageShim._cache[k] = items[k];\\n }\\n }\\n }\\n })\\n .catch(function () {});\\n\\n try {\\n Object.defineProperty(window, \"localStorage\", {\\n get: function () {\\n return localStorageShim;\\n },\\n configurable: true,\\n });\\n } catch (e) {\\n // If we can\\'t override localStorage, leave the native (broken) one.\\n }\\n\\n // ----------------------------------------------------------------\\n // IndexedDB shim — minimal proxy supporting open / transaction / objectStore CRUD\\n // ----------------------------------------------------------------\\n var IDBShimDatabase = function (name) {\\n this.name = name;\\n this._closed = false;\\n };\\n\\n IDBShimDatabase.prototype.close = function () {\\n this._closed = true;\\n };\\n\\n IDBShimDatabase.prototype.transaction = function (storeNames) {\\n return new IDBShimTransaction(this.name, storeNames);\\n };\\n\\n // Expose objectStoreNames for compatibility (always returns the default store).\\n Object.defineProperty(IDBShimDatabase.prototype, \"objectStoreNames\", {\\n get: function () {\\n return {\\n length: 1,\\n item: function () {\\n return \"__default__\";\\n },\\n contains: function () {\\n return true;\\n },\\n };\\n },\\n });\\n\\n var IDBShimTransaction = function (dbName, storeNames) {\\n this._dbName = dbName;\\n this._storeNames = storeNames;\\n this.oncomplete = null;\\n this.onerror = null;\\n this.onabort = null;\\n\\n // Fire oncomplete asynchronously.\\n var self = this;\\n setTimeout(function () {\\n if (typeof self.oncomplete === \"function\") {\\n self.oncomplete({ target: self });\\n }\\n }, 0);\\n };\\n\\n IDBShimTransaction.prototype.objectStore = function (name) {\\n return new IDBShimObjectStore(this._dbName, name);\\n };\\n\\n var IDBShimObjectStore = function (dbName, storeName) {\\n this._dbName = dbName;\\n this._storeName = storeName;\\n };\\n\\n IDBShimObjectStore.prototype.get = function (key) {\\n return createIDBRequest(\\n sendRequest(\"idb-get\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n key: key,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.getAll = function () {\\n return createIDBRequest(\\n sendRequest(\"idb-getAll\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.put = function (value, key) {\\n return createIDBRequest(\\n sendRequest(\"idb-put\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n key: key,\\n value: value,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.delete = function (key) {\\n return createIDBRequest(\\n sendRequest(\"idb-delete\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n key: key,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.clear = function () {\\n return createIDBRequest(\\n sendRequest(\"idb-clear\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.getAllKeys = function () {\\n return createIDBRequest(\\n sendRequest(\"idb-getAll\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n }).then(function (items) {\\n if (items && typeof items === \"object\") {\\n return Object.keys(items);\\n }\\n return [];\\n }),\\n );\\n };\\n\\n IDBShimObjectStore.prototype.openKeyCursor = function () {\\n return this.openCursor();\\n };\\n\\n IDBShimObjectStore.prototype.openCursor = function () {\\n var request = {\\n result: null,\\n error: null,\\n onsuccess: null,\\n onerror: null,\\n readyState: \"pending\",\\n };\\n\\n sendRequest(\"idb-getAll\", {\\n dbName: this._dbName,\\n storeName: this._storeName,\\n })\\n .then(function (items) {\\n var keys =\\n items && typeof items === \"object\" ? Object.keys(items) : [];\\n var index = 0;\\n\\n function advanceCursor() {\\n if (index >= keys.length) {\\n request.result = null;\\n request.readyState = \"done\";\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n return;\\n }\\n\\n var currentKey = keys[index];\\n var currentValue = items[currentKey];\\n\\n var cursor = {\\n key: currentKey,\\n primaryKey: currentKey,\\n value: currentValue,\\n continue: function () {\\n index++;\\n advanceCursor();\\n },\\n };\\n\\n request.result = cursor;\\n request.readyState = \"done\";\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n }\\n\\n advanceCursor();\\n })\\n .catch(function (err) {\\n request.error = err;\\n request.readyState = \"done\";\\n if (typeof request.onerror === \"function\") {\\n request.onerror({ target: request });\\n }\\n });\\n\\n return request;\\n };\\n\\n function createIDBRequest(promise) {\\n var request = {\\n result: undefined,\\n error: null,\\n onsuccess: null,\\n onerror: null,\\n readyState: \"pending\",\\n };\\n\\n promise\\n .then(function (result) {\\n request.result = result;\\n request.readyState = \"done\";\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n })\\n .catch(function (err) {\\n request.error = err;\\n request.readyState = \"done\";\\n if (typeof request.onerror === \"function\") {\\n request.onerror({ target: request });\\n }\\n });\\n\\n return request;\\n }\\n\\n // indexedDB.open() shim\\n var indexedDBShim = {\\n open: function (name) {\\n var request = {\\n result: null,\\n error: null,\\n onsuccess: null,\\n onerror: null,\\n onupgradeneeded: null,\\n readyState: \"pending\",\\n };\\n\\n // Simulate async open.\\n setTimeout(function () {\\n request.result = new IDBShimDatabase(name);\\n request.readyState = \"done\";\\n\\n // Fire onupgradeneeded first (for initial setup), then onsuccess.\\n if (typeof request.onupgradeneeded === \"function\") {\\n request.onupgradeneeded({\\n target: request,\\n oldVersion: 0,\\n newVersion: 1,\\n });\\n }\\n if (typeof request.onsuccess === \"function\") {\\n request.onsuccess({ target: request });\\n }\\n }, 0);\\n\\n return request;\\n },\\n\\n deleteDatabase: function (name) {\\n var request = createIDBRequest(\\n sendRequest(\"idb-deleteDatabase\", { dbName: name }),\\n );\\n return request;\\n },\\n };\\n\\n try {\\n Object.defineProperty(window, \"indexedDB\", {\\n get: function () {\\n return indexedDBShim;\\n },\\n configurable: true,\\n });\\n } catch (e) {\\n // If we can\\'t override, leave native.\\n }\\n }\\n})();\\n';\n\nexport const FILE_VIEWER_PREVIEW_BRIDGE_SCRIPT: string =\n '/**\\n * file-viewer-preview-bridge.js\\n *\\n * Injected into sandboxed preview iframes (file viewer + pages HTML preview)\\n * via a per-render nonce. Intercepts link clicks and posts them to the parent\\n * so the app can handle workspace-relative navigation.\\n *\\n * SECURITY: This file is served same-origin and loaded with a per-render nonce.\\n * The Trusted Types policy and nonce-gated CSP prevent any other scripts from\\n * running inside the sandboxed srcdoc iframe.\\n */\\n\\n(function () {\\n \"use strict\";\\n\\n // ---------------------------------------------------------------------------\\n // BroadcastChannel Opaque-Origin Proxy Bridge\\n // ---------------------------------------------------------------------------\\n // When allow-same-origin is omitted from sandboxed preview iframes, the iframe\\n // operates under a null (opaque) origin. Native BroadcastChannel instances are\\n // partitioned by origin, preventing direct communication between parent/worker\\n // tools and the iframe.\\n //\\n // This bridge wraps window.BroadcastChannel inside the iframe so that any\\n // message posted by iframe scripts (e.g., tool responses) is automatically\\n // relayed to the parent window via postMessage. It also listens for commands\\n // posted from the parent window and re-emits them to the iframe\\'s BroadcastChannel.\\n // ---------------------------------------------------------------------------\\n var isRelayingCommandFromParent = false;\\n\\n if (\\n typeof BroadcastChannel !== \"undefined\" &&\\n !window._shadowClawBcBridgeInstalled\\n ) {\\n window._shadowClawBcBridgeInstalled = true;\\n var NativeBroadcastChannel = window.BroadcastChannel;\\n var origPostMessage = NativeBroadcastChannel.prototype.postMessage;\\n\\n NativeBroadcastChannel.prototype.postMessage = function (message) {\\n origPostMessage.call(this, message);\\n if (isRelayingCommandFromParent) {\\n return;\\n }\\n try {\\n if (window.parent && window.parent !== window) {\\n window.parent.postMessage(\\n {\\n type: \"shadow-claw-broadcast-result\",\\n channel: this.name,\\n payload: message,\\n },\\n \"*\",\\n );\\n }\\n } catch (e) {\\n // Ignore postMessage transfer errors\\n }\\n };\\n }\\n\\n window.addEventListener(\"message\", function (event) {\\n if (!event.data || typeof event.data !== \"object\") {\\n return;\\n }\\n\\n if (event.data.type === \"shadow-claw-broadcast-command\") {\\n var channelName = event.data.channel;\\n var payload = event.data.payload;\\n if (channelName && typeof NativeBroadcastChannel !== \"undefined\") {\\n try {\\n var bc = new NativeBroadcastChannel(channelName);\\n isRelayingCommandFromParent = true;\\n bc.postMessage(payload);\\n isRelayingCommandFromParent = false;\\n bc.close();\\n } catch (e) {\\n isRelayingCommandFromParent = false;\\n // Ignore command relay errors\\n }\\n }\\n return;\\n }\\n\\n if (event.data.type === \"shadow-claw-theme-update\") {\\n if (event.data.customProperties) {\\n for (var key in event.data.customProperties) {\\n if (\\n Object.prototype.hasOwnProperty.call(\\n event.data.customProperties,\\n key,\\n )\\n ) {\\n document.documentElement.style.setProperty(\\n key,\\n event.data.customProperties[key],\\n );\\n }\\n }\\n }\\n\\n var isDark = event.data.theme === \"dark\";\\n if (isDark) {\\n document.documentElement.classList.add(\"dark-mode\");\\n document.documentElement.classList.remove(\"light-mode\");\\n if (document.body) {\\n document.body.classList.add(\"dark-mode\");\\n document.body.classList.remove(\"light-mode\");\\n }\\n } else {\\n document.documentElement.classList.add(\"light-mode\");\\n document.documentElement.classList.remove(\"dark-mode\");\\n if (document.body) {\\n document.body.classList.add(\"light-mode\");\\n document.body.classList.remove(\"dark-mode\");\\n }\\n }\\n try {\\n document.documentElement.style.colorScheme = isDark ? \"dark\" : \"light\";\\n } catch (e) {}\\n }\\n\\n if (event.data.type === \"shadow-claw-scroll-to-anchor\") {\\n var anchorId = event.data.anchor || \"\";\\n if (anchorId) {\\n var el =\\n document.getElementById(anchorId) ||\\n document.querySelector(\\'a[name=\"\\' + anchorId + \\'\"]\\');\\n if (el && typeof el.scrollIntoView === \"function\") {\\n el.scrollIntoView({ behavior: \"smooth\", block: \"start\" });\\n }\\n }\\n return;\\n }\\n\\n if (event.data.type === \"shadow-claw-update-url-params\") {\\n var searchStr = event.data.search || \"\";\\n if (searchStr) {\\n try {\\n window.history.replaceState(\\n null,\\n \"\",\\n window.location.pathname + searchStr,\\n );\\n } catch (e) {}\\n\\n try {\\n window.dispatchEvent(new Event(\"popstate\"));\\n window.dispatchEvent(new Event(\"locationchange\"));\\n } catch (e) {}\\n\\n var customEls = document.querySelectorAll(\"*\");\\n var retriggered = false;\\n for (var i = 0; i < customEls.length; i++) {\\n var el = customEls[i];\\n if (el.tagName && el.tagName.indexOf(\"-\") !== -1 && el.parentNode) {\\n try {\\n var cb = el.connectedCallback;\\n var clone = el.cloneNode(true);\\n if (typeof cb === \"function\") {\\n clone.connectedCallback = cb;\\n }\\n el.parentNode.replaceChild(clone, el);\\n if (typeof clone.connectedCallback === \"function\") {\\n try {\\n clone.connectedCallback();\\n } catch (e3) {}\\n }\\n retriggered = true;\\n } catch (err) {\\n if (typeof el.connectedCallback === \"function\") {\\n try {\\n el.connectedCallback();\\n retriggered = true;\\n } catch (e2) {}\\n }\\n }\\n }\\n }\\n\\n if (!retriggered) {\\n window.location.reload();\\n }\\n }\\n return;\\n }\\n });\\n\\n function isNavSuppressed(event) {\\n if (!event) return false;\\n var navAttributes = [\\n \"data-no-nav\",\\n \"data-no-swipe\",\\n \"data-no-page-nav\",\\n \"data-prevent-nav\",\\n \"data-prevent-page-nav\",\\n \"data-isolate-input\",\\n \"data-isolate-navigation\",\\n \"data-game-controls\",\\n ];\\n\\n var path =\\n typeof event.composedPath === \"function\" ? event.composedPath() : [];\\n\\n for (var i = 0; i < path.length; i++) {\\n var node = path[i];\\n if (node && node.nodeType === 1) {\\n var tag = (node.tagName || \"\").toLowerCase();\\n if (\\n tag === \"input\" ||\\n tag === \"textarea\" ||\\n tag === \"select\" ||\\n tag === \"option\" ||\\n node.isContentEditable ||\\n node.getAttribute(\"contenteditable\") === \"true\"\\n ) {\\n return true;\\n }\\n\\n for (var j = 0; j < navAttributes.length; j++) {\\n if (node.hasAttribute(navAttributes[j])) {\\n return true;\\n }\\n }\\n }\\n }\\n var target = event.target;\\n if (target && target.nodeType === 3) {\\n target = target.parentNode;\\n }\\n\\n if (target && target instanceof Element) {\\n var targetTag = (target.tagName || \"\").toLowerCase();\\n if (\\n targetTag === \"input\" ||\\n targetTag === \"textarea\" ||\\n targetTag === \"select\" ||\\n targetTag === \"option\" ||\\n target.isContentEditable ||\\n target.getAttribute(\"contenteditable\") === \"true\"\\n ) {\\n return true;\\n }\\n\\n for (var k = 0; k < navAttributes.length; k++) {\\n if (target.closest(\"[\" + navAttributes[k] + \"]\")) {\\n return true;\\n }\\n }\\n }\\n\\n return false;\\n }\\n\\n var touchStartX = 0;\\n var touchStartY = 0;\\n var touchStartTime = 0;\\n\\n document.addEventListener(\\n \"touchstart\",\\n function (event) {\\n if (isNavSuppressed(event)) {\\n touchStartX = 0;\\n touchStartY = 0;\\n touchStartTime = 0;\\n return;\\n }\\n if (event.touches && event.touches.length === 1) {\\n touchStartX = event.touches[0].clientX;\\n touchStartY = event.touches[0].clientY;\\n touchStartTime = Date.now();\\n }\\n },\\n { passive: true },\\n );\\n\\n document.addEventListener(\\n \"touchend\",\\n function (event) {\\n if (!touchStartTime || isNavSuppressed(event)) {\\n touchStartTime = 0;\\n return;\\n }\\n if (event.changedTouches && event.changedTouches.length === 1) {\\n var touchEndX = event.changedTouches[0].clientX;\\n var touchEndY = event.changedTouches[0].clientY;\\n var deltaTime = Date.now() - touchStartTime;\\n\\n var deltaX = touchEndX - touchStartX;\\n var deltaY = touchEndY - touchStartY;\\n\\n if (\\n Math.abs(deltaX) >= 50 &&\\n Math.abs(deltaX) > Math.abs(deltaY) &&\\n deltaTime <= 600\\n ) {\\n var direction = deltaX < 0 ? \"left\" : \"right\";\\n window.parent.postMessage(\\n { type: \"shadow-claw-swipe\", direction: direction },\\n \"*\",\\n );\\n }\\n }\\n touchStartTime = 0;\\n },\\n { passive: true },\\n );\\n\\n var mouseStartX = 0;\\n var mouseStartY = 0;\\n var mouseStartTime = 0;\\n var isMouseDown = false;\\n\\n document.addEventListener(\\n \"mousedown\",\\n function (event) {\\n if (event.button !== 0 || isNavSuppressed(event)) {\\n isMouseDown = false;\\n return;\\n }\\n isMouseDown = true;\\n mouseStartX = event.clientX;\\n mouseStartY = event.clientY;\\n mouseStartTime = Date.now();\\n },\\n { passive: true },\\n );\\n\\n document.addEventListener(\\n \"mouseup\",\\n function (event) {\\n if (!isMouseDown) {\\n return;\\n }\\n isMouseDown = false;\\n if (isNavSuppressed(event)) {\\n return;\\n }\\n\\n var selection = window.getSelection();\\n if (selection && selection.toString().length > 0) {\\n return;\\n }\\n\\n var mouseEndX = event.clientX;\\n var mouseEndY = event.clientY;\\n var deltaTime = Date.now() - mouseStartTime;\\n\\n var deltaX = mouseEndX - mouseStartX;\\n var deltaY = mouseEndY - mouseStartY;\\n\\n if (\\n Math.abs(deltaX) >= 50 &&\\n Math.abs(deltaX) > Math.abs(deltaY) &&\\n deltaTime <= 600\\n ) {\\n var direction = deltaX < 0 ? \"left\" : \"right\";\\n window.parent.postMessage(\\n { type: \"shadow-claw-swipe\", direction: direction },\\n \"*\",\\n );\\n }\\n },\\n { passive: true },\\n );\\n\\n document.addEventListener(\"click\", function (event) {\\n // Only handle unmodified primary clicks.\\n if (event.defaultPrevented || event.button !== 0) {\\n return;\\n }\\n\\n if (event.metaKey || event.ctrlKey || event.shiftKey || event.altKey) {\\n return;\\n }\\n\\n var target = event.target;\\n if (!target) {\\n return;\\n }\\n\\n if (target.nodeType === 3) {\\n {\\n // Node.TEXT_NODE;\\n }\\n\\n target = target.parentNode;\\n }\\n\\n if (!(target instanceof Element)) {\\n return;\\n }\\n\\n var link = target.closest(\"a\");\\n if (!(link instanceof HTMLAnchorElement)) {\\n return;\\n }\\n\\n var href = link.getAttribute(\"href\") || \"\";\\n if (!href) {\\n return;\\n }\\n\\n // Let fragment-only same-page anchors pass through normally.\\n if (\\n href.startsWith(\"#\") &&\\n !href.includes(\"?\") &&\\n !href.includes(\"groupId\")\\n ) {\\n return;\\n }\\n\\n // Intercept all links so sandboxed preview iframes never navigate away from srcdoc.\\n event.preventDefault();\\n\\n window.parent.postMessage(\\n {\\n type: \"shadow-claw-file-viewer-link\",\\n href: href,\\n target: link.getAttribute(\"target\") || \"\",\\n },\\n \"*\",\\n );\\n });\\n\\n var lastReportedHeight = -1;\\n\\n function reportHeight() {\\n var body = document.body;\\n var docEl = document.documentElement;\\n\\n if (!body && !docEl) {\\n return;\\n }\\n\\n // Temporarily collapse documentElement height so that scrollHeight reflects\\n // only the natural content size — not the height the parent previously\\n // injected into the iframe via style.height. Without this reset the\\n // browser keeps scrollHeight equal to the externally-set height, which\\n // creates a feedback loop that leaves a scrollbar on the parent at wide\\n // widths (the iframe reports its own height, the parent honours it, repeat).\\n var prevDocElHeight = docEl ? docEl.style.height : null;\\n if (docEl) {\\n docEl.style.height = \"0\";\\n }\\n\\n var height = Math.max(\\n body ? body.scrollHeight : 0,\\n body ? body.offsetHeight : 0,\\n );\\n\\n if (body && body.lastElementChild) {\\n try {\\n var lastEl = body.lastElementChild;\\n var rect = lastEl.getBoundingClientRect();\\n var bodyRect = body.getBoundingClientRect();\\n var lastElBottom = rect.bottom - bodyRect.top + (window.scrollY || 0);\\n if (lastElBottom > height) {\\n height = Math.ceil(lastElBottom);\\n }\\n } catch (e) {\\n // Fallback if bounding rect computation fails\\n }\\n }\\n\\n // Restore documentElement height.\\n if (docEl) {\\n docEl.style.height = prevDocElHeight || \"\";\\n }\\n\\n if (height > 0 && Math.abs(height - lastReportedHeight) > 1) {\\n lastReportedHeight = height;\\n window.parent.postMessage(\\n { type: \"shadow-claw-iframe-resize\", height: height },\\n \"*\",\\n );\\n }\\n }\\n\\n // Always schedule via rAF so layout is settled before measuring.\\n function scheduleReportHeight() {\\n if (typeof requestAnimationFrame === \"function\") {\\n requestAnimationFrame(reportHeight);\\n } else {\\n reportHeight();\\n }\\n }\\n\\n // First measurement: wait for DOM to be parsed.\\n // If the script runs during \"loading\" (sync <script> in <head>) we listen\\n // for DOMContentLoaded; otherwise the DOM is already ready so measure now.\\n if (document.readyState === \"loading\") {\\n document.addEventListener(\"DOMContentLoaded\", scheduleReportHeight);\\n } else {\\n scheduleReportHeight();\\n }\\n\\n // Re-measure after all sub-resources (images, fonts, etc.) have loaded,\\n // in case they affect the layout height.\\n window.addEventListener(\"load\", scheduleReportHeight);\\n\\n // Re-measure on viewport resize (e.g. window narrowed → text reflows taller).\\n window.addEventListener(\"resize\", scheduleReportHeight);\\n\\n // Ongoing: watch for dynamic content changes after initial load.\\n if (typeof ResizeObserver !== \"undefined\") {\\n var ro = new ResizeObserver(scheduleReportHeight);\\n if (document.documentElement) {\\n ro.observe(document.documentElement);\\n }\\n if (document.body) {\\n ro.observe(document.body);\\n }\\n }\\n})();\\n';\n\n/**\n * Escapes any closing script tags to ensure safe HTML interpolation.\n */\nexport function safeInlineScript(code: string): string {\n return code.replace(/<\\/script/gi, (m) => `<\\\\/${m.slice(2)}`);\n}\n"],"mappings":"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"}
package/dist/lib/index.js CHANGED
@@ -2,7 +2,7 @@ import ShadowClawElement from "./components/shadow-claw-element.js";
2
2
  import { computeDelay, sleep, yieldToMain } from "./utils/delay.js";
3
3
  import { ulid } from "./utils/ulid.js";
4
4
  import { escapeHtml, escapeJsonForHtmlScript, stripHtml, unescapeHtml } from "./utils/html.js";
5
- import { o as handleSpecialLinkNavigation, s as sanitizeHtml } from "./trusted-types-CfwZl_rr.js";
5
+ import { o as handleSpecialLinkNavigation, s as sanitizeHtml } from "./trusted-types-HwsGS5Nj.js";
6
6
  import { getNamespacedItem, getNamespacedStorageKey, removeNamespacedItem, setNamespacedItem } from "./utils/namespaced-storage.js";
7
7
  import { normalizeStringList } from "./utils/normalize-string-list.js";
8
8
  import { isPagePathAllowed } from "./utils/is-page-path-allowed.js";
@@ -12,50 +12,50 @@ import { applyJsonPatch } from "./utils/json-patch.js";
12
12
  import { isTruthyConfigValue, parseBooleanConfig } from "./utils/parse-boolean-config.js";
13
13
  import { parseStoredStringList } from "./utils/parse-stored-string-list.js";
14
14
  import { bufferToHex, computeSha256, toArrayBuffer } from "./utils/crypto.js";
15
- import { t as ShadowClaw } from "./shadow-claw-DoQ7fgl5.js";
16
- import { t as ShadowClawChat } from "./shadow-claw-chat-SGUDT31r.js";
15
+ import { t as ShadowClaw } from "./shadow-claw-CypGVlVO.js";
16
+ import { t as ShadowClawChat } from "./shadow-claw-chat-B92cPaft.js";
17
17
  import { IMAGE_MIME_TYPES, MIME_TYPES, getImageMimeType, getMimeType, guessMimeTypeFromFilename, inferAttachmentMimeType, isImagePath, isMimeType, mime } from "./utils/mime.js";
18
18
  import { createFrontmatterDetailsElement, createFrontmatterElement, renderFrontmatterMarkup, splitFrontmatter } from "./utils/frontmatter.js";
19
19
  import { basename, cleanFilename, sanitizeFilename } from "./utils/filename.js";
20
- import { t as ShadowClawA2UI } from "./shadow-claw-a2ui-Br6qJMs1.js";
20
+ import { t as ShadowClawA2UI } from "./shadow-claw-a2ui-lG0vQbW8.js";
21
21
  import { formatDateForFilename, formatTimestamp } from "./utils/date.js";
22
22
  import { t as ShadowClawPageHeaderActionButton } from "./shadow-claw-page-header-action-button-BXXm5b5N.js";
23
23
  import { ShadowClawA2UIInterceptor } from "./components/shadow-claw-a2ui-interceptor.js";
24
24
  import { ShadowClawDialog } from "./components/shadow-claw-dialog.js";
25
- import { t as ShadowClawPageHeader } from "./shadow-claw-page-header-DMGO-TSe.js";
26
- import { t as ShadowClawFiles } from "./shadow-claw-files-DN7irmE1.js";
25
+ import { t as ShadowClawPageHeader } from "./shadow-claw-page-header-C_Qr3xZM.js";
26
+ import { t as ShadowClawFiles } from "./shadow-claw-files-cT6HL7ye.js";
27
27
  import { t as ShadowClawEmptyState } from "./shadow-claw-empty-state-D9bnqWMF.js";
28
- import { t as ShadowClawFileViewer } from "./shadow-claw-file-viewer-C1V8WTiU.js";
28
+ import { t as ShadowClawFileViewer } from "./shadow-claw-file-viewer-DFfyP7s5.js";
29
29
  import { t as ShadowClawPdfViewer } from "./shadow-claw-pdf-viewer-D-7W4CFV.js";
30
- import { t as ShadowClawTasks } from "./shadow-claw-tasks-BjaxsmUx.js";
31
- import { n as ShadowClawTerminal } from "./shadow-claw-terminal-C-4wreFe.js";
30
+ import { t as ShadowClawTasks } from "./shadow-claw-tasks-Bg0uM15I.js";
31
+ import { n as ShadowClawTerminal } from "./shadow-claw-terminal-fyJPppY_.js";
32
32
  import { resolvePageScriptDependencies } from "./utils/resolve-page-script-dependencies.js";
33
33
  import { extractMarkdownDescription, formatSeoTitle, patchHtmlHeadMetadata, resolveCanonicalUrl } from "./utils/seo.js";
34
- import { t as ShadowClawPages } from "./shadow-claw-pages-BiRM6qiA.js";
34
+ import { t as ShadowClawPages } from "./shadow-claw-pages-BCo3ihZI.js";
35
35
  import { asNumber, asStringArray, asUidArray, coerce, coerceArray, coerceNumber, coerceStringArray, coerceUidArray } from "./utils/coerce.js";
36
36
  import { base64, base64ToBytes, bytesToBase64 } from "./utils/base64.js";
37
- import { t as ShadowClawSettings } from "./shadow-claw-settings-CcT5EK08.js";
38
- import { t as ShadowClawPeerJs } from "./shadow-claw-peerjs-BZu7jNSe.js";
39
- import { t as ShadowClawChannelConfig } from "./shadow-claw-channel-config-IKiL34tI.js";
40
- import { t as ShadowClawChannels } from "./shadow-claw-channels-JgEzuHWK.js";
41
- import { t as ShadowClawProviderModelPicker } from "./shadow-claw-provider-model-picker-BXYXEobD.js";
37
+ import { t as ShadowClawSettings } from "./shadow-claw-settings-BMwne0bh.js";
38
+ import { t as ShadowClawPeerJs } from "./shadow-claw-peerjs-CFNjfrY5.js";
39
+ import { t as ShadowClawChannelConfig } from "./shadow-claw-channel-config-DJpDovkF.js";
40
+ import { t as ShadowClawChannels } from "./shadow-claw-channels-DJLwRovH.js";
41
+ import { t as ShadowClawProviderModelPicker } from "./shadow-claw-provider-model-picker-B-Ct4yW-.js";
42
42
  import { t as ShadowClawProviderModuleSettings } from "./shadow-claw-provider-module-settings-3sCTnCSp.js";
43
- import { t as ShadowClawConversations } from "./shadow-claw-conversations-D23GJ7qo.js";
43
+ import { t as ShadowClawConversations } from "./shadow-claw-conversations-CsVyDOny.js";
44
44
  import { t as ShadowClawToast } from "./shadow-claw-toast-DEqsSFJH.js";
45
- import { t as ShadowClawTools } from "./shadow-claw-tools-COdrGZJk.js";
45
+ import { t as ShadowClawTools } from "./shadow-claw-tools-D0T8m3go.js";
46
46
  import { t as ShadowClawActions } from "./shadow-claw-actions-G99P9oxr.js";
47
47
  import { t as ShadowClawCard } from "./shadow-claw-card-D9azfSMu.js";
48
- import { t as ShadowClawAccounts } from "./shadow-claw-accounts-BTDILfWw.js";
49
- import { t as ShadowClawControlPlane } from "./shadow-claw-control-plane-CRWFZ3vD.js";
50
- import { t as ShadowClawGit } from "./shadow-claw-git-D-1oIh65.js";
51
- import { t as ShadowClawIntegrations } from "./shadow-claw-integrations-CZjnm7cM.js";
52
- import { t as ShadowClawLlm } from "./shadow-claw-llm-4Gefh5FN.js";
53
- import { t as ShadowClawMcpRemote } from "./shadow-claw-mcp-remote-B9ssb3YV.js";
54
- import { t as ShadowClawNetworking } from "./shadow-claw-networking-BN5BB4hb.js";
55
- import { t as ShadowClawNotifications } from "./shadow-claw-notifications-71KARtkY.js";
56
- import { t as ShadowClawStorage } from "./shadow-claw-storage-eTOpbvpi.js";
57
- import { t as ShadowClawTaskServer } from "./shadow-claw-task-server-DFImTUbw.js";
58
- import { t as ShadowClawWebvm } from "./shadow-claw-webvm-sxqVjO0L.js";
48
+ import { t as ShadowClawAccounts } from "./shadow-claw-accounts-CkqyCxwp.js";
49
+ import { t as ShadowClawControlPlane } from "./shadow-claw-control-plane-fvn-qyHj.js";
50
+ import { t as ShadowClawGit } from "./shadow-claw-git-Cv9mQgTx.js";
51
+ import { t as ShadowClawIntegrations } from "./shadow-claw-integrations-RZZ-m-Id.js";
52
+ import { t as ShadowClawLlm } from "./shadow-claw-llm-CKOYzPDp.js";
53
+ import { t as ShadowClawMcpRemote } from "./shadow-claw-mcp-remote-BKFROurv.js";
54
+ import { t as ShadowClawNetworking } from "./shadow-claw-networking-DYfiUQaH.js";
55
+ import { t as ShadowClawNotifications } from "./shadow-claw-notifications-JJlzriuX.js";
56
+ import { t as ShadowClawStorage } from "./shadow-claw-storage-DUY8B9m-.js";
57
+ import { t as ShadowClawTaskServer } from "./shadow-claw-task-server-yWeoA3eL.js";
58
+ import { t as ShadowClawWebvm } from "./shadow-claw-webvm-CQvzJwKI.js";
59
59
  import "./components/index.js";
60
60
  import { hasPathTraversal, normalizeWorkspacePath, toPosixPath, trimSlashes } from "./utils/normalize-workspace-path.js";
61
61
  import { HttpError } from "./utils/http-error.js";
@@ -1,5 +1,5 @@
1
1
  import { t as getConfig } from "./get-config-BWhs5HFF.js";
2
- import { r as CONFIG_KEYS } from "./config-DxNI3TlW.js";
2
+ import { r as CONFIG_KEYS } from "./config-BrHR97zt.js";
3
3
  import { t as setConfig } from "./set-config-CUadvYZ1.js";
4
4
 
5
5
  //#region src/components/shadow-claw/utils/clamp-chat-split-height.ts
@@ -129,4 +129,4 @@ async function initChatSplitResize(shadow, shadowClaw, handle, db) {
129
129
 
130
130
  //#endregion
131
131
  export { initChatSplitResize };
132
- //# sourceMappingURL=init-chat-split-resize-B0ODULx9.js.map
132
+ //# sourceMappingURL=init-chat-split-resize-Cc0bd2z9.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"init-chat-split-resize-B0ODULx9.js","names":[],"sources":["../../src/components/shadow-claw/utils/clamp-chat-split-height.ts","../../src/components/shadow-claw/utils/persist-chat-split-height.ts","../../src/components/shadow-claw/utils/set-chat-split-height.ts","../../src/components/shadow-claw/utils/init-chat-split-resize.ts"],"sourcesContent":["import { MIN_CHAT_SPLIT_HEIGHT_PX } from \"../constants.js\";\n\nexport function clampChatSplitHeight(\n shadow: ShadowRoot | null,\n px: number,\n): number {\n const mainContent = shadow?.querySelector(\".main-content\");\n\n if (!(mainContent instanceof HTMLElement)) {\n return Math.max(MIN_CHAT_SPLIT_HEIGHT_PX, px);\n }\n\n const containerHeight =\n mainContent.getBoundingClientRect().height || window.innerHeight || 600;\n const maxByContainer = Math.max(\n MIN_CHAT_SPLIT_HEIGHT_PX,\n containerHeight - 100,\n );\n\n return Math.max(MIN_CHAT_SPLIT_HEIGHT_PX, Math.min(maxByContainer, px));\n}\n","import { CONFIG_KEYS } from \"../../../config/config.js\";\nimport { setConfig } from \"../../../db/set-config.js\";\n\nimport type { ShadowClawDatabase } from \"../../../db/types.js\";\n\nexport async function persistChatSplitHeight(\n db: ShadowClawDatabase,\n px: number,\n): Promise<void> {\n if (!db) {\n return;\n }\n\n try {\n await setConfig(db, CONFIG_KEYS.CHAT_SPLIT_VIEW_HEIGHT, px);\n } catch {\n // Ignore persistence failures so resize remains usable in degraded test/runtime states.\n }\n}\n","import { clampChatSplitHeight } from \"./clamp-chat-split-height.js\";\n\nexport function setChatSplitHeight(\n shadow: ShadowRoot | null,\n px: number,\n): void {\n const mainContent = shadow?.querySelector(\".main-content\");\n\n if (!(mainContent instanceof HTMLElement)) {\n return;\n }\n\n const clamped = clampChatSplitHeight(shadow, px);\n mainContent.style.setProperty(\"--chat-split-height\", `${clamped}px`);\n}\n","import { CONFIG_KEYS } from \"../../../config/config.js\";\nimport { getConfig } from \"../../../db/get-config.js\";\n\nimport {\n DEFAULT_CHAT_SPLIT_HEIGHT_PX,\n MIN_CHAT_SPLIT_HEIGHT_PX,\n} from \"../constants.js\";\n\nimport { clampChatSplitHeight } from \"./clamp-chat-split-height.js\";\nimport { persistChatSplitHeight } from \"./persist-chat-split-height.js\";\nimport { setChatSplitHeight } from \"./set-chat-split-height.js\";\n\nimport type { ShadowClawDatabase } from \"../../../db/types.js\";\n\ninterface ChatSplitResizeHost {\n addCleanup: (fn: () => void) => void;\n}\n\nexport async function initChatSplitResize(\n shadow: ShadowRoot | null,\n shadowClaw: ChatSplitResizeHost,\n handle: HTMLElement,\n db: ShadowClawDatabase | undefined,\n): Promise<void> {\n if (!shadow || !handle) {\n return;\n }\n\n handle.setAttribute(\"tabindex\", \"0\");\n handle.setAttribute(\"role\", \"separator\");\n handle.setAttribute(\"aria-orientation\", \"horizontal\");\n handle.setAttribute(\"aria-label\", \"Resize chat panel height\");\n\n const getCurrentHeight = () => {\n const mainContent = shadow.querySelector(\".main-content\");\n if (!(mainContent instanceof HTMLElement)) {\n return DEFAULT_CHAT_SPLIT_HEIGHT_PX;\n }\n\n const stored = parseFloat(\n mainContent.style.getPropertyValue(\"--chat-split-height\"),\n );\n if (Number.isFinite(stored) && stored > 0) {\n return stored;\n }\n\n const chatPage = shadow.querySelector(\".chat-page\");\n return (\n (chatPage instanceof HTMLElement &&\n chatPage.getBoundingClientRect().height) ||\n DEFAULT_CHAT_SPLIT_HEIGHT_PX\n );\n };\n\n const updateAria = () => {\n const current = Math.round(\n clampChatSplitHeight(shadow, getCurrentHeight()),\n );\n const max = Math.round(\n clampChatSplitHeight(shadow, Number.MAX_SAFE_INTEGER),\n );\n handle.setAttribute(\"aria-valuemin\", String(MIN_CHAT_SPLIT_HEIGHT_PX));\n handle.setAttribute(\"aria-valuemax\", String(max));\n handle.setAttribute(\"aria-valuenow\", String(current));\n };\n\n try {\n const saved = db\n ? await getConfig(db, CONFIG_KEYS.CHAT_SPLIT_VIEW_HEIGHT)\n : undefined;\n\n if (typeof saved === \"number\" && Number.isFinite(saved) && saved > 0) {\n setChatSplitHeight(shadow, saved);\n } else if (typeof saved === \"string\" && !isNaN(parseFloat(saved))) {\n setChatSplitHeight(shadow, parseFloat(saved));\n } else {\n setChatSplitHeight(shadow, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n }\n } catch {\n setChatSplitHeight(shadow, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n }\n\n let activePointerId: number | null = null;\n let startY = 0;\n let startHeight = 0;\n\n const onPointerMove = (event: PointerEvent) => {\n if (event.pointerId !== activePointerId) {\n return;\n }\n\n // Dragging handle UP (delta > 0) increases height of bottom chat panel\n const delta = startY - event.clientY;\n const nextHeight = startHeight + delta;\n setChatSplitHeight(shadow, nextHeight);\n updateAria();\n };\n\n const stopResize = () => {\n if (activePointerId === null) {\n return;\n }\n\n activePointerId = null;\n handle.classList.remove(\"active\");\n document.removeEventListener(\"pointermove\", onPointerMove);\n\n const mainContent = shadow.querySelector(\".main-content\");\n if (mainContent instanceof HTMLElement) {\n const value = parseFloat(\n mainContent.style.getPropertyValue(\"--chat-split-height\"),\n );\n if (Number.isFinite(value) && value > 0 && db) {\n void persistChatSplitHeight(db, value);\n }\n }\n };\n\n const onPointerUp = (event: PointerEvent) => {\n if (event.pointerId !== activePointerId) {\n return;\n }\n\n stopResize();\n };\n\n handle.addEventListener(\"pointerdown\", (event: PointerEvent) => {\n if (\n event.pointerType === \"mouse\" &&\n event.button !== 0 &&\n event.button !== -1\n ) {\n return;\n }\n\n if (window.innerWidth < 896) {\n return;\n }\n\n event.preventDefault();\n activePointerId = event.pointerId;\n startY = event.clientY;\n const chatPage = shadow.querySelector(\".chat-page\");\n startHeight =\n chatPage instanceof HTMLElement &&\n chatPage.getBoundingClientRect().height > 0\n ? chatPage.getBoundingClientRect().height\n : getCurrentHeight();\n handle.classList.add(\"active\");\n\n handle.setPointerCapture(event.pointerId);\n document.addEventListener(\"pointermove\", onPointerMove);\n });\n\n handle.addEventListener(\"pointerup\", onPointerUp);\n handle.addEventListener(\"pointercancel\", stopResize);\n handle.addEventListener(\"dblclick\", () => {\n setChatSplitHeight(shadow, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n if (db) {\n void persistChatSplitHeight(db, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n }\n\n updateAria();\n });\n\n handle.addEventListener(\"keydown\", (event: KeyboardEvent) => {\n if (window.innerWidth < 896) {\n return;\n }\n\n const step = event.shiftKey ? 32 : 12;\n const current = getCurrentHeight();\n let next: number | null = null;\n\n if (event.key === \"ArrowUp\") {\n next = current + step;\n } else if (event.key === \"ArrowDown\") {\n next = current - step;\n } else if (event.key === \"Home\") {\n next = MIN_CHAT_SPLIT_HEIGHT_PX;\n } else if (event.key === \"End\") {\n next = clampChatSplitHeight(shadow, Number.MAX_SAFE_INTEGER);\n }\n\n if (next === null) {\n return;\n }\n\n event.preventDefault();\n setChatSplitHeight(shadow, next);\n updateAria();\n if (db) {\n void persistChatSplitHeight(\n db,\n clampChatSplitHeight(shadow, getCurrentHeight()),\n );\n }\n });\n\n updateAria();\n\n shadowClaw.addCleanup(() => {\n stopResize();\n handle.removeEventListener(\"pointerup\", onPointerUp);\n handle.removeEventListener(\"pointercancel\", stopResize);\n });\n}\n"],"mappings":"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"}
1
+ {"version":3,"file":"init-chat-split-resize-Cc0bd2z9.js","names":[],"sources":["../../src/components/shadow-claw/utils/clamp-chat-split-height.ts","../../src/components/shadow-claw/utils/persist-chat-split-height.ts","../../src/components/shadow-claw/utils/set-chat-split-height.ts","../../src/components/shadow-claw/utils/init-chat-split-resize.ts"],"sourcesContent":["import { MIN_CHAT_SPLIT_HEIGHT_PX } from \"../constants.js\";\n\nexport function clampChatSplitHeight(\n shadow: ShadowRoot | null,\n px: number,\n): number {\n const mainContent = shadow?.querySelector(\".main-content\");\n\n if (!(mainContent instanceof HTMLElement)) {\n return Math.max(MIN_CHAT_SPLIT_HEIGHT_PX, px);\n }\n\n const containerHeight =\n mainContent.getBoundingClientRect().height || window.innerHeight || 600;\n const maxByContainer = Math.max(\n MIN_CHAT_SPLIT_HEIGHT_PX,\n containerHeight - 100,\n );\n\n return Math.max(MIN_CHAT_SPLIT_HEIGHT_PX, Math.min(maxByContainer, px));\n}\n","import { CONFIG_KEYS } from \"../../../config/config.js\";\nimport { setConfig } from \"../../../db/set-config.js\";\n\nimport type { ShadowClawDatabase } from \"../../../db/types.js\";\n\nexport async function persistChatSplitHeight(\n db: ShadowClawDatabase,\n px: number,\n): Promise<void> {\n if (!db) {\n return;\n }\n\n try {\n await setConfig(db, CONFIG_KEYS.CHAT_SPLIT_VIEW_HEIGHT, px);\n } catch {\n // Ignore persistence failures so resize remains usable in degraded test/runtime states.\n }\n}\n","import { clampChatSplitHeight } from \"./clamp-chat-split-height.js\";\n\nexport function setChatSplitHeight(\n shadow: ShadowRoot | null,\n px: number,\n): void {\n const mainContent = shadow?.querySelector(\".main-content\");\n\n if (!(mainContent instanceof HTMLElement)) {\n return;\n }\n\n const clamped = clampChatSplitHeight(shadow, px);\n mainContent.style.setProperty(\"--chat-split-height\", `${clamped}px`);\n}\n","import { CONFIG_KEYS } from \"../../../config/config.js\";\nimport { getConfig } from \"../../../db/get-config.js\";\n\nimport {\n DEFAULT_CHAT_SPLIT_HEIGHT_PX,\n MIN_CHAT_SPLIT_HEIGHT_PX,\n} from \"../constants.js\";\n\nimport { clampChatSplitHeight } from \"./clamp-chat-split-height.js\";\nimport { persistChatSplitHeight } from \"./persist-chat-split-height.js\";\nimport { setChatSplitHeight } from \"./set-chat-split-height.js\";\n\nimport type { ShadowClawDatabase } from \"../../../db/types.js\";\n\ninterface ChatSplitResizeHost {\n addCleanup: (fn: () => void) => void;\n}\n\nexport async function initChatSplitResize(\n shadow: ShadowRoot | null,\n shadowClaw: ChatSplitResizeHost,\n handle: HTMLElement,\n db: ShadowClawDatabase | undefined,\n): Promise<void> {\n if (!shadow || !handle) {\n return;\n }\n\n handle.setAttribute(\"tabindex\", \"0\");\n handle.setAttribute(\"role\", \"separator\");\n handle.setAttribute(\"aria-orientation\", \"horizontal\");\n handle.setAttribute(\"aria-label\", \"Resize chat panel height\");\n\n const getCurrentHeight = () => {\n const mainContent = shadow.querySelector(\".main-content\");\n if (!(mainContent instanceof HTMLElement)) {\n return DEFAULT_CHAT_SPLIT_HEIGHT_PX;\n }\n\n const stored = parseFloat(\n mainContent.style.getPropertyValue(\"--chat-split-height\"),\n );\n if (Number.isFinite(stored) && stored > 0) {\n return stored;\n }\n\n const chatPage = shadow.querySelector(\".chat-page\");\n return (\n (chatPage instanceof HTMLElement &&\n chatPage.getBoundingClientRect().height) ||\n DEFAULT_CHAT_SPLIT_HEIGHT_PX\n );\n };\n\n const updateAria = () => {\n const current = Math.round(\n clampChatSplitHeight(shadow, getCurrentHeight()),\n );\n const max = Math.round(\n clampChatSplitHeight(shadow, Number.MAX_SAFE_INTEGER),\n );\n handle.setAttribute(\"aria-valuemin\", String(MIN_CHAT_SPLIT_HEIGHT_PX));\n handle.setAttribute(\"aria-valuemax\", String(max));\n handle.setAttribute(\"aria-valuenow\", String(current));\n };\n\n try {\n const saved = db\n ? await getConfig(db, CONFIG_KEYS.CHAT_SPLIT_VIEW_HEIGHT)\n : undefined;\n\n if (typeof saved === \"number\" && Number.isFinite(saved) && saved > 0) {\n setChatSplitHeight(shadow, saved);\n } else if (typeof saved === \"string\" && !isNaN(parseFloat(saved))) {\n setChatSplitHeight(shadow, parseFloat(saved));\n } else {\n setChatSplitHeight(shadow, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n }\n } catch {\n setChatSplitHeight(shadow, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n }\n\n let activePointerId: number | null = null;\n let startY = 0;\n let startHeight = 0;\n\n const onPointerMove = (event: PointerEvent) => {\n if (event.pointerId !== activePointerId) {\n return;\n }\n\n // Dragging handle UP (delta > 0) increases height of bottom chat panel\n const delta = startY - event.clientY;\n const nextHeight = startHeight + delta;\n setChatSplitHeight(shadow, nextHeight);\n updateAria();\n };\n\n const stopResize = () => {\n if (activePointerId === null) {\n return;\n }\n\n activePointerId = null;\n handle.classList.remove(\"active\");\n document.removeEventListener(\"pointermove\", onPointerMove);\n\n const mainContent = shadow.querySelector(\".main-content\");\n if (mainContent instanceof HTMLElement) {\n const value = parseFloat(\n mainContent.style.getPropertyValue(\"--chat-split-height\"),\n );\n if (Number.isFinite(value) && value > 0 && db) {\n void persistChatSplitHeight(db, value);\n }\n }\n };\n\n const onPointerUp = (event: PointerEvent) => {\n if (event.pointerId !== activePointerId) {\n return;\n }\n\n stopResize();\n };\n\n handle.addEventListener(\"pointerdown\", (event: PointerEvent) => {\n if (\n event.pointerType === \"mouse\" &&\n event.button !== 0 &&\n event.button !== -1\n ) {\n return;\n }\n\n if (window.innerWidth < 896) {\n return;\n }\n\n event.preventDefault();\n activePointerId = event.pointerId;\n startY = event.clientY;\n const chatPage = shadow.querySelector(\".chat-page\");\n startHeight =\n chatPage instanceof HTMLElement &&\n chatPage.getBoundingClientRect().height > 0\n ? chatPage.getBoundingClientRect().height\n : getCurrentHeight();\n handle.classList.add(\"active\");\n\n handle.setPointerCapture(event.pointerId);\n document.addEventListener(\"pointermove\", onPointerMove);\n });\n\n handle.addEventListener(\"pointerup\", onPointerUp);\n handle.addEventListener(\"pointercancel\", stopResize);\n handle.addEventListener(\"dblclick\", () => {\n setChatSplitHeight(shadow, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n if (db) {\n void persistChatSplitHeight(db, DEFAULT_CHAT_SPLIT_HEIGHT_PX);\n }\n\n updateAria();\n });\n\n handle.addEventListener(\"keydown\", (event: KeyboardEvent) => {\n if (window.innerWidth < 896) {\n return;\n }\n\n const step = event.shiftKey ? 32 : 12;\n const current = getCurrentHeight();\n let next: number | null = null;\n\n if (event.key === \"ArrowUp\") {\n next = current + step;\n } else if (event.key === \"ArrowDown\") {\n next = current - step;\n } else if (event.key === \"Home\") {\n next = MIN_CHAT_SPLIT_HEIGHT_PX;\n } else if (event.key === \"End\") {\n next = clampChatSplitHeight(shadow, Number.MAX_SAFE_INTEGER);\n }\n\n if (next === null) {\n return;\n }\n\n event.preventDefault();\n setChatSplitHeight(shadow, next);\n updateAria();\n if (db) {\n void persistChatSplitHeight(\n db,\n clampChatSplitHeight(shadow, getCurrentHeight()),\n );\n }\n });\n\n updateAria();\n\n shadowClaw.addCleanup(() => {\n stopResize();\n handle.removeEventListener(\"pointerup\", onPointerUp);\n handle.removeEventListener(\"pointercancel\", stopResize);\n });\n}\n"],"mappings":"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"}
@@ -1,9 +1,9 @@
1
1
  import { i as __toESM } from "./rolldown-runtime-DwyhSnWe.js";
2
2
  import { o as getDb } from "./get-config-BWhs5HFF.js";
3
3
  import { t as require_browser } from "./browser-sqa-Vhnx.js";
4
- import { r as CONFIG_KEYS } from "./config-DxNI3TlW.js";
5
- import { o as getDeploymentNamespace } from "./app-routes-DJdIjp2V.js";
6
- import { t as toolsStore, u as getAllTasks } from "./tools-Beuyh8y1.js";
4
+ import { r as CONFIG_KEYS } from "./config-BrHR97zt.js";
5
+ import { a as getDeploymentNamespace } from "./app-routes-BXiRvlNl.js";
6
+ import { t as toolsStore, u as getAllTasks } from "./tools-B8OJ4sMF.js";
7
7
  import { ulid } from "./utils/ulid.js";
8
8
 
9
9
  //#region src/core/control-plane-client.ts
@@ -432,7 +432,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
432
432
  switch (action) {
433
433
  case "send-message": {
434
434
  if (!args.text) throw new Error("Missing text parameter");
435
- const { orchestratorStore } = await import("./orchestrator-i_QJ-o22.js").then((n) => n.n);
435
+ const { orchestratorStore } = await import("./orchestrator-CCARkxQC.js").then((n) => n.n);
436
436
  const orch = options.orchestrator || orchestratorStore.orchestrator;
437
437
  const targetGroupId = args.groupId || orchestratorStore.activeGroupId || "br:main";
438
438
  if (orch?.browserChat?.submit) {
@@ -468,7 +468,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
468
468
  return { tasks };
469
469
  }
470
470
  case "read-state": {
471
- const { orchestratorStore } = await import("./orchestrator-i_QJ-o22.js").then((n) => n.n);
471
+ const { orchestratorStore } = await import("./orchestrator-CCARkxQC.js").then((n) => n.n);
472
472
  const orch = options.orchestrator || orchestratorStore.orchestrator;
473
473
  return {
474
474
  clientId,
@@ -481,7 +481,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
481
481
  }
482
482
  case "list-tools": {
483
483
  try {
484
- const { getWebMcpTools } = await import("./webmcp-DCfAFiIO.js").then((n) => n.c);
484
+ const { getWebMcpTools } = await import("./webmcp-BoMTvgmX.js").then((n) => n.c);
485
485
  const webMcpTools = await getWebMcpTools();
486
486
  if (webMcpTools && webMcpTools.length > 0) return { tools: webMcpTools.map((t) => ({
487
487
  name: t.name,
@@ -491,13 +491,13 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
491
491
  })) };
492
492
  } catch (_) {}
493
493
  try {
494
- const { orchestratorStore } = await import("./orchestrator-i_QJ-o22.js").then((n) => n.n);
494
+ const { orchestratorStore } = await import("./orchestrator-CCARkxQC.js").then((n) => n.n);
495
495
  const orch = options.orchestrator || orchestratorStore.orchestrator || (typeof document !== "undefined" ? document.querySelector("shadow-claw")?.orchestrator : null);
496
496
  const activeGroupId = args.groupId || orch?.activeGroupId || orchestratorStore.activeGroupId || "br:main";
497
497
  const group = orchestratorStore.groups.find((g) => g.groupId === activeGroupId);
498
498
  if (group?.toolTags && group.toolTags.length > 0) {
499
499
  const { TOOL_DEFINITIONS } = await import("./tools-tRG7Gu0x.js").then((n) => n.n);
500
- const { parseWebMcpInputSchema } = await import("./webmcp-DCfAFiIO.js").then((n) => n.c);
500
+ const { parseWebMcpInputSchema } = await import("./webmcp-BoMTvgmX.js").then((n) => n.c);
501
501
  return { tools: TOOL_DEFINITIONS.filter((t) => group.toolTags.includes(t.name)).map((t) => ({
502
502
  name: t.name,
503
503
  description: t.description,
@@ -506,7 +506,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
506
506
  }
507
507
  } catch (_) {}
508
508
  const { TOOL_DEFINITIONS } = await import("./tools-tRG7Gu0x.js").then((n) => n.n);
509
- const { parseWebMcpInputSchema } = await import("./webmcp-DCfAFiIO.js").then((n) => n.c);
509
+ const { parseWebMcpInputSchema } = await import("./webmcp-BoMTvgmX.js").then((n) => n.c);
510
510
  return { tools: TOOL_DEFINITIONS.map((t) => ({
511
511
  name: t.name,
512
512
  description: t.description,
@@ -516,7 +516,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
516
516
  case "invoke-tool": {
517
517
  if (!args.toolName) throw new Error("Missing toolName parameter");
518
518
  try {
519
- const { orchestratorStore } = await import("./orchestrator-i_QJ-o22.js").then((n) => n.n);
519
+ const { orchestratorStore } = await import("./orchestrator-CCARkxQC.js").then((n) => n.n);
520
520
  const orch = options.orchestrator || orchestratorStore.orchestrator || (typeof document !== "undefined" ? document.querySelector("shadow-claw")?.orchestrator : null);
521
521
  const activeGroupId = args.groupId || orch?.activeGroupId || orchestratorStore.activeGroupId || "br:main";
522
522
  const group = orchestratorStore.groups.find((g) => g.groupId === activeGroupId);
@@ -543,7 +543,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
543
543
  } catch (err) {
544
544
  if (err.message && err.message.includes("is not enabled")) throw err;
545
545
  }
546
- const { executeWebMcpTool } = await import("./webmcp-DCfAFiIO.js").then((n) => n.c);
546
+ const { executeWebMcpTool } = await import("./webmcp-BoMTvgmX.js").then((n) => n.c);
547
547
  if (typeof ctx.executeTool === "function") {
548
548
  if (matchedTool) try {
549
549
  return { result: await executeWebMcpTool(ctx, matchedTool, args.input) };
@@ -569,7 +569,7 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
569
569
  return { result: await ctx.invoke(args.toolName, typeof args.input === "string" ? JSON.parse(args.input) : args.input || {}) };
570
570
  } catch (_) {}
571
571
  }
572
- const { orchestratorStore } = await import("./orchestrator-i_QJ-o22.js").then((n) => n.n);
572
+ const { orchestratorStore } = await import("./orchestrator-CCARkxQC.js").then((n) => n.n);
573
573
  const orch = options.orchestrator || orchestratorStore.orchestrator || (typeof document !== "undefined" ? document.querySelector("shadow-claw")?.orchestrator : null);
574
574
  const worker = orch?.agentWorker;
575
575
  if (worker && typeof worker.postMessage === "function") {
@@ -605,10 +605,10 @@ async function executeClientControlCommand(action, args = {}, options = {}) {
605
605
  throw new Error(`Tool ${args.toolName} could not be executed (no context or worker available)`);
606
606
  }
607
607
  case "trigger-backup": {
608
- const { orchestratorStore } = await import("./orchestrator-i_QJ-o22.js").then((n) => n.n);
608
+ const { orchestratorStore } = await import("./orchestrator-CCARkxQC.js").then((n) => n.n);
609
609
  const targetGroupId = args.groupId || options.orchestrator?.activeGroupId || orchestratorStore.activeGroupId || "br:main";
610
610
  const db = await getDb();
611
- const { getGroupDir } = await import("./parse-path-DPCn-HwI.js").then((n) => n.r);
611
+ const { getGroupDir } = await import("./parse-path-BOHQP_IQ.js").then((n) => n.r);
612
612
  const groupDir = await getGroupDir(db, targetGroupId);
613
613
  async function collectFiles(dir, prefix = "") {
614
614
  const result = [];
@@ -726,4 +726,4 @@ async function ensureControlPlaneConnected(options = {}) {
726
726
 
727
727
  //#endregion
728
728
  export { detectDeviceLabel, ensureControlPlaneConnected, executeClientControlCommand, getOrCreateControlPlaneClientId, isControlPlaneEnabled, shouldConnectControlPlane, stopControlPlaneClient };
729
- //# sourceMappingURL=init-control-plane-C1FRRmjC.js.map
729
+ //# sourceMappingURL=init-control-plane-B7blDVIE.js.map