abtars 0.3.4-alpha.0 → 0.3.4-alpha.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (392) hide show
  1. package/bundle/{_registry.generated-7DRCE4V6.js → _registry.generated-RC6PEH6Z.js} +16 -15
  2. package/bundle/{_registry.generated-7DRCE4V6.js.map → _registry.generated-RC6PEH6Z.js.map} +1 -1
  3. package/bundle/abtars-browser.js +6 -5
  4. package/bundle/abtars-browser.js.map +1 -1
  5. package/bundle/abtars-cli.js +73 -46
  6. package/bundle/abtars-cli.js.map +3 -3
  7. package/bundle/abtars-restart.js +7 -7
  8. package/bundle/abtars-rss.js +2 -1
  9. package/bundle/abtars-rss.js.map +2 -2
  10. package/bundle/abtars-task.js +6 -5
  11. package/bundle/abtars-task.js.map +1 -1
  12. package/bundle/abtars-todo.js +2 -1
  13. package/bundle/abtars-todo.js.map +1 -1
  14. package/bundle/abtars.js +307 -212
  15. package/bundle/abtars.js.map +4 -4
  16. package/bundle/{acp-raw-client-AZJCEB6S.js → acp-raw-client-E6FM45NC.js} +4 -3
  17. package/bundle/{acp-raw-client-AZJCEB6S.js.map → acp-raw-client-E6FM45NC.js.map} +1 -1
  18. package/bundle/{action-gate-QYJL57IX.js → action-gate-G2V47NHW.js} +4 -3
  19. package/bundle/{action-gate-QYJL57IX.js.map → action-gate-G2V47NHW.js.map} +1 -1
  20. package/bundle/{agent-api-adapter-PYMNQXHE.js → agent-api-adapter-PTJYZKQK.js} +5 -4
  21. package/bundle/{agent-api-adapter-PYMNQXHE.js.map → agent-api-adapter-PTJYZKQK.js.map} +1 -1
  22. package/bundle/{agent-api-rate-limit-4GEZ4YN5.js → agent-api-rate-limit-WCFXJMGY.js} +6 -5
  23. package/bundle/{agent-registry-563P4EUJ.js → agent-registry-GU7ABOK5.js} +9 -8
  24. package/bundle/bootstrap-POWWTU6I.js +63 -0
  25. package/bundle/bootstrap-POWWTU6I.js.map +7 -0
  26. package/bundle/{bridge-lock-transport-LXCF2IVN.js → bridge-lock-transport-4ZH7QTJP.js} +6 -5
  27. package/bundle/{browser-2VZOGOGX.js → browser-EJNS35NT.js} +8 -7
  28. package/bundle/{budget-PPA7WY3D.js → budget-45QOBDWA.js} +5 -4
  29. package/bundle/{budget-PPA7WY3D.js.map → budget-45QOBDWA.js.map} +1 -1
  30. package/bundle/{capability-WXEA2WFK.js → capability-JFWX3IQF.js} +7 -6
  31. package/bundle/{chunk-CB6S3ZRF.js → chunk-2FAZIA37.js} +3 -3
  32. package/bundle/{chunk-VJATH7AN.js → chunk-2KC5G3EA.js} +9 -8
  33. package/bundle/chunk-2KC5G3EA.js.map +7 -0
  34. package/bundle/{chunk-OY2HAK33.js → chunk-36ZEYDKZ.js} +1 -1
  35. package/bundle/chunk-36ZEYDKZ.js.map +7 -0
  36. package/bundle/{chunk-2FZJDMAF.js → chunk-3CACHBDI.js} +10 -10
  37. package/bundle/{chunk-O4GKI3Q3.js → chunk-4S554KLW.js} +4 -4
  38. package/bundle/{chunk-3QW2K53E.js → chunk-5GCLBUBS.js} +11 -19
  39. package/bundle/chunk-5GCLBUBS.js.map +7 -0
  40. package/bundle/{chunk-RJX45XIC.js → chunk-5HDSQFT6.js} +9 -4
  41. package/bundle/chunk-5HDSQFT6.js.map +7 -0
  42. package/bundle/{chunk-EDZGF6BC.js → chunk-5NY2YULC.js} +11 -4
  43. package/bundle/chunk-5NY2YULC.js.map +7 -0
  44. package/bundle/{chunk-LE23VPN3.js → chunk-63A7ZRIH.js} +4 -4
  45. package/bundle/{chunk-LE23VPN3.js.map → chunk-63A7ZRIH.js.map} +1 -1
  46. package/bundle/{chunk-SSCGWDIC.js → chunk-65VCEC32.js} +2 -2
  47. package/bundle/{chunk-V2QIAXWZ.js → chunk-7BSQ5UQO.js} +3 -3
  48. package/bundle/{chunk-E7MV7WFT.js → chunk-7Z3HBPRY.js} +6 -6
  49. package/bundle/{chunk-TY26WMQY.js → chunk-AFREM7FX.js} +2 -2
  50. package/bundle/{chunk-GCFIK6OB.js → chunk-AO32N2VB.js} +92 -20
  51. package/bundle/chunk-AO32N2VB.js.map +7 -0
  52. package/bundle/{chunk-N5VROZ7A.js → chunk-B6ZN6COK.js} +5 -5
  53. package/bundle/{chunk-M6Q3IQ4H.js → chunk-BFDBGESM.js} +259 -122
  54. package/bundle/chunk-BFDBGESM.js.map +7 -0
  55. package/bundle/{chunk-YEOZN5IE.js → chunk-DYBW4XXL.js} +2 -2
  56. package/bundle/{chunk-56D3Y44D.js → chunk-EFJVUJBE.js} +10 -10
  57. package/bundle/{chunk-S6HEHCCG.js → chunk-EQSG2CRM.js} +83 -46
  58. package/bundle/chunk-EQSG2CRM.js.map +7 -0
  59. package/bundle/{chunk-FIAVVKGN.js → chunk-EUZDKV3C.js} +3 -3
  60. package/bundle/{chunk-2LKQV2ND.js → chunk-FRKW6LWB.js} +3 -3
  61. package/bundle/{chunk-H2K23MOF.js → chunk-GALQBVKO.js} +21 -5
  62. package/bundle/chunk-GALQBVKO.js.map +7 -0
  63. package/bundle/{chunk-DNDYD5SL.js → chunk-GP4XUKI5.js} +3 -3
  64. package/bundle/{chunk-SXNY6HC4.js → chunk-GPZNXY2U.js} +6 -6
  65. package/bundle/chunk-GPZNXY2U.js.map +7 -0
  66. package/bundle/{chunk-W726UGI6.js → chunk-GRVWZO4C.js} +3 -3
  67. package/bundle/{chunk-IXKQ4JMX.js → chunk-GVM5YU5I.js} +33 -17
  68. package/bundle/chunk-GVM5YU5I.js.map +7 -0
  69. package/bundle/{chunk-OOKNHOCB.js → chunk-GWILHZPT.js} +2 -2
  70. package/bundle/{chunk-3LQOJVTB.js → chunk-HFOCNYEO.js} +1842 -1220
  71. package/bundle/{chunk-3LQOJVTB.js.map → chunk-HFOCNYEO.js.map} +4 -4
  72. package/bundle/{chunk-NP72ZB7P.js → chunk-HMKVL7AX.js} +53 -47
  73. package/bundle/chunk-HMKVL7AX.js.map +7 -0
  74. package/bundle/{chunk-BNBC4T45.js → chunk-HT2BPTZY.js} +3 -3
  75. package/bundle/{chunk-BU7LTI2W.js → chunk-HZDLFLRP.js} +6 -7
  76. package/bundle/chunk-HZDLFLRP.js.map +7 -0
  77. package/bundle/{chunk-FVUL44T4.js → chunk-IJT4KWXT.js} +2 -2
  78. package/bundle/{chunk-IK4R3RBZ.js → chunk-JNIHEDKF.js} +3 -3
  79. package/bundle/{chunk-J5NOL4DB.js → chunk-JQDJPUHM.js} +16 -6
  80. package/bundle/chunk-JQDJPUHM.js.map +7 -0
  81. package/bundle/{chunk-SESM4GBM.js → chunk-KTYGKPYM.js} +52 -25
  82. package/bundle/chunk-KTYGKPYM.js.map +7 -0
  83. package/bundle/chunk-LME23AA2.js +37 -0
  84. package/bundle/chunk-LME23AA2.js.map +7 -0
  85. package/bundle/{chunk-4PIVWXUJ.js → chunk-LUNA6PM5.js} +2 -2
  86. package/bundle/{chunk-37EX63K4.js → chunk-LUW62WGO.js} +6998 -3621
  87. package/bundle/chunk-LUW62WGO.js.map +7 -0
  88. package/bundle/{chunk-MV5KOWOR.js → chunk-NDCRWEEJ.js} +7 -7
  89. package/bundle/{chunk-7WHXTCVD.js → chunk-NRUSRJXR.js} +8 -3
  90. package/bundle/chunk-NRUSRJXR.js.map +7 -0
  91. package/bundle/{chunk-C3EYYJN3.js → chunk-O7KQG6ME.js} +17 -5
  92. package/bundle/chunk-O7KQG6ME.js.map +7 -0
  93. package/bundle/{chunk-ZOCEBV62.js → chunk-OKAQICWY.js} +3 -3
  94. package/bundle/{chunk-TCI6FZTP.js → chunk-OLAURO5G.js} +9 -9
  95. package/bundle/{chunk-YME7NRGP.js → chunk-OXTSWQCX.js} +2 -2
  96. package/bundle/{chunk-HDOFJVFS.js → chunk-PEDX56EL.js} +3 -3
  97. package/bundle/{chunk-7RAGSHSH.js → chunk-PROPYS3P.js} +12 -10
  98. package/bundle/chunk-PROPYS3P.js.map +7 -0
  99. package/bundle/{chunk-ASYX43OU.js → chunk-Q32H6VPU.js} +26 -26
  100. package/bundle/{chunk-P5O6QZDC.js → chunk-QROWBWLL.js} +10 -6
  101. package/bundle/chunk-QROWBWLL.js.map +7 -0
  102. package/bundle/{chunk-S7ZIGIR5.js → chunk-R76K6L6H.js} +27 -27
  103. package/bundle/{chunk-S7ZIGIR5.js.map → chunk-R76K6L6H.js.map} +1 -1
  104. package/bundle/{chunk-MQJG7OJX.js → chunk-RIHQ37U5.js} +38 -36
  105. package/bundle/chunk-RIHQ37U5.js.map +7 -0
  106. package/bundle/{chunk-IQKADER4.js → chunk-RWRRGE4U.js} +2 -2
  107. package/bundle/{chunk-72T2Q7IG.js → chunk-S5GD5EJ5.js} +271 -282
  108. package/bundle/chunk-S5GD5EJ5.js.map +7 -0
  109. package/bundle/{chunk-ULO2PX3T.js → chunk-TEFZ4JA4.js} +3 -3
  110. package/bundle/{chunk-2RGR3LSV.js → chunk-TMUYFERL.js} +2 -2
  111. package/bundle/{chunk-KBPVJGD7.js → chunk-URQPDCK5.js} +3 -3
  112. package/bundle/chunk-UUIHL65U.js +77 -0
  113. package/bundle/chunk-UUIHL65U.js.map +7 -0
  114. package/bundle/{chunk-FJF42RZY.js → chunk-VUIX5AGB.js} +3 -3
  115. package/bundle/{chunk-5V4VHKEA.js → chunk-WBTJ2E62.js} +5 -4
  116. package/bundle/chunk-WBTJ2E62.js.map +7 -0
  117. package/bundle/{chunk-ZY6DH2S4.js → chunk-WTIGZO3N.js} +80 -70
  118. package/bundle/chunk-WTIGZO3N.js.map +7 -0
  119. package/bundle/{chunk-4HNCOQSK.js → chunk-WYHGNI56.js} +7 -7
  120. package/bundle/{chunk-24V4A6RP.js → chunk-XX6BGTPO.js} +4 -4
  121. package/bundle/{chunk-T7TAWGBX.js → chunk-Y76VUJSF.js} +2 -2
  122. package/bundle/{chunk-TVSPVZTX.js → chunk-YDY6QVWJ.js} +3 -3
  123. package/bundle/{chunk-V6CV3QPH.js → chunk-YRSMGJFP.js} +2 -2
  124. package/bundle/{chunk-WP7FZHMI.js → chunk-YSKCQH6E.js} +2 -2
  125. package/bundle/{chunk-NGZVJ52F.js → chunk-ZKJOFASV.js} +7 -7
  126. package/bundle/{chunk-WGWM4IZM.js → chunk-ZT5ZBGWS.js} +4 -4
  127. package/bundle/{chunk-WGWM4IZM.js.map → chunk-ZT5ZBGWS.js.map} +1 -1
  128. package/bundle/{chunk-43DKPXTP.js → chunk-ZV4IWKDJ.js} +4 -4
  129. package/bundle/{commands-XXFU2ZF7.js → commands-EWA4HNCM.js} +20 -20
  130. package/bundle/{config-EWDZ234X.js → config-M3P5IOAI.js} +8 -7
  131. package/bundle/{config-show-6J33O4TE.js → config-show-3DHPP26D.js} +5 -5
  132. package/bundle/{context-OCS7HLJP.js → context-5P7IYYU2.js} +5 -2
  133. package/bundle/{context-OCS7HLJP.js.map → context-5P7IYYU2.js.map} +1 -1
  134. package/bundle/{daemon-LTDAXNA2.js → daemon-TB23FFWY.js} +7 -7
  135. package/bundle/{delegation-tools-YDTWQMZD.js → delegation-tools-P2SCNL23.js} +14 -11
  136. package/bundle/{registry-client-VN2MM2HI.js → deploy-YYUCGGP3.js} +10 -6
  137. package/bundle/{deploy-lib-import-RGZJ3CGC.js → deploy-lib-import-T3UP4G6G.js} +5 -3
  138. package/bundle/{deps-PHSLIA77.js → deps-WVK553KF.js} +21 -19
  139. package/bundle/deps-WVK553KF.js.map +7 -0
  140. package/bundle/{direct-api-transport-OAKYQBJR.js → direct-api-transport-WQ6HA5OX.js} +30 -28
  141. package/bundle/direct-api-transport-WQ6HA5OX.js.map +7 -0
  142. package/bundle/{discord-adapter-WUNYPTDE.js → discord-adapter-4TTETYDI.js} +26 -26
  143. package/bundle/{dist-7HEHHQI2.js → dist-KMK7TZGN.js} +376 -348
  144. package/bundle/dist-KMK7TZGN.js.map +7 -0
  145. package/bundle/{dns-wakeup-F55ALHXJ.js → dns-wakeup-IDOJIXBX.js} +4 -3
  146. package/bundle/{dns-wakeup-F55ALHXJ.js.map → dns-wakeup-IDOJIXBX.js.map} +1 -1
  147. package/bundle/{doctor-probes-3SLIUGKS.js → doctor-probes-VDWFJKUB.js} +4 -3
  148. package/bundle/{env-schema-MSDP2YBO.js → env-schema-4JXQUOH4.js} +5 -4
  149. package/bundle/{gossip-CS3G3447.js → gossip-3C3BSNPN.js} +7 -6
  150. package/bundle/{guardrails-24XK2COI.js → guardrails-DL7ZSWVN.js} +6 -5
  151. package/bundle/{health-check-FRUNRVNQ.js → health-check-YKWFD2LZ.js} +5 -6
  152. package/bundle/{health-check-FRUNRVNQ.js.map → health-check-YKWFD2LZ.js.map} +2 -2
  153. package/bundle/{heartbeat-system-G4IFQXT6.js → heartbeat-system-TDDIOVTC.js} +7 -6
  154. package/bundle/{heartbeat-tier3-3ZO3EVXP.js → heartbeat-tier3-55T2HUNE.js} +45 -44
  155. package/bundle/heartbeat-tier3-55T2HUNE.js.map +7 -0
  156. package/bundle/{hook-system-X6INNJGV.js → hook-system-M3POLUIB.js} +5 -4
  157. package/bundle/{hotskills-6FQYTJIO.js → hotskills-FWX4QI7V.js} +7 -6
  158. package/bundle/{install-ZAHTZ5M5.js → install-4MXBYIUG.js} +23 -20
  159. package/bundle/install-4MXBYIUG.js.map +7 -0
  160. package/bundle/{install-manifest-QX7KVDCA.js → install-manifest-5PPWMD2W.js} +4 -3
  161. package/bundle/{install-manifest-QX7KVDCA.js.map → install-manifest-5PPWMD2W.js.map} +1 -1
  162. package/bundle/{irc-adapter-IEJQKKJF.js → irc-adapter-PTTZD32W.js} +5 -4
  163. package/bundle/{irc-adapter-IEJQKKJF.js.map → irc-adapter-PTTZD32W.js.map} +1 -1
  164. package/bundle/{irc-config-TTWNYFLH.js → irc-config-CP7ZMUOX.js} +6 -5
  165. package/bundle/{irc-config-TTWNYFLH.js.map → irc-config-CP7ZMUOX.js.map} +1 -1
  166. package/bundle/{kanban-board-J6RO3ZU7.js → kanban-board-M326B2XJ.js} +7 -5
  167. package/bundle/{kanban-channel-5EIXBFSA.js → kanban-channel-IJ52OMNA.js} +8 -6
  168. package/bundle/{lazy-require-V6EFUATC.js → lazy-require-KCRVT4SI.js} +11 -6
  169. package/bundle/{logger-Y3VILPRH.js → logger-OWCSNYCA.js} +4 -3
  170. package/bundle/{logs-YS3GDURO.js → logs-FXS4SCEM.js} +5 -5
  171. package/bundle/{main-chat-YLZDNQPO.js → main-chat-ZNUZCTNS.js} +6 -5
  172. package/bundle/{master-user-Z4M7KCJE.js → master-user-HSKM4ZFN.js} +7 -6
  173. package/bundle/{media-utils-P6RZ2K3U.js → media-utils-3ZYOD7SK.js} +44 -43
  174. package/bundle/{media-utils-P6RZ2K3U.js.map → media-utils-3ZYOD7SK.js.map} +2 -2
  175. package/bundle/{message-pipeline-MHEBDJLH.js → message-pipeline-KSONH4MT.js} +20 -20
  176. package/bundle/meta.json +9327 -8582
  177. package/bundle/{migrate-layout-RJJQLVGR.js → migrate-layout-IJIEJY3A.js} +8 -4
  178. package/bundle/migrate-layout-IJIEJY3A.js.map +7 -0
  179. package/bundle/{nerve-VZNMFDGY.js → nerve-IGSXBKZZ.js} +5 -4
  180. package/bundle/{notification-VV2OR6NW.js → notification-BFSIEECG.js} +8 -7
  181. package/bundle/{openrouter-credits-LXC7P4G6.js → openrouter-credits-NTVZDRYM.js} +5 -4
  182. package/bundle/{openrouter-credits-LXC7P4G6.js.map → openrouter-credits-NTVZDRYM.js.map} +1 -1
  183. package/bundle/{orc-KC4USP55.js → orc-EIGVTHAV.js} +4 -4
  184. package/bundle/{orc-tools-CHRSXSAS.js → orc-tools-A3G7WCSJ.js} +5 -4
  185. package/bundle/{paths-EDK6KWHG.js → paths-3ZVW3NFL.js} +6 -2
  186. package/bundle/{paths-RZF6WDMG.js → paths-X4LRYUI6.js} +3 -2
  187. package/bundle/{peer-auth-SRONOLNG.js → peer-auth-QC4EF2PM.js} +9 -8
  188. package/bundle/{peer-client-VOF77T6C.js → peer-client-RGEU5HOK.js} +9 -8
  189. package/bundle/{peer-client-VOF77T6C.js.map → peer-client-RGEU5HOK.js.map} +1 -1
  190. package/bundle/{peer-config-FRWLEYQ5.js → peer-config-TN55LFDC.js} +6 -5
  191. package/bundle/{peer-jwt-XY3XRIA2.js → peer-jwt-NCCPXJRX.js} +6 -5
  192. package/bundle/{peer-transport-UBBXTDRP.js → peer-transport-I6JPLFZ2.js} +8 -7
  193. package/bundle/{phase-transport-4NQHZX75.js → phase-transport-2BRWACDF.js} +18 -16
  194. package/bundle/public/css/dashboard.css +542 -0
  195. package/bundle/public/index.html +180 -0
  196. package/bundle/public/js/app.js +437 -0
  197. package/bundle/public/memory-universe.js +384 -0
  198. package/bundle/{reconcile-2EUXJ6W5.js → reconcile-CTFCLQRN.js} +5 -4
  199. package/bundle/{reconciler-FFQGV4DO.js → reconciler-FHESO6OC.js} +14 -11
  200. package/bundle/{reconciler-FFQGV4DO.js.map → reconciler-FHESO6OC.js.map} +1 -1
  201. package/bundle/{restore-NFDE2RG6.js → restore-IFHPI7I7.js} +13 -9
  202. package/bundle/{restore-NFDE2RG6.js.map → restore-IFHPI7I7.js.map} +3 -3
  203. package/bundle/{rollback-MVZ53XS4.js → rollback-ANRI3T5Z.js} +5 -5
  204. package/bundle/{chunk-SKY6656M.js → sandbox-runtime-QROWHDCS.js} +11 -28
  205. package/bundle/{chunk-SKY6656M.js.map → sandbox-runtime-QROWHDCS.js.map} +1 -1
  206. package/bundle/{self-healer-utils-KD6LV63S.js → self-healer-utils-IFAYOQO2.js} +5 -4
  207. package/bundle/{self-healer-utils-KD6LV63S.js.map → self-healer-utils-IFAYOQO2.js.map} +1 -1
  208. package/bundle/{sha-tracker-2DB4R2TW.js → sha-tracker-ZWBP6CIJ.js} +5 -4
  209. package/bundle/{skill-session-BPDVA6ZG.js → skill-session-AXBDQSLQ.js} +5 -4
  210. package/bundle/{skill-session-BPDVA6ZG.js.map → skill-session-AXBDQSLQ.js.map} +1 -1
  211. package/bundle/{skill-stats-TPD2NROA.js → skill-stats-JORH5DGM.js} +6 -5
  212. package/bundle/{skill-watcher-D7QYYYON.js → skill-watcher-E4MGLKLS.js} +6 -5
  213. package/bundle/{sleep-GH6DLBJJ.js → sleep-SRCSXY6T.js} +10 -9
  214. package/bundle/{soul-bundle-GXLMDBCC.js → soul-bundle-VWAVHCZ6.js} +10 -9
  215. package/bundle/{spin-4DBYHS3E.js → spin-IMW2MZOH.js} +13 -10
  216. package/bundle/{spin-notifications-IKYJPER5.js → spin-notifications-SE2HVZI7.js} +7 -5
  217. package/bundle/{spin-notifications-IKYJPER5.js.map → spin-notifications-SE2HVZI7.js.map} +1 -1
  218. package/bundle/{spin-types-PLJH3SIK.js → spin-types-BLPYAETA.js} +5 -4
  219. package/bundle/{src-SUFZ27S5.js → src-6BTCMOD3.js} +4 -4
  220. package/bundle/{sse-parser-anthropic-U7ILHOY5.js → sse-parser-anthropic-A6R4Z2TB.js} +5 -4
  221. package/bundle/{sse-parser-anthropic-U7ILHOY5.js.map → sse-parser-anthropic-A6R4Z2TB.js.map} +1 -1
  222. package/bundle/{sse-parser-responses-OI73R3AH.js → sse-parser-responses-HSZY3QGJ.js} +5 -4
  223. package/bundle/{sse-parser-responses-OI73R3AH.js.map → sse-parser-responses-HSZY3QGJ.js.map} +1 -1
  224. package/bundle/{ssrf-guard-6GP4QYVA.js → ssrf-guard-O6SHIK6Q.js} +5 -4
  225. package/bundle/{ssrf-guard-6GP4QYVA.js.map → ssrf-guard-O6SHIK6Q.js.map} +1 -1
  226. package/bundle/{start-JT2BPMSW.js → start-7QZIWO3S.js} +5 -5
  227. package/bundle/start-7QZIWO3S.js.map +7 -0
  228. package/bundle/{stt-KD3AABKG.js → stt-LGVPXMVR.js} +6 -5
  229. package/bundle/{subagent-runtime-LVECAUPV.js → subagent-runtime-3UJB4HUB.js} +6 -5
  230. package/bundle/system-status-ATGKRRQI.js +349 -0
  231. package/bundle/system-status-ATGKRRQI.js.map +7 -0
  232. package/bundle/{task-store-2XRDM3AW.js → task-store-W5BFIAIH.js} +6 -5
  233. package/bundle/{telegram-adapter-UJ3RYYV6.js → telegram-adapter-7G773NII.js} +35 -35
  234. package/bundle/{tool-registry-YU6WBXPA.js → tool-registry-J6TE3I2T.js} +25 -23
  235. package/bundle/{tool-sandbox-RNNPDR5M.js → tool-sandbox-4UC6GAKA.js} +6 -5
  236. package/bundle/{transport-config-OK3MZPJK.js → transport-config-KBF5W2DP.js} +9 -8
  237. package/bundle/{update-ENNPRW7Y.js → update-424ZZQQ6.js} +6 -6
  238. package/bundle/{update-check-SJB6GV3A.js → update-check-7UWKBJOP.js} +3 -2
  239. package/bundle/{update-check-SJB6GV3A.js.map → update-check-7UWKBJOP.js.map} +1 -1
  240. package/bundle/{usage-tracker-HRSGC7QC.js → usage-tracker-NXD364VX.js} +2 -2
  241. package/bundle/{user-registry-6PUJJ5J2.js → user-registry-35BW4XKM.js} +6 -5
  242. package/bundle/{wrapper-WLHLG4MI.js → wrapper-W66YICNZ.js} +3 -3
  243. package/bundle/{ws-peer-client-WHW3RJTD.js → ws-peer-client-AIXCXF7V.js} +15 -14
  244. package/bundle/{ws-peer-client-WHW3RJTD.js.map → ws-peer-client-AIXCXF7V.js.map} +2 -2
  245. package/package.json +4 -8
  246. package/scripts/emergency-deploy.sh +11 -8
  247. package/scripts/emergency-update.sh +156 -23
  248. package/templates/config/.env +1 -1
  249. package/templates/config/models.json +13 -0
  250. package/bundle/chunk-37EX63K4.js.map +0 -7
  251. package/bundle/chunk-3QW2K53E.js.map +0 -7
  252. package/bundle/chunk-5V4VHKEA.js.map +0 -7
  253. package/bundle/chunk-72T2Q7IG.js.map +0 -7
  254. package/bundle/chunk-7RAGSHSH.js.map +0 -7
  255. package/bundle/chunk-7WHXTCVD.js.map +0 -7
  256. package/bundle/chunk-BU7LTI2W.js.map +0 -7
  257. package/bundle/chunk-C3EYYJN3.js.map +0 -7
  258. package/bundle/chunk-CAOIIVFP.js +0 -110
  259. package/bundle/chunk-CAOIIVFP.js.map +0 -7
  260. package/bundle/chunk-EDZGF6BC.js.map +0 -7
  261. package/bundle/chunk-GCFIK6OB.js.map +0 -7
  262. package/bundle/chunk-H2K23MOF.js.map +0 -7
  263. package/bundle/chunk-HAZHNBBY.js +0 -156
  264. package/bundle/chunk-HAZHNBBY.js.map +0 -7
  265. package/bundle/chunk-IXKQ4JMX.js.map +0 -7
  266. package/bundle/chunk-J5NOL4DB.js.map +0 -7
  267. package/bundle/chunk-JAJ3DUQ2.js +0 -30
  268. package/bundle/chunk-JAJ3DUQ2.js.map +0 -7
  269. package/bundle/chunk-KMFR5AVY.js +0 -45
  270. package/bundle/chunk-KMFR5AVY.js.map +0 -7
  271. package/bundle/chunk-M6Q3IQ4H.js.map +0 -7
  272. package/bundle/chunk-MQJG7OJX.js.map +0 -7
  273. package/bundle/chunk-NP72ZB7P.js.map +0 -7
  274. package/bundle/chunk-OY2HAK33.js.map +0 -7
  275. package/bundle/chunk-P5O6QZDC.js.map +0 -7
  276. package/bundle/chunk-RJX45XIC.js.map +0 -7
  277. package/bundle/chunk-S6HEHCCG.js.map +0 -7
  278. package/bundle/chunk-SESM4GBM.js.map +0 -7
  279. package/bundle/chunk-SXNY6HC4.js.map +0 -7
  280. package/bundle/chunk-VJATH7AN.js.map +0 -7
  281. package/bundle/chunk-ZY6DH2S4.js.map +0 -7
  282. package/bundle/deps-PHSLIA77.js.map +0 -7
  283. package/bundle/direct-api-transport-OAKYQBJR.js.map +0 -7
  284. package/bundle/dist-7HEHHQI2.js.map +0 -7
  285. package/bundle/heartbeat-tier3-3ZO3EVXP.js.map +0 -7
  286. package/bundle/install-ZAHTZ5M5.js.map +0 -7
  287. package/bundle/migrate-layout-RJJQLVGR.js.map +0 -7
  288. package/bundle/phase-config-V4XETN5F.js +0 -18
  289. package/bundle/sandbox-runtime-WHACQLLN.js +0 -22
  290. package/bundle/start-JT2BPMSW.js.map +0 -7
  291. package/bundle/system-status-XXJWTVJN.js +0 -243
  292. package/bundle/system-status-XXJWTVJN.js.map +0 -7
  293. package/bundle/user-registry-6PUJJ5J2.js.map +0 -7
  294. package/bundle/wrapper-WLHLG4MI.js.map +0 -7
  295. /package/bundle/{agent-api-rate-limit-4GEZ4YN5.js.map → agent-api-rate-limit-WCFXJMGY.js.map} +0 -0
  296. /package/bundle/{agent-registry-563P4EUJ.js.map → agent-registry-GU7ABOK5.js.map} +0 -0
  297. /package/bundle/{bridge-lock-transport-LXCF2IVN.js.map → bridge-lock-transport-4ZH7QTJP.js.map} +0 -0
  298. /package/bundle/{browser-2VZOGOGX.js.map → browser-EJNS35NT.js.map} +0 -0
  299. /package/bundle/{capability-WXEA2WFK.js.map → capability-JFWX3IQF.js.map} +0 -0
  300. /package/bundle/{chunk-CB6S3ZRF.js.map → chunk-2FAZIA37.js.map} +0 -0
  301. /package/bundle/{chunk-2FZJDMAF.js.map → chunk-3CACHBDI.js.map} +0 -0
  302. /package/bundle/{chunk-O4GKI3Q3.js.map → chunk-4S554KLW.js.map} +0 -0
  303. /package/bundle/{chunk-SSCGWDIC.js.map → chunk-65VCEC32.js.map} +0 -0
  304. /package/bundle/{chunk-V2QIAXWZ.js.map → chunk-7BSQ5UQO.js.map} +0 -0
  305. /package/bundle/{chunk-E7MV7WFT.js.map → chunk-7Z3HBPRY.js.map} +0 -0
  306. /package/bundle/{chunk-TY26WMQY.js.map → chunk-AFREM7FX.js.map} +0 -0
  307. /package/bundle/{chunk-N5VROZ7A.js.map → chunk-B6ZN6COK.js.map} +0 -0
  308. /package/bundle/{chunk-YEOZN5IE.js.map → chunk-DYBW4XXL.js.map} +0 -0
  309. /package/bundle/{chunk-56D3Y44D.js.map → chunk-EFJVUJBE.js.map} +0 -0
  310. /package/bundle/{chunk-FIAVVKGN.js.map → chunk-EUZDKV3C.js.map} +0 -0
  311. /package/bundle/{chunk-2LKQV2ND.js.map → chunk-FRKW6LWB.js.map} +0 -0
  312. /package/bundle/{chunk-DNDYD5SL.js.map → chunk-GP4XUKI5.js.map} +0 -0
  313. /package/bundle/{chunk-W726UGI6.js.map → chunk-GRVWZO4C.js.map} +0 -0
  314. /package/bundle/{chunk-OOKNHOCB.js.map → chunk-GWILHZPT.js.map} +0 -0
  315. /package/bundle/{chunk-BNBC4T45.js.map → chunk-HT2BPTZY.js.map} +0 -0
  316. /package/bundle/{chunk-FVUL44T4.js.map → chunk-IJT4KWXT.js.map} +0 -0
  317. /package/bundle/{chunk-IK4R3RBZ.js.map → chunk-JNIHEDKF.js.map} +0 -0
  318. /package/bundle/{chunk-4PIVWXUJ.js.map → chunk-LUNA6PM5.js.map} +0 -0
  319. /package/bundle/{chunk-MV5KOWOR.js.map → chunk-NDCRWEEJ.js.map} +0 -0
  320. /package/bundle/{chunk-ZOCEBV62.js.map → chunk-OKAQICWY.js.map} +0 -0
  321. /package/bundle/{chunk-TCI6FZTP.js.map → chunk-OLAURO5G.js.map} +0 -0
  322. /package/bundle/{chunk-YME7NRGP.js.map → chunk-OXTSWQCX.js.map} +0 -0
  323. /package/bundle/{chunk-HDOFJVFS.js.map → chunk-PEDX56EL.js.map} +0 -0
  324. /package/bundle/{chunk-ASYX43OU.js.map → chunk-Q32H6VPU.js.map} +0 -0
  325. /package/bundle/{chunk-IQKADER4.js.map → chunk-RWRRGE4U.js.map} +0 -0
  326. /package/bundle/{chunk-ULO2PX3T.js.map → chunk-TEFZ4JA4.js.map} +0 -0
  327. /package/bundle/{chunk-2RGR3LSV.js.map → chunk-TMUYFERL.js.map} +0 -0
  328. /package/bundle/{chunk-KBPVJGD7.js.map → chunk-URQPDCK5.js.map} +0 -0
  329. /package/bundle/{chunk-FJF42RZY.js.map → chunk-VUIX5AGB.js.map} +0 -0
  330. /package/bundle/{chunk-4HNCOQSK.js.map → chunk-WYHGNI56.js.map} +0 -0
  331. /package/bundle/{chunk-24V4A6RP.js.map → chunk-XX6BGTPO.js.map} +0 -0
  332. /package/bundle/{chunk-T7TAWGBX.js.map → chunk-Y76VUJSF.js.map} +0 -0
  333. /package/bundle/{chunk-TVSPVZTX.js.map → chunk-YDY6QVWJ.js.map} +0 -0
  334. /package/bundle/{chunk-V6CV3QPH.js.map → chunk-YRSMGJFP.js.map} +0 -0
  335. /package/bundle/{chunk-WP7FZHMI.js.map → chunk-YSKCQH6E.js.map} +0 -0
  336. /package/bundle/{chunk-NGZVJ52F.js.map → chunk-ZKJOFASV.js.map} +0 -0
  337. /package/bundle/{chunk-43DKPXTP.js.map → chunk-ZV4IWKDJ.js.map} +0 -0
  338. /package/bundle/{commands-XXFU2ZF7.js.map → commands-EWA4HNCM.js.map} +0 -0
  339. /package/bundle/{config-EWDZ234X.js.map → config-M3P5IOAI.js.map} +0 -0
  340. /package/bundle/{config-show-6J33O4TE.js.map → config-show-3DHPP26D.js.map} +0 -0
  341. /package/bundle/{daemon-LTDAXNA2.js.map → daemon-TB23FFWY.js.map} +0 -0
  342. /package/bundle/{delegation-tools-YDTWQMZD.js.map → delegation-tools-P2SCNL23.js.map} +0 -0
  343. /package/bundle/{deploy-lib-import-RGZJ3CGC.js.map → deploy-YYUCGGP3.js.map} +0 -0
  344. /package/bundle/{doctor-probes-3SLIUGKS.js.map → deploy-lib-import-T3UP4G6G.js.map} +0 -0
  345. /package/bundle/{discord-adapter-WUNYPTDE.js.map → discord-adapter-4TTETYDI.js.map} +0 -0
  346. /package/bundle/{env-schema-MSDP2YBO.js.map → doctor-probes-VDWFJKUB.js.map} +0 -0
  347. /package/bundle/{gossip-CS3G3447.js.map → env-schema-4JXQUOH4.js.map} +0 -0
  348. /package/bundle/{guardrails-24XK2COI.js.map → gossip-3C3BSNPN.js.map} +0 -0
  349. /package/bundle/{heartbeat-system-G4IFQXT6.js.map → guardrails-DL7ZSWVN.js.map} +0 -0
  350. /package/bundle/{hook-system-X6INNJGV.js.map → heartbeat-system-TDDIOVTC.js.map} +0 -0
  351. /package/bundle/{hotskills-6FQYTJIO.js.map → hook-system-M3POLUIB.js.map} +0 -0
  352. /package/bundle/{kanban-board-J6RO3ZU7.js.map → hotskills-FWX4QI7V.js.map} +0 -0
  353. /package/bundle/{kanban-channel-5EIXBFSA.js.map → kanban-board-M326B2XJ.js.map} +0 -0
  354. /package/bundle/{lazy-require-V6EFUATC.js.map → kanban-channel-IJ52OMNA.js.map} +0 -0
  355. /package/bundle/{logger-Y3VILPRH.js.map → lazy-require-KCRVT4SI.js.map} +0 -0
  356. /package/bundle/{main-chat-YLZDNQPO.js.map → logger-OWCSNYCA.js.map} +0 -0
  357. /package/bundle/{logs-YS3GDURO.js.map → logs-FXS4SCEM.js.map} +0 -0
  358. /package/bundle/{master-user-Z4M7KCJE.js.map → main-chat-ZNUZCTNS.js.map} +0 -0
  359. /package/bundle/{message-pipeline-MHEBDJLH.js.map → master-user-HSKM4ZFN.js.map} +0 -0
  360. /package/bundle/{nerve-VZNMFDGY.js.map → message-pipeline-KSONH4MT.js.map} +0 -0
  361. /package/bundle/{notification-VV2OR6NW.js.map → nerve-IGSXBKZZ.js.map} +0 -0
  362. /package/bundle/{orc-tools-CHRSXSAS.js.map → notification-BFSIEECG.js.map} +0 -0
  363. /package/bundle/{orc-KC4USP55.js.map → orc-EIGVTHAV.js.map} +0 -0
  364. /package/bundle/{paths-EDK6KWHG.js.map → orc-tools-A3G7WCSJ.js.map} +0 -0
  365. /package/bundle/{paths-RZF6WDMG.js.map → paths-3ZVW3NFL.js.map} +0 -0
  366. /package/bundle/{peer-auth-SRONOLNG.js.map → paths-X4LRYUI6.js.map} +0 -0
  367. /package/bundle/{peer-config-FRWLEYQ5.js.map → peer-auth-QC4EF2PM.js.map} +0 -0
  368. /package/bundle/{peer-jwt-XY3XRIA2.js.map → peer-config-TN55LFDC.js.map} +0 -0
  369. /package/bundle/{peer-transport-UBBXTDRP.js.map → peer-jwt-NCCPXJRX.js.map} +0 -0
  370. /package/bundle/{phase-config-V4XETN5F.js.map → peer-transport-I6JPLFZ2.js.map} +0 -0
  371. /package/bundle/{phase-transport-4NQHZX75.js.map → phase-transport-2BRWACDF.js.map} +0 -0
  372. /package/bundle/{reconcile-2EUXJ6W5.js.map → reconcile-CTFCLQRN.js.map} +0 -0
  373. /package/bundle/{registry-client-VN2MM2HI.js.map → rollback-ANRI3T5Z.js.map} +0 -0
  374. /package/bundle/{rollback-MVZ53XS4.js.map → sha-tracker-ZWBP6CIJ.js.map} +0 -0
  375. /package/bundle/{sandbox-runtime-WHACQLLN.js.map → skill-stats-JORH5DGM.js.map} +0 -0
  376. /package/bundle/{sha-tracker-2DB4R2TW.js.map → skill-watcher-E4MGLKLS.js.map} +0 -0
  377. /package/bundle/{skill-stats-TPD2NROA.js.map → sleep-SRCSXY6T.js.map} +0 -0
  378. /package/bundle/{skill-watcher-D7QYYYON.js.map → soul-bundle-VWAVHCZ6.js.map} +0 -0
  379. /package/bundle/{sleep-GH6DLBJJ.js.map → spin-IMW2MZOH.js.map} +0 -0
  380. /package/bundle/{soul-bundle-GXLMDBCC.js.map → spin-types-BLPYAETA.js.map} +0 -0
  381. /package/bundle/{spin-4DBYHS3E.js.map → src-6BTCMOD3.js.map} +0 -0
  382. /package/bundle/{spin-types-PLJH3SIK.js.map → stt-LGVPXMVR.js.map} +0 -0
  383. /package/bundle/{src-SUFZ27S5.js.map → subagent-runtime-3UJB4HUB.js.map} +0 -0
  384. /package/bundle/{stt-KD3AABKG.js.map → task-store-W5BFIAIH.js.map} +0 -0
  385. /package/bundle/{telegram-adapter-UJ3RYYV6.js.map → telegram-adapter-7G773NII.js.map} +0 -0
  386. /package/bundle/{subagent-runtime-LVECAUPV.js.map → tool-registry-J6TE3I2T.js.map} +0 -0
  387. /package/bundle/{task-store-2XRDM3AW.js.map → tool-sandbox-4UC6GAKA.js.map} +0 -0
  388. /package/bundle/{tool-registry-YU6WBXPA.js.map → transport-config-KBF5W2DP.js.map} +0 -0
  389. /package/bundle/{tool-sandbox-RNNPDR5M.js.map → update-424ZZQQ6.js.map} +0 -0
  390. /package/bundle/{transport-config-OK3MZPJK.js.map → usage-tracker-NXD364VX.js.map} +0 -0
  391. /package/bundle/{update-ENNPRW7Y.js.map → user-registry-35BW4XKM.js.map} +0 -0
  392. /package/bundle/{usage-tracker-HRSGC7QC.js.map → wrapper-W66YICNZ.js.map} +0 -0
