abtars 0.3.4-alpha.7 → 0.3.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/bundle/{_registry.generated-WGR4WOPT.js → _registry.generated-AVR7DK2A.js} +17 -14
- package/bundle/{_registry.generated-WGR4WOPT.js.map → _registry.generated-AVR7DK2A.js.map} +1 -1
- package/bundle/{abmind-lazy-7Z44NODV.js → abmind-lazy-E3YCFKQ5.js} +15 -5
- package/bundle/abtars-browser.js +4 -4
- package/bundle/abtars-cli.js +23 -13
- package/bundle/abtars-cli.js.map +2 -2
- package/bundle/abtars-restart.js +3 -3
- package/bundle/abtars-task.js +3 -3
- package/bundle/abtars-task.js.map +2 -2
- package/bundle/abtars.js +610 -455
- package/bundle/abtars.js.map +4 -4
- package/bundle/{acp-raw-client-E6FM45NC.js → acp-raw-client-UCNK3OTU.js} +2 -2
- package/bundle/{action-gate-G2V47NHW.js → action-gate-V4FCBHFB.js} +2 -2
- package/bundle/{agent-api-adapter-YAHKQMMZ.js → agent-api-adapter-7HEPYSIN.js} +3 -3
- package/bundle/{agent-api-rate-limit-WCFXJMGY.js → agent-api-rate-limit-RZSAM3SW.js} +4 -4
- package/bundle/{agent-registry-GI6CLT3Z.js → agent-registry-46A2R5KP.js} +7 -7
- package/bundle/{bootstrap-X2QYIZIJ.js → bootstrap-MIHJJSWU.js} +2 -2
- package/bundle/{bridge-lock-transport-4ZH7QTJP.js → bridge-lock-transport-7RSN7OLJ.js} +4 -4
- package/bundle/{browser-DMARZJIN.js → browser-F6BCWJWW.js} +6 -6
- package/bundle/{budget-45QOBDWA.js → budget-WUM3SPKW.js} +3 -3
- package/bundle/{capability-JFWX3IQF.js → capability-QVRKGRFC.js} +5 -5
- package/bundle/{chunk-YSKCQH6E.js → chunk-2IYJ4I66.js} +2 -2
- package/bundle/{chunk-KTYGKPYM.js → chunk-2NLUT5S2.js} +6 -6
- package/bundle/chunk-3BG3AIDP.js +191 -0
- package/bundle/chunk-3BG3AIDP.js.map +7 -0
- package/bundle/{chunk-OKAQICWY.js → chunk-3GQX34S2.js} +3 -3
- package/bundle/{chunk-QROWBWLL.js → chunk-3XZ773BS.js} +2 -2
- package/bundle/{chunk-DYBW4XXL.js → chunk-467SRLLR.js} +2 -2
- package/bundle/{chunk-LGP6TYFI.js → chunk-4AILRHUI.js} +97 -8
- package/bundle/chunk-4AILRHUI.js.map +7 -0
- package/bundle/{chunk-GPZNXY2U.js → chunk-4S3H4OK7.js} +4 -4
- package/bundle/{chunk-NDCRWEEJ.js → chunk-4Y5MJQRE.js} +6 -6
- package/bundle/{chunk-FRKW6LWB.js → chunk-55UWKI5C.js} +3 -3
- package/bundle/{chunk-4UL3KINB.js → chunk-5PNJFDSW.js} +8 -8
- package/bundle/{chunk-LUNA6PM5.js → chunk-5RVOEFGT.js} +4 -2
- package/bundle/{chunk-LUNA6PM5.js.map → chunk-5RVOEFGT.js.map} +2 -2
- package/bundle/{chunk-OXTSWQCX.js → chunk-5Y3FJ2Y7.js} +2 -2
- package/bundle/{chunk-TMUYFERL.js → chunk-6B5ZFUPD.js} +2 -2
- package/bundle/{chunk-65VCEC32.js → chunk-6PA5JBUU.js} +2 -2
- package/bundle/chunk-BNXV7SZI.js +195 -0
- package/bundle/chunk-BNXV7SZI.js.map +7 -0
- package/bundle/{chunk-AFREM7FX.js → chunk-CK7YTA2F.js} +2 -2
- package/bundle/{chunk-NRUSRJXR.js → chunk-DZJ5QZFD.js} +2 -2
- package/bundle/{chunk-YRSMGJFP.js → chunk-E67KESEG.js} +2 -2
- package/bundle/{chunk-ZV4IWKDJ.js → chunk-E7XD5UGB.js} +3 -3
- package/bundle/{chunk-GXL7HJPT.js → chunk-EAX5ZZUL.js} +63 -39
- package/bundle/chunk-EAX5ZZUL.js.map +7 -0
- package/bundle/{chunk-PEDX56EL.js → chunk-EFGBM555.js} +2 -2
- package/bundle/{chunk-EQSG2CRM.js → chunk-FGYDIX54.js} +22 -15
- package/bundle/chunk-FGYDIX54.js.map +7 -0
- package/bundle/{chunk-XWRADSXO.js → chunk-GF6NVNA7.js} +15 -5
- package/bundle/chunk-GF6NVNA7.js.map +7 -0
- package/bundle/{chunk-SIFPBTI4.js → chunk-HGSHCQ5F.js} +113 -73
- package/bundle/chunk-HGSHCQ5F.js.map +7 -0
- package/bundle/{chunk-YRU2K3O6.js → chunk-IMIGG5EO.js} +39 -39
- package/bundle/chunk-IMIGG5EO.js.map +7 -0
- package/bundle/{chunk-W4EA4GCA.js → chunk-ITOFPJAV.js} +43 -31
- package/bundle/chunk-ITOFPJAV.js.map +7 -0
- package/bundle/{chunk-UPRZDU6T.js → chunk-IY6UKLPS.js} +3 -3
- package/bundle/{chunk-EUZDKV3C.js → chunk-J4RUFAPK.js} +3 -3
- package/bundle/{chunk-HZDLFLRP.js → chunk-J7DRPVMU.js} +35 -5
- package/bundle/chunk-J7DRPVMU.js.map +7 -0
- package/bundle/{chunk-EGL6UMAO.js → chunk-JG4BKXBN.js} +7 -1
- package/bundle/chunk-JG4BKXBN.js.map +7 -0
- package/bundle/{chunk-5B5B6EHL.js → chunk-JLWYPGWI.js} +5 -5
- package/bundle/{chunk-5QUTMUIK.js → chunk-JXYWDAHD.js} +12 -12
- package/bundle/{chunk-GRVWZO4C.js → chunk-KOSFXW2S.js} +24 -3
- package/bundle/{chunk-GRVWZO4C.js.map → chunk-KOSFXW2S.js.map} +1 -1
- package/bundle/{chunk-ONBF5DDU.js → chunk-L72RIPEC.js} +248 -182
- package/bundle/chunk-L72RIPEC.js.map +7 -0
- package/bundle/{chunk-TEFZ4JA4.js → chunk-NHPLD3C7.js} +2 -2
- package/bundle/{chunk-2KC5G3EA.js → chunk-OWUO5RS3.js} +5 -5
- package/bundle/{chunk-4MULJ5SS.js → chunk-OY4Q6AMY.js} +71 -49
- package/bundle/chunk-OY4Q6AMY.js.map +7 -0
- package/bundle/{chunk-WBTJ2E62.js → chunk-P3NODAHF.js} +2 -5
- package/bundle/{chunk-WBTJ2E62.js.map → chunk-P3NODAHF.js.map} +2 -2
- package/bundle/{chunk-BROFMHC2.js → chunk-PB5GF4FG.js} +334 -237
- package/bundle/chunk-PB5GF4FG.js.map +7 -0
- package/bundle/{chunk-WYHGNI56.js → chunk-PMD5BLFS.js} +6 -6
- package/bundle/{chunk-URQPDCK5.js → chunk-Q66LQMMZ.js} +3 -3
- package/bundle/{chunk-HKRSMUXJ.js → chunk-SC2Y5NR2.js} +71 -132
- package/bundle/chunk-SC2Y5NR2.js.map +7 -0
- package/bundle/chunk-SFL4EPCZ.js +555 -0
- package/bundle/chunk-SFL4EPCZ.js.map +7 -0
- package/bundle/{chunk-LDUOOKQY.js → chunk-SJPUNDZ3.js} +5 -5
- package/bundle/{chunk-LDUOOKQY.js.map → chunk-SJPUNDZ3.js.map} +1 -1
- package/bundle/{chunk-JQDJPUHM.js → chunk-TWB2ZGVH.js} +2 -2
- package/bundle/{chunk-IJT4KWXT.js → chunk-U4U47YE7.js} +2 -2
- package/bundle/{chunk-2FAZIA37.js → chunk-W546CU3A.js} +3 -3
- package/bundle/chunk-WC5O5KOE.js +211 -0
- package/bundle/chunk-WC5O5KOE.js.map +7 -0
- package/bundle/{chunk-JNIHEDKF.js → chunk-XPWYDNWL.js} +2 -2
- package/bundle/{chunk-GWILHZPT.js → chunk-XRTXYN66.js} +10 -7
- package/bundle/{chunk-GWILHZPT.js.map → chunk-XRTXYN66.js.map} +2 -2
- package/bundle/{chunk-EFJVUJBE.js → chunk-Y5FEFKGM.js} +6 -6
- package/bundle/chunk-YJZE4OK3.js +169 -0
- package/bundle/chunk-YJZE4OK3.js.map +7 -0
- package/bundle/{chunk-GVM5YU5I.js → chunk-Z4FZPB42.js} +2 -2
- package/bundle/{chunk-7BSQ5UQO.js → chunk-ZSIDQ66D.js} +3 -3
- package/bundle/{chunk-XX6BGTPO.js → chunk-ZZZCJJEO.js} +4 -4
- package/bundle/{commands-XYEGVUZF.js → commands-2ZW6CMLC.js} +17 -16
- package/bundle/{config-M3P5IOAI.js → config-YMY5YHKN.js} +6 -6
- package/bundle/{context-2RJHC2LE.js → context-CL2RSLII.js} +7 -5
- package/bundle/context-CL2RSLII.js.map +7 -0
- package/bundle/{daemon-TB23FFWY.js → daemon-D7SU63OY.js} +3 -3
- package/bundle/{delegation-tools-QKNYQGTQ.js → delegation-tools-WS7Z56KZ.js} +12 -12
- package/bundle/{deploy-EPDWNHJU.js → deploy-AMTVKIMU.js} +2 -2
- package/bundle/{deps-WVK553KF.js → deps-T63AVJKJ.js} +3 -3
- package/bundle/{direct-api-transport-E3LNDBJT.js → direct-api-transport-QNNY2WWP.js} +56 -33
- package/bundle/direct-api-transport-QNNY2WWP.js.map +7 -0
- package/bundle/{discord-adapter-IT3KP3VB.js → discord-adapter-ABAD56Y2.js} +21 -20
- package/bundle/{discord-adapter-IT3KP3VB.js.map → discord-adapter-ABAD56Y2.js.map} +1 -1
- package/bundle/{dns-wakeup-IDOJIXBX.js → dns-wakeup-V3LEFXPE.js} +9 -33
- package/bundle/dns-wakeup-V3LEFXPE.js.map +7 -0
- package/bundle/{doctor-probes-B54JFIW3.js → doctor-probes-O6YI6XSZ.js} +6 -2
- package/bundle/{env-schema-4JXQUOH4.js → env-schema-B5RB32DC.js} +3 -3
- package/bundle/{gossip-3C3BSNPN.js → gossip-SKRCPOBS.js} +9 -5
- package/bundle/{guardrails-DL7ZSWVN.js → guardrails-64GQ5Y5K.js} +4 -4
- package/bundle/{heartbeat-system-MVTRS4GP.js → heartbeat-system-X4MUTKJD.js} +6 -6
- package/bundle/{heartbeat-tier3-ABWL3P7M.js → heartbeat-tier3-2PTPWEQQ.js} +53 -76
- package/bundle/heartbeat-tier3-2PTPWEQQ.js.map +7 -0
- package/bundle/{hook-system-M3POLUIB.js → hook-system-YB635OC4.js} +3 -3
- package/bundle/{hotskills-FWX4QI7V.js → hotskills-Q75D2DK3.js} +5 -5
- package/bundle/{install-OS3CU7NF.js → install-RFKKFSGS.js} +17 -30
- package/bundle/install-RFKKFSGS.js.map +7 -0
- package/bundle/{install-manifest-5PPWMD2W.js → install-manifest-J7ICPCJN.js} +2 -2
- package/bundle/{irc-adapter-PTTZD32W.js → irc-adapter-TVEV4R6H.js} +3 -3
- package/bundle/{irc-config-CP7ZMUOX.js → irc-config-M676FOFI.js} +4 -4
- package/bundle/{kanban-board-M326B2XJ.js → kanban-board-DLEJUCNN.js} +9 -7
- package/bundle/{kanban-channel-IJ52OMNA.js → kanban-channel-XOLUHJZJ.js} +6 -6
- package/bundle/kanban-delivery-C4QPBNPX.js +45 -0
- package/bundle/kanban-delivery-C4QPBNPX.js.map +7 -0
- package/bundle/{lazy-require-KCRVT4SI.js → lazy-require-JKQSALXN.js} +3 -3
- package/bundle/{logger-OWCSNYCA.js → logger-3EGHBD4R.js} +2 -2
- package/bundle/{main-chat-ZNUZCTNS.js → main-chat-3H63REKK.js} +4 -4
- package/bundle/{master-user-HSKM4ZFN.js → master-user-MUBUP3KD.js} +5 -5
- package/bundle/{media-utils-3ZYOD7SK.js → media-utils-HUUIALAJ.js} +3 -3
- package/bundle/{message-pipeline-P5GAQU4Z.js → message-pipeline-GRDRWONR.js} +17 -16
- package/bundle/meta.json +3699 -3138
- package/bundle/{metrics-collector-L3VPEHII.js → metrics-collector-YMUGY3PI.js} +31 -2
- package/bundle/metrics-collector-YMUGY3PI.js.map +7 -0
- package/bundle/{model-health-registry-MLEIZSTV.js → model-health-registry-QADMFQFQ.js} +2 -2
- package/bundle/{nerve-IGSXBKZZ.js → nerve-QPAEBRKX.js} +3 -3
- package/bundle/{notification-BFSIEECG.js → notification-3JICGXWU.js} +6 -6
- package/bundle/{openrouter-credits-NTVZDRYM.js → openrouter-credits-7NEIPYJN.js} +3 -3
- package/bundle/{orc-tools-4CHEFWSN.js → orc-tools-UZVPONKY.js} +5 -3
- package/bundle/{peer-auth-QC4EF2PM.js → peer-auth-RI43DKJE.js} +24 -15
- package/bundle/{peer-client-RGEU5HOK.js → peer-client-UITTMWJ2.js} +34 -29
- package/bundle/peer-client-UITTMWJ2.js.map +7 -0
- package/bundle/{peer-config-TN55LFDC.js → peer-config-URM7DCW6.js} +9 -4
- package/bundle/{peer-transport-I6JPLFZ2.js → peer-transport-SI7I72DB.js} +12 -10
- package/bundle/{phase-transport-PGKU2KD4.js → phase-transport-ESWWACZI.js} +17 -17
- package/bundle/{reconcile-CTFCLQRN.js → reconcile-GFDQYNBD.js} +3 -3
- package/bundle/{reconciler-EBKH3JNU.js → reconciler-IEUJXJN2.js} +12 -12
- package/bundle/{restore-IFHPI7I7.js → restore-FARTGLQQ.js} +3 -3
- package/bundle/{rollback-ANRI3T5Z.js → rollback-GEWPZABG.js} +2 -2
- package/bundle/{sandbox-runtime-QROWHDCS.js → sandbox-runtime-DV6E25J6.js} +2 -2
- package/bundle/{self-healer-utils-IFAYOQO2.js → self-healer-utils-P4SKNNEM.js} +3 -3
- package/bundle/{sha-tracker-ZWBP6CIJ.js → sha-tracker-77SHLYNY.js} +3 -3
- package/bundle/{skill-session-BMSRQSHV.js → skill-session-5HSMXY54.js} +3 -3
- package/bundle/{skill-stats-JORH5DGM.js → skill-stats-MI3RSWWL.js} +4 -4
- package/bundle/{skill-watcher-E4MGLKLS.js → skill-watcher-5L7JE6TN.js} +4 -4
- package/bundle/{sleep-36XS6MHJ.js → sleep-I4JFASCY.js} +11 -8
- package/bundle/{soul-bundle-VWAVHCZ6.js → soul-bundle-522C3IRH.js} +9 -8
- package/bundle/{spin-TI3TSVVT.js → spin-VHNGNWTD.js} +11 -11
- package/bundle/{spin-notifications-SE2HVZI7.js → spin-notifications-7NC5XZEM.js} +5 -5
- package/bundle/{spin-types-BLPYAETA.js → spin-types-C5KOQOPD.js} +7 -3
- package/bundle/{sse-parser-anthropic-A6R4Z2TB.js → sse-parser-anthropic-MMTVWHLI.js} +3 -3
- package/bundle/{sse-parser-responses-HSZY3QGJ.js → sse-parser-responses-3AOFN64C.js} +3 -3
- package/bundle/{ssrf-guard-O6SHIK6Q.js → ssrf-guard-U2JA72TC.js} +3 -3
- package/bundle/{start-7QZIWO3S.js → start-H5IUFAWF.js} +4 -2
- package/bundle/{start-7QZIWO3S.js.map → start-H5IUFAWF.js.map} +2 -2
- package/bundle/{stt-LGVPXMVR.js → stt-PSOPPBV4.js} +4 -4
- package/bundle/{system-status-JZU5FO7B.js → system-status-4LYGOFNO.js} +38 -24
- package/bundle/system-status-4LYGOFNO.js.map +7 -0
- package/bundle/{task-store-W5BFIAIH.js → task-store-MNCW42BW.js} +4 -4
- package/bundle/{telegram-adapter-H6PMFPMB.js → telegram-adapter-O6KIZDY6.js} +69 -46
- package/bundle/telegram-adapter-O6KIZDY6.js.map +7 -0
- package/bundle/{tool-registry-IZX2IOBM.js → tool-registry-JJMWCQKZ.js} +26 -24
- package/bundle/{tool-sandbox-4UC6GAKA.js → tool-sandbox-CNL6V6IH.js} +4 -4
- package/bundle/{transport-config-KBF5W2DP.js → transport-config-6MB2K2XC.js} +7 -7
- package/bundle/tribe-GDTFYJTK.js +111 -0
- package/bundle/tribe-GDTFYJTK.js.map +7 -0
- package/bundle/{update-MESYO4LO.js → update-HGQAOC5L.js} +3 -3
- package/bundle/{usage-tracker-NXD364VX.js → usage-tracker-SR4BI6ZT.js} +2 -2
- package/bundle/{user-registry-35BW4XKM.js → user-registry-4PACZJIJ.js} +4 -4
- package/bundle/wire-platform-KKPWNNNQ.js +88 -0
- package/bundle/wire-platform-KKPWNNNQ.js.map +7 -0
- package/bundle/ws-peer-client-U3NNPOK7.js +370 -0
- package/bundle/ws-peer-client-U3NNPOK7.js.map +7 -0
- package/package.json +1 -1
- package/scripts/abtars-watchdog.service +2 -1
- package/scripts/abtars-watchdog.sh +1 -5
- package/scripts/emergency-deploy.sh +2 -2
- package/scripts/emergency-update.sh +88 -41
- package/bundle/chunk-3AAENI2K.js +0 -210
- package/bundle/chunk-3AAENI2K.js.map +0 -7
- package/bundle/chunk-4MULJ5SS.js.map +0 -7
- package/bundle/chunk-4S554KLW.js +0 -105
- package/bundle/chunk-4S554KLW.js.map +0 -7
- package/bundle/chunk-5GCLBUBS.js +0 -257
- package/bundle/chunk-5GCLBUBS.js.map +0 -7
- package/bundle/chunk-BROFMHC2.js.map +0 -7
- package/bundle/chunk-EGL6UMAO.js.map +0 -7
- package/bundle/chunk-EQSG2CRM.js.map +0 -7
- package/bundle/chunk-GXL7HJPT.js.map +0 -7
- package/bundle/chunk-HKRSMUXJ.js.map +0 -7
- package/bundle/chunk-HT2BPTZY.js +0 -241
- package/bundle/chunk-HT2BPTZY.js.map +0 -7
- package/bundle/chunk-HZDLFLRP.js.map +0 -7
- package/bundle/chunk-IKUZPMVA.js +0 -82
- package/bundle/chunk-IKUZPMVA.js.map +0 -7
- package/bundle/chunk-LGP6TYFI.js.map +0 -7
- package/bundle/chunk-ONBF5DDU.js.map +0 -7
- package/bundle/chunk-RWRRGE4U.js +0 -72
- package/bundle/chunk-RWRRGE4U.js.map +0 -7
- package/bundle/chunk-SIFPBTI4.js.map +0 -7
- package/bundle/chunk-VUIX5AGB.js +0 -65
- package/bundle/chunk-VUIX5AGB.js.map +0 -7
- package/bundle/chunk-W4EA4GCA.js.map +0 -7
- package/bundle/chunk-XWRADSXO.js.map +0 -7
- package/bundle/chunk-Y76VUJSF.js +0 -75
- package/bundle/chunk-Y76VUJSF.js.map +0 -7
- package/bundle/chunk-YRU2K3O6.js.map +0 -7
- package/bundle/context-2RJHC2LE.js.map +0 -7
- package/bundle/direct-api-transport-E3LNDBJT.js.map +0 -7
- package/bundle/dns-wakeup-IDOJIXBX.js.map +0 -7
- package/bundle/heartbeat-tier3-ABWL3P7M.js.map +0 -7
- package/bundle/install-OS3CU7NF.js.map +0 -7
- package/bundle/metrics-collector-L3VPEHII.js.map +0 -7
- package/bundle/peer-client-RGEU5HOK.js.map +0 -7
- package/bundle/peer-jwt-NCCPXJRX.js +0 -18
- package/bundle/public/css/dashboard.css +0 -542
- package/bundle/public/index.html +0 -180
- package/bundle/public/js/app.js +0 -437
- package/bundle/public/memory-universe.js +0 -384
- package/bundle/stream-single-RFJNUTL6.js +0 -34
- package/bundle/stream-single-RFJNUTL6.js.map +0 -7
- package/bundle/subagent-runtime-5QUVES3W.js +0 -14
- package/bundle/system-status-JZU5FO7B.js.map +0 -7
- package/bundle/telegram-adapter-H6PMFPMB.js.map +0 -7
- package/bundle/usage-tracker-NXD364VX.js.map +0 -7
- package/bundle/user-registry-35BW4XKM.js.map +0 -7
- package/bundle/ws-peer-client-AIXCXF7V.js +0 -173
- package/bundle/ws-peer-client-AIXCXF7V.js.map +0 -7
- /package/bundle/{abmind-lazy-7Z44NODV.js.map → abmind-lazy-E3YCFKQ5.js.map} +0 -0
- /package/bundle/{acp-raw-client-E6FM45NC.js.map → acp-raw-client-UCNK3OTU.js.map} +0 -0
- /package/bundle/{action-gate-G2V47NHW.js.map → action-gate-V4FCBHFB.js.map} +0 -0
- /package/bundle/{agent-api-adapter-YAHKQMMZ.js.map → agent-api-adapter-7HEPYSIN.js.map} +0 -0
- /package/bundle/{agent-api-rate-limit-WCFXJMGY.js.map → agent-api-rate-limit-RZSAM3SW.js.map} +0 -0
- /package/bundle/{agent-registry-GI6CLT3Z.js.map → agent-registry-46A2R5KP.js.map} +0 -0
- /package/bundle/{bootstrap-X2QYIZIJ.js.map → bootstrap-MIHJJSWU.js.map} +0 -0
- /package/bundle/{bridge-lock-transport-4ZH7QTJP.js.map → bridge-lock-transport-7RSN7OLJ.js.map} +0 -0
- /package/bundle/{browser-DMARZJIN.js.map → browser-F6BCWJWW.js.map} +0 -0
- /package/bundle/{budget-45QOBDWA.js.map → budget-WUM3SPKW.js.map} +0 -0
- /package/bundle/{capability-JFWX3IQF.js.map → capability-QVRKGRFC.js.map} +0 -0
- /package/bundle/{chunk-YSKCQH6E.js.map → chunk-2IYJ4I66.js.map} +0 -0
- /package/bundle/{chunk-KTYGKPYM.js.map → chunk-2NLUT5S2.js.map} +0 -0
- /package/bundle/{chunk-OKAQICWY.js.map → chunk-3GQX34S2.js.map} +0 -0
- /package/bundle/{chunk-QROWBWLL.js.map → chunk-3XZ773BS.js.map} +0 -0
- /package/bundle/{chunk-DYBW4XXL.js.map → chunk-467SRLLR.js.map} +0 -0
- /package/bundle/{chunk-GPZNXY2U.js.map → chunk-4S3H4OK7.js.map} +0 -0
- /package/bundle/{chunk-NDCRWEEJ.js.map → chunk-4Y5MJQRE.js.map} +0 -0
- /package/bundle/{chunk-FRKW6LWB.js.map → chunk-55UWKI5C.js.map} +0 -0
- /package/bundle/{chunk-4UL3KINB.js.map → chunk-5PNJFDSW.js.map} +0 -0
- /package/bundle/{chunk-OXTSWQCX.js.map → chunk-5Y3FJ2Y7.js.map} +0 -0
- /package/bundle/{chunk-TMUYFERL.js.map → chunk-6B5ZFUPD.js.map} +0 -0
- /package/bundle/{chunk-65VCEC32.js.map → chunk-6PA5JBUU.js.map} +0 -0
- /package/bundle/{chunk-AFREM7FX.js.map → chunk-CK7YTA2F.js.map} +0 -0
- /package/bundle/{chunk-NRUSRJXR.js.map → chunk-DZJ5QZFD.js.map} +0 -0
- /package/bundle/{chunk-YRSMGJFP.js.map → chunk-E67KESEG.js.map} +0 -0
- /package/bundle/{chunk-ZV4IWKDJ.js.map → chunk-E7XD5UGB.js.map} +0 -0
- /package/bundle/{chunk-PEDX56EL.js.map → chunk-EFGBM555.js.map} +0 -0
- /package/bundle/{chunk-UPRZDU6T.js.map → chunk-IY6UKLPS.js.map} +0 -0
- /package/bundle/{chunk-EUZDKV3C.js.map → chunk-J4RUFAPK.js.map} +0 -0
- /package/bundle/{chunk-5B5B6EHL.js.map → chunk-JLWYPGWI.js.map} +0 -0
- /package/bundle/{chunk-5QUTMUIK.js.map → chunk-JXYWDAHD.js.map} +0 -0
- /package/bundle/{chunk-TEFZ4JA4.js.map → chunk-NHPLD3C7.js.map} +0 -0
- /package/bundle/{chunk-2KC5G3EA.js.map → chunk-OWUO5RS3.js.map} +0 -0
- /package/bundle/{chunk-WYHGNI56.js.map → chunk-PMD5BLFS.js.map} +0 -0
- /package/bundle/{chunk-URQPDCK5.js.map → chunk-Q66LQMMZ.js.map} +0 -0
- /package/bundle/{chunk-JQDJPUHM.js.map → chunk-TWB2ZGVH.js.map} +0 -0
- /package/bundle/{chunk-IJT4KWXT.js.map → chunk-U4U47YE7.js.map} +0 -0
- /package/bundle/{chunk-2FAZIA37.js.map → chunk-W546CU3A.js.map} +0 -0
- /package/bundle/{chunk-JNIHEDKF.js.map → chunk-XPWYDNWL.js.map} +0 -0
- /package/bundle/{chunk-EFJVUJBE.js.map → chunk-Y5FEFKGM.js.map} +0 -0
- /package/bundle/{chunk-GVM5YU5I.js.map → chunk-Z4FZPB42.js.map} +0 -0
- /package/bundle/{chunk-7BSQ5UQO.js.map → chunk-ZSIDQ66D.js.map} +0 -0
- /package/bundle/{chunk-XX6BGTPO.js.map → chunk-ZZZCJJEO.js.map} +0 -0
- /package/bundle/{commands-XYEGVUZF.js.map → commands-2ZW6CMLC.js.map} +0 -0
- /package/bundle/{config-M3P5IOAI.js.map → config-YMY5YHKN.js.map} +0 -0
- /package/bundle/{daemon-TB23FFWY.js.map → daemon-D7SU63OY.js.map} +0 -0
- /package/bundle/{delegation-tools-QKNYQGTQ.js.map → delegation-tools-WS7Z56KZ.js.map} +0 -0
- /package/bundle/{deploy-EPDWNHJU.js.map → deploy-AMTVKIMU.js.map} +0 -0
- /package/bundle/{deps-WVK553KF.js.map → deps-T63AVJKJ.js.map} +0 -0
- /package/bundle/{doctor-probes-B54JFIW3.js.map → doctor-probes-O6YI6XSZ.js.map} +0 -0
- /package/bundle/{env-schema-4JXQUOH4.js.map → env-schema-B5RB32DC.js.map} +0 -0
- /package/bundle/{gossip-3C3BSNPN.js.map → gossip-SKRCPOBS.js.map} +0 -0
- /package/bundle/{guardrails-DL7ZSWVN.js.map → guardrails-64GQ5Y5K.js.map} +0 -0
- /package/bundle/{heartbeat-system-MVTRS4GP.js.map → heartbeat-system-X4MUTKJD.js.map} +0 -0
- /package/bundle/{hook-system-M3POLUIB.js.map → hook-system-YB635OC4.js.map} +0 -0
- /package/bundle/{hotskills-FWX4QI7V.js.map → hotskills-Q75D2DK3.js.map} +0 -0
- /package/bundle/{install-manifest-5PPWMD2W.js.map → install-manifest-J7ICPCJN.js.map} +0 -0
- /package/bundle/{irc-adapter-PTTZD32W.js.map → irc-adapter-TVEV4R6H.js.map} +0 -0
- /package/bundle/{irc-config-CP7ZMUOX.js.map → irc-config-M676FOFI.js.map} +0 -0
- /package/bundle/{kanban-board-M326B2XJ.js.map → kanban-board-DLEJUCNN.js.map} +0 -0
- /package/bundle/{kanban-channel-IJ52OMNA.js.map → kanban-channel-XOLUHJZJ.js.map} +0 -0
- /package/bundle/{lazy-require-KCRVT4SI.js.map → lazy-require-JKQSALXN.js.map} +0 -0
- /package/bundle/{logger-OWCSNYCA.js.map → logger-3EGHBD4R.js.map} +0 -0
- /package/bundle/{main-chat-ZNUZCTNS.js.map → main-chat-3H63REKK.js.map} +0 -0
- /package/bundle/{master-user-HSKM4ZFN.js.map → master-user-MUBUP3KD.js.map} +0 -0
- /package/bundle/{media-utils-3ZYOD7SK.js.map → media-utils-HUUIALAJ.js.map} +0 -0
- /package/bundle/{message-pipeline-P5GAQU4Z.js.map → message-pipeline-GRDRWONR.js.map} +0 -0
- /package/bundle/{model-health-registry-MLEIZSTV.js.map → model-health-registry-QADMFQFQ.js.map} +0 -0
- /package/bundle/{nerve-IGSXBKZZ.js.map → nerve-QPAEBRKX.js.map} +0 -0
- /package/bundle/{notification-BFSIEECG.js.map → notification-3JICGXWU.js.map} +0 -0
- /package/bundle/{openrouter-credits-NTVZDRYM.js.map → openrouter-credits-7NEIPYJN.js.map} +0 -0
- /package/bundle/{orc-tools-4CHEFWSN.js.map → orc-tools-UZVPONKY.js.map} +0 -0
- /package/bundle/{peer-auth-QC4EF2PM.js.map → peer-auth-RI43DKJE.js.map} +0 -0
- /package/bundle/{peer-config-TN55LFDC.js.map → peer-config-URM7DCW6.js.map} +0 -0
- /package/bundle/{peer-jwt-NCCPXJRX.js.map → peer-transport-SI7I72DB.js.map} +0 -0
- /package/bundle/{peer-transport-I6JPLFZ2.js.map → phase-transport-ESWWACZI.js.map} +0 -0
- /package/bundle/{phase-transport-PGKU2KD4.js.map → reconcile-GFDQYNBD.js.map} +0 -0
- /package/bundle/{reconciler-EBKH3JNU.js.map → reconciler-IEUJXJN2.js.map} +0 -0
- /package/bundle/{restore-IFHPI7I7.js.map → restore-FARTGLQQ.js.map} +0 -0
- /package/bundle/{reconcile-CTFCLQRN.js.map → rollback-GEWPZABG.js.map} +0 -0
- /package/bundle/{sandbox-runtime-QROWHDCS.js.map → sandbox-runtime-DV6E25J6.js.map} +0 -0
- /package/bundle/{self-healer-utils-IFAYOQO2.js.map → self-healer-utils-P4SKNNEM.js.map} +0 -0
- /package/bundle/{rollback-ANRI3T5Z.js.map → sha-tracker-77SHLYNY.js.map} +0 -0
- /package/bundle/{skill-session-BMSRQSHV.js.map → skill-session-5HSMXY54.js.map} +0 -0
- /package/bundle/{sha-tracker-ZWBP6CIJ.js.map → skill-stats-MI3RSWWL.js.map} +0 -0
- /package/bundle/{skill-stats-JORH5DGM.js.map → skill-watcher-5L7JE6TN.js.map} +0 -0
- /package/bundle/{skill-watcher-E4MGLKLS.js.map → sleep-I4JFASCY.js.map} +0 -0
- /package/bundle/{sleep-36XS6MHJ.js.map → soul-bundle-522C3IRH.js.map} +0 -0
- /package/bundle/{soul-bundle-VWAVHCZ6.js.map → spin-VHNGNWTD.js.map} +0 -0
- /package/bundle/{spin-notifications-SE2HVZI7.js.map → spin-notifications-7NC5XZEM.js.map} +0 -0
- /package/bundle/{spin-TI3TSVVT.js.map → spin-types-C5KOQOPD.js.map} +0 -0
- /package/bundle/{sse-parser-anthropic-A6R4Z2TB.js.map → sse-parser-anthropic-MMTVWHLI.js.map} +0 -0
- /package/bundle/{sse-parser-responses-HSZY3QGJ.js.map → sse-parser-responses-3AOFN64C.js.map} +0 -0
- /package/bundle/{ssrf-guard-O6SHIK6Q.js.map → ssrf-guard-U2JA72TC.js.map} +0 -0
- /package/bundle/{spin-types-BLPYAETA.js.map → stt-PSOPPBV4.js.map} +0 -0
- /package/bundle/{stt-LGVPXMVR.js.map → task-store-MNCW42BW.js.map} +0 -0
- /package/bundle/{subagent-runtime-5QUVES3W.js.map → tool-registry-JJMWCQKZ.js.map} +0 -0
- /package/bundle/{task-store-W5BFIAIH.js.map → tool-sandbox-CNL6V6IH.js.map} +0 -0
- /package/bundle/{tool-registry-IZX2IOBM.js.map → transport-config-6MB2K2XC.js.map} +0 -0
- /package/bundle/{tool-sandbox-4UC6GAKA.js.map → update-HGQAOC5L.js.map} +0 -0
- /package/bundle/{transport-config-KBF5W2DP.js.map → usage-tracker-SR4BI6ZT.js.map} +0 -0
- /package/bundle/{update-MESYO4LO.js.map → user-registry-4PACZJIJ.js.map} +0 -0
|
@@ -0,0 +1,370 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
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_wrapper,
|
|
5
|
+
wrapper_default
|
|
6
|
+
} from "./chunk-ZT5ZBGWS.js";
|
|
7
|
+
import "./chunk-R76K6L6H.js";
|
|
8
|
+
import {
|
|
9
|
+
init_peer_config,
|
|
10
|
+
loadPeerConfig
|
|
11
|
+
} from "./chunk-3BG3AIDP.js";
|
|
12
|
+
import "./chunk-5RVOEFGT.js";
|
|
13
|
+
import {
|
|
14
|
+
init_peer_auth,
|
|
15
|
+
signRequest,
|
|
16
|
+
verifyServerCert
|
|
17
|
+
} from "./chunk-WC5O5KOE.js";
|
|
18
|
+
import {
|
|
19
|
+
init_logger,
|
|
20
|
+
logDebug,
|
|
21
|
+
logInfo,
|
|
22
|
+
logWarn
|
|
23
|
+
} from "./chunk-XRTXYN66.js";
|
|
24
|
+
import {
|
|
25
|
+
abtarsHome,
|
|
26
|
+
init_paths
|
|
27
|
+
} from "./chunk-GALQBVKO.js";
|
|
28
|
+
import "./chunk-O7KQG6ME.js";
|
|
29
|
+
import {
|
|
30
|
+
__esm,
|
|
31
|
+
__require
|
|
32
|
+
} from "./chunk-7K2YZTLD.js";
|
|
33
|
+
|
|
34
|
+
// src/components/peer-transport/ws-peer-client.ts
|
|
35
|
+
import { randomUUID } from "node:crypto";
|
|
36
|
+
import { existsSync, readFileSync, writeFileSync, unlinkSync } from "node:fs";
|
|
37
|
+
import { join } from "node:path";
|
|
38
|
+
var TAG, MAX_BACKOFF_MS, REQUEST_TIMEOUT_MS, QUEUE_MAX, WsPeerClient;
|
|
39
|
+
var init_ws_peer_client = __esm({
|
|
40
|
+
"src/components/peer-transport/ws-peer-client.ts"() {
|
|
41
|
+
init_wrapper();
|
|
42
|
+
init_peer_auth();
|
|
43
|
+
init_peer_config();
|
|
44
|
+
init_logger();
|
|
45
|
+
init_paths();
|
|
46
|
+
TAG = "ws-peer";
|
|
47
|
+
MAX_BACKOFF_MS = 3e4;
|
|
48
|
+
REQUEST_TIMEOUT_MS = 3e4;
|
|
49
|
+
QUEUE_MAX = 200;
|
|
50
|
+
WsPeerClient = class {
|
|
51
|
+
ws = null;
|
|
52
|
+
peerName;
|
|
53
|
+
entry;
|
|
54
|
+
backoff = 1e3;
|
|
55
|
+
reconnectTimer = null;
|
|
56
|
+
pushHandler = null;
|
|
57
|
+
pending = /* @__PURE__ */ new Map();
|
|
58
|
+
destroyed = false;
|
|
59
|
+
/** Durable outbound queue: pending messages while disconnected. */
|
|
60
|
+
_queue = [];
|
|
61
|
+
queuePath;
|
|
62
|
+
constructor(peerName, entry) {
|
|
63
|
+
this.peerName = peerName;
|
|
64
|
+
this.entry = entry;
|
|
65
|
+
this.queuePath = join(abtarsHome(), `ws-queue-${peerName}.json`);
|
|
66
|
+
this.loadQueue();
|
|
67
|
+
}
|
|
68
|
+
onPush(handler) {
|
|
69
|
+
this.pushHandler = handler;
|
|
70
|
+
}
|
|
71
|
+
connect() {
|
|
72
|
+
if (this.destroyed) return;
|
|
73
|
+
if (this.ws && (this.ws.readyState === wrapper_default.OPEN || this.ws.readyState === wrapper_default.CONNECTING)) {
|
|
74
|
+
return;
|
|
75
|
+
}
|
|
76
|
+
const config = loadPeerConfig();
|
|
77
|
+
if (!this.entry.verifyKey) {
|
|
78
|
+
logWarn(TAG, `Cannot connect to ${this.peerName}: no verifyKey (not enrolled)`);
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
const url = `wss://${this.entry.host}:${this.entry.port}/v1/ws`;
|
|
82
|
+
const sigHeaders = signRequest("GET", "/v1/ws", "", config.self.signingKey, config.self.name);
|
|
83
|
+
this.ws = new wrapper_default(url, {
|
|
84
|
+
headers: sigHeaders,
|
|
85
|
+
minVersion: "TLSv1.3",
|
|
86
|
+
rejectUnauthorized: true,
|
|
87
|
+
checkServerIdentity: (_host, cert) => {
|
|
88
|
+
if (!cert.raw) return new Error("No cert from peer");
|
|
89
|
+
try {
|
|
90
|
+
const { createPublicKey } = __require("node:crypto");
|
|
91
|
+
const keyObj = createPublicKey({ key: cert.raw, format: "der", type: "spki" });
|
|
92
|
+
const certDerB64 = cert.raw.toString("base64");
|
|
93
|
+
const certPemBlock = `-----BEGIN CERTIFICATE-----
|
|
94
|
+
${certDerB64.match(/.{1,64}/g).join("\n")}
|
|
95
|
+
-----END CERTIFICATE-----
|
|
96
|
+
`;
|
|
97
|
+
if (!verifyServerCert(certPemBlock, this.entry.verifyKey)) {
|
|
98
|
+
return new Error(`${this.peerName} cert key != enrolled verifyKey`);
|
|
99
|
+
}
|
|
100
|
+
} catch (e) {
|
|
101
|
+
return new Error(`Cert verify: ${e instanceof Error ? e.message : String(e)}`);
|
|
102
|
+
}
|
|
103
|
+
return void 0;
|
|
104
|
+
}
|
|
105
|
+
});
|
|
106
|
+
this.ws.on("open", () => {
|
|
107
|
+
logInfo(TAG, `Connected to ${this.peerName}`);
|
|
108
|
+
this.backoff = 1e3;
|
|
109
|
+
this.ws._socket?.setKeepAlive(true, 2e4);
|
|
110
|
+
this.drainQueue();
|
|
111
|
+
});
|
|
112
|
+
this.ws.on("message", (data) => this.handleMessage(data.toString()));
|
|
113
|
+
this.ws.on("close", () => {
|
|
114
|
+
this.cleanup();
|
|
115
|
+
if (!this.destroyed) this.scheduleReconnect();
|
|
116
|
+
});
|
|
117
|
+
this.ws.on("error", (err) => {
|
|
118
|
+
logDebug(TAG, `WS error (${this.peerName}): ${err.message}`);
|
|
119
|
+
this.ws?.close();
|
|
120
|
+
});
|
|
121
|
+
}
|
|
122
|
+
/**
|
|
123
|
+
* Send a message over the WS. If disconnected, enqueues it for delivery on reconnect.
|
|
124
|
+
*/
|
|
125
|
+
async send(method, payload) {
|
|
126
|
+
if (!this.ws || this.ws.readyState !== wrapper_default.OPEN) {
|
|
127
|
+
return this.enqueue(method, payload);
|
|
128
|
+
}
|
|
129
|
+
return this.sendNow(method, payload);
|
|
130
|
+
}
|
|
131
|
+
get connected() {
|
|
132
|
+
return this.ws?.readyState === wrapper_default.OPEN;
|
|
133
|
+
}
|
|
134
|
+
destroy() {
|
|
135
|
+
this.destroyed = true;
|
|
136
|
+
if (this.reconnectTimer) clearTimeout(this.reconnectTimer);
|
|
137
|
+
this.cleanup();
|
|
138
|
+
this.ws?.close();
|
|
139
|
+
this.clearPersistedQueue();
|
|
140
|
+
}
|
|
141
|
+
async sendNow(method, payload) {
|
|
142
|
+
if (!this.ws || this.ws.readyState !== wrapper_default.OPEN) {
|
|
143
|
+
throw new Error(`WS not connected to ${this.peerName}`);
|
|
144
|
+
}
|
|
145
|
+
const id = randomUUID();
|
|
146
|
+
const config = loadPeerConfig();
|
|
147
|
+
const payloadStr = JSON.stringify(payload);
|
|
148
|
+
const sigHeaders = signRequest("POST", `/${method}`, payloadStr, config.self.signingKey, config.self.name);
|
|
149
|
+
return new Promise((resolve, reject) => {
|
|
150
|
+
const timer = setTimeout(() => {
|
|
151
|
+
this.pending.delete(id);
|
|
152
|
+
reject(new Error(`WS request timeout (${this.peerName}/${method})`));
|
|
153
|
+
}, REQUEST_TIMEOUT_MS);
|
|
154
|
+
this.pending.set(id, { resolve, reject, timer });
|
|
155
|
+
this.ws.send(JSON.stringify({ type: "request", id, method, payload, ...sigHeaders }));
|
|
156
|
+
});
|
|
157
|
+
}
|
|
158
|
+
enqueue(method, payload) {
|
|
159
|
+
return new Promise((resolve, reject) => {
|
|
160
|
+
if (this._queue.length >= QUEUE_MAX) {
|
|
161
|
+
const dropped = this._queue.shift();
|
|
162
|
+
logWarn(TAG, `[warn] ws queue for ${this.peerName} full, dropping oldest (${dropped.method})`);
|
|
163
|
+
}
|
|
164
|
+
const entry = { method, payload, id: randomUUID() };
|
|
165
|
+
this._queue.push(entry);
|
|
166
|
+
this.persistQueue();
|
|
167
|
+
resolve({ queued: true, id: entry.id });
|
|
168
|
+
});
|
|
169
|
+
}
|
|
170
|
+
drainQueue() {
|
|
171
|
+
if (this._queue.length === 0) return;
|
|
172
|
+
logInfo(TAG, `Draining ${this._queue.length} queued message(s) for ${this.peerName}`);
|
|
173
|
+
const queue = this._queue.splice(0);
|
|
174
|
+
this.clearPersistedQueue();
|
|
175
|
+
for (const entry of queue) {
|
|
176
|
+
this.sendNow(entry.method, entry.payload).catch((err) => {
|
|
177
|
+
logWarn(TAG, `Queue drain failed for ${this.peerName}/${entry.method}: ${err.message}`);
|
|
178
|
+
});
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
persistQueue() {
|
|
182
|
+
try {
|
|
183
|
+
writeFileSync(this.queuePath, JSON.stringify(this._queue), { encoding: "utf-8", mode: 384 });
|
|
184
|
+
} catch {
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
clearPersistedQueue() {
|
|
188
|
+
try {
|
|
189
|
+
if (existsSync(this.queuePath)) unlinkSync(this.queuePath);
|
|
190
|
+
} catch {
|
|
191
|
+
}
|
|
192
|
+
}
|
|
193
|
+
loadQueue() {
|
|
194
|
+
try {
|
|
195
|
+
if (existsSync(this.queuePath)) {
|
|
196
|
+
const data = readFileSync(this.queuePath, "utf-8");
|
|
197
|
+
const parsed = JSON.parse(data);
|
|
198
|
+
if (Array.isArray(parsed)) {
|
|
199
|
+
this._queue = parsed.slice(0, QUEUE_MAX);
|
|
200
|
+
if (this._queue.length > 0) {
|
|
201
|
+
logInfo(TAG, `Loaded ${this._queue.length} queued message(s) for ${this.peerName} from disk`);
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
} catch {
|
|
206
|
+
}
|
|
207
|
+
}
|
|
208
|
+
handleMessage(raw) {
|
|
209
|
+
try {
|
|
210
|
+
const msg = JSON.parse(raw);
|
|
211
|
+
if (msg.type === "response" && msg.id && this.pending.has(msg.id)) {
|
|
212
|
+
const p = this.pending.get(msg.id);
|
|
213
|
+
this.pending.delete(msg.id);
|
|
214
|
+
clearTimeout(p.timer);
|
|
215
|
+
p.resolve(msg.payload);
|
|
216
|
+
} else if (msg.type === "push") {
|
|
217
|
+
this.pushHandler?.(msg.method, msg.payload);
|
|
218
|
+
}
|
|
219
|
+
} catch {
|
|
220
|
+
}
|
|
221
|
+
}
|
|
222
|
+
cleanup() {
|
|
223
|
+
for (const [, p] of this.pending) {
|
|
224
|
+
clearTimeout(p.timer);
|
|
225
|
+
p.reject(new Error("WS connection closed"));
|
|
226
|
+
}
|
|
227
|
+
this.pending.clear();
|
|
228
|
+
}
|
|
229
|
+
scheduleReconnect() {
|
|
230
|
+
const jitter = this.backoff * (0.8 + Math.random() * 0.4);
|
|
231
|
+
logDebug(TAG, `Reconnecting to ${this.peerName} in ${Math.round(jitter)}ms`);
|
|
232
|
+
this.reconnectTimer = setTimeout(() => {
|
|
233
|
+
this.reconnectTimer = null;
|
|
234
|
+
this.connect();
|
|
235
|
+
}, jitter);
|
|
236
|
+
this.backoff = Math.min(this.backoff * 2, MAX_BACKOFF_MS);
|
|
237
|
+
}
|
|
238
|
+
/**
|
|
239
|
+
* Dialer-side enrollment handshake over /v1/enroll-ws.
|
|
240
|
+
* Called by `abtars tribe join`.
|
|
241
|
+
*/
|
|
242
|
+
async enroll(tribeToken, selfSigningKey, selfVerifyKey, selfName) {
|
|
243
|
+
const { randomBytes } = await import("node:crypto");
|
|
244
|
+
const {
|
|
245
|
+
macTribe,
|
|
246
|
+
signEnroll,
|
|
247
|
+
verifyAck
|
|
248
|
+
} = await import("./peer-auth-RI43DKJE.js");
|
|
249
|
+
const { clearPeerConfigCache } = await import("./peer-config-URM7DCW6.js");
|
|
250
|
+
const { writeFileSync: writeFileSync2, existsSync: exSync, mkdirSync } = await import("node:fs");
|
|
251
|
+
const enrollUrl = `wss://${this.entry.host}:${this.entry.port}/v1/enroll-ws`;
|
|
252
|
+
const nonceI = randomBytes(16).toString("hex");
|
|
253
|
+
const tsNow = Math.floor(Date.now() / 1e3);
|
|
254
|
+
return new Promise((resolve, reject) => {
|
|
255
|
+
const enrollWs = new wrapper_default(enrollUrl, {
|
|
256
|
+
minVersion: "TLSv1.3",
|
|
257
|
+
rejectUnauthorized: false
|
|
258
|
+
// Can't pin yet — cert is verified via MAC binding in step B
|
|
259
|
+
});
|
|
260
|
+
let stage = 0;
|
|
261
|
+
let nonceR = "";
|
|
262
|
+
let pubKeyR = "";
|
|
263
|
+
enrollWs.on("open", () => {
|
|
264
|
+
enrollWs.send(JSON.stringify({
|
|
265
|
+
pubKey_i: selfVerifyKey,
|
|
266
|
+
nonce_i: nonceI,
|
|
267
|
+
ts: tsNow
|
|
268
|
+
}));
|
|
269
|
+
stage = 1;
|
|
270
|
+
});
|
|
271
|
+
enrollWs.on("message", async (rawData) => {
|
|
272
|
+
try {
|
|
273
|
+
const msg = JSON.parse(rawData.toString());
|
|
274
|
+
if (stage === 1) {
|
|
275
|
+
const { pubKey_r, nonce_r, ts, mac_r } = msg;
|
|
276
|
+
if (!pubKey_r || !nonce_r || !mac_r) {
|
|
277
|
+
reject(new Error("Invalid challenge"));
|
|
278
|
+
enrollWs.close();
|
|
279
|
+
return;
|
|
280
|
+
}
|
|
281
|
+
const expectedMacR = macTribe(tribeToken, pubKey_r + nonceI);
|
|
282
|
+
if (mac_r !== expectedMacR) {
|
|
283
|
+
reject(new Error("tribe token mismatch \u2014 not same tribe"));
|
|
284
|
+
enrollWs.close();
|
|
285
|
+
return;
|
|
286
|
+
}
|
|
287
|
+
nonceR = nonce_r;
|
|
288
|
+
pubKeyR = pubKey_r;
|
|
289
|
+
stage = 2;
|
|
290
|
+
const macI = macTribe(tribeToken, selfVerifyKey + nonceR);
|
|
291
|
+
const selfSig = signEnroll(selfSigningKey, selfVerifyKey, nonceR, selfName);
|
|
292
|
+
enrollWs.send(JSON.stringify({
|
|
293
|
+
mac_i: macI,
|
|
294
|
+
name: selfName,
|
|
295
|
+
nonce_r: nonceR,
|
|
296
|
+
ts: Math.floor(Date.now() / 1e3),
|
|
297
|
+
selfSig
|
|
298
|
+
}));
|
|
299
|
+
return;
|
|
300
|
+
}
|
|
301
|
+
if (stage === 2) {
|
|
302
|
+
const { name_r, pubKey_r: pubKeyRd, ackSig } = msg;
|
|
303
|
+
if (!ackSig || !name_r) {
|
|
304
|
+
reject(new Error("Invalid ack"));
|
|
305
|
+
enrollWs.close();
|
|
306
|
+
return;
|
|
307
|
+
}
|
|
308
|
+
if (!verifyAck(ackSig, pubKeyRd, name_r, pubKeyRd, nonceR)) {
|
|
309
|
+
reject(new Error("Invalid ack signature"));
|
|
310
|
+
enrollWs.close();
|
|
311
|
+
return;
|
|
312
|
+
}
|
|
313
|
+
const peersPath = join(abtarsHome(), "config", "peers.json");
|
|
314
|
+
let raw = {};
|
|
315
|
+
if (exSync(peersPath)) {
|
|
316
|
+
try {
|
|
317
|
+
raw = JSON.parse(__require("fs").readFileSync(peersPath, "utf-8"));
|
|
318
|
+
} catch {
|
|
319
|
+
raw = {};
|
|
320
|
+
}
|
|
321
|
+
}
|
|
322
|
+
if (!raw.peers || typeof raw.peers !== "object") raw.peers = {};
|
|
323
|
+
raw.peers[name_r] = {
|
|
324
|
+
host: this.entry.host,
|
|
325
|
+
port: this.entry.port,
|
|
326
|
+
verifyKey: pubKeyRd,
|
|
327
|
+
trust: 1,
|
|
328
|
+
transport: "ws-outbound"
|
|
329
|
+
};
|
|
330
|
+
writeFileSync2(peersPath, JSON.stringify(raw, null, 2) + "\n", { encoding: "utf-8" });
|
|
331
|
+
clearPeerConfigCache();
|
|
332
|
+
logInfo(TAG, `Enrolled with '${name_r}' at trust=1`);
|
|
333
|
+
this.ws = enrollWs;
|
|
334
|
+
enrollWs.removeAllListeners("message");
|
|
335
|
+
enrollWs.on("message", (data) => this.handleMessage(data.toString()));
|
|
336
|
+
enrollWs.on("close", () => {
|
|
337
|
+
this.cleanup();
|
|
338
|
+
if (!this.destroyed) this.scheduleReconnect();
|
|
339
|
+
});
|
|
340
|
+
enrollWs.on("error", (err) => {
|
|
341
|
+
logDebug(TAG, `WS error (${this.peerName}): ${err.message}`);
|
|
342
|
+
this.ws?.close();
|
|
343
|
+
});
|
|
344
|
+
resolve();
|
|
345
|
+
}
|
|
346
|
+
} catch (err) {
|
|
347
|
+
reject(err);
|
|
348
|
+
enrollWs.close();
|
|
349
|
+
}
|
|
350
|
+
});
|
|
351
|
+
enrollWs.on("error", (err) => reject(new Error(`Enrollment WS error: ${err.message}`)));
|
|
352
|
+
enrollWs.on("close", (code, reason) => {
|
|
353
|
+
if (stage < 2) reject(new Error(`Enrollment WS closed early: ${code} ${reason}`));
|
|
354
|
+
});
|
|
355
|
+
setTimeout(() => {
|
|
356
|
+
if (stage < 2) {
|
|
357
|
+
reject(new Error("Enrollment timeout"));
|
|
358
|
+
enrollWs.close();
|
|
359
|
+
}
|
|
360
|
+
}, 3e4);
|
|
361
|
+
});
|
|
362
|
+
}
|
|
363
|
+
};
|
|
364
|
+
}
|
|
365
|
+
});
|
|
366
|
+
init_ws_peer_client();
|
|
367
|
+
export {
|
|
368
|
+
WsPeerClient
|
|
369
|
+
};
|
|
370
|
+
//# sourceMappingURL=ws-peer-client-U3NNPOK7.js.map
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": 3,
|
|
3
|
+
"sources": ["../src/components/peer-transport/ws-peer-client.ts"],
|
|
4
|
+
"sourcesContent": ["/**\n * ws-peer-client.ts \u2014 Persistent outbound WebSocket to a peer (#972, #1293).\n *\n * #1293 changes:\n * - Auth: Ed25519 request signatures replacing JWT header\n * - Removed own ping setInterval (dead-detection via HB tick)\n * - setKeepAlive(true, 20_000) to hold NAT hole\n * - Durable outbound queue (persist to disk, drain on reconnect)\n */\nimport WebSocket from \"ws\";\nimport { randomUUID } from \"node:crypto\";\nimport { signRequest, verifyServerCert } from \"./peer-auth.js\";\nimport { loadPeerConfig, deriveVerifyKey, type PeerEntry } from \"../peer-config.js\";\nimport { logInfo, logWarn, logDebug } from \"../logger.js\";\nimport { existsSync, readFileSync, writeFileSync, unlinkSync } from \"node:fs\";\nimport { join } from \"node:path\";\nimport { abtarsHome } from \"../../paths.js\";\n\nconst TAG = \"ws-peer\";\nconst MAX_BACKOFF_MS = 30_000;\nconst REQUEST_TIMEOUT_MS = 30_000;\nconst QUEUE_MAX = 200;\n\ntype PushHandler = (method: string, payload: unknown) => void;\ntype PendingRequest = { resolve: (v: unknown) => void; reject: (e: Error) => void; timer: ReturnType<typeof setTimeout> };\n\ninterface QueueEntry {\n method: string;\n payload: unknown;\n id: string;\n}\n\nexport class WsPeerClient {\n private ws: WebSocket | null = null;\n private readonly peerName: string;\n private readonly entry: PeerEntry;\n private backoff = 1000;\n private reconnectTimer: ReturnType<typeof setTimeout> | null = null;\n private pushHandler: PushHandler | null = null;\n private pending = new Map<string, PendingRequest>();\n private destroyed = false;\n /** Durable outbound queue: pending messages while disconnected. */\n private _queue: QueueEntry[] = [];\n private readonly queuePath: string;\n\n constructor(peerName: string, entry: PeerEntry) {\n this.peerName = peerName;\n this.entry = entry;\n this.queuePath = join(abtarsHome(), `ws-queue-${peerName}.json`);\n this.loadQueue();\n }\n\n onPush(handler: PushHandler): void { this.pushHandler = handler; }\n\n connect(): void {\n if (this.destroyed) return;\n if (this.ws && (this.ws.readyState === WebSocket.OPEN || this.ws.readyState === WebSocket.CONNECTING)) {\n return; // already connected / connecting\n }\n\n const config = loadPeerConfig();\n if (!this.entry.verifyKey) {\n logWarn(TAG, `Cannot connect to ${this.peerName}: no verifyKey (not enrolled)`);\n return;\n }\n\n const url = `wss://${this.entry.host}:${this.entry.port}/v1/ws`;\n const sigHeaders = signRequest(\"GET\", \"/v1/ws\", \"\", config.self.signingKey, config.self.name);\n\n this.ws = new WebSocket(url, {\n headers: sigHeaders,\n minVersion: \"TLSv1.3\",\n rejectUnauthorized: true,\n checkServerIdentity: (_host: string, cert: { raw?: Buffer }) => {\n if (!cert.raw) return new Error(\"No cert from peer\");\n try {\n const { createPublicKey } = require(\"node:crypto\") as typeof import(\"node:crypto\");\n const keyObj = createPublicKey({ key: cert.raw, format: \"der\", type: \"spki\" });\n // Build PEM cert block from raw DER\n const certDerB64 = cert.raw.toString(\"base64\");\n const certPemBlock = `-----BEGIN CERTIFICATE-----\\n${certDerB64.match(/.{1,64}/g)!.join(\"\\n\")}\\n-----END CERTIFICATE-----\\n`;\n if (!verifyServerCert(certPemBlock, this.entry.verifyKey)) {\n return new Error(`${this.peerName} cert key != enrolled verifyKey`);\n }\n } catch (e) {\n return new Error(`Cert verify: ${e instanceof Error ? e.message : String(e)}`);\n }\n return undefined;\n },\n } as any);\n\n this.ws.on(\"open\", () => {\n logInfo(TAG, `Connected to ${this.peerName}`);\n this.backoff = 1000;\n // NAT keepalive: 20s idle probe\n (this.ws as any)._socket?.setKeepAlive(true, 20_000);\n this.drainQueue();\n });\n\n this.ws.on(\"message\", (data) => this.handleMessage(data.toString()));\n\n this.ws.on(\"close\", () => {\n this.cleanup();\n if (!this.destroyed) this.scheduleReconnect();\n });\n\n this.ws.on(\"error\", (err) => {\n logDebug(TAG, `WS error (${this.peerName}): ${err.message}`);\n this.ws?.close();\n });\n }\n\n /**\n * Send a message over the WS. If disconnected, enqueues it for delivery on reconnect.\n */\n async send(method: string, payload: unknown): Promise<unknown> {\n if (!this.ws || this.ws.readyState !== WebSocket.OPEN) {\n // Enqueue instead of throwing\n return this.enqueue(method, payload);\n }\n return this.sendNow(method, payload);\n }\n\n get connected(): boolean { return this.ws?.readyState === WebSocket.OPEN; }\n\n destroy(): void {\n this.destroyed = true;\n if (this.reconnectTimer) clearTimeout(this.reconnectTimer);\n this.cleanup();\n this.ws?.close();\n this.clearPersistedQueue();\n }\n\n private async sendNow(method: string, payload: unknown): Promise<unknown> {\n if (!this.ws || this.ws.readyState !== WebSocket.OPEN) {\n throw new Error(`WS not connected to ${this.peerName}`);\n }\n const id = randomUUID();\n const config = loadPeerConfig();\n // Sign the serialized payload as a \"request\"\n const payloadStr = JSON.stringify(payload);\n const sigHeaders = signRequest(\"POST\", `/${method}`, payloadStr, config.self.signingKey, config.self.name);\n\n return new Promise((resolve, reject) => {\n const timer = setTimeout(() => {\n this.pending.delete(id);\n reject(new Error(`WS request timeout (${this.peerName}/${method})`));\n }, REQUEST_TIMEOUT_MS);\n this.pending.set(id, { resolve, reject, timer });\n this.ws!.send(JSON.stringify({ type: \"request\", id, method, payload, ...sigHeaders }));\n });\n }\n\n private enqueue(method: string, payload: unknown): Promise<unknown> {\n return new Promise((resolve, reject) => {\n if (this._queue.length >= QUEUE_MAX) {\n const dropped = this._queue.shift()!;\n logWarn(TAG, `[warn] ws queue for ${this.peerName} full, dropping oldest (${dropped.method})`);\n }\n const entry: QueueEntry = { method, payload, id: randomUUID() };\n this._queue.push(entry);\n this.persistQueue();\n // We can't resolve/reject immediately for queued messages\n // Resolve immediately with a sentinel (fire-and-forget semantics)\n resolve({ queued: true, id: entry.id });\n });\n }\n\n private drainQueue(): void {\n if (this._queue.length === 0) return;\n logInfo(TAG, `Draining ${this._queue.length} queued message(s) for ${this.peerName}`);\n const queue = this._queue.splice(0);\n this.clearPersistedQueue();\n for (const entry of queue) {\n this.sendNow(entry.method, entry.payload).catch(err => {\n logWarn(TAG, `Queue drain failed for ${this.peerName}/${entry.method}: ${err.message}`);\n });\n }\n }\n\n private persistQueue(): void {\n try {\n writeFileSync(this.queuePath, JSON.stringify(this._queue), { encoding: \"utf-8\", mode: 0o600 });\n } catch { /* best effort */ }\n }\n\n private clearPersistedQueue(): void {\n try { if (existsSync(this.queuePath)) unlinkSync(this.queuePath); } catch { /* best effort */ }\n }\n\n private loadQueue(): void {\n try {\n if (existsSync(this.queuePath)) {\n const data = readFileSync(this.queuePath, \"utf-8\");\n const parsed = JSON.parse(data) as QueueEntry[];\n if (Array.isArray(parsed)) {\n this._queue = parsed.slice(0, QUEUE_MAX);\n if (this._queue.length > 0) {\n logInfo(TAG, `Loaded ${this._queue.length} queued message(s) for ${this.peerName} from disk`);\n }\n }\n }\n } catch { /* best effort \u2014 corrupt queue, start fresh */ }\n }\n\n private handleMessage(raw: string): void {\n try {\n const msg = JSON.parse(raw);\n if (msg.type === \"response\" && msg.id && this.pending.has(msg.id)) {\n const p = this.pending.get(msg.id)!;\n this.pending.delete(msg.id);\n clearTimeout(p.timer);\n p.resolve(msg.payload);\n } else if (msg.type === \"push\") {\n this.pushHandler?.(msg.method, msg.payload);\n }\n } catch { /* malformed \u2014 ignore */ }\n }\n\n private cleanup(): void {\n // Reject all pending requests\n for (const [, p] of this.pending) {\n clearTimeout(p.timer);\n p.reject(new Error(\"WS connection closed\"));\n }\n this.pending.clear();\n }\n\n private scheduleReconnect(): void {\n const jitter = this.backoff * (0.8 + Math.random() * 0.4); // \u00B120%\n logDebug(TAG, `Reconnecting to ${this.peerName} in ${Math.round(jitter)}ms`);\n this.reconnectTimer = setTimeout(() => {\n this.reconnectTimer = null;\n this.connect();\n }, jitter);\n this.backoff = Math.min(this.backoff * 2, MAX_BACKOFF_MS);\n }\n\n /**\n * Dialer-side enrollment handshake over /v1/enroll-ws.\n * Called by `abtars tribe join`.\n */\n async enroll(tribeToken: string, selfSigningKey: string, selfVerifyKey: string, selfName: string): Promise<void> {\n const { randomBytes } = await import(\"node:crypto\");\n const {\n macTribe, signEnroll, verifyAck,\n } = await import(\"./peer-auth.js\");\n const { clearPeerConfigCache } = await import(\"../peer-config.js\");\n const { writeFileSync, existsSync: exSync, mkdirSync } = await import(\"node:fs\");\n\n const enrollUrl = `wss://${this.entry.host}:${this.entry.port}/v1/enroll-ws`;\n const nonceI = randomBytes(16).toString(\"hex\");\n const tsNow = Math.floor(Date.now() / 1000);\n\n return new Promise((resolve, reject) => {\n // No auth headers for enrollment path\n const enrollWs = new WebSocket(enrollUrl, {\n minVersion: \"TLSv1.3\",\n rejectUnauthorized: false, // Can't pin yet \u2014 cert is verified via MAC binding in step B\n } as any);\n\n let stage = 0;\n let nonceR = \"\";\n let pubKeyR = \"\";\n\n enrollWs.on(\"open\", () => {\n // Step A: knock\n enrollWs.send(JSON.stringify({\n pubKey_i: selfVerifyKey,\n nonce_i: nonceI,\n ts: tsNow,\n }));\n stage = 1;\n });\n\n enrollWs.on(\"message\", async (rawData) => {\n try {\n const msg = JSON.parse(rawData.toString());\n\n if (stage === 1) {\n // Step B: challenge\n const { pubKey_r, nonce_r, ts, mac_r } = msg as { pubKey_r: string; nonce_r: string; ts: number; mac_r: string };\n if (!pubKey_r || !nonce_r || !mac_r) { reject(new Error(\"Invalid challenge\")); enrollWs.close(); return; }\n\n // Verify mac_r: HMAC(tribeToken, pubKey_r + nonce_i)\n const expectedMacR = macTribe(tribeToken, pubKey_r + nonceI);\n if (mac_r !== expectedMacR) { reject(new Error(\"tribe token mismatch \u2014 not same tribe\")); enrollWs.close(); return; }\n\n nonceR = nonce_r;\n pubKeyR = pubKey_r;\n stage = 2;\n\n // Step C: enroll\n const macI = macTribe(tribeToken, selfVerifyKey + nonceR);\n const selfSig = signEnroll(selfSigningKey, selfVerifyKey, nonceR, selfName);\n enrollWs.send(JSON.stringify({\n mac_i: macI,\n name: selfName,\n nonce_r: nonceR,\n ts: Math.floor(Date.now() / 1000),\n selfSig,\n }));\n return;\n }\n\n if (stage === 2) {\n // Step D: ack\n const { name_r, pubKey_r: pubKeyRd, ackSig } = msg as { name_r: string; pubKey_r: string; ackSig: string };\n if (!ackSig || !name_r) { reject(new Error(\"Invalid ack\")); enrollWs.close(); return; }\n\n if (!verifyAck(ackSig, pubKeyRd, name_r, pubKeyRd, nonceR)) {\n reject(new Error(\"Invalid ack signature\")); enrollWs.close(); return;\n }\n\n // Persist responder to own peers.json\n const peersPath = join(abtarsHome(), \"config\", \"peers.json\");\n let raw: Record<string, unknown> = {};\n if (exSync(peersPath)) { try { raw = JSON.parse(require(\"fs\").readFileSync(peersPath, \"utf-8\")); } catch { raw = {}; } }\n if (!raw.peers || typeof raw.peers !== \"object\") raw.peers = {};\n (raw.peers as Record<string, unknown>)[name_r] = {\n host: this.entry.host,\n port: this.entry.port,\n verifyKey: pubKeyRd,\n trust: 1,\n transport: \"ws-outbound\",\n };\n writeFileSync(peersPath, JSON.stringify(raw, null, 2) + \"\\n\", { encoding: \"utf-8\" });\n clearPeerConfigCache();\n\n logInfo(TAG, `Enrolled with '${name_r}' at trust=1`);\n // Keep WS alive as steady-state peer connection\n this.ws = enrollWs;\n enrollWs.removeAllListeners(\"message\");\n enrollWs.on(\"message\", (data) => this.handleMessage(data.toString()));\n enrollWs.on(\"close\", () => { this.cleanup(); if (!this.destroyed) this.scheduleReconnect(); });\n enrollWs.on(\"error\", (err) => { logDebug(TAG, `WS error (${this.peerName}): ${err.message}`); this.ws?.close(); });\n resolve();\n }\n } catch (err) {\n reject(err);\n enrollWs.close();\n }\n });\n\n enrollWs.on(\"error\", (err) => reject(new Error(`Enrollment WS error: ${err.message}`)));\n enrollWs.on(\"close\", (code, reason) => {\n if (stage < 2) reject(new Error(`Enrollment WS closed early: ${code} ${reason}`));\n });\n\n setTimeout(() => { if (stage < 2) { reject(new Error(\"Enrollment timeout\")); enrollWs.close(); } }, 30_000);\n });\n }\n}\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["writeFileSync"]
|
|
7
|
+
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "abtars",
|
|
3
|
-
"version": "0.3.4
|
|
3
|
+
"version": "0.3.4",
|
|
4
4
|
"description": "Agentic framework for connecting LLMs to messaging platforms, with persistent memory, skills, scheduled tasks, self-healing supervision, and distributed multi-agent collaboration",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "bundle/abtars.js",
|
|
@@ -5,7 +5,8 @@ After=network.target
|
|
|
5
5
|
[Service]
|
|
6
6
|
Type=simple
|
|
7
7
|
ExecStart=%h/.abtars-releases/src/abtars/scripts/abtars-watchdog.sh
|
|
8
|
-
Restart=
|
|
8
|
+
Restart=always
|
|
9
|
+
RestartPreventExitStatus=2
|
|
9
10
|
RestartSec=5
|
|
10
11
|
Environment=PATH=%h/.abtars/bin:%h/.local/bin:%h/.npm-global/bin:/usr/local/bin:/usr/bin:/bin
|
|
11
12
|
Environment=NODE_PATH=%h/.local/lib/node_modules
|
|
@@ -5,7 +5,6 @@ AB="${ABTARS_HOME:-$HOME/.abtars}"
|
|
|
5
5
|
LOCK="$AB/bridge.lock"
|
|
6
6
|
STALE=300
|
|
7
7
|
POLL=60
|
|
8
|
-
LOG="$AB/logs/bridge.log"
|
|
9
8
|
STATE="$AB/deploy.state"
|
|
10
9
|
|
|
11
10
|
# Singleton: flock (Linux) / lockf (macOS)
|
|
@@ -59,15 +58,12 @@ while true; do
|
|
|
59
58
|
exit 0 ;;
|
|
60
59
|
esac
|
|
61
60
|
|
|
62
|
-
# Pre-flight doctor
|
|
63
|
-
command -v abtars &>/dev/null && abtars doctor --fix >> "$AB/logs/watchdog.log" 2>&1 || true
|
|
64
|
-
|
|
65
61
|
# Start bridge
|
|
66
62
|
BRIDGE_REASON="${REASON:-watchdog-respawn}"
|
|
67
63
|
# #1261: exec replaces the subshell with the env->nohup->node chain so $! is the real node PID.
|
|
68
64
|
# Without exec, bash forks a subshell for `cd && env=value cmd &` and $! returns the subshell,
|
|
69
65
|
# leaving node as a grandchild that gets orphaned when the subshell dies.
|
|
70
|
-
cd "$AB" && exec env ABTARS_WATCHDOG_PID=$$ NODE_PATH="$HOME/.local/lib/node_modules:${NODE_PATH:-}" ABTARS_START_REASON="$BRIDGE_REASON" nohup node --max-old-space-size=1024 app/bundle/abtars.js
|
|
66
|
+
cd "$AB" && exec env ABTARS_WATCHDOG_PID=$$ NODE_PATH="$HOME/.local/lib/node_modules:${NODE_PATH:-}" ABTARS_START_REASON="$BRIDGE_REASON" nohup node --max-old-space-size=1024 app/bundle/abtars.js 200>&- &
|
|
71
67
|
PID=$!
|
|
72
68
|
disown $PID
|
|
73
69
|
SPAWNED_AT=$(date +%s)
|
|
@@ -77,10 +77,10 @@ echo "Restarting..."
|
|
|
77
77
|
if launchctl list 2>/dev/null | grep -q abtars; then
|
|
78
78
|
echo "LaunchAgent manages watchdog — it will restart the bridge."
|
|
79
79
|
elif [ -f "$HOME_DIR/scripts/abtars-watchdog.sh" ]; then
|
|
80
|
-
nohup bash "$HOME_DIR/scripts/abtars-watchdog.sh"
|
|
80
|
+
nohup bash "$HOME_DIR/scripts/abtars-watchdog.sh" &
|
|
81
81
|
echo "Watchdog restarted (PID $!) — it will start the bridge."
|
|
82
82
|
else
|
|
83
|
-
nohup node "$HOME_DIR/app/bundle/abtars.js"
|
|
83
|
+
nohup node "$HOME_DIR/app/bundle/abtars.js" &
|
|
84
84
|
echo $! > "$HOME_DIR/bridge.pid"
|
|
85
85
|
echo "Bridge started (PID $!)."
|
|
86
86
|
fi
|