@@ -85,4 +85,4 @@ export {
85
85
  writeKeyVerify,
86
86
  validateKey
87
87
  };
88
- //# sourceMappingURL=chunk-OY2HAK33.js.map
88
+ //# sourceMappingURL=chunk-36ZEYDKZ.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../src/utils/crypto.ts"],
4
+ "sourcesContent": ["/**\n * crypto.ts \u2014 AES-256-GCM encryption for abtars secrets.\n * Shared utility (same logic in abmind). See shared-utilities.md.\n *\n * Key: ~/.abtars/secret/abtars.key (32-byte hex, passphrase-derived via scrypt).\n * Purpose derivation: HKDF(master, \"abtars-secrets-v1\") for file encryption.\n */\n\nimport { createDecipheriv, createCipheriv, randomBytes, hkdfSync, scryptSync, createHash } from \"node:crypto\";\nimport { existsSync, readFileSync, writeFileSync, mkdirSync } from \"node:fs\";\nimport { join, dirname } from \"node:path\";\n\nconst ALGO = \"aes-256-gcm\";\nconst IV_LEN = 12;\nconst TAG_LEN = 16;\nconst PURPOSE = \"abtars-secrets-v1\";\n\n/** Load master key from file. Returns null if file doesn't exist. */\nexport function loadKey(keyPath: string): Buffer | null {\n try {\n if (!existsSync(keyPath)) return null;\n const hex = readFileSync(keyPath, \"utf-8\").trim();\n if (hex.length !== 64) return null;\n return Buffer.from(hex, \"hex\");\n } catch { return null; }\n}\n\n/** Derive purpose-specific key from master via HKDF. */\nexport function deriveKey(master: Buffer, purpose: string = PURPOSE): Buffer {\n return Buffer.from(hkdfSync(\"sha256\", master, \"\", purpose, 32));\n}\n\n/** Derive master key from passphrase + username (same algorithm as abmind). */\nexport function deriveFromPassphrase(passphrase: string, username: string): Buffer {\n const salt = createHash(\"sha256\").update(\"abtars:\" + username).digest().subarray(0, 16);\n return scryptSync(passphrase, salt, 32, { N: 16384, r: 8, p: 1 });\n}\n\n/** Encrypt plaintext. Returns \"ENC:\" + base64(version + iv + ciphertext + tag). */\nexport function encrypt(plaintext: string, key: Buffer): string {\n const iv = randomBytes(IV_LEN);\n const c = createCipheriv(ALGO, key, iv);\n const enc = Buffer.concat([c.update(plaintext, \"utf-8\"), c.final()]);\n return \"ENC:\" + Buffer.concat([Buffer.from([0x01]), iv, enc, c.getAuthTag()]).toString(\"base64\");\n}\n\n/** Decrypt \"ENC:...\" string. Returns plaintext or null on failure. */\nexport function decrypt(raw: string, key: Buffer): string | null {\n try {\n const buf = Buffer.from(raw.slice(4), \"base64\");\n const iv = buf.subarray(1, 1 + IV_LEN);\n const tag = buf.subarray(buf.length - TAG_LEN);\n const ct = buf.subarray(1 + IV_LEN, buf.length - TAG_LEN);\n const d = createDecipheriv(ALGO, key, iv);\n d.setAuthTag(tag);\n return d.update(ct, undefined, \"utf-8\") + d.final(\"utf-8\");\n } catch { return null; }\n}\n\n/** Write key to file (hex, mode 600). Creates parent dir if needed. */\nexport function writeKeyFile(keyPath: string, master: Buffer): void {\n mkdirSync(dirname(keyPath), { recursive: true });\n writeFileSync(keyPath, master.toString(\"hex\"), { mode: 0o600 });\n}\n\nconst VERIFY_PLAINTEXT = \"abtars-verify\";\n\n/** Create key.verify file next to the key (encrypt known plaintext). */\nexport function writeKeyVerify(keyPath: string, key: Buffer): void {\n const iv = randomBytes(IV_LEN);\n const cipher = createCipheriv(ALGO, key, iv);\n const enc = Buffer.concat([cipher.update(VERIFY_PLAINTEXT, \"utf-8\"), cipher.final()]);\n const blob = Buffer.concat([iv, enc, cipher.getAuthTag()]).toString(\"base64\");\n writeFileSync(join(dirname(keyPath), \"key.verify\"), blob, { mode: 0o600 });\n}\n\n/** Validate a key against key.verify. Returns true if key is correct or no verify file exists. */\nexport function validateKey(keyPath: string, key: Buffer): boolean {\n const verifyPath = join(dirname(keyPath), \"key.verify\");\n if (!existsSync(verifyPath)) return true; // no verify file = skip validation\n try {\n const blob = readFileSync(verifyPath, \"utf-8\").trim();\n const buf = Buffer.from(blob, \"base64\");\n const iv = buf.subarray(0, IV_LEN);\n const tag = buf.subarray(buf.length - TAG_LEN);\n const ct = buf.subarray(IV_LEN, buf.length - TAG_LEN);\n const d = createDecipheriv(ALGO, key, iv);\n d.setAuthTag(tag);\n const result = d.update(ct, undefined, \"utf-8\") + d.final(\"utf-8\");\n return result === VERIFY_PLAINTEXT;\n } catch { return false; }\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -3,12 +3,12 @@
3
3
  import {
4
4
  init_log_and_swallow,
5
5
  logAndSwallow
6
- } from "./chunk-WP7FZHMI.js";
6
+ } from "./chunk-YSKCQH6E.js";
7
7
  import {
8
8
  init_logger,
9
9
  logInfo,
10
10
  logWarn
11
- } from "./chunk-OOKNHOCB.js";
11
+ } from "./chunk-GWILHZPT.js";
12
12
 
13
13
  // src/components/subagent-runtime.ts
14
14
  init_log_and_swallow();
@@ -57,7 +57,7 @@ var SubagentRuntime = class {
57
57
  }
58
58
  /** Send a prompt to a named agent and get the response. */
59
59
  async complete(agent, prompt, opts) {
60
- const { checkBudget, sendBudgetNotification } = await import("./budget-PPA7WY3D.js");
60
+ const { checkBudget, sendBudgetNotification } = await import("./budget-45QOBDWA.js");
61
61
  const budgetCheck = checkBudget(agent);
62
62
  if (!budgetCheck.allowed) {
63
63
  const reason = budgetCheck.remaining.tokens <= 0 ? "token" : "call";
@@ -69,7 +69,7 @@ var SubagentRuntime = class {
69
69
  const cached = this.cache.get(agent);
70
70
  if (cached && sessionStrategy === "fresh") {
71
71
  await cached.transport.resetSession?.(cached.sessionKey);
72
- (await import("./tool-registry-YU6WBXPA.js")).resetStoreCounter();
72
+ (await import("./tool-registry-J6TE3I2T.js")).resetStoreCounter();
73
73
  }
74
74
  const { transport, model, sessionKey } = cached ?? await this.createAgent(agent, opts?.sessionType);
75
75
  if (opts?.timeoutMs && transport.setTimeoutOverride) {
@@ -173,26 +173,26 @@ var SubagentRuntime = class {
173
173
  const resolvedType = sessionType || typeMap[agent];
174
174
  const sandboxTypes = /* @__PURE__ */ new Set(["B", "C", "W"]);
175
175
  if (this._sandboxEnabled && resolvedType && sandboxTypes.has(resolvedType)) {
176
- const { logInfo: logInfo2 } = await import("./logger-Y3VILPRH.js");
176
+ const { logInfo: logInfo2 } = await import("./logger-OWCSNYCA.js");
177
177
  logInfo2("subagent", `Sandbox spawn: ${agent} (type=${resolvedType}) \u2192 Docker container`);
178
178
  }
179
- const { createSubagentTransport } = await import("./agent-registry-563P4EUJ.js");
179
+ const { createSubagentTransport } = await import("./agent-registry-GU7ABOK5.js");
180
180
  const role = AGENT_TO_ROLE[agent];
181
181
  const mainModel = this._mainTransport && "currentModel" in this._mainTransport ? this._mainTransport.currentModel : void 0;
182
182
  const { transport, model } = await createSubagentTransport(role, this._registry ?? void 0, mainModel);
183
183
  if (transport.agent?.pid) {
184
- import("./bridge-lock-transport-LXCF2IVN.js").then(({ trackAcpPid }) => trackAcpPid(transport.agent.pid)).catch(() => {
184
+ import("./bridge-lock-transport-4ZH7QTJP.js").then(({ trackAcpPid }) => trackAcpPid(transport.agent.pid)).catch(() => {
185
185
  });
186
186
  }
187
187
  if (resolvedType && "setSystemPrompt" in transport && typeof transport.setSystemPrompt === "function") {
188
- const { buildSoulBundle } = await import("./soul-bundle-GXLMDBCC.js");
188
+ const { buildSoulBundle } = await import("./soul-bundle-VWAVHCZ6.js");
189
189
  const bundle = buildSoulBundle(resolvedType);
190
190
  if (bundle) transport.setSystemPrompt(bundle);
191
191
  }
192
192
  const sessionKey = `system:${cacheKey ?? agent}`;
193
193
  const entry = { transport, model, sessionKey };
194
194
  this.cache.set(cacheKey ?? agent, entry);
195
- (await import("./tool-registry-YU6WBXPA.js")).resetStoreCounter();
195
+ (await import("./tool-registry-J6TE3I2T.js")).resetStoreCounter();
196
196
  return entry;
197
197
  }
198
198
  };
@@ -207,4 +207,4 @@ var AGENT_TO_ROLE = {
207
207
  export {
208
208
  SubagentRuntime
209
209
  };
210
- //# sourceMappingURL=chunk-2FZJDMAF.js.map
210
+ //# sourceMappingURL=chunk-3CACHBDI.js.map
@@ -4,16 +4,16 @@ import {
4
4
  PEERS_SCHEMA,
5
5
  init_config_validator,
6
6
  validateShape
7
- } from "./chunk-4PIVWXUJ.js";
7
+ } from "./chunk-LUNA6PM5.js";
8
8
  import {
9
9
  init_logger,
10
10
  logInfo,
11
11
  logWarn
12
- } from "./chunk-OOKNHOCB.js";
12
+ } from "./chunk-GWILHZPT.js";
13
13
  import {
14
14
  abtarsHome,
15
15
  init_paths
16
- } from "./chunk-H2K23MOF.js";
16
+ } from "./chunk-GALQBVKO.js";
17
17
  import {
18
18
  __esm,
19
19
  __export
@@ -102,4 +102,4 @@ export {
102
102
  peer_config_exports,
103
103
  init_peer_config
104
104
  };
105
- //# sourceMappingURL=chunk-O4GKI3Q3.js.map
105
+ //# sourceMappingURL=chunk-4S554KLW.js.map
@@ -3,17 +3,17 @@
3
3
  import {
4
4
  getAlivePeers,
5
5
  init_gossip
6
- } from "./chunk-BNBC4T45.js";
6
+ } from "./chunk-HT2BPTZY.js";
7
7
  import {
8
8
  init_peer_config,
9
9
  loadPeerConfig
10
- } from "./chunk-O4GKI3Q3.js";
10
+ } from "./chunk-4S554KLW.js";
11
11
  import {
12
12
  init_logger,
13
13
  logDebug,
14
14
  logInfo,
15
15
  logTrace
16
- } from "./chunk-OOKNHOCB.js";
16
+ } from "./chunk-GWILHZPT.js";
17
17
  import {
18
18
  __esm
19
19
  } from "./chunk-7K2YZTLD.js";
@@ -38,14 +38,14 @@ var init_http_transport = __esm({
38
38
  /** Init WS connections for all ws-outbound peers. Call on boot. */
39
39
  async initWsConnections() {
40
40
  const config = loadPeerConfig();
41
- const { WsPeerClient: Client } = await import("./ws-peer-client-WHW3RJTD.js");
41
+ const { WsPeerClient: Client } = await import("./ws-peer-client-AIXCXF7V.js");
42
42
  for (const [name, entry] of Object.entries(config.peers)) {
43
43
  if (entry.transport !== "ws-outbound") continue;
44
44
  const client = new Client(name, entry);
45
45
  client.onPush((method, payload) => {
46
46
  if (method === "callback") {
47
47
  const p = payload;
48
- import("./kanban-board-J6RO3ZU7.js").then(({ kanbanList, kanbanComplete, kanbanFail, kanbanAddTokens }) => {
48
+ import("./kanban-board-M326B2XJ.js").then(({ kanbanList, kanbanComplete, kanbanFail, kanbanAddTokens }) => {
49
49
  const cards = kanbanList("running", "status").filter((c) => {
50
50
  if (c.type !== "remote") return false;
51
51
  try {
@@ -58,14 +58,14 @@ var init_http_transport = __esm({
58
58
  if (!cards.length) return;
59
59
  const card = cards[0];
60
60
  if (p.tokens_used) kanbanAddTokens(card.id, p.tokens_used);
61
- if (p.status === "done") kanbanComplete(card.id, void 0, p.result_summary);
61
+ if (p.status === "done") kanbanComplete(card.id, null, p.result_summary ?? "");
62
62
  else kanbanFail(card.id, p.error ?? "remote failure");
63
- import("./nerve-VZNMFDGY.js").then(({ nerve }) => nerve.emit(p.status === "done" ? "card:done" : "card:failed", card.id));
63
+ import("./nerve-IGSXBKZZ.js").then(({ nerve }) => nerve.emit(p.status === "done" ? "card:done" : "card:failed", card.id));
64
64
  }).catch(() => {
65
65
  });
66
66
  } else if (method === "channel") {
67
67
  const p = payload;
68
- import("./kanban-channel-5EIXBFSA.js").then(({ channelPost }) => {
68
+ import("./kanban-channel-IJ52OMNA.js").then(({ channelPost }) => {
69
69
  channelPost(p.card_id, p.from_agent, "ALL", p.message);
70
70
  }).catch(() => {
71
71
  });
@@ -81,20 +81,12 @@ var init_http_transport = __esm({
81
81
  hasWsConnection(peer) {
82
82
  return this.wsClients.get(peer)?.connected ?? false;
83
83
  }
84
- /** Send via WS if available, otherwise fall back to HTTP. */
85
- async wsOrHttp(peer, method, payload, httpFallback) {
86
- const ws = this.wsClients.get(peer);
87
- if (ws?.connected) {
88
- return ws.send(method, payload);
89
- }
90
- return httpFallback();
91
- }
92
84
  discover() {
93
85
  return getAlivePeers();
94
86
  }
95
87
  async send(peer, message) {
96
88
  if (message.type === "ask") {
97
- const { callPeer } = await import("./peer-client-VOF77T6C.js");
89
+ const { callPeer } = await import("./peer-client-RGEU5HOK.js");
98
90
  const config = loadPeerConfig();
99
91
  return callPeer(peer, message.payload.prompt, config.maxHops);
100
92
  }
@@ -194,7 +186,7 @@ var init_http_transport = __esm({
194
186
  await this.httpCall(entry, peer, "POST", `/v1/tasks/${cardId}/messages`, JSON.stringify({ from_agent: from, message, created_at: createdAt }));
195
187
  }
196
188
  async httpCall(entry, peerName, method, path, body) {
197
- const { mintPeerJwt, signBody, tlsOptions } = await import("./peer-auth-SRONOLNG.js");
189
+ const { mintPeerJwt, signBody, tlsOptions } = await import("./peer-auth-QC4EF2PM.js");
198
190
  const jwt = mintPeerJwt(peerName);
199
191
  const finalBody = body ? await signBody(peerName, body) : void 0;
200
192
  const tls = tlsOptions(entry);
@@ -262,4 +254,4 @@ export {
262
254
  initPeerTransport,
263
255
  init_peer_transport
264
256
  };
265
- //# sourceMappingURL=chunk-3QW2K53E.js.map
257
+ //# sourceMappingURL=chunk-5GCLBUBS.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../src/components/peer-transport/http-transport.ts", "../src/components/peer-transport/index.ts"],
4
+ "sourcesContent": ["/**\n * peer-transport/http-transport.ts \u2014 HTTP implementation of PeerTransport (#911).\n *\n * Wraps existing peer-client.ts (JWT auth, TLS, Ed25519 signing) behind the\n * PeerTransport interface. discover() reads peers.json (static).\n */\n\nimport type { PeerTransport, PeerCard, PeerMessage, TaskResult } from \"./interface.js\";\nimport { getAlivePeers } from \"./gossip.js\";\nimport { loadPeerConfig, type PeerEntry } from \"../peer-config.js\";\nimport { logInfo, logDebug, logTrace } from \"../logger.js\";\nimport type { WsPeerClient } from \"./ws-peer-client.js\";\n\nconst TAG = \"http-transport\";\n\nexport class HttpTransport implements PeerTransport {\n private handlers: Array<(from: string, message: PeerMessage) => void> = [];\n private wsClients = new Map<string, WsPeerClient>();\n\n /** Init WS connections for all ws-outbound peers. Call on boot. */\n async initWsConnections(): Promise<void> {\n const config = loadPeerConfig();\n const { WsPeerClient: Client } = await import(\"./ws-peer-client.js\");\n for (const [name, entry] of Object.entries(config.peers)) {\n if (entry.transport !== \"ws-outbound\") continue;\n const client = new Client(name, entry);\n client.onPush((method, payload) => {\n if (method === \"callback\") {\n // Inbound callback from peer \u2014 fire as if it arrived via HTTP /v1/callbacks\n const p = payload as { task_id: number; status: string; result_summary?: string; error?: string; tokens_used?: number };\n import(\"../tasks/kanban-board.js\").then(({ kanbanList, kanbanComplete, kanbanFail, kanbanAddTokens }) => {\n const cards = kanbanList(\"running\", \"status\").filter(c => {\n if (c.type !== \"remote\") return false;\n try { const m = JSON.parse(c.notes ?? \"{}\"); return m.peer === name && m.remote_task_id === p.task_id; } catch { return false; }\n });\n if (!cards.length) return;\n const card = cards[0]!;\n if (p.tokens_used) kanbanAddTokens(card.id, p.tokens_used);\n if (p.status === \"done\") kanbanComplete(card.id, null, p.result_summary ?? \"\");\n else kanbanFail(card.id, p.error ?? \"remote failure\");\n import(\"../nerve.js\").then(({ nerve }) => nerve.emit(p.status === \"done\" ? \"card:done\" : \"card:failed\", card.id));\n }).catch(() => {});\n } else if (method === \"channel\") {\n // Inbound channel message from peer\n const p = payload as { card_id: number; from_agent: string; message: string; created_at: string };\n import(\"../tasks/kanban-channel.js\").then(({ channelPost }) => {\n channelPost(p.card_id, p.from_agent, \"ALL\", p.message);\n }).catch(() => {});\n }\n for (const h of this.handlers) h(name, { type: method as any, payload: payload as any });\n });\n client.connect();\n this.wsClients.set(name, client);\n logInfo(TAG, `WS outbound: connecting to ${name}`);\n }\n }\n\n /** Check if a peer is reachable via WS. */\n hasWsConnection(peer: string): boolean {\n return this.wsClients.get(peer)?.connected ?? false;\n }\n\n discover(): PeerCard[] {\n return getAlivePeers();\n }\n\n async send(peer: string, message: PeerMessage): Promise<unknown> {\n if (message.type === \"ask\") {\n const { callPeer } = await import(\"../peer-client.js\");\n const config = loadPeerConfig();\n return callPeer(peer, message.payload.prompt as string, config.maxHops);\n }\n if (message.type === \"task\" && message.payload.action === \"callback\") {\n const config = loadPeerConfig();\n const entry = resolvePeer(config.peers, peer);\n logDebug(TAG, `\u2192 callback ${peer}: task_id=${message.payload.task_id} status=${message.payload.status}`);\n logTrace(TAG, `\u2192 callback ${peer} result: ${String(message.payload.result_summary ?? \"\").slice(0, 200)}`);\n const payload: Record<string, unknown> = { task_id: message.payload.task_id, status: message.payload.status, result_summary: message.payload.result_summary, error: message.payload.error };\n if (message.payload.artifacts) payload.artifacts = message.payload.artifacts;\n\n // #972: Push via WS if connected\n const ws = this.wsClients.get(peer);\n if (ws?.connected) {\n await ws.send(\"callback\", payload);\n logInfo(TAG, `CALLBACK ${peer} (ws) task_id=${message.payload.task_id}`);\n return;\n }\n\n const body = JSON.stringify(payload);\n return this.httpCall(entry, peer, \"POST\", \"/v1/callbacks\", body);\n }\n if (message.type === \"task\") return this.delegateTask(peer, message.payload.goal as string, message.payload as any);\n if (message.type === \"check\") return this.checkTask(peer, message.payload.taskId as number);\n if (message.type === \"terminate\") return this.terminateTask(peer, message.payload.taskId as number);\n throw new Error(`Unknown message type: ${message.type}`);\n }\n\n async broadcast(message: PeerMessage): Promise<void> {\n const peers = this.discover();\n await Promise.allSettled(peers.map(p => this.send(p.name, message)));\n }\n\n onMessage(handler: (from: string, message: PeerMessage) => void): void {\n this.handlers.push(handler);\n }\n\n /** Called by agent-api-server when an inbound peer message arrives. */\n dispatchInbound(from: string, message: PeerMessage): void {\n for (const h of this.handlers) { try { h(from, message); } catch {} }\n }\n\n async delegateTask(peer: string, goal: string, opts?: { priority?: string; context?: string; artifacts?: Array<{ name: string; content: string }> }): Promise<{ taskId: number; remoteSessionId?: string }> {\n const config = loadPeerConfig();\n const entry = resolvePeer(config.peers, peer);\n\n // Callback: remote peer looks us up in its peers.json by name\n\n logDebug(TAG, `\u2192 peer_delegate ${peer}: priority=${opts?.priority ?? \"MEDIUM\"}, goal=${goal.length}ch`);\n logTrace(TAG, `\u2192 peer_delegate ${peer} goal: ${goal.slice(0, 300)}`);\n\n // Size guard for artifacts (#928)\n if (opts?.artifacts?.length) {\n const MAX_SINGLE = 1_400_000; // 1.4MB base64 per artifact\n const MAX_TOTAL = 5_000_000; // 5MB total\n let total = 0;\n for (const a of opts.artifacts) {\n if (a.content.length > MAX_SINGLE) throw new Error(`Artifact '${a.name}' exceeds 1.4MB limit (${a.content.length} bytes)`);\n total += a.content.length;\n }\n if (total > MAX_TOTAL) throw new Error(`Total artifacts exceed 5MB limit (${total} bytes)`);\n }\n\n const payload: Record<string, unknown> = { goal, priority: opts?.priority ?? \"MEDIUM\", context: opts?.context, callback_peer: config.self.name };\n if (opts?.artifacts?.length) payload.artifacts = opts.artifacts;\n\n // #972: Route via WS if connected, otherwise HTTP\n const ws = this.wsClients.get(peer);\n if (ws?.connected) {\n const result = await ws.send(\"delegate\", payload) as any;\n logInfo(TAG, `PEER_DELEGATE ${peer} (ws) \u2192 remote#${result.taskId} (${goal.length}ch)`);\n return { taskId: result.taskId, remoteSessionId: result.session_id };\n }\n\n const body = JSON.stringify(payload);\n const response = await this.httpCall(entry, peer, \"POST\", \"/v1/tasks\", body);\n const parsed = JSON.parse(response);\n logInfo(TAG, `PEER_DELEGATE ${peer} \u2192 remote#${parsed.task_id} (${goal.length}ch)`);\n return { taskId: parsed.task_id, remoteSessionId: parsed.session_id };\n }\n\n async checkTask(peer: string, taskId: number): Promise<TaskResult> {\n const config = loadPeerConfig();\n const entry = resolvePeer(config.peers, peer);\n logDebug(TAG, `\u2192 peer_check ${peer}#${taskId}`);\n const response = await this.httpCall(entry, peer, \"GET\", `/v1/tasks/${taskId}`);\n const parsed = JSON.parse(response);\n logDebug(TAG, `\u2190 peer_check ${peer}#${taskId}: status=${parsed.status}`);\n logTrace(TAG, `\u2190 peer_check ${peer}#${taskId} result: ${(parsed.result_summary ?? \"\").slice(0, 200)}`);\n return {\n taskId: parsed.id ?? taskId,\n status: parsed.status,\n result: parsed.result_summary,\n error: parsed.error,\n tokensUsed: parsed.tokens_used,\n };\n }\n\n async terminateTask(peer: string, taskId: number): Promise<void> {\n const config = loadPeerConfig();\n const entry = resolvePeer(config.peers, peer);\n logDebug(TAG, `\u2192 peer_terminate ${peer}#${taskId}`);\n await this.httpCall(entry, peer, \"DELETE\", `/v1/tasks/${taskId}`);\n logInfo(TAG, `PEER_TERMINATE ${peer}#${taskId}`);\n }\n\n /** #949: Push a channel message to a remote peer. */\n async pushChannelMessage(peer: string, cardId: number, from: string, message: string, createdAt: string): Promise<void> {\n const config = loadPeerConfig();\n const entry = resolvePeer(config.peers, peer);\n await this.httpCall(entry, peer, \"POST\", `/v1/tasks/${cardId}/messages`, JSON.stringify({ from_agent: from, message, created_at: createdAt }));\n }\n\n private async httpCall(entry: PeerEntry, peerName: string, method: string, path: string, body?: string): Promise<string> {\n const { mintPeerJwt, signBody, tlsOptions } = await import(\"./peer-auth.js\");\n const jwt = mintPeerJwt(peerName);\n const finalBody = body ? await signBody(peerName, body) : undefined;\n const tls = tlsOptions(entry);\n const http = await import(\"node:https\");\n\n return new Promise((resolve, reject) => {\n const headers: Record<string, string> = {\n \"Authorization\": `Bearer ${jwt}`,\n \"Content-Type\": \"application/json\",\n };\n if (finalBody) headers[\"Content-Length\"] = String(Buffer.byteLength(finalBody));\n\n const req = http.request({\n hostname: entry.host,\n port: entry.port,\n path,\n method,\n headers,\n timeout: 60_000,\n ...tls,\n } as any, (res: any) => {\n let data = \"\";\n res.on(\"data\", (c: any) => data += c);\n res.on(\"end\", () => {\n if (res.statusCode >= 400) {\n reject(new Error(`Peer ${peerName} returned ${res.statusCode}: ${data.slice(0, 200)}`));\n return;\n }\n resolve(data);\n });\n });\n req.on(\"timeout\", () => { req.destroy(); reject(new Error(`Peer ${peerName} timeout`)); });\n req.on(\"error\", (err: Error) => reject(new Error(`Peer ${peerName} unreachable: ${err.message}`)));\n if (finalBody) req.write(finalBody);\n req.end();\n });\n }\n}\n\nfunction resolvePeer(peers: Record<string, PeerEntry>, name: string): PeerEntry {\n const key = Object.keys(peers).find(k => k.toLowerCase() === name.toLowerCase());\n if (!key || !peers[key]) throw new Error(`Unknown peer '${name}'. Available: ${Object.keys(peers).join(\", \")}`);\n return peers[key];\n}\n", "/**\n * peer-transport/index.ts \u2014 Factory + singleton (#911).\n */\n\nexport type { PeerTransport, PeerCard, PeerMessage, TaskResult, PeerHealth } from \"./interface.js\";\nexport { HttpTransport } from \"./http-transport.js\";\nexport { startGossipListener, gossipBroadcast, getAlivePeers, getPeerTable, setGossipInterval, stopGossipListener } from \"./gossip.js\";\n\nimport { HttpTransport } from \"./http-transport.js\";\nimport type { PeerTransport } from \"./interface.js\";\n\nlet _instance: PeerTransport | null = null;\n\n/** Get the singleton PeerTransport instance. */\nexport function getPeerTransport(): PeerTransport {\n if (!_instance) _instance = new HttpTransport();\n return _instance;\n}\n\n/** Initialize peer transport + WS outbound connections. Call at boot. */\nexport async function initPeerTransport(): Promise<void> {\n const transport = getPeerTransport() as HttpTransport;\n await transport.initWsConnections();\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -3,7 +3,7 @@
3
3
  import {
4
4
  abtarsHome,
5
5
  init_paths
6
- } from "./chunk-H2K23MOF.js";
6
+ } from "./chunk-GALQBVKO.js";
7
7
  import {
8
8
  __require
9
9
  } from "./chunk-7K2YZTLD.js";
@@ -12,6 +12,7 @@ import {
12
12
  init_paths();
13
13
  import { existsSync, readFileSync, readdirSync, statSync } from "node:fs";
14
14
  import { join } from "node:path";
15
+ import { homedir } from "node:os";
15
16
  var home = abtarsHome();
16
17
  var configDir = join(home, "config");
17
18
  function readJson(path) {
@@ -131,8 +132,12 @@ async function probeSpin() {
131
132
  async function probeKanban() {
132
133
  const dbPath = join(home, "kanban", "kanban.db");
133
134
  if (!existsSync(dbPath)) return { name: "kanban", status: "skipped", detail: "kanban.db not found" };
135
+ const sharedNm = join(homedir(), ".local", "lib", "node_modules", "better-sqlite3");
136
+ if (!existsSync(sharedNm)) return { name: "kanban", status: "skipped", detail: "better-sqlite3 not installed (run: abtars deps install)" };
134
137
  try {
135
- const Db = __require("better-sqlite3");
138
+ const { createRequire } = await import("node:module");
139
+ const _require = createRequire(import.meta.url);
140
+ const Db = _require(sharedNm);
136
141
  const db = new Db(dbPath, { readonly: true });
137
142
  const row = db.prepare("SELECT COUNT(*) as cnt FROM cards").get();
138
143
  const stuck = db.prepare("SELECT COUNT(*) as cnt FROM cards WHERE status='running' AND updated_at < datetime('now', '-10 minutes')").get();
@@ -265,7 +270,7 @@ async function runAllProbes() {
265
270
  }
266
271
  async function runFixes() {
267
272
  const { chmodSync, unlinkSync, mkdirSync, existsSync: ex, readdirSync: rd, statSync: st, readFileSync: rf, writeFileSync: wf } = await import("node:fs");
268
- const { execSync, spawnSync } = await import("node:child_process");
273
+ const { spawnSync } = await import("node:child_process");
269
274
  const fixes = [];
270
275
  function fix(probe, action, fn) {
271
276
  try {
@@ -448,4 +453,4 @@ export {
448
453
  renderHuman,
449
454
  renderJson
450
455
  };
451
- //# sourceMappingURL=chunk-RJX45XIC.js.map
456
+ //# sourceMappingURL=chunk-5HDSQFT6.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../src/cli/commands/doctor-probes.ts"],
4
+ "sourcesContent": ["/**\n * doctor-probes.ts \u2014 structured health probes grouped by subsystem layer.\n * Replaces scripts/doctor.sh entirely.\n */\n\nimport { existsSync, readFileSync, readdirSync, statSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { homedir } from \"node:os\";\nimport { abtarsHome } from \"../../paths.js\";\n\n// \u2500\u2500 Types \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport interface ProbeResult {\n name: string;\n status: \"ok\" | \"failed\" | \"skipped\";\n detail?: string;\n ms?: number;\n}\n\nexport interface FixResult {\n probe: string;\n action: string;\n success: boolean;\n}\n\nexport type LayerName = \"body\" | \"heart\" | \"brain\" | \"soul\" | \"tribe\";\n\nexport interface DoctorOutput {\n version: \"1.0\";\n totalMs: number;\n layers: Record<LayerName, ProbeResult[]>;\n fixes?: FixResult[];\n}\n\n// \u2500\u2500 Helpers \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nconst home = abtarsHome();\nconst configDir = join(home, \"config\");\n\nfunction readJson(path: string): any | null {\n try { return JSON.parse(readFileSync(path, \"utf-8\")); } catch { return null; }\n}\n\nfunction readEnv(): Map<string, string> {\n const envPath = join(configDir, \".env\");\n const map = new Map<string, string>();\n if (!existsSync(envPath)) return map;\n for (const line of readFileSync(envPath, \"utf-8\").split(\"\\n\")) {\n const m = line.match(/^([A-Z_]+)=(.*)$/);\n if (m) map.set(m[1]!, m[2]!.replace(/^[\"']|[\"']$/g, \"\"));\n }\n return map;\n}\n\nfunction pidAlive(pid: number): boolean {\n try { process.kill(pid, 0); return true; } catch { return false; }\n}\n\nfunction ago(ms: number): string {\n const s = Math.round(ms / 1000);\n if (s < 60) return `${s}s ago`;\n return `${Math.round(s / 60)}m ago`;\n}\n\nasync function timedProbe(fn: () => Promise<ProbeResult>): Promise<ProbeResult> {\n const start = Date.now();\n try {\n const r = await fn();\n r.ms = r.ms ?? (Date.now() - start);\n return r;\n } catch (err) {\n return { name: \"unknown\", status: \"failed\", detail: String(err), ms: Date.now() - start };\n }\n}\n\n// \u2500\u2500 Body Probes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nasync function probePlatforms(): Promise<ProbeResult> {\n const env = readEnv();\n const parts: string[] = [];\n if (env.get(\"TELEGRAM_BOT_TOKEN\") || env.get(\"TELEGRAM_TOKEN\")) parts.push(\"telegram\");\n if (env.get(\"DISCORD_TOKEN\") || env.get(\"DISCORD_BOT_TOKEN\")) parts.push(\"discord\");\n if (env.get(\"IRC_SERVER\")) parts.push(\"irc\");\n\n if (parts.length === 0) return { name: \"platforms\", status: \"failed\", detail: \"no platform configured\" };\n\n // Check bridge.lock for running status\n const lock = readJson(join(home, \"bridge.lock\"));\n if (lock?.pid && pidAlive(lock.pid)) {\n return { name: \"platforms\", status: \"ok\", detail: parts.map(p => `${p} \u2713`).join(\", \") };\n }\n return { name: \"platforms\", status: \"ok\", detail: `configured: ${parts.join(\", \")} (bridge not running)` };\n}\n\nasync function probeDashboard(): Promise<ProbeResult> {\n const env = readEnv();\n if (env.get(\"ENABLE_DASHBOARD\") !== \"true\") return { name: \"dashboard\", status: \"skipped\", detail: \"not enabled\" };\n const port = env.get(\"DASHBOARD_PORT\") || env.get(\"WEB_PORT\") || \"3000\";\n try {\n const res = await fetch(`http://127.0.0.1:${port}/`, { signal: AbortSignal.timeout(3000) });\n return { name: \"dashboard\", status: res.ok ? \"ok\" : \"failed\", detail: `:${port}` };\n } catch {\n return { name: \"dashboard\", status: \"failed\", detail: `:${port} unreachable` };\n }\n}\n\nasync function probeSecurity(): Promise<ProbeResult> {\n const env = readEnv();\n const mode = env.get(\"SECURITY_MODE\") || \"off\";\n const validModes = [\"off\", \"guardrails\", \"seatbelt\", \"docker\"];\n if (!validModes.includes(mode)) return { name: \"security\", status: \"failed\", detail: `invalid mode: ${mode}` };\n\n // Check secret file perms\n const secretDir = join(home, \"secret\");\n let permIssues = 0;\n if (existsSync(secretDir)) {\n for (const f of readdirSync(secretDir)) {\n const st = statSync(join(secretDir, f));\n if (st.isFile() && (st.mode & 0o777) !== 0o600) permIssues++;\n }\n }\n\n const parts = [mode];\n if (existsSync(join(home, \"auth\", \"rules.json\"))) parts.push(\"ActionGate\");\n if (permIssues > 0) return { name: \"security\", status: \"failed\", detail: `${mode}, ${permIssues} file(s) not 600` };\n return { name: \"security\", status: \"ok\", detail: parts.join(\", \") };\n}\n\nasync function probeWatchdog(): Promise<ProbeResult> {\n const lock = readJson(join(home, \"bridge.lock\"));\n if (!lock) return { name: \"watchdog\", status: \"failed\", detail: \"bridge.lock missing\" };\n\n const bridgePid = lock.pid ?? 0;\n const wdPid = lock.watchdogPid ?? 0;\n const bridgeAlive = bridgePid > 0 && pidAlive(bridgePid);\n const wdAlive = wdPid > 0 && pidAlive(wdPid);\n\n if (bridgeAlive && wdAlive) return { name: \"watchdog\", status: \"ok\", detail: `bridge:${bridgePid}, wd:${wdPid}` };\n if (!bridgeAlive && !wdAlive) return { name: \"watchdog\", status: \"failed\", detail: `bridge:${bridgePid} dead, wd:${wdPid} dead` };\n if (!wdAlive) return { name: \"watchdog\", status: \"failed\", detail: `bridge:${bridgePid} alive, wd:${wdPid} dead (unprotected)` };\n return { name: \"watchdog\", status: \"failed\", detail: `bridge:${bridgePid} dead, wd:${wdPid} alive (will restart)` };\n}\n\n// \u2500\u2500 Heart Probes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nasync function probeHeartbeat(): Promise<ProbeResult> {\n const lock = readJson(join(home, \"bridge.lock\"));\n if (!lock?.lastHeartbeat) return { name: \"heartbeat\", status: \"skipped\", detail: \"no bridge.lock\" };\n const ageMs = Date.now() - lock.lastHeartbeat;\n if (ageMs > 120_000) return { name: \"heartbeat\", status: \"failed\", detail: `stale (${ago(ageMs)})` };\n return { name: \"heartbeat\", status: \"ok\", detail: ago(ageMs) };\n}\n\n// \u2500\u2500 Brain Probes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nasync function probeTransport(): Promise<ProbeResult> {\n const tPath = join(configDir, \"transport.json\");\n const t = readJson(tPath);\n if (!t) return { name: \"transport\", status: \"failed\", detail: \"transport.json missing or invalid\" };\n const agents = Object.keys(t.agents ?? {});\n if (agents.length === 0) return { name: \"transport\", status: \"failed\", detail: \"no agents configured\" };\n return { name: \"transport\", status: \"ok\", detail: `${agents.length} agent(s): ${agents.join(\", \")}` };\n}\n\nasync function probeSpin(): Promise<ProbeResult> {\n const lock = readJson(join(home, \"bridge.lock\"));\n if (!lock?.pid || !pidAlive(lock.pid)) return { name: \"spin\", status: \"failed\", detail: \"bridge not running\" };\n return { name: \"spin\", status: \"ok\", detail: \"bridge alive\" };\n}\n\nasync function probeKanban(): Promise<ProbeResult> {\n const dbPath = join(home, \"kanban\", \"kanban.db\");\n if (!existsSync(dbPath)) return { name: \"kanban\", status: \"skipped\", detail: \"kanban.db not found\" };\n const sharedNm = join(homedir(), \".local\", \"lib\", \"node_modules\", \"better-sqlite3\");\n if (!existsSync(sharedNm)) return { name: \"kanban\", status: \"skipped\", detail: \"better-sqlite3 not installed (run: abtars deps install)\" };\n try {\n const { createRequire } = await import(\"node:module\");\n const _require = createRequire(import.meta.url);\n const Db = _require(sharedNm);\n const db = new Db(dbPath, { readonly: true });\n const row = db.prepare(\"SELECT COUNT(*) as cnt FROM cards\").get() as { cnt: number };\n const stuck = db.prepare(\"SELECT COUNT(*) as cnt FROM cards WHERE status='running' AND updated_at < datetime('now', '-10 minutes')\").get() as { cnt: number };\n db.close();\n const detail = stuck.cnt > 0 ? `${row.cnt} cards, ${stuck.cnt} stuck` : `${row.cnt} cards`;\n return { name: \"kanban\", status: stuck.cnt > 0 ? \"failed\" : \"ok\", detail };\n } catch {\n return { name: \"kanban\", status: \"skipped\", detail: \"better-sqlite3 not available\" };\n }\n}\n\nasync function probeSkills(): Promise<ProbeResult> {\n const catalog = join(home, \"skills\", \"skills_catalog.md\");\n if (!existsSync(catalog)) return { name: \"skills\", status: \"failed\", detail: \"skills_catalog.md missing\" };\n const content = readFileSync(catalog, \"utf-8\");\n const count = (content.match(/^## /gm) || []).length;\n if (count === 0) return { name: \"skills\", status: \"failed\", detail: \"catalog empty\" };\n return { name: \"skills\", status: \"ok\", detail: `${count} loaded` };\n}\n\nasync function probeSha(): Promise<ProbeResult> {\n // Check if healer skill exists in catalog\n const catalog = join(home, \"skills\", \"skills_catalog.md\");\n if (!existsSync(catalog)) return { name: \"sha\", status: \"skipped\", detail: \"no catalog\" };\n const content = readFileSync(catalog, \"utf-8\");\n if (/self.heal|healer|auto.fix/i.test(content)) return { name: \"sha\", status: \"ok\", detail: \"rules loaded\" };\n // Check sha-policy.json\n if (existsSync(join(configDir, \"sha-policy.json\"))) return { name: \"sha\", status: \"ok\", detail: \"rules loaded\" };\n return { name: \"sha\", status: \"skipped\", detail: \"no healer rules configured\" };\n}\n\n// \u2500\u2500 Tribe Probes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nasync function probeAgentApi(): Promise<ProbeResult> {\n const env = readEnv();\n if (env.get(\"ENABLE_AGENT_API\") !== \"true\") return { name: \"agent-api\", status: \"skipped\", detail: \"not enabled\" };\n const port = parseInt(env.get(\"AGENT_API_PORT\") || \"7100\", 10);\n try {\n const { createConnection } = await import(\"node:net\");\n await new Promise<void>((resolve, reject) => {\n const sock = createConnection({ port, host: \"127.0.0.1\" }, () => { sock.destroy(); resolve(); });\n sock.on(\"error\", reject);\n sock.setTimeout(2000, () => { sock.destroy(); reject(new Error(\"timeout\")); });\n });\n return { name: \"agent-api\", status: \"ok\", detail: `:${port}` };\n } catch {\n return { name: \"agent-api\", status: \"failed\", detail: `:${port} not listening` };\n }\n}\n\nasync function probePeers(): Promise<ProbeResult> {\n const peersPath = join(configDir, \"peers.json\");\n const peers = readJson(peersPath);\n if (!peers) return { name: \"peers\", status: \"skipped\", detail: \"peers.json missing\" };\n const peerCount = Object.keys(peers.peers ?? {}).length;\n if (peerCount === 0) return { name: \"peers\", status: \"ok\", detail: \"no peers configured\" };\n\n const lock = readJson(join(home, \"bridge.lock\"));\n const gossipAge = lock?.lastGossipBroadcast ? ago(Date.now() - lock.lastGossipBroadcast) : \"unknown\";\n return { name: \"peers\", status: \"ok\", detail: `${peerCount} configured, gossip: ${gossipAge}` };\n}\n\nasync function probeTls(): Promise<ProbeResult> {\n const env = readEnv();\n if (env.get(\"ENABLE_AGENT_API\") !== \"true\") return { name: \"tls\", status: \"skipped\", detail: \"agent-api disabled\" };\n const certExists = existsSync(join(configDir, \"identity.crt\"));\n const keyExists = existsSync(join(configDir, \"identity.tls.key\"));\n if (certExists && keyExists) return { name: \"tls\", status: \"ok\", detail: \"certs present\" };\n const missing = [!certExists && \"identity.crt\", !keyExists && \"identity.tls.key\"].filter(Boolean);\n return { name: \"tls\", status: \"failed\", detail: `missing: ${missing.join(\", \")}` };\n}\n\nasync function probeA2a(): Promise<ProbeResult> {\n const peersPath = join(configDir, \"peers.json\");\n const peers = readJson(peersPath) as { gossipSecret?: string; peers?: Record<string, { token?: string }>; self?: { udpPort?: number } } | null;\n if (!peers?.self?.udpPort) return { name: \"a2a\", status: \"skipped\", detail: \"no gossip port configured\" };\n\n const port = peers.self.udpPort;\n try {\n const dgram = await import(\"node:dgram\");\n const { createHmac } = await import(\"node:crypto\");\n const key = peers.gossipSecret ?? Object.values(peers.peers ?? {})[0]?.token ?? \"default\";\n const payload = JSON.stringify({ type: \"ping\", name: \"__doctor__\" });\n const sig = createHmac(\"sha256\", key).update(payload).digest(\"base64url\").slice(0, 16);\n const ping = Buffer.from(`${payload}|${sig}`);\n\n const alive = await new Promise<boolean>((resolve) => {\n const sock = dgram.createSocket(\"udp4\");\n const timer = setTimeout(() => { sock.close(); resolve(false); }, 500);\n sock.on(\"message\", () => { clearTimeout(timer); sock.close(); resolve(true); });\n sock.on(\"error\", () => { clearTimeout(timer); sock.close(); resolve(false); });\n sock.send(ping, port, \"127.0.0.1\");\n });\n return { name: \"a2a\", status: alive ? \"ok\" : \"failed\", detail: alive ? `UDP :${port} alive` : `UDP :${port} no response` };\n } catch {\n return { name: \"a2a\", status: \"failed\", detail: \"UDP probe error\" };\n }\n}\n\n// \u2500\u2500 Soul Probes \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nasync function probeMind(): Promise<ProbeResult> {\n try {\n const { spawnSync } = await import(\"node:child_process\");\n const r = spawnSync(\"abmind\", [\"doctor\", \"--json\"], { encoding: \"utf-8\", timeout: 10_000 });\n if (r.status === null || r.error) return { name: \"mind\", status: \"skipped\", detail: \"abmind not on PATH\" };\n const data = JSON.parse(r.stdout);\n const checks: Array<{ name: string; status: string }> = data.checks ?? [];\n const total = checks.length;\n const ok = checks.filter(c => c.status === \"ok\").length;\n const warnings = checks.filter(c => c.status === \"warn\" || c.status === \"error\");\n if (warnings.length === 0) return { name: \"mind\", status: \"ok\", detail: `abmind: ${ok}/${total} ok` };\n const names = warnings.slice(0, 3).map(w => w.name).join(\", \");\n return { name: \"mind\", status: \"failed\", detail: `abmind: ${ok}/${total} (${warnings.length} issues: ${names})` };\n } catch {\n return { name: \"mind\", status: \"skipped\", detail: \"abmind doctor failed\" };\n }\n}\n\n// \u2500\u2500 Runner \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport async function runAllProbes(): Promise<DoctorOutput> {\n const start = Date.now();\n\n const [body, heart, brain, soul, tribe] = await Promise.all([\n Promise.all([probePlatforms(), probeDashboard(), probeSecurity(), probeWatchdog()].map(p => timedProbe(() => p))),\n Promise.all([probeHeartbeat()].map(p => timedProbe(() => p))),\n Promise.all([probeTransport(), probeSpin(), probeKanban(), probeSkills(), probeSha()].map(p => timedProbe(() => p))),\n Promise.all([probeMind()].map(p => timedProbe(() => p))),\n Promise.all([probeAgentApi(), probePeers(), probeTls(), probeA2a()].map(p => timedProbe(() => p))),\n ]);\n\n return { version: \"1.0\", totalMs: Date.now() - start, layers: { body, heart, brain, soul, tribe } };\n}\n\n// \u2500\u2500 Fix Logic \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nexport async function runFixes(): Promise<FixResult[]> {\n const { chmodSync, unlinkSync, mkdirSync, existsSync: ex, readdirSync: rd, statSync: st, readFileSync: rf, writeFileSync: wf } = await import(\"node:fs\");\n const { spawnSync } = await import(\"node:child_process\");\n const fixes: FixResult[] = [];\n\n function fix(probe: string, action: string, fn: () => void): void {\n try { fn(); fixes.push({ probe, action, success: true }); }\n catch { fixes.push({ probe, action, success: false }); }\n }\n\n // 1. chmod 700 sensitive dirs\n for (const dir of [\"config\", \"secret\", \"auth\", \"hooks\"]) {\n const p = join(home, dir);\n if (ex(p) && (st(p).mode & 0o777) !== 0o700) {\n fix(\"security\", `${dir}/ \u2192 700`, () => chmodSync(p, 0o700));\n }\n }\n\n // 2. chmod 600 secret files\n const secretDir = join(home, \"secret\");\n if (ex(secretDir)) {\n for (const f of rd(secretDir)) {\n const fp = join(secretDir, f);\n if (st(fp).isFile() && (st(fp).mode & 0o777) !== 0o600) {\n fix(\"security\", `${f} \u2192 600`, () => chmodSync(fp, 0o600));\n }\n }\n }\n\n // 3. chmod 600 config files\n if (ex(configDir)) {\n for (const f of rd(configDir)) {\n const fp = join(configDir, f);\n if (st(fp).isFile() && (st(fp).mode & 0o777) !== 0o600) {\n fix(\"security\", `config/${f} \u2192 600`, () => chmodSync(fp, 0o600));\n }\n }\n }\n\n // 4. Stale deploy.lock\n const deployLock = join(home, \"deploy.lock\");\n if (ex(deployLock)) {\n const lock = readJson(deployLock);\n const lockAge = lock?.startedAt ? (Date.now() - new Date(lock.startedAt).getTime()) / 1000 : 9999;\n const lockPid = lock?.pid ?? 0;\n if (lockAge > 300 && (lockPid === 0 || !pidAlive(lockPid))) {\n fix(\"watchdog\", \"removed stale deploy.lock\", () => unlinkSync(deployLock));\n }\n }\n\n // 5. Stale .start-reason\n const startReason = join(home, \".start-reason\");\n if (ex(startReason)) {\n const age = (Date.now() - st(startReason).mtimeMs) / 1000;\n if (age > 300) fix(\"watchdog\", \"removed stale .start-reason\", () => unlinkSync(startReason));\n }\n\n // 6. Create missing dirs\n for (const dir of [\"logs\", \"workspace\", \"overflow\", \"received\"]) {\n const p = join(home, dir);\n if (!ex(p)) fix(\"watchdog\", `created ${dir}/`, () => mkdirSync(p, { recursive: true }));\n }\n\n // 7. Kill orphan CLI processes\n try {\n const lock = readJson(join(home, \"bridge.lock\"));\n const bridgePid = lock?.pid ?? 0;\n const wdPid = lock?.watchdogPid ?? 0;\n\n // Orphan kiro-cli\n const kiro = spawnSync(\"pgrep\", [\"-f\", \"kiro-cli.*acp\"], { encoding: \"utf-8\" });\n if (kiro.stdout) {\n for (const pid of kiro.stdout.trim().split(\"\\n\").filter(Boolean).map(Number)) {\n if (pid > 0 && pid !== bridgePid && pid !== wdPid && pid !== process.pid) {\n fix(\"brain\", `killed orphan kiro-cli ${pid}`, () => process.kill(pid, \"SIGTERM\"));\n }\n }\n }\n\n // Orphan abtars-sleep\n const sleep = spawnSync(\"pgrep\", [\"-f\", \"abtars-sleep\"], { encoding: \"utf-8\" });\n if (sleep.stdout) {\n for (const pid of sleep.stdout.trim().split(\"\\n\").filter(Boolean).map(Number)) {\n if (pid > 0 && pid !== bridgePid) {\n fix(\"brain\", `killed orphan abtars-sleep ${pid}`, () => process.kill(pid, \"SIGTERM\"));\n }\n }\n }\n } catch { /* pgrep not available or no orphans */ }\n\n // 8. Stale locks/sockets\n for (const f of [\"sleep.lock\", \"memory.sock\"]) {\n const p = join(home, f);\n if (ex(p)) {\n const age = (Date.now() - st(p).mtimeMs) / 1000;\n const lock = readJson(join(home, \"bridge.lock\"));\n if (age > 600 && (!lock?.pid || !pidAlive(lock.pid))) {\n fix(\"watchdog\", `removed stale ${f}`, () => unlinkSync(p));\n }\n }\n }\n\n // 9. Retention: delete old logs/overflow/media\n const LOGS_KEEP_DAYS = 7;\n const DATA_KEEP_DAYS = 30;\n try {\n const cutoffLogs = Date.now() - LOGS_KEEP_DAYS * 86400_000;\n const cutoffData = Date.now() - DATA_KEEP_DAYS * 86400_000;\n\n for (const [dir, cutoff] of [[join(home, \"logs\"), cutoffLogs], [join(home, \"overflow\"), cutoffData], [join(home, \"received\", \"media\"), cutoffLogs]] as const) {\n if (!ex(dir)) continue;\n let deleted = 0;\n for (const f of rd(dir)) {\n const fp = join(dir, f);\n if (st(fp).isFile() && st(fp).mtimeMs < cutoff) { unlinkSync(fp); deleted++; }\n }\n if (deleted > 0) fixes.push({ probe: \"retention\", action: `deleted ${deleted} stale file(s) from ${dir.split(\"/\").pop()}`, success: true });\n }\n\n // Truncate audit.jsonl if >10MB\n const auditPath = join(home, \"auth\", \"audit.jsonl\");\n if (ex(auditPath) && st(auditPath).size > 10_000_000) {\n const lines = rf(auditPath, \"utf-8\").split(\"\\n\");\n wf(auditPath, lines.slice(-1000).join(\"\\n\"));\n fixes.push({ probe: \"retention\", action: \"truncated audit.jsonl\", success: true });\n }\n } catch { /* retention errors non-fatal */ }\n\n // 10. Kill duplicate bridges\n try {\n const lock = readJson(join(home, \"bridge.lock\"));\n const expectedPid = lock?.pid ?? 0;\n const pgrep = spawnSync(\"pgrep\", [\"-f\", \"abtars.*main\"], { encoding: \"utf-8\" });\n if (pgrep.stdout) {\n for (const pid of pgrep.stdout.trim().split(\"\\n\").filter(Boolean).map(Number)) {\n if (pid > 0 && pid !== expectedPid && pid !== process.pid) {\n fix(\"watchdog\", `killed duplicate bridge ${pid}`, () => process.kill(pid, \"SIGTERM\"));\n }\n }\n }\n } catch { /* non-fatal */ }\n\n // 11. Hooks dir perms\n const hooksDir = join(home, \"hooks\");\n if (ex(hooksDir) && (st(hooksDir).mode & 0o777) !== 0o700) {\n fix(\"security\", \"hooks/ \u2192 700\", () => chmodSync(hooksDir, 0o700));\n }\n\n // 12. Install watchdog service if missing\n try {\n const manifest = readJson(join(home, \"manifest.json\"));\n if (manifest?.installMode === \"daemon\") {\n const { platform } = await import(\"node:os\");\n if (platform() === \"darwin\") {\n const plist = `${home}/com.abtars.watchdog.plist`;\n const dst = `${process.env[\"HOME\"]}/Library/LaunchAgents/com.abtars.watchdog.plist`;\n if (ex(plist) && !ex(dst)) {\n fix(\"watchdog\", \"installed LaunchAgent\", () => {\n const { copyFileSync } = require(\"node:fs\");\n copyFileSync(plist, dst);\n spawnSync(\"launchctl\", [\"load\", dst]);\n });\n }\n } else {\n const svc = `${home}/abtars-watchdog.service`;\n const dst = `${process.env[\"HOME\"]}/.config/systemd/user/abtars-watchdog.service`;\n if (ex(svc) && !ex(dst)) {\n fix(\"watchdog\", \"installed systemd unit\", () => {\n mkdirSync(join(process.env[\"HOME\"]!, \".config\", \"systemd\", \"user\"), { recursive: true });\n const { copyFileSync } = require(\"node:fs\");\n copyFileSync(svc, dst);\n spawnSync(\"systemctl\", [\"--user\", \"enable\", \"--now\", \"abtars-watchdog.service\"]);\n });\n }\n }\n }\n } catch { /* non-fatal */ }\n\n return fixes;\n}\n\n// \u2500\u2500 Renderer \u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\u2500\n\nconst ICON = { ok: \"\u2713\", failed: \"\u2717\", skipped: \"~\" } as const;\n\nexport function renderHuman(output: DoctorOutput): string {\n const lines: string[] = [];\n for (const [layer, probes] of Object.entries(output.layers) as [string, ProbeResult[]][]) {\n lines.push(`${layer.charAt(0).toUpperCase() + layer.slice(1)}:`);\n for (const p of probes) {\n const ms = p.ms && p.ms > 500 ? ` (${p.ms}ms)` : \"\";\n const detail = p.detail ? ` \u2014 ${p.detail}` : \"\";\n lines.push(` ${ICON[p.status]} ${p.name}${ms}${detail}`);\n }\n }\n const total = Object.values(output.layers).flat();\n const okCount = total.filter(r => r.status === \"ok\").length;\n lines.push(`\\n${okCount}/${total.length} ok (${(output.totalMs / 1000).toFixed(1)}s)`);\n return lines.join(\"\\n\");\n}\n\nexport function renderJson(output: DoctorOutput): string {\n return JSON.stringify(output, null, 2);\n}\n"],
5
+ "mappings": "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",
6
+ "names": []
7
+ }
@@ -1,5 +1,11 @@
1
1
  #!/usr/bin/env node
2
2
  import { createRequire as __bundleCreateRequire } from 'node:module'; import { fileURLToPath as __bundleFileURLToPath } from 'node:url'; import { dirname as __bundleDirname } from 'node:path'; const require = __bundleCreateRequire(import.meta.url); const __chunk_filename = __bundleFileURLToPath(import.meta.url); const __chunk_dirname = __bundleDirname(__chunk_filename);
3
+ import {
4
+ init_paths
5
+ } from "./chunk-O7KQG6ME.js";
6
+
7
+ // src/cli/deploy-lib/index.ts
8
+ init_paths();
3
9
 
4
10
  // src/cli/deploy-lib/manifest.ts
5
11
  import { readFile, writeFile } from "node:fs/promises";
@@ -165,19 +171,20 @@ function configSnapshot(configDir) {
165
171
  }
166
172
  }
167
173
  }
168
- async function healthProbe(home, afterTimestamp, timeoutMs = 6e4) {
174
+ async function healthProbe(home, afterTimestamp, timeoutMs = 6e4, opts) {
169
175
  const lockPath = join(home, "bridge.lock");
170
176
  const deadline = Date.now() + timeoutMs;
177
+ const readLock2 = opts?.lockReader ?? ((p) => readFileSync(p, "utf-8"));
171
178
  const oldPid = (() => {
172
179
  try {
173
- return JSON.parse(readFileSync(lockPath, "utf-8")).pid;
180
+ return JSON.parse(readLock2(lockPath)).pid;
174
181
  } catch {
175
182
  return 0;
176
183
  }
177
184
  })();
178
185
  while (Date.now() < deadline) {
179
186
  try {
180
- const content = JSON.parse(await readFile3(lockPath, "utf-8"));
187
+ const content = JSON.parse(readLock2(lockPath));
181
188
  if (content.pid !== oldPid && content.lastHeartbeat && content.lastHeartbeat > afterTimestamp) {
182
189
  return { healthy: true, pid: content.pid, heartbeat: content.lastHeartbeat };
183
190
  }
@@ -303,4 +310,4 @@ export {
303
310
  removePath,
304
311
  safeCopyTree
305
312
  };
306
- //# sourceMappingURL=chunk-EDZGF6BC.js.map
313
+ //# sourceMappingURL=chunk-5NY2YULC.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../src/cli/deploy-lib/index.ts", "../src/cli/deploy-lib/manifest.ts", "../src/cli/deploy-lib/lock.ts", "../src/cli/deploy-lib/releases.ts", "../src/cli/deploy-lib/cleanup.ts", "../src/cli/deploy-lib/safe-copy.ts"],
4
+ "sourcesContent": ["/**\n * Deploy-lib: shared install/update/rollback primitives.\n *\n * Consumed by both `abmind` CLI (its own runtime at ~/.abmind) and by\n * `abtars` (via file:../abmind dependency, managing ~/.abtars).\n *\n * Entry points are the module files directly:\n * import { resolveAbtarsHome } from 'abmind/deploy-lib/paths.js'\n * import { readManifest, writeManifest } from 'abmind/deploy-lib/manifest.js'\n * etc.\n *\n * See abproject/docs/plans/158-deploy-rewrite.md for the full contract.\n */\n\nexport * from './paths.js';\nexport * from './manifest.js';\nexport * from './lock.js';\nexport * from './releases.js';\nexport * from './cleanup.js';\nexport * from './safe-copy.js';\n", "/**\n * Runtime manifest: the single source of truth for \"what's installed\".\n *\n * Location: $HOME/manifest.json (per packagePaths().manifest).\n * Read by: `status`, cross-package compatibility checks, doctor.\n * Written by: `install`, `update`, `rollback`, migrations.\n */\n\nimport { readFile, writeFile } from 'node:fs/promises';\n\nexport interface Manifest {\n readonly package: 'abtars' | 'abmind';\n /** Currently active release version. */\n readonly version: string;\n /** Git SHA of the source that produced the active release, if known. */\n readonly commit: string | null;\n /** Git branch, if known. */\n readonly branch: string | null;\n /** Hash of package-lock.json at time of last install. */\n readonly packageLockHash: string | null;\n /** ISO timestamp of when the active release became active. */\n readonly activatedAt: string;\n /** Hostname where install lives (informational). */\n readonly host: string;\n /** Source adapter that produced the current release. */\n readonly source: 'dev' | 'alpha' | 'stable' | 'local' | 'npm' | 'github';\n /** Applied migrations (ordered). */\n readonly migrationsApplied: readonly string[];\n /** Previous version (for rollback). Null on first install. */\n readonly previousVersion: string | null;\n /** Previous commit (for rollback reference). */\n readonly previousCommit: string | null;\n /** Install mode: simple (manual) or daemon (watchdog + OS integration if available). */\n readonly installMode?: 'simple' | 'daemon';\n /** Repo root path (set when source=local). Null for npm installs. */\n readonly repoRoot?: string | null;\n}\n\nexport async function readManifest(path: string): Promise<Manifest | null> {\n try {\n const raw = await readFile(path, 'utf-8');\n return JSON.parse(raw) as Manifest;\n } catch (err) {\n if ((err as NodeJS.ErrnoException).code === 'ENOENT') return null;\n throw err;\n }\n}\n\nexport async function writeManifest(path: string, manifest: Manifest): Promise<void> {\n await writeFile(path, JSON.stringify(manifest, null, 2) + '\\n', 'utf-8');\n}\n\nexport function emptyManifest(pkg: 'abtars' | 'abmind', host: string): Manifest {\n return {\n package: pkg,\n version: '',\n commit: null,\n branch: null,\n packageLockHash: null,\n activatedAt: new Date().toISOString(),\n host,\n source: 'dev',\n migrationsApplied: [],\n previousVersion: null,\n previousCommit: null,\n };\n}\n", "/**\n * Update lock: prevents concurrent `install` / `update` / `rollback` runs\n * in the same runtime from colliding.\n *\n * Mechanism: write a JSON pidfile at packagePaths().lock. If file exists and\n * the PID is alive and the mtime is recent (<1h), refuse to proceed. Otherwise\n * take the lock.\n *\n * Stale timeout matches plan: 1 hour (our updates take minutes). Compared to\n * claude-code's 7-day timeout which accommodates laptop sleep during a long\n * install \u2014 not applicable for our short-lived updates.\n */\n\nimport { readFile, unlink, writeFile } from 'node:fs/promises';\nimport { unlinkSync } from 'node:fs';\nimport { hostname } from 'node:os';\n\nconst STALE_MS = 5 * 60 * 1000; // 5 minutes \u2014 deploys take <2min\n\nexport interface LockContent {\n readonly pid: number;\n readonly host: string;\n readonly startedAt: string;\n readonly cmd: string;\n}\n\nexport class LockHeldError extends Error {\n constructor(\n public readonly content: LockContent,\n public readonly isStale: boolean,\n ) {\n const staleMsg = isStale ? ' (appears stale \u2014 process may have crashed)' : '';\n super(\n `Lock held by pid ${content.pid} since ${content.startedAt} ` +\n `(cmd: ${content.cmd})${staleMsg}`,\n );\n this.name = 'LockHeldError';\n }\n}\n\nfunction isPidAlive(pid: number): boolean {\n try {\n process.kill(pid, 0);\n return true;\n } catch (err) {\n return (err as NodeJS.ErrnoException).code === 'EPERM';\n }\n}\n\nasync function readLock(path: string): Promise<LockContent | null> {\n try {\n return JSON.parse(await readFile(path, 'utf-8')) as LockContent;\n } catch (err) {\n if ((err as NodeJS.ErrnoException).code === 'ENOENT') return null;\n throw err;\n }\n}\n\n/**\n * Acquire the lock or throw LockHeldError. Returns a release function.\n * Caller must call release() on both success and failure; the returned\n * function is idempotent.\n */\nexport async function acquireLock(path: string, cmd: string): Promise<() => Promise<void>> {\n const existing = await readLock(path);\n if (existing) {\n const alive = isPidAlive(existing.pid);\n const started = Date.parse(existing.startedAt);\n const age = Date.now() - (Number.isFinite(started) ? started : 0);\n const stale = !alive || age > STALE_MS;\n if (!stale) {\n throw new LockHeldError(existing, false);\n }\n // Stale: fall through and take it, but tell the caller so doctor can surface.\n }\n\n const content: LockContent = {\n pid: process.pid,\n host: hostname(),\n startedAt: new Date().toISOString(),\n cmd,\n };\n await writeFile(path, JSON.stringify(content, null, 2) + '\\n', 'utf-8');\n\n let released = false;\n const release = async (): Promise<void> => {\n if (released) return;\n released = true;\n try {\n await unlink(path);\n } catch (err) {\n if ((err as NodeJS.ErrnoException).code !== 'ENOENT') throw err;\n }\n };\n\n // Best-effort cleanup on unexpected exit.\n const exitHandler = (): void => {\n try {\n unlinkSync(path);\n } catch {\n /* ignore \u2014 stale detection handles orphans next run */\n }\n };\n process.once('exit', exitHandler);\n\n return release;\n}\n\nexport async function inspectLock(path: string): Promise<\n | { held: false }\n | { held: true; content: LockContent; stale: boolean }\n> {\n const content = await readLock(path);\n if (!content) return { held: false };\n const alive = isPidAlive(content.pid);\n const started = Date.parse(content.startedAt);\n const age = Date.now() - (Number.isFinite(started) ? started : 0);\n const stale = !alive || age > STALE_MS;\n return { held: true, content, stale };\n}\n", "/**\n * Deploy primitives: atomic swap, config snapshot, health probe, hash.\n *\n * #785: replaces the old releases/current symlink model with\n * app/ + app.prev/ atomic rename swap.\n */\n\nimport { createHash } from 'node:crypto';\nimport { existsSync, mkdirSync, rmSync, renameSync, readdirSync, cpSync, readFileSync, writeFileSync } from 'node:fs';\nimport { readFile } from 'node:fs/promises';\nimport { join } from 'node:path';\n\n/**\n * Atomic swap with 3-prior rotation.\n * app.prev.3/ \u2192 delete, app.prev.2/ \u2192 .3, app.prev.1/ \u2192 .2, app/ \u2192 .prev.1, staging/ \u2192 app/\n * Backward compat: migrates old app.prev/ \u2192 app.prev.1/ if found.\n */\nexport function atomicSwap(appDir: string, _appPrevLegacy: string, appStagingDir: string): void {\n const prev1 = appDir.replace(/\\/app$/, '/app.prev.1');\n const prev2 = appDir.replace(/\\/app$/, '/app.prev.2');\n const prev3 = appDir.replace(/\\/app$/, '/app.prev.3');\n const legacyPrev = _appPrevLegacy; // app.prev/ (old format)\n\n // Migrate old app.prev/ \u2192 app.prev.1/ if exists\n if (existsSync(legacyPrev) && !existsSync(prev1)) {\n renameSync(legacyPrev, prev1);\n } else if (existsSync(legacyPrev)) {\n rmSync(legacyPrev, { recursive: true, force: true });\n }\n\n // Skip rotation if current app/ has same version as staging (no-op redeploy)\n try {\n const curPkg = join(appDir, \"package.json\");\n const stagePkg = join(appStagingDir, \"package.json\");\n if (existsSync(curPkg) && existsSync(stagePkg)) {\n const curVer = JSON.parse(readFileSync(curPkg, \"utf-8\")).version;\n const stageVer = JSON.parse(readFileSync(stagePkg, \"utf-8\")).version;\n if (curVer && curVer === stageVer) {\n // Same version \u2014 just replace app/ without rotating priors\n rmSync(appDir, { recursive: true, force: true });\n renameSync(appStagingDir, appDir);\n return;\n }\n }\n } catch { /* proceed with normal rotation if read fails */ }\n\n // Rotate: 3 \u2192 delete, 2 \u2192 3, 1 \u2192 2\n if (existsSync(prev3)) rmSync(prev3, { recursive: true, force: true });\n if (existsSync(prev2)) renameSync(prev2, prev3);\n if (existsSync(prev1)) renameSync(prev1, prev2);\n\n // app/ \u2192 app.prev.1/\n if (existsSync(appDir)) renameSync(appDir, prev1);\n\n // app.staging/ \u2192 app/\n renameSync(appStagingDir, appDir);\n}\n\n/**\n * Rotate config snapshots (3 slots) and create a fresh snapshot.\n * Excludes .pre-update* dirs from the copy to avoid recursion.\n */\nexport function configSnapshot(configDir: string): void {\n const slot0 = join(configDir, '.pre-update');\n const slot1 = join(configDir, '.pre-update.1');\n const slot2 = join(configDir, '.pre-update.2');\n\n // Rotate\n if (existsSync(slot2)) rmSync(slot2, { recursive: true, force: true });\n if (existsSync(slot1)) renameSync(slot1, slot2);\n if (existsSync(slot0)) renameSync(slot0, slot1);\n\n // Fresh snapshot \u2014 copy config/ contents excluding .pre-update* dirs\n mkdirSync(slot0, { recursive: true });\n if (!existsSync(configDir)) return;\n for (const entry of readdirSync(configDir, { withFileTypes: true })) {\n if (entry.name.startsWith('.pre-update')) continue;\n const src = join(configDir, entry.name);\n const dst = join(slot0, entry.name);\n if (entry.isDirectory()) {\n cpSync(src, dst, { recursive: true });\n } else {\n cpSync(src, dst);\n }\n }\n}\n\n/**\n * Poll bridge.lock for a fresh lastHeartbeat after restart.\n * Returns true if healthy within timeoutMs, false otherwise.\n */\nexport async function healthProbe(\n home: string,\n afterTimestamp: number,\n timeoutMs: number = 60_000,\n opts?: { lockReader?: (path: string) => string },\n): Promise<{ healthy: boolean; pid?: number; heartbeat?: number }> {\n const lockPath = join(home, 'bridge.lock');\n const deadline = Date.now() + timeoutMs;\n const readLock = opts?.lockReader ?? ((p: string) => readFileSync(p, 'utf-8'));\n const oldPid = (() => { try { return JSON.parse(readLock(lockPath)).pid; } catch { return 0; } })();\n while (Date.now() < deadline) {\n try {\n const content = JSON.parse(readLock(lockPath));\n // Verify bridge restarted (new PID) AND is healthy (fresh heartbeat)\n if (content.pid !== oldPid && content.lastHeartbeat && content.lastHeartbeat > afterTimestamp) {\n return { healthy: true, pid: content.pid, heartbeat: content.lastHeartbeat };\n }\n } catch {}\n await new Promise(r => setTimeout(r, 3000));\n }\n return { healthy: false };\n}\n\n/**\n * Write/read/clear the update sentinel.\n */\nexport interface UpdateSentinel {\n version: string;\n previousVersion: string | null;\n startedAt: string;\n status: 'pending' | 'success';\n}\n\nexport function writeSentinel(home: string, sentinel: UpdateSentinel): void {\n const dir = join(home, 'state');\n mkdirSync(dir, { recursive: true });\n writeFileSync(join(dir, 'update.sentinel'), JSON.stringify(sentinel, null, 2) + '\\n');\n}\n\nexport function readSentinel(home: string): UpdateSentinel | null {\n try {\n const content = readFileSync(join(home, 'state', 'update.sentinel'), 'utf-8');\n return JSON.parse(content);\n } catch {\n return null;\n }\n}\n\nexport function clearSentinel(home: string, _version: string): void {\n const path = join(home, 'state', 'update.sentinel');\n if (!existsSync(path)) return;\n try {\n const sentinel: UpdateSentinel = JSON.parse(readFileSync(path, 'utf-8'));\n sentinel.status = 'success';\n writeFileSync(path, JSON.stringify(sentinel, null, 2) + '\\n');\n } catch {\n // Best effort\n }\n}\n\nexport async function hashFile(path: string): Promise<string | null> {\n try {\n const buf = await readFile(path);\n return createHash('sha256').update(buf).digest('hex');\n } catch (err) {\n if ((err as NodeJS.ErrnoException).code === 'ENOENT') return null;\n throw err;\n }\n}\n\n/**\n * Clean up stale app.staging/ from a previously interrupted update.\n */\nexport function cleanStaleStaging(stagingDir: string): void {\n if (existsSync(stagingDir)) {\n rmSync(stagingDir, { recursive: true, force: true });\n }\n}\n", "/**\n * Safety-guarded destructive ops for `reset` / `uninstall`.\n *\n * Cleanup utilities for deploy operations.\n * Key primitive: isUnsafeRemovalTarget() rejects catastrophic paths ('/',\n * '~', empty, etc.) BEFORE any caller invokes rm. Caller must always check.\n */\n\nimport { rm } from 'node:fs/promises';\nimport { homedir } from 'node:os';\nimport { resolve } from 'node:path';\n\n/**\n * True if the path is something we refuse to remove, regardless of flags.\n *\n * Rejects:\n * - empty / whitespace-only strings\n * - '/', '\\\\', or any path that resolves to root\n * - '~' (home), home dir itself, or parents of home\n * - Anything not under the user's home dir (defense-in-depth against\n * config pointing at /etc/... by mistake)\n *\n * Callers SHOULD still confirm with the user before removing even \"safe\"\n * paths; this function is a hard floor, not a substitute for confirmation.\n */\nexport function isUnsafeRemovalTarget(path: string): boolean {\n const trimmed = path.trim();\n if (trimmed === '') return true;\n if (trimmed === '~' || trimmed === '/' || trimmed === '\\\\') return true;\n const abs = resolve(trimmed);\n if (abs === '/' || abs === '') return true;\n const home = homedir();\n if (abs === home) return true;\n // Must be under home (defense in depth).\n const homeWithSep = home.endsWith('/') ? home : home + '/';\n if (!abs.startsWith(homeWithSep)) return true;\n return false;\n}\n\nexport interface RemovePlan {\n readonly path: string;\n readonly willRemove: boolean;\n readonly reason: string;\n}\n\n/**\n * Plan a remove without executing. Used by --dry-run flows in reset/uninstall.\n */\nexport function planRemoval(path: string): RemovePlan {\n if (isUnsafeRemovalTarget(path)) {\n return { path, willRemove: false, reason: 'refused: unsafe target' };\n }\n return { path, willRemove: true, reason: 'would remove recursively' };\n}\n\n/**\n * Remove a path after validating safety. Throws if the target is unsafe.\n * Returns true if the path was removed, false if it didn't exist.\n */\nexport async function removePath(path: string, opts: { dryRun?: boolean } = {}): Promise<boolean> {\n if (isUnsafeRemovalTarget(path)) {\n throw new Error(`Refused to remove unsafe target: ${path}`);\n }\n if (opts.dryRun) return true;\n try {\n await rm(path, { recursive: true });\n return true;\n } catch (err) {\n if ((err as NodeJS.ErrnoException).code === 'ENOENT') return false;\n throw err;\n }\n}\n", "/**\n * Safe recursive copy that skips non-regular-file entries Node's cp()\n * refuses to handle (EINVAL on sockets). Real runtime roots can contain\n * UNIX sockets (browser.sock, memory.sock, etc.) which are ephemeral IPC\n * endpoints \u2014 not data we want or can back up.\n *\n * Skipped: sockets, FIFOs, block devices, character devices.\n * Copied: regular files, directories, symlinks.\n */\n\nimport { cp, lstat } from 'node:fs/promises';\n\nexport interface SafeCopyOptions {\n readonly preserveTimestamps?: boolean;\n /** Overwrite existing entries at the destination. Default: false. */\n readonly force?: boolean;\n}\n\nasync function shouldCopy(src: string): Promise<boolean> {\n try {\n const s = await lstat(src);\n if (s.isSocket() || s.isFIFO() || s.isBlockDevice() || s.isCharacterDevice()) {\n return false;\n }\n return true;\n } catch {\n // Let the subsequent cp call surface the real error if any.\n return true;\n }\n}\n\nexport async function safeCopyTree(src: string, dst: string, opts: SafeCopyOptions = {}): Promise<void> {\n await cp(src, dst, {\n recursive: true,\n preserveTimestamps: opts.preserveTimestamps === true,\n force: opts.force === true,\n filter: shouldCopy,\n });\n}\n"],
5
+ "mappings": "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",
6
+ "names": ["readFile", "writeFile", "readFile", "readLock"]
7
+ }
@@ -9,14 +9,14 @@ import {
9
9
  require_subprotocol,
10
10
  require_websocket,
11
11
  require_websocket_server
12
- } from "./chunk-S7ZIGIR5.js";
12
+ } from "./chunk-R76K6L6H.js";
13
13
  import {
14
14
  __commonJS
15
15
  } from "./chunk-7K2YZTLD.js";
16
16
 
17
- // node_modules/.pnpm/ws@8.21.0/node_modules/ws/index.js
17
+ // node_modules/ws/index.js
18
18
  var require_ws = __commonJS({
19
- "node_modules/.pnpm/ws@8.21.0/node_modules/ws/index.js"(exports, module) {
19
+ "node_modules/ws/index.js"(exports, module) {
20
20
  "use strict";
21
21
  var createWebSocketStream = require_stream();
22
22
  var extension = require_extension();
@@ -42,4 +42,4 @@ var require_ws = __commonJS({
42
42
  export {
43
43
  require_ws
44
44
  };
45
- //# sourceMappingURL=chunk-LE23VPN3.js.map
45
+ //# sourceMappingURL=chunk-63A7ZRIH.js.map
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "version": 3,
3
- "sources": ["../node_modules/.pnpm/ws@8.21.0/node_modules/ws/index.js"],
3
+ "sources": ["../node_modules/ws/index.js"],
4
4
  "sourcesContent": ["'use strict';\n\nconst createWebSocketStream = require('./lib/stream');\nconst extension = require('./lib/extension');\nconst PerMessageDeflate = require('./lib/permessage-deflate');\nconst Receiver = require('./lib/receiver');\nconst Sender = require('./lib/sender');\nconst subprotocol = require('./lib/subprotocol');\nconst WebSocket = require('./lib/websocket');\nconst WebSocketServer = require('./lib/websocket-server');\n\nWebSocket.createWebSocketStream = createWebSocketStream;\nWebSocket.extension = extension;\nWebSocket.PerMessageDeflate = PerMessageDeflate;\nWebSocket.Receiver = Receiver;\nWebSocket.Sender = Sender;\nWebSocket.Server = WebSocketServer;\nWebSocket.subprotocol = subprotocol;\nWebSocket.WebSocket = WebSocket;\nWebSocket.WebSocketServer = WebSocketServer;\n\nmodule.exports = WebSocket;\n"],
5
5
  "mappings": ";;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAEA,QAAM,wBAAwB;AAC9B,QAAM,YAAY;AAClB,QAAM,oBAAoB;AAC1B,QAAM,WAAW;AACjB,QAAM,SAAS;AACf,QAAM,cAAc;AACpB,QAAM,YAAY;AAClB,QAAM,kBAAkB;AAExB,cAAU,wBAAwB;AAClC,cAAU,YAAY;AACtB,cAAU,oBAAoB;AAC9B,cAAU,WAAW;AACrB,cAAU,SAAS;AACnB,cAAU,SAAS;AACnB,cAAU,cAAc;AACxB,cAAU,YAAY;AACtB,cAAU,kBAAkB;AAE5B,WAAO,UAAU;AAAA;AAAA;",
6
6
  "names": []
@@ -4,7 +4,7 @@ import {
4
4
  init_logger,
5
5
  logInfo,
6
6
  logWarn
7
- } from "./chunk-OOKNHOCB.js";
7
+ } from "./chunk-GWILHZPT.js";
8
8
  import {
9
9
  __esm
10
10
  } from "./chunk-7K2YZTLD.js";
@@ -306,4 +306,4 @@ export {
306
306
  _resetEnv,
307
307
  init_env_schema
308
308
  };
309
- //# sourceMappingURL=chunk-SSCGWDIC.js.map
309
+ //# sourceMappingURL=chunk-65VCEC32.js.map
@@ -2,11 +2,11 @@
2
2
  import { createRequire as __bundleCreateRequire } from 'node:module'; import { fileURLToPath as __bundleFileURLToPath } from 'node:url'; import { dirname as __bundleDirname } from 'node:path'; const require = __bundleCreateRequire(import.meta.url); const __chunk_filename = __bundleFileURLToPath(import.meta.url); const __chunk_dirname = __bundleDirname(__chunk_filename);
3
3
  import {
4
4
  sendToMainChat
5
- } from "./chunk-2LKQV2ND.js";
5
+ } from "./chunk-FRKW6LWB.js";
6
6
  import {
7
7
  init_log_and_swallow,
8
8
  logAndSwallow
9
- } from "./chunk-WP7FZHMI.js";
9
+ } from "./chunk-YSKCQH6E.js";
10
10
 
11
11
  // src/components/notification.ts
12
12
  init_log_and_swallow();
@@ -21,4 +21,4 @@ function sendNotification(ctx, msg) {
21
21
  export {
22
22
  sendNotification
23
23
  };
24
- //# sourceMappingURL=chunk-V2QIAXWZ.js.map
24
+ //# sourceMappingURL=chunk-7BSQ5UQO.js.map