elanous 0.2.21 → 0.2.23
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/NOTICE +7 -0
- package/README.md +32 -22
- package/apps/pwa/out/404/index.html +1 -1
- package/apps/pwa/out/404.html +1 -1
- package/apps/pwa/out/_next/static/chunks/{119fc678.6f591cdb84ca5791.js → 0673cc54.8e2ef1c23e49e190.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{a9f2b54d-40c16bd0efdb04b8.js → 0a09e062-34f747a17d8d8c2e.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{f8626309.a4e5d362b1d55e59.js → 0e3acd34.d42b2ef87fdf4234.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/1168.a0fb3d9db76c00bd.js +77 -0
- package/apps/pwa/out/_next/static/chunks/{7175-350f4ce2873bc038.js → 1325-dc3f3c21eb181cb4.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/1357.a843c41d2cd7ec31.js +34 -0
- package/apps/pwa/out/_next/static/chunks/1430.53f49882b17607c2.js +24 -0
- package/apps/pwa/out/_next/static/chunks/1459-be6509b3419d8a9f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{6767.8e6c5f6e744fcd9f.js → 1505.5826671109111e75.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/153.0a4e3cd516930491.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1572.7bc291352e241a45.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1593-d07ad068c120dfb0.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1608.b7c900baa56cab32.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1615-4d8156febaac4b35.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1646.e03f0fbc26bc72f6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{7327-2d69fb321ba73389.js → 1669-da843ed73aa301f5.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/176.13ba0659e3e96fd4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1990.9c60f495ef33c070.js +36 -0
- package/apps/pwa/out/_next/static/chunks/2042e469.f86158dd5c1e51a1.js +122 -0
- package/apps/pwa/out/_next/static/chunks/2528.0af5c0e1fad88df6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2543-28ec6aeb80a5e1e1.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2561.43c99d6ee914ee6a.js +62 -0
- package/apps/pwa/out/_next/static/chunks/2638.b39ab2f674caa1a5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/272-b23d2e92161d11fd.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{7899.597af4a9996c907f.js → 2721.bc9a8f36bd85c07a.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/2778.67e0c1d484189ccf.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2841.10ff309f6a3168af.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2886-9639f97d523d752a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2978.57fb87ce21cc5a85.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3664.15f968c39d15bd28.js +149 -0
- package/apps/pwa/out/_next/static/chunks/3786-935eb3fcde90e496.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3813.df4a01ae89c6f63f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3961-fbef064c213b2b18.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3992.f79c70480e8c4077.js +309 -0
- package/apps/pwa/out/_next/static/chunks/40-413e8641de9ed1e5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4054-521f11a503daed64.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4315.e7356f34c7d8ec79.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4489-bf629de6f04f7681.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4540.557733cc88c6a82b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/462.0275b4338c5b6337.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4658-7ed9266098a787e4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4945-0f4046cfc3228ea3.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{d70879db.c66c56a95a91efc6.js → 4c5e95ce.83e9b16add6fcd8c.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/5105-18b4165c5d3a86b0.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5205-6992210fe31f45f4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5287-72898b126d722457.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{6158.566c890adc06a459.js → 5313.1697309c532b9856.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/{79b78388.663188133449d707.js → 53746282.1be36038d1abd949.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/5474.991b90688c3cb321.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5544-871146192d095594.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5578.ac963634373b28c6.js +286 -0
- package/apps/pwa/out/_next/static/chunks/5935.d5e8ca3e096772e8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5967-c0a80f8ffe5d4050.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{1268.0840ff91e083fcbd.js → 5974.360f8441eb0ac1ec.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/6006.84e8b418a7a0db97.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6013-1267ba7454d6764b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6038-1e0f7ee1086da4cf.js +1 -0
- package/apps/pwa/out/_next/static/chunks/617.709dd0019fe99796.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6261.fb9bf94947094636.js +74 -0
- package/apps/pwa/out/_next/static/chunks/6411.1966866fae31ffa9.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6481-b829d99aa8d158f5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6541.2b7daa043100d0fa.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6571-926ddf024a6ad5df.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6597.2d7a6d77ab485b27.js +64 -0
- package/apps/pwa/out/_next/static/chunks/67.5dd2dc543c2fa3de.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{9832.2ab2e818013574c7.js → 6702.ebbd165d5e4a4a14.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/6777-312496b0d774719b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/681.0116f7036cfb4e8d.js +32 -0
- package/apps/pwa/out/_next/static/chunks/6871.30b2bf23b3126e36.js +24 -0
- package/apps/pwa/out/_next/static/chunks/6882.737d366d54e29d83.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7035.54c2c535164b1c9b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7086-8bfa7e8f796a03d9.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7126.5e5599f251726b67.js +93 -0
- package/apps/pwa/out/_next/static/chunks/7203-47ff0740a293e284.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7268.017f49dafb5f0ff3.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7355.5d65a87e9567ae08.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7392.4018c2a62177f296.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{6110.1297d4093fdfbb0d.js → 740.90b31555290236a9.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/7471.3a3d1be50559cfb8.js +148 -0
- package/apps/pwa/out/_next/static/chunks/7500.73489a345cef2201.js +226 -0
- package/apps/pwa/out/_next/static/chunks/{9070.067c106528ec1ae6.js → 7518.49161e8f5814abdb.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/7565.c2f72a15c1ed0396.js +27 -0
- package/apps/pwa/out/_next/static/chunks/7651.6d1c984d3d8587a4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7713.7ab863ed59b2d661.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7793.d7cd2026767ddd54.js +115 -0
- package/apps/pwa/out/_next/static/chunks/7837.c7c267e5dceadb11.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7891.09266382daf70d1c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7905.b230b9d06cb4ad5d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7990-cbf6a01bcbdcb7e6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8119-819c549e0c197786.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8186-74ea19a3700d04a8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{8194.484f51e273d9abd2.js → 8264.00e434fbd02e9311.js} +16 -16
- package/apps/pwa/out/_next/static/chunks/8267-e7b3262b735ae106.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8386.86518e55b75f7cf5.js +8 -0
- package/apps/pwa/out/_next/static/chunks/{088d8e8a.8069543d082bec12.js → 83cfc5c8.349535543c1548b6.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/8437.ba6eeeb29590042f.js +23 -0
- package/apps/pwa/out/_next/static/chunks/{1948.5f35b39eef222a94.js → 8438.ee7f0df3b3f6fcb4.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/8469-1500be57e582296f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8483-7164cecdaf178ca6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{4588.ad3364cb7fb97ada.js → 8532.a86e99acf9b761cb.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/8569.b853a8daa8f31d12.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8722-4c940f02c496ad36.js +1 -0
- package/apps/pwa/out/_next/static/chunks/887-41d0dcf5af48c628.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8925-2abfb48af477fb7f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{88729267.9c6c000157c83f2f.js → 89849432.9eaa2f4c9c010965.js} +3 -3
- package/apps/pwa/out/_next/static/chunks/9039.da86361496797522.js +90 -0
- package/apps/pwa/out/_next/static/chunks/905.d5745a25884754d4.js +94 -0
- package/apps/pwa/out/_next/static/chunks/9089-d909f3d4478b0628.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9096.dc5c7a267f83790c.js +41 -0
- package/apps/pwa/out/_next/static/chunks/93.a567257b6bdb7fe4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9320.419acb9665b46597.js +287 -0
- package/apps/pwa/out/_next/static/chunks/9356.b8ceda6634612ff8.js +79 -0
- package/apps/pwa/out/_next/static/chunks/94.e9e1043b35cd3eed.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9400-7498ea90b2e6ee8f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{3522-1de1319d028ac89c.js → 9502-32c5dc22e8f120f5.js} +3 -3
- package/apps/pwa/out/_next/static/chunks/9930-58644af9c813d6e1.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9932.367cf4725fedd6e2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9935.1628b904cdc8ce0e.js +104 -0
- package/apps/pwa/out/_next/static/chunks/{7630.2b9a68659053ff4e.js → 9976.8f28864317639fe6.js} +16 -16
- package/apps/pwa/out/_next/static/chunks/app/_not-found/page-a2aa8709d193ee0d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/approvals/page-d5341ac96203a983.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/autopilot/page-0160ab83c8685a12.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/board/page-55c631c032dcc47e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/botlab/page-ad3bd8084048bee4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/bots/page-e6784759a2531031.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ceo/page-5c5d0e370f495ef6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/chat/page-c325e21543cd48a8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/consult/{page-111cabe4d1fd69ae.js → page-6168a7c43e6ef8f5.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/control/page-31417d3604154a6d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/decisions/page-e9606dc0bdec9305.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/design-check/page-a648bc464c9dc754.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/editor/page-25bb425afdb27541.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/exec/page-32d72fdef1afe11a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/field/page-d27b794c8ba76bbb.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/healthz/route-a2aa8709d193ee0d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/inside/page-2bd9ce9c020d02d4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/intake/page-a34096245e63b9f2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/layout-22170f4f00a15496.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/live/page-4cc66d22ca4ec502.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/live-run/page-83b14c729fcea837.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/loops/page-6e2781c523dad761.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/market/page-26dd415c8f13f341.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-ccdb83ed40c8d724.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/morning/page-7ad3de8fa06fdea9.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/not-found-015c02c4fec4023e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/observatory/page-6b0ae5b5c42f6d2f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-786111f30b6f0969.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/release/page-48fb31810693c357.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-4e17cce5e2ed0fee.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/outputs/page-cb154acadb025414.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/page-16258e956ea93fc2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/reflection/page-c2dd2b19c93f90ab.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/scheduler/page-85f35dd1dd96ae87.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/sessions/page-d3c007c8a0ddd7ee.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-7837ce2aacb97b04.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/settings/page-7350ee93f4fe1033.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/done/page-00723458575f2b19.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/layout-a2aa8709d193ee0d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/page-745d9b6c015076f8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/share/page-736d33c7414a8a1a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/showroom/page-119be9a0444d2482.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/tasks/page-fa806c018833e332.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/term/page-c782041b5f5199ba.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/today/page-d431fbdea6ad93dd.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/trace/page-0c056abff82b9891.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/vault/page-242d668e4fbf72c4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-847c3de6ca8a4416.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workflows/page-81dd0d8ae923ed72.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workspace/page-74e69ba2c8e970d4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/worktrees/page-70038f41ae7cf931.js +1 -0
- package/apps/pwa/out/_next/static/chunks/b4e12462-5fab4a813a63dadd.js +1 -0
- package/apps/pwa/out/_next/static/chunks/cd39fa05.fac4545f42a3ef70.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{f6b7c9ba.64a895b8b2fedbdc.js → ce383d63.d2ede338788ed18e.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{framework-5c169757551134ed.js → framework-b2763b10dc6b3836.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/main-app-27893e93b0ec193d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/main-f280047194e1daf8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/pages/_app-e90eff2d0b70564c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/pages/_error-70f2d654b3435d34.js +1 -0
- package/apps/pwa/out/_next/static/chunks/webpack-4794f053bd5e4230.js +1 -0
- package/apps/pwa/out/_next/static/css/5619d59e87eddf66.css +1 -0
- package/apps/pwa/out/_next/static/css/d0a48dc099ed86cf.css +1 -0
- package/apps/pwa/out/_next/static/{MObU8ujkMciAKr6ljAV05 → rfkMm4movqkqMebBrCXiR}/_buildManifest.js +1 -1
- package/apps/pwa/out/approvals/index.html +1 -1
- package/apps/pwa/out/approvals/index.txt +23 -23
- package/apps/pwa/out/autopilot/index.html +1 -1
- package/apps/pwa/out/autopilot/index.txt +23 -23
- package/apps/pwa/out/board/index.html +1 -1
- package/apps/pwa/out/board/index.txt +23 -23
- package/apps/pwa/out/botlab/index.html +1 -1
- package/apps/pwa/out/botlab/index.txt +22 -22
- package/apps/pwa/out/bots/index.html +1 -1
- package/apps/pwa/out/bots/index.txt +22 -22
- package/apps/pwa/out/ceo/index.html +1 -1
- package/apps/pwa/out/ceo/index.txt +23 -23
- package/apps/pwa/out/chat/index.html +1 -1
- package/apps/pwa/out/chat/index.txt +22 -22
- package/apps/pwa/out/consult/index.html +1 -1
- package/apps/pwa/out/consult/index.txt +23 -23
- package/apps/pwa/out/control/index.html +1 -1
- package/apps/pwa/out/control/index.txt +23 -23
- package/apps/pwa/out/decisions/index.html +1 -1
- package/apps/pwa/out/decisions/index.txt +22 -22
- package/apps/pwa/out/design-check/index.html +1 -1
- package/apps/pwa/out/design-check/index.txt +23 -23
- package/apps/pwa/out/editor/index.html +1 -1
- package/apps/pwa/out/editor/index.txt +24 -23
- package/apps/pwa/out/exec/index.html +1 -1
- package/apps/pwa/out/exec/index.txt +23 -23
- package/apps/pwa/out/field/index.html +1 -1
- package/apps/pwa/out/field/index.txt +23 -23
- package/apps/pwa/out/healthz +1 -1
- package/apps/pwa/out/index.html +1 -1
- package/apps/pwa/out/index.txt +22 -22
- package/apps/pwa/out/inside/index.html +1 -1
- package/apps/pwa/out/inside/index.txt +22 -22
- package/apps/pwa/out/intake/index.html +1 -1
- package/apps/pwa/out/intake/index.txt +23 -23
- package/apps/pwa/out/live/index.html +1 -1
- package/apps/pwa/out/live/index.txt +23 -23
- package/apps/pwa/out/live-run/index.html +1 -1
- package/apps/pwa/out/live-run/index.txt +24 -23
- package/apps/pwa/out/loops/index.html +1 -1
- package/apps/pwa/out/loops/index.txt +22 -22
- package/apps/pwa/out/market/index.html +1 -1
- package/apps/pwa/out/market/index.txt +22 -22
- package/apps/pwa/out/missions/placeholder/index.html +1 -1
- package/apps/pwa/out/missions/placeholder/index.txt +22 -22
- package/apps/pwa/out/morning/index.html +1 -1
- package/apps/pwa/out/morning/index.txt +23 -23
- package/apps/pwa/out/observatory/index.html +1 -1
- package/apps/pwa/out/observatory/index.txt +23 -23
- package/apps/pwa/out/ops/checklist/index.html +1 -1
- package/apps/pwa/out/ops/checklist/index.txt +22 -22
- package/apps/pwa/out/ops/release/index.html +1 -1
- package/apps/pwa/out/ops/release/index.txt +22 -22
- package/apps/pwa/out/ops/seats/index.html +1 -1
- package/apps/pwa/out/ops/seats/index.txt +22 -22
- package/apps/pwa/out/outputs/index.html +1 -1
- package/apps/pwa/out/outputs/index.txt +22 -22
- package/apps/pwa/out/reflection/index.html +1 -1
- package/apps/pwa/out/reflection/index.txt +23 -23
- package/apps/pwa/out/scheduler/index.html +1 -1
- package/apps/pwa/out/scheduler/index.txt +23 -23
- package/apps/pwa/out/sessions/index.html +1 -1
- package/apps/pwa/out/sessions/index.txt +22 -22
- package/apps/pwa/out/settings/devices/index.html +1 -1
- package/apps/pwa/out/settings/devices/index.txt +23 -23
- package/apps/pwa/out/settings/index.html +1 -1
- package/apps/pwa/out/settings/index.txt +23 -23
- package/apps/pwa/out/setup/done/index.html +1 -1
- package/apps/pwa/out/setup/done/index.txt +23 -23
- package/apps/pwa/out/setup/index.html +1 -1
- package/apps/pwa/out/setup/index.txt +23 -23
- package/apps/pwa/out/share/index.html +1 -1
- package/apps/pwa/out/share/index.txt +23 -23
- package/apps/pwa/out/showroom/index.html +1 -1
- package/apps/pwa/out/showroom/index.txt +22 -22
- package/apps/pwa/out/tasks/index.html +1 -1
- package/apps/pwa/out/tasks/index.txt +23 -23
- package/apps/pwa/out/term/index.html +1 -1
- package/apps/pwa/out/term/index.txt +23 -23
- package/apps/pwa/out/today/index.html +1 -1
- package/apps/pwa/out/today/index.txt +23 -23
- package/apps/pwa/out/trace/index.html +1 -1
- package/apps/pwa/out/trace/index.txt +23 -23
- package/apps/pwa/out/vault/index.html +1 -1
- package/apps/pwa/out/vault/index.txt +23 -23
- package/apps/pwa/out/workflows/chat-ui/index.html +1 -1
- package/apps/pwa/out/workflows/chat-ui/index.txt +23 -23
- package/apps/pwa/out/workflows/index.html +1 -1
- package/apps/pwa/out/workflows/index.txt +23 -23
- package/apps/pwa/out/workspace/index.html +1 -1
- package/apps/pwa/out/workspace/index.txt +23 -23
- package/apps/pwa/out/worktrees/index.html +1 -1
- package/apps/pwa/out/worktrees/index.txt +23 -23
- package/catalog/models/anthropic/claude-haiku-5-5.yaml +32 -0
- package/catalog/models/anthropic/claude-opus-5-5.yaml +5 -0
- package/catalog/models/anthropic/claude-sonnet-5-5.yaml +31 -0
- package/catalog/models/anthropic/claude-sonnet-5.yaml +8 -2
- package/catalog/models/openai/gpt-6-astra.yaml +6 -0
- package/catalog/models/openai/gpt-6-luna.yaml +6 -0
- package/catalog/models/openai/gpt-6-sol.yaml +6 -0
- package/graphs/catalog/catalog.yaml +1 -1
- package/graphs/drafts/recipes.yaml +2 -2
- package/graphs/log-horizon/log-horizon-watch.yaml +25 -0
- package/graphs/log-horizon/recipes.yaml +3 -0
- package/graphs/release/recipes.yaml +1 -1
- package/graphs/release/release-loop.yaml +6 -2
- package/graphs/release-rehearsal/recipes.yaml +12 -0
- package/graphs/release-rehearsal/release-rehearsal.yaml +17 -0
- package/graphs/test-diet/recipes.yaml +3 -0
- package/graphs/test-diet/test-diet.yaml +3 -1
- package/package.json +4 -1
- package/scripts/bench-report.ts +82 -3
- package/scripts/ci-typecheck-changed.ts +10 -1
- package/scripts/f-session-monitor.ts +69 -0
- package/scripts/hq/hq-fence-wrapper.sh +148 -0
- package/scripts/hq/standby-snapshot.ts +7 -3
- package/scripts/knowledge-compress.ts +11 -0
- package/scripts/lib/typecheck-ratchet.ts +51 -0
- package/scripts/nightly-docops.ts +90 -3
- package/scripts/openai-relay-server.ts +5 -1
- package/scripts/release-loop/docs-node.ts +258 -43
- package/scripts/release-loop/gate-method.ts +59 -0
- package/scripts/release-loop/gate-node.ts +73 -7
- package/scripts/release-loop/gate-wall.ts +208 -0
- package/scripts/release-loop/known-issues-node.ts +53 -8
- package/scripts/release-loop/publish-at.ts +14 -0
- package/scripts/release-loop/publish-node.ts +17 -2
- package/scripts/release-loop/resume-release.ts +34 -4
- package/scripts/release-loop/resume.ts +53 -0
- package/scripts/release-loop/shard-plan.ts +3 -11
- package/scripts/release-loop/tui-node-checks.ts +22 -0
- package/scripts/release-loop/unattended-release.ts +8 -1
- package/scripts/research-coo-admin-dates.ts +39 -0
- package/scripts/rhythm/daily.ts +51 -2
- package/scripts/rhythm/weekly.ts +3 -2
- package/scripts/skills/public-check.ts +7 -2
- package/scripts/smart-merge/resync-shadow.ts +5 -3
- package/scripts/test-diet/lib.ts +81 -1
- package/scripts/test-diet/node.ts +48 -2
- package/scripts/tsc-main-safety-net.ts +189 -0
- package/scripts/usage-rollup.ts +8 -4
- package/scripts/verify-coo-admin-evidence.ts +83 -0
- package/src/acp/client.ts +4 -2
- package/src/acp/codex-plugins.ts +48 -6
- package/src/agent/monad-agent-turn.ts +67 -5
- package/src/agent/run-context.ts +14 -0
- package/src/agent/tool-profile.ts +28 -2
- package/src/agent-env/profile.ts +25 -5
- package/src/agent-mission/acp-judge.ts +8 -2
- package/src/agent-mission/capabilities-cli.ts +16 -1
- package/src/agent-mission/driver.ts +27 -13
- package/src/agent-mission/pr-review-watch.ts +6 -2
- package/src/agent-mission/review-loop.ts +33 -5
- package/src/agent-mission/supervisor-metrics.ts +17 -2
- package/src/agent-substrate/acp-reviewer.ts +25 -9
- package/src/agent-substrate/pr-reviewer.ts +175 -32
- package/src/agent-substrate/review-intent.ts +106 -5
- package/src/agent-substrate/self-review-cli.ts +111 -16
- package/src/agent-substrate/shard-boundary-intent.ts +92 -26
- package/src/ask-user-question/pending-questions.ts +8 -2
- package/src/autopilot/build/llm-conflict-merge.ts +238 -20
- package/src/autopilot/codebase-grounding.ts +44 -0
- package/src/autopilot/llm-control-brain.ts +13 -1
- package/src/autopilot/mission-codebase-gate.ts +8 -77
- package/src/autopilot/pr-manager.ts +30 -11
- package/src/away/release-watch.ts +47 -8
- package/src/boot/acp-server.ts +4 -7
- package/src/boot/acp-socket-path.ts +7 -0
- package/src/briefing/brief-items.ts +123 -22
- package/src/chat/index.ts +13 -3
- package/src/cli/agent-cli.ts +20 -0
- package/src/cli/brief-cli.ts +46 -22
- package/src/cli/cli-user-error.ts +9 -2
- package/src/cli/config-classify.ts +83 -0
- package/src/cli/control-cli.ts +14 -0
- package/src/cli/decisions-cli.ts +26 -16
- package/src/cli/log-event-names.ts +3 -0
- package/src/cli/logs-cli.ts +1 -0
- package/src/cli/logs-model-input.ts +1 -1
- package/src/cli/mcp-login.ts +111 -37
- package/src/cli/plugin-cli.ts +21 -1
- package/src/cli/pod-cli.ts +26 -0
- package/src/cli/pr-cli.ts +94 -9
- package/src/cli/pr-land-overlap-evidence.ts +131 -0
- package/src/cli/release-cli.ts +74 -15
- package/src/cli/self-update.ts +173 -10
- package/src/cli/skills-cli.ts +12 -3
- package/src/cli/tasks-cli.ts +241 -28
- package/src/connectors/types.ts +6 -6
- package/src/context-bus/context-first.ts +51 -2
- package/src/context-bus/context-now-surfaces.ts +29 -0
- package/src/context-bus/coord-events.ts +32 -4
- package/src/context-bus/long-term-memory.ts +26 -7
- package/src/context-bus/nightly-condense.ts +170 -21
- package/src/control/control-status.ts +87 -0
- package/src/control-plane/light-member.ts +5 -3
- package/src/control-plane/member.ts +172 -7
- package/src/core-turn/run-goal-loop.ts +108 -3
- package/src/dashboard/chat-fold.ts +20 -0
- package/src/dashboard/first-screen-band.ts +151 -1
- package/src/dashboard/index.ts +27 -5
- package/src/dashboard/slash-runtime/dashboard-handlers.ts +14 -3
- package/src/dashboard/stale-install-check.ts +13 -2
- package/src/dashboard/turn-stream-formatter.ts +25 -0
- package/src/debug/log-diet.ts +159 -0
- package/src/debug/log.ts +52 -17
- package/src/decisions/decision-cards.ts +20 -1
- package/src/decisions/decision-ledger.ts +11 -8
- package/src/decisions/web-push-decision-cards.ts +19 -3
- package/src/discord-self-message.ts +2 -2
- package/src/display/coordinator.ts +25 -2
- package/src/domains/coo-admin-dates.evidence.json +876 -0
- package/src/domains/coo-admin-tool.ts +75 -14
- package/src/domains/cron-match.ts +1 -0
- package/src/domains/ops-status.ts +53 -0
- package/src/domains/outbound-alert.ts +41 -7
- package/src/domains/release-tool.ts +119 -10
- package/src/domains/schedule-registry.ts +10 -7
- package/src/domains/schedule-runner.ts +1 -0
- package/src/elanous-config-dir.ts +2 -2
- package/src/elanous-daemon.ts +3 -3
- package/src/exec-requests/planner.ts +6 -0
- package/src/execution-loop/launch-gate.ts +1 -1
- package/src/expression/i18n/messages.en.ts +5 -0
- package/src/expression/i18n/messages.ja.ts +5 -0
- package/src/expression/i18n/messages.ko.ts +5 -0
- package/src/expression/i18n/messages.zh.ts +5 -0
- package/src/expression/i18n/types.ts +8 -0
- package/src/github/pr-labels.ts +1 -0
- package/src/graph-kinds/registry.ts +6 -6
- package/src/graph-runner/graph-cli.ts +34 -2
- package/src/graph-runner/graph-run-api.ts +7 -0
- package/src/graph-runner/graph-tick.ts +73 -12
- package/src/graph-runner/runner.ts +94 -13
- package/src/graph-unify/wf-to-graph.ts +79 -0
- package/src/graph-wizard/generate.ts +34 -2
- package/src/graph-wizard/steps.ts +13 -0
- package/src/harness/dispatch-backpressure.ts +259 -0
- package/src/harness/harness-cli-command.ts +227 -50
- package/src/harness/harness-queue.ts +58 -14
- package/src/harness/harness-seams.ts +2 -20
- package/src/harness/harness-substrate-default.ts +72 -1
- package/src/harness/launch-advice.ts +23 -0
- package/src/harness/nested-elanous-policy.ts +4 -2
- package/src/hq/fence-wrapper.ts +7 -0
- package/src/hq/hq.ts +33 -2
- package/src/hq/lease.ts +13 -0
- package/src/hq/seats.ts +114 -18
- package/src/index.ts +199 -71
- package/src/intake-plane/collect-github.ts +19 -1
- package/src/intake-plane/digest.ts +45 -20
- package/src/intake-plane/lens.ts +36 -8
- package/src/intelligence-map/model-alias.ts +6 -0
- package/src/intelligence-map/model-catalog.ts +41 -0
- package/src/knowledge/conclusion-compress.ts +93 -0
- package/src/knowledge/kgs/pack.ts +5 -2
- package/src/knowledge/kgs/sqlite-store.ts +15 -0
- package/src/knowledge/know-find.ts +9 -2
- package/src/knowledge/query.ts +20 -0
- package/src/knowledge/tools/knowledge-query.ts +20 -2
- package/src/knowledge/write.ts +234 -2
- package/src/llm/bedrock-provider.ts +175 -0
- package/src/llm/bedrock.ts +345 -0
- package/src/llm/provider-credentials.ts +3 -1
- package/src/llm.ts +332 -51
- package/src/loops/budget.ts +150 -0
- package/src/loops/neighbor-runtime.ts +88 -0
- package/src/loops/orchestrator/author-depth.ts +29 -11
- package/src/loops/orchestrator/overlap.ts +7 -1
- package/src/loops/orchestrator/resync-shadow.ts +1 -1
- package/src/loops/orchestrator/seat-share.ts +6 -49
- package/src/loops/orchestrator/tick.ts +35 -2
- package/src/loops/orchestrator/traffic.ts +6 -80
- package/src/loops/registry.ts +5 -0
- package/src/market/publish.ts +17 -1
- package/src/market/signed-index.ts +42 -0
- package/src/maturity/feature-maturity.ts +2 -1
- package/src/mcp/mcp-oauth.ts +136 -17
- package/src/model-tier/llm-tier-map.ts +48 -4
- package/src/models/prompts.ts +22 -1
- package/src/mss/logging/horizon-watch.ts +168 -0
- package/src/mss/logging/log-store.ts +204 -15
- package/src/mss/logging/redaction.ts +17 -0
- package/src/native-tool-catalog.ts +1 -1
- package/src/nexus/api/consult-requests.ts +7 -10
- package/src/nexus/api/discord-trigger-bot.ts +6 -3
- package/src/nexus/api/draft-metrics.ts +22 -8
- package/src/nexus/api/error-reports.ts +30 -8
- package/src/nexus/api/graph-peer-edit.ts +77 -0
- package/src/nexus/api/graph-wizard-api.ts +9 -1
- package/src/nexus/api/graphs-api.ts +145 -7
- package/src/nexus/api/http-server.ts +101 -8
- package/src/nexus/api/loop-resources.ts +42 -0
- package/src/nexus/api/outbound-report.ts +8 -3
- package/src/nexus/api/plugins-market.ts +24 -0
- package/src/nexus/api/telegram-trigger-bot.ts +6 -3
- package/src/nexus/index.ts +13 -2
- package/src/nexus/outbound/format.ts +2 -0
- package/src/nexus/outbound/router.ts +198 -13
- package/src/oauth/claude-pty-maturity.ts +24 -0
- package/src/oauth/codex-account-rotation.ts +16 -18
- package/src/oauth/codex-account-store.ts +134 -5
- package/src/oauth/fallback-chain.ts +50 -15
- package/src/onboarding.ts +2 -1
- package/src/plugins/adapters/claude-package.ts +4 -12
- package/src/plugins/core/capability-policy.ts +141 -0
- package/src/plugins/core/host.ts +21 -8
- package/src/plugins/core/manifest.ts +19 -2
- package/src/plugins/core/trust-store.ts +15 -0
- package/src/plugins/core/types.ts +12 -0
- package/src/plugins/install/market-fetch.ts +68 -16
- package/src/plugins/install/plugin-install.ts +187 -16
- package/src/plugins/maker/market-bundle.ts +9 -0
- package/src/plugins/maker/plugin-maker.ts +32 -21
- package/src/plugins/maker/wizard-generate.ts +87 -9
- package/src/policy/llm-policy.ts +24 -6
- package/src/process/pid-liveness.ts +1 -1
- package/src/prompt-cache/openai.ts +10 -6
- package/src/prompt-cache/openrouter.ts +94 -0
- package/src/prompt-enhance/enhance.ts +46 -5
- package/src/prompt-library/family-prompt-coverage.ts +1 -0
- package/src/prompt-library/universal-preamble.ts +2 -2
- package/src/registry/discovery/openrouter-live-resolve.ts +122 -0
- package/src/registry/loader.ts +6 -1
- package/src/release-loop/checklist-board.ts +27 -0
- package/src/release-loop/checklist.ts +62 -9
- package/src/release-loop/feature-store.ts +3 -0
- package/src/release-loop/gate-shards.ts +48 -4
- package/src/release-loop/landed-to-green.ts +81 -0
- package/src/release-loop/light-rc.ts +11 -1
- package/src/release-loop/merged-pr-checklist.ts +10 -0
- package/src/release-loop/placement.ts +91 -22
- package/src/release-loop/rehearsal.ts +317 -0
- package/src/release-loop/release-schedule.ts +13 -1
- package/src/release-loop/rubric-types.ts +1 -0
- package/src/release-loop/rubric.ts +2 -2
- package/src/retro/daily.ts +23 -9
- package/src/seat-address/seat-address.ts +1 -0
- package/src/seat-loop/seat-loop.ts +208 -21
- package/src/seat-loop/seat-report.ts +29 -1
- package/src/seat-loop/traffic-signal.ts +44 -0
- package/src/self-dev/ask-launch-flow.ts +2 -2
- package/src/self-dev/dev-cli.ts +157 -11
- package/src/self-dev/dev-pipeline.ts +18 -1
- package/src/self-dev/draft-residue.ts +463 -0
- package/src/self-dev/draft-sweep.ts +195 -17
- package/src/self-dev/draft-triage-rules.ts +27 -1
- package/src/self-dev/launch-preflight-text.ts +549 -0
- package/src/self-dev/launch-preflight.ts +10 -545
- package/src/self-dev/orchestrate-cli.ts +57 -2
- package/src/self-dev/orchestrate-summary-line.ts +13 -0
- package/src/self-dev/orchestrate.ts +9 -133
- package/src/self-dev/review-provider-fallback.ts +179 -0
- package/src/self-dev/run-store.ts +1 -3
- package/src/self-dev/run-supervisor.ts +8 -23
- package/src/self-dev/run-types.ts +178 -0
- package/src/self-dev/shard-aggregate.ts +61 -13
- package/src/self-dev/shard-plan.ts +5 -1
- package/src/self-dev/shard-run.ts +23 -5
- package/src/self-dev/supervisor-verdict-edges.ts +2 -4
- package/src/self-implement/blocked-draft-policy.ts +3 -19
- package/src/self-implement/draft-on-stop-mode.ts +18 -0
- package/src/self-implement/follow-up-goals.ts +114 -38
- package/src/self-implement/gate-baseline-reap.ts +157 -0
- package/src/self-implement/gate-baseline.ts +78 -16
- package/src/self-implement/gate-cli.ts +12 -2
- package/src/self-implement/gate-remote.ts +17 -6
- package/src/self-implement/goal-author.ts +24 -4
- package/src/self-implement/goal-digest.ts +19 -0
- package/src/self-implement/graph-overlay-condition.ts +4 -0
- package/src/self-implement/harness-policy-gates.ts +7 -5
- package/src/self-implement/headless-elanous-driver.ts +11 -9
- package/src/self-implement/host-regate.ts +148 -43
- package/src/self-implement/l8-merge-queue.ts +147 -13
- package/src/self-implement/merge-train.ts +131 -0
- package/src/self-implement/off-diff-evidence.ts +9 -0
- package/src/self-implement/orchestrator.ts +201 -43
- package/src/self-implement/review-finding-recurrence.ts +28 -0
- package/src/self-implement/rework-policy.ts +2 -1
- package/src/self-implement/round-summary-card.ts +63 -0
- package/src/self-implement/run-ledger.ts +4 -3
- package/src/self-implement/run-step-projection.ts +147 -0
- package/src/self-implement/run-stop.ts +1 -1
- package/src/self-implement/seams.ts +41 -6
- package/src/self-implement/self-implement-cli.ts +6 -0
- package/src/self-implement/train-gate-remote.ts +158 -0
- package/src/session-runtime/index.ts +10 -1
- package/src/session-runtime/retry-api.ts +11 -1
- package/src/shell-env-bootstrap.ts +19 -4
- package/src/skills/gift-install.ts +119 -0
- package/src/skills/runner.ts +59 -2
- package/src/skills/skill-feedback.ts +31 -1
- package/src/skills/skill-tier.ts +1 -0
- package/src/smart-wizard/capability-index.ts +231 -0
- package/src/smart-wizard/rung.ts +74 -0
- package/src/steward/launch.ts +20 -9
- package/src/steward/triage.ts +29 -10
- package/src/storage/file-lock.ts +40 -4
- package/src/task-agent/actions.ts +4 -0
- package/src/task-agent/card-evidence.ts +59 -13
- package/src/task-agent/completion-evidence.ts +31 -3
- package/src/task-agent/cover.ts +61 -0
- package/src/task-agent/judge.ts +4 -3
- package/src/task-agent/land-worktree.ts +201 -0
- package/src/task-agent/live-move-history.ts +133 -0
- package/src/task-agent/live-moves.ts +222 -12
- package/src/task-agent/parent-host.ts +117 -8
- package/src/task-agent/rejudge-on-head.ts +297 -0
- package/src/task-agent/review-result-capture.ts +218 -0
- package/src/task-agent/shadow.ts +118 -7
- package/src/task-agent/task-hand.ts +138 -11
- package/src/task-orchestrator/surfaces/pod-child-providers.ts +29 -0
- package/src/task-orchestrator/surfaces/pod-command-job.ts +6 -3
- package/src/task-orchestrator/surfaces/pod-failure-reason.ts +16 -2
- package/src/task-orchestrator/surfaces/pod-image-source.ts +212 -0
- package/src/task-orchestrator/surfaces/pod-lease.ts +93 -12
- package/src/task-orchestrator/surfaces/pod-ledger-collect.ts +25 -2
- package/src/task-orchestrator/surfaces/pod-pool.ts +203 -28
- package/src/task-orchestrator/surfaces/self-implement-pod.ts +259 -36
- package/src/task-orchestrator/surfaces/self-implement.ts +11 -0
- package/src/telegram-commands.ts +8 -0
- package/src/telegram-project-command.ts +6 -0
- package/src/telegram-service.ts +5 -1
- package/src/telegram.ts +17 -4
- package/src/time/format.ts +13 -4
- package/src/tool-runtime/goal-author-runtime.ts +1 -0
- package/src/tool-runtime/self-cognition-catalog.ts +23 -0
- package/src/tool-runtime/self-cognition-runtimes.ts +2 -24
- package/src/typecheck-ratchet.ts +2 -1
- package/src/user-config.ts +167 -28
- package/src/ux-sim/slash-menu-frames.ts +168 -0
- package/src/version/packed-revision.json +1 -1
- package/src/web-terminal/preview-tap-registry.ts +5 -2
- package/src/workflow-runtime/executor.ts +24 -2
- package/src/workflow-runtime/triggers/registry.ts +27 -0
- package/src/workflow-runtime/triggers/schedule-source.ts +30 -3
- package/src/workflow-runtime/triggers/scheduler.ts +1 -0
- package/apps/pwa/out/_next/static/chunks/1109.78a7a3288c0259d9.js +0 -148
- package/apps/pwa/out/_next/static/chunks/115.1c6690b8604f81c4.js +0 -32
- package/apps/pwa/out/_next/static/chunks/1262.76a3f08e67c5f816.js +0 -309
- package/apps/pwa/out/_next/static/chunks/1307-c97eba9fb72a9a5e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1358d292.5c87f12cad6eaa91.js +0 -122
- package/apps/pwa/out/_next/static/chunks/1438.27a1a7b8f2308004.js +0 -149
- package/apps/pwa/out/_next/static/chunks/1442.02d85cd88f4c1eac.js +0 -79
- package/apps/pwa/out/_next/static/chunks/1501-1aad662d82ba43f7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1584.9e2dd53da6e6d4b1.js +0 -24
- package/apps/pwa/out/_next/static/chunks/1586.b989b0614afb77e6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1609.2ad355062870151f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1612-f6df0fc0eed7157b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1826-5d279da64bbbc2de.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1923.37f1d5fe7ebe3860.js +0 -27
- package/apps/pwa/out/_next/static/chunks/195-fb1d7690bf30bab4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1986-33e13d648a9df765.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1993.3fd074a2a246234e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/211-9c9090c59e2c5907.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2140.d2daf9ee96e295d1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2196-4700653d12a44b40.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2212.0359851457473efc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/224.583e562365a52f74.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2328.0f37465646bafa7d.js +0 -36
- package/apps/pwa/out/_next/static/chunks/2372.bf71372184991937.js +0 -286
- package/apps/pwa/out/_next/static/chunks/2489-ff55a35b202c0f94.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2537-6c289376caa88ca1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2549-a8515c86f9e8cb96.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2655.72cc6a97276c5acc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2699-325cc923ba7b8631.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2743-ef6e8c3ced74cce5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2840-5458ad50c49cac6a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2856.f75d5baef7f49b74.js +0 -1
- package/apps/pwa/out/_next/static/chunks/311.e685738f92e6e2ec.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3194-807b212fb8eae065.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3324-d1d2979821dfa845.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3344.0de4b0ec5a454b7a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/335.a13f339e97893437.js +0 -94
- package/apps/pwa/out/_next/static/chunks/3394.646348f34b2500be.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3443.6276909b53d72d53.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3495.abd4254d808bf2dc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3558-bbb5ab553a0471d3.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3721.ba5b82db0d9a5572.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3857-995ea9f5ef33d71e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3916-3d02dd1fc257dd3c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3919.9ff7dc25afefee33.js +0 -74
- package/apps/pwa/out/_next/static/chunks/3998.bd9a69d9b50e9bd2.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4003.ab6db1dc266576c9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4144-fad095b48a1862ee.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4216.e8ac94b9fe6b96ab.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4327.c44dc2b55cb43ee5.js +0 -34
- package/apps/pwa/out/_next/static/chunks/4401.94257d497b6d26bc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4559.17ca2cdbaa8d414f.js +0 -115
- package/apps/pwa/out/_next/static/chunks/4565-3d7e3fdeb43686a8.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4706.97e734bd4c9816ca.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4795-f372490b178583fc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4982.6e44352f751b9a1b.js +0 -77
- package/apps/pwa/out/_next/static/chunks/5342.49c5c5a530e62b50.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5360-08a80abdf3a4da99.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5431.66c58ab1327ee0b7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5717.bcfcb96e701b82e0.js +0 -90
- package/apps/pwa/out/_next/static/chunks/5755-30d102586789bf7f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5957.3f1a4012388dd962.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5977-59fedea50d13c762.js +0 -1
- package/apps/pwa/out/_next/static/chunks/602.9bf02ac8e9502598.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6020.3a1b347e2d2dfacc.js +0 -8
- package/apps/pwa/out/_next/static/chunks/6375.fce1d174ba6d0324.js +0 -64
- package/apps/pwa/out/_next/static/chunks/6546.92a828aef441271f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/658.957fdb0a8c6c6c8e.js +0 -287
- package/apps/pwa/out/_next/static/chunks/6706.323590aabb8b1293.js +0 -226
- package/apps/pwa/out/_next/static/chunks/6747.b67947f293a4c02d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6868.000b24a3045c5574.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6877-74399f69c7da1433.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6946.bba74e9c96050f30.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7033.a558f1b2f6912a53.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7065.46029c26c53eac50.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7087.6fae577d09249bc1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/722.de8d9801e0f6d414.js +0 -41
- package/apps/pwa/out/_next/static/chunks/726.83532d69452ee24b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7290-f09c928a06c52e2d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7497.57981e9d7a75a52a.js +0 -24
- package/apps/pwa/out/_next/static/chunks/7672.4af122ad892117c7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/771.6ab889a233e7dae7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7797-df5aa0381fdc078f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8060-cc008cc6fedfa818.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8085-d065d0393c1760f5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8096.f7da0776cfde6300.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8401-35e94e9091f5eb8d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8682-7061dd4fa7bd62ed.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8695-846034ce44852c70.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8769.815ca69879f608b4.js +0 -104
- package/apps/pwa/out/_next/static/chunks/8857-f1762140ef9a96b1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8f835b4f.048eeb02299e3e12.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9068.5f2764fccf86c1b2.js +0 -93
- package/apps/pwa/out/_next/static/chunks/9103-60fbef33e66f0a46.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9247-7581825d511a64c0.js +0 -1
- package/apps/pwa/out/_next/static/chunks/935.4ddaa99fc1d1126c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9451.ebfb0dcc9c02250f.js +0 -23
- package/apps/pwa/out/_next/static/chunks/9497-b0e758d1cd4ae8d7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9559.e648369b1d57cf9a.js +0 -62
- package/apps/pwa/out/_next/static/chunks/app/_not-found/page-c1a96669158471ec.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/approvals/page-937c92292a4ab4f0.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/autopilot/page-d781be3e3a9cfd74.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/board/page-b0a80997903852d8.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/botlab/page-2b1263165630d9c8.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/bots/page-ea998f7f5d156bea.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ceo/page-33c328b64ca508f8.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/chat/page-e2d6bed48ac20120.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/control/page-544dd4bd4847eeb7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/decisions/page-3ee191319bf97d87.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/design-check/page-e4bcb2c503dab04b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/editor/page-300897dcbbd5ed76.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/exec/page-a449f1ed472b81c2.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/field/page-9045094d6d3b5cd0.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/healthz/route-c1a96669158471ec.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/inside/page-c06673596849ef45.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/intake/page-103fa3191c1b2e08.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/layout-9f81233f29dcd409.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/live/page-be8b4615c919e36c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/live-run/page-c685b104e0dfa609.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/loops/page-8d693331cfbb6add.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/market/page-cef4f30a4c22fae1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-66ea1b54fc83fa15.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/morning/page-7a12f61be4a579d1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/not-found-c85b0589591a99c9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/observatory/page-725a4da02dd129eb.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-8cc707bd09a497d9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/release/page-90b55be1f15ce0e8.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-cb16606e08be65db.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/outputs/page-16dc64b74ed6a40a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/page-21bec4afeb2f0917.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/reflection/page-dc39ee7a36d26385.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/scheduler/page-84ae759f76053672.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/sessions/page-3db58ddb61fe2be9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-c5315e30f3528dc4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/settings/page-2fe368efb6de3b6a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/done/page-8d04132dd0ac5e10.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/layout-c1a96669158471ec.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/page-f23484de467c9ea3.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/share/page-c69762987b751174.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/showroom/page-5456692bda39aafb.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/tasks/page-d75f7cd65845ce98.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/term/page-5603f5e568b25ce3.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/today/page-d2cc0f4e89f42028.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/trace/page-a6eb73b8a4840f1c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/vault/page-c0a3f4d10edb83fa.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-6c0b88068c143f15.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workflows/page-7f8d7fcdf058a845.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workspace/page-22163556cd38bc88.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/worktrees/page-141436fd26dd56fc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/f6231284-45726550aba08fca.js +0 -1
- package/apps/pwa/out/_next/static/chunks/main-59fe95fed40c7a01.js +0 -1
- package/apps/pwa/out/_next/static/chunks/main-app-4ca74dbbee7057c6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/pages/_app-13a0a886df4d97a1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/pages/_error-6af8591cd3a3f038.js +0 -1
- package/apps/pwa/out/_next/static/chunks/webpack-f2b4016b9b981bc8.js +0 -1
- package/apps/pwa/out/_next/static/css/e81df11490b4413b.css +0 -1
- /package/apps/pwa/out/_next/static/{MObU8ujkMciAKr6ljAV05 → rfkMm4movqkqMebBrCXiR}/_ssgManifest.js +0 -0
|
@@ -0,0 +1,189 @@
|
|
|
1
|
+
import { spawnSync } from 'node:child_process';
|
|
2
|
+
import { appendFileSync, existsSync, mkdirSync, readFileSync } from 'node:fs';
|
|
3
|
+
import { dirname, join, resolve } from 'node:path';
|
|
4
|
+
import { debug } from '../src/debug/log.js';
|
|
5
|
+
import { effectiveInstanceRoot } from '../src/instance/resolve.js';
|
|
6
|
+
import { GATE_REMOTE_DEFAULTS, isValidGateHost, resolveGateRemoteSettings, runOnRemote, type ExecResult, type RemoteRunOptions, type RemoteRunOutcome } from '../src/self-implement/gate-remote.js';
|
|
7
|
+
import { getUserConfig } from '../src/user-config.js';
|
|
8
|
+
import { parseTypecheckErrors, tscEnv } from '../src/typecheck-ratchet.js';
|
|
9
|
+
import { compareDiagnostics, normalizeDiagnostics, type NormalizedDiagnostic } from './tsc-baseline-comparison.js';
|
|
10
|
+
|
|
11
|
+
const TSC_ARGV = ['bunx', 'tsc', '--noEmit', '-p', 'tsconfig.gate.json', '--incremental', 'false'];
|
|
12
|
+
const COMMIT = /^[0-9a-f]{40}$/i;
|
|
13
|
+
const UNMEASURABLE = /\berror TS(?:2688|5083|6053):/;
|
|
14
|
+
|
|
15
|
+
export interface SafetyNetEntry {
|
|
16
|
+
at: string;
|
|
17
|
+
commit: string;
|
|
18
|
+
outcome: 'clean' | 'added' | 'unmeasured' | 'baseline';
|
|
19
|
+
total: number;
|
|
20
|
+
added: NormalizedDiagnostic[];
|
|
21
|
+
removed: number;
|
|
22
|
+
ms: number;
|
|
23
|
+
host: string;
|
|
24
|
+
/** Full measured snapshot: `added` alone cannot serve as the next day's baseline. */
|
|
25
|
+
diagnostics?: NormalizedDiagnostic[];
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
export interface SafetyNetDeps {
|
|
29
|
+
local?: (cmd: string, args: string[], cwd: string, options?: { env?: NodeJS.ProcessEnv }) => ExecResult;
|
|
30
|
+
remote?: (options: RemoteRunOptions) => RemoteRunOutcome;
|
|
31
|
+
compare?: typeof compareDiagnostics;
|
|
32
|
+
exists?: (path: string) => boolean;
|
|
33
|
+
instanceRoot?: () => string;
|
|
34
|
+
settings?: () => ReturnType<typeof resolveGateRemoteSettings>;
|
|
35
|
+
now?: () => number;
|
|
36
|
+
observed?: (entry: { commit: string; outcome: SafetyNetEntry['outcome']; total: number; added: number; removed: number; ms: number; host: string }) => void;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
const realLocal: NonNullable<SafetyNetDeps['local']> = (cmd, args, cwd, options) => {
|
|
40
|
+
const result = spawnSync(cmd, args, { cwd, encoding: 'utf8', maxBuffer: 64 * 1024 * 1024, ...(options?.env ? { env: options.env } : {}) });
|
|
41
|
+
return { rc: result.status, stdout: result.stdout ?? '', stderr: result.stderr ?? '', ...(result.error ? { error: String(result.error) } : {}) };
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
function flags(argv: readonly string[]): { local: boolean; host?: string; ledger?: string; json: boolean } {
|
|
45
|
+
let local = false;
|
|
46
|
+
let host: string | undefined;
|
|
47
|
+
let ledger: string | undefined;
|
|
48
|
+
let json = false;
|
|
49
|
+
for (let i = 0; i < argv.length; i++) {
|
|
50
|
+
const arg = argv[i];
|
|
51
|
+
if (arg === '--local') local = true;
|
|
52
|
+
else if (arg === '--json') json = true;
|
|
53
|
+
else if (arg === '--remote' || arg === '--ledger') {
|
|
54
|
+
const value = argv[++i];
|
|
55
|
+
if (!value || value.startsWith('--')) throw new Error(`${arg} requires a value`);
|
|
56
|
+
if (arg === '--remote') host = value;
|
|
57
|
+
else ledger = value;
|
|
58
|
+
} else throw new Error(`unknown argument: ${arg}`);
|
|
59
|
+
}
|
|
60
|
+
if (local && host) throw new Error('--local and --remote cannot be combined');
|
|
61
|
+
if (host && !isValidGateHost(host)) throw new Error(`invalid --remote host: ${host}`);
|
|
62
|
+
return { local, host, ledger, json };
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
function measuredSnapshot(path: string): NormalizedDiagnostic[] | undefined {
|
|
66
|
+
if (!existsSync(path)) return undefined;
|
|
67
|
+
const rows = readFileSync(path, 'utf8').trim().split('\n').filter(Boolean);
|
|
68
|
+
for (let i = rows.length - 1; i >= 0; i--) {
|
|
69
|
+
const entry = JSON.parse(rows[i]!) as SafetyNetEntry;
|
|
70
|
+
if (entry.outcome === 'unmeasured') continue;
|
|
71
|
+
if (!Array.isArray(entry.diagnostics) || !entry.diagnostics.every((d) => d && typeof d.file === 'string' && typeof d.code === 'string' && typeof d.message === 'string')) {
|
|
72
|
+
throw new Error('last measured ledger entry has no valid diagnostic snapshot');
|
|
73
|
+
}
|
|
74
|
+
return entry.diagnostics;
|
|
75
|
+
}
|
|
76
|
+
return undefined;
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
function diagnosticsOf(result: { rc: number | null; stdout: string; stderr: string; error?: string }, root: string): NormalizedDiagnostic[] | undefined {
|
|
80
|
+
const output = `${result.stdout}\n${result.stderr}`;
|
|
81
|
+
if (result.error || result.rc === null || (result.rc !== 0 && result.rc !== 1 && result.rc !== 2) || UNMEASURABLE.test(output)
|
|
82
|
+
|| /heap out of memory|Ineffective mark-compacts near heap limit/i.test(output)) return undefined;
|
|
83
|
+
const parsed = parseTypecheckErrors(output);
|
|
84
|
+
const errorLines = output.split(/\r?\n/).filter((line) => /\berror TS\d+:/.test(line));
|
|
85
|
+
if (parsed.length !== errorLines.length || (result.rc === 0 && errorLines.length > 0) || (result.rc !== 0 && parsed.length === 0)) return undefined;
|
|
86
|
+
if (output.split(/\r?\n/).some((line) => line.trim() && !/^.+\(\d+,\d+\):\s+error\s+TS\d+:/.test(line) && !/^\s+/.test(line)
|
|
87
|
+
&& !/^Found \d+ errors?\.?$/.test(line))) return undefined;
|
|
88
|
+
return normalizeDiagnostics(parsed, root);
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
export async function runSafetyNet(repo: string, argv: readonly string[] = [], deps: SafetyNetDeps = {}): Promise<{ exitCode: number; entry: SafetyNetEntry; json: boolean }> {
|
|
92
|
+
const input = flags(argv);
|
|
93
|
+
const run = deps.local ?? realLocal;
|
|
94
|
+
const remote = deps.remote ?? runOnRemote;
|
|
95
|
+
const exists = deps.exists ?? existsSync;
|
|
96
|
+
const root = deps.instanceRoot?.() ?? effectiveInstanceRoot();
|
|
97
|
+
const settings = deps.settings?.() ?? (input.local ? GATE_REMOTE_DEFAULTS : resolveGateRemoteSettings(getUserConfig().gateRemote));
|
|
98
|
+
const host = input.local ? 'local' : (input.host ?? settings.host ?? GATE_REMOTE_DEFAULTS.host);
|
|
99
|
+
if (host !== 'local' && !isValidGateHost(host)) throw new Error(`invalid gateRemote host: ${host}`);
|
|
100
|
+
const ledger = resolve(input.ledger ?? join(root, 'tsc-safety-net', 'ledger.jsonl'));
|
|
101
|
+
const worktree = join(root, 'tsc-safety-net', 'worktree');
|
|
102
|
+
const started = (deps.now ?? Date.now)();
|
|
103
|
+
let commit = '';
|
|
104
|
+
let diagnostics: NormalizedDiagnostic[] | undefined;
|
|
105
|
+
let reason: string | undefined;
|
|
106
|
+
let dependencyFailed = false;
|
|
107
|
+
const git = (args: string[], cwd: string): ExecResult => {
|
|
108
|
+
const env = { ...process.env };
|
|
109
|
+
delete env.GIT_DIR; delete env.GIT_WORK_TREE; delete env.GIT_COMMON_DIR;
|
|
110
|
+
return run('git', args, cwd, { env });
|
|
111
|
+
};
|
|
112
|
+
const checked = (args: string[], cwd: string): ExecResult => {
|
|
113
|
+
const result = git(args, cwd);
|
|
114
|
+
if (result.error || result.rc !== 0) throw new Error(`git ${args.join(' ')}: ${result.error ?? result.stderr ?? `rc=${result.rc}`}`);
|
|
115
|
+
return result;
|
|
116
|
+
};
|
|
117
|
+
try {
|
|
118
|
+
checked(['fetch', 'origin', '+refs/heads/main:refs/remotes/origin/main'], repo);
|
|
119
|
+
commit = checked(['rev-parse', '--verify', 'origin/main^{commit}'], repo).stdout.trim();
|
|
120
|
+
if (!COMMIT.test(commit)) throw new Error('origin/main did not resolve to a commit');
|
|
121
|
+
if (!exists(worktree)) {
|
|
122
|
+
mkdirSync(dirname(worktree), { recursive: true });
|
|
123
|
+
checked(['worktree', 'add', '--detach', worktree, commit], repo);
|
|
124
|
+
} else {
|
|
125
|
+
const listed = checked(['worktree', 'list', '--porcelain'], repo).stdout;
|
|
126
|
+
if (!listed.split('\n').some((line) => line === `worktree ${worktree}`)) throw new Error('worktree path is not a registered git worktree');
|
|
127
|
+
}
|
|
128
|
+
const status = checked(['status', '--porcelain'], worktree).stdout;
|
|
129
|
+
if (status.trim()) checked(['reset', '--hard'], worktree);
|
|
130
|
+
// Porcelain status omits ignored files, including stale .ts files from a previous measurement.
|
|
131
|
+
checked(['clean', '-fdx', '-e', 'node_modules'], worktree);
|
|
132
|
+
checked(['checkout', '--detach', 'origin/main'], worktree);
|
|
133
|
+
if (checked(['rev-parse', 'HEAD'], worktree).stdout.trim() !== commit || checked(['status', '--porcelain'], worktree).stdout.trim()) throw new Error('worktree is not clean at origin/main');
|
|
134
|
+
if (input.local) {
|
|
135
|
+
// The retained node_modules may belong to yesterday's lockfile; frozen install reconciles it to this checkout.
|
|
136
|
+
dependencyFailed = true;
|
|
137
|
+
const install = run('bun', ['install', '--frozen-lockfile'], worktree);
|
|
138
|
+
if (install.rc !== 0 || install.error || !exists(join(worktree, 'node_modules'))) {
|
|
139
|
+
throw new Error(`local dependencies unavailable: ${install.error ?? install.stderr ?? `rc=${install.rc}`}`);
|
|
140
|
+
}
|
|
141
|
+
dependencyFailed = false;
|
|
142
|
+
const result = run(TSC_ARGV[0]!, TSC_ARGV.slice(1), worktree, { env: tscEnv() });
|
|
143
|
+
diagnostics = diagnosticsOf(result, worktree);
|
|
144
|
+
if (!diagnostics) reason = 'local tsc did not produce a complete measurement';
|
|
145
|
+
} else {
|
|
146
|
+
const result = remote({ repo: worktree, host, mirror: settings.mirror, hostCap: settings.hostCap, argv: TSC_ARGV });
|
|
147
|
+
if (result.kind === 'ran') {
|
|
148
|
+
if (result.commit !== commit) throw new Error('remote measured a different commit');
|
|
149
|
+
diagnostics = diagnosticsOf({ rc: result.rc, stdout: result.stdout.toString('utf8'), stderr: result.stderr.toString('utf8') }, worktree);
|
|
150
|
+
if (!diagnostics) reason = 'remote tsc did not produce a complete measurement';
|
|
151
|
+
} else reason = result.kind === 'busy' ? 'remote busy' : `remote infra: ${result.reason}`;
|
|
152
|
+
}
|
|
153
|
+
} catch (error) {
|
|
154
|
+
reason = error instanceof Error ? error.message : String(error);
|
|
155
|
+
}
|
|
156
|
+
let previous: NormalizedDiagnostic[] | undefined;
|
|
157
|
+
try { previous = measuredSnapshot(ledger); }
|
|
158
|
+
catch (error) { diagnostics = undefined; reason = `ledger unreadable: ${error instanceof Error ? error.message : String(error)}`; }
|
|
159
|
+
const comparison = diagnostics && previous ? (deps.compare ?? compareDiagnostics)(diagnostics, previous) : undefined;
|
|
160
|
+
if (comparison?.kind === 'unavailable') reason = `comparison unavailable: ${comparison.reason}`;
|
|
161
|
+
const outcome: SafetyNetEntry['outcome'] = !diagnostics || comparison?.kind === 'unavailable'
|
|
162
|
+
? 'unmeasured' : !previous ? 'baseline' : comparison?.kind === 'added' ? 'added' : 'clean';
|
|
163
|
+
const entry: SafetyNetEntry = {
|
|
164
|
+
at: new Date((deps.now ?? Date.now)()).toISOString(), commit, outcome, total: diagnostics?.length ?? 0,
|
|
165
|
+
added: comparison && comparison.kind !== 'unavailable' ? comparison.added : [],
|
|
166
|
+
removed: comparison && comparison.kind !== 'unavailable' ? comparison.removed.length : 0,
|
|
167
|
+
ms: (deps.now ?? Date.now)() - started, host,
|
|
168
|
+
...(outcome !== 'unmeasured' && diagnostics ? { diagnostics } : {}),
|
|
169
|
+
};
|
|
170
|
+
if (!dependencyFailed) {
|
|
171
|
+
mkdirSync(dirname(ledger), { recursive: true });
|
|
172
|
+
appendFileSync(ledger, `${JSON.stringify(entry)}\n`);
|
|
173
|
+
}
|
|
174
|
+
const observation = { commit, outcome, total: entry.total, added: entry.added.length, removed: entry.removed, ms: entry.ms, host };
|
|
175
|
+
(deps.observed ?? ((data) => debug.log('tsc.safety-net', 'run', data)))(observation);
|
|
176
|
+
if (reason) console.error(`[tsc.safety-net] ${reason}`);
|
|
177
|
+
return { exitCode: outcome === 'unmeasured' ? 2 : outcome === 'added' ? 1 : 0, entry, json: input.json };
|
|
178
|
+
}
|
|
179
|
+
|
|
180
|
+
if (import.meta.main) {
|
|
181
|
+
try {
|
|
182
|
+
const result = await runSafetyNet(process.cwd(), process.argv.slice(2));
|
|
183
|
+
console.log(result.json ? JSON.stringify(result.entry) : `[tsc.safety-net] ${result.entry.outcome} commit=${result.entry.commit} total=${result.entry.total} added=${result.entry.added.length} removed=${result.entry.removed} host=${result.entry.host}`);
|
|
184
|
+
process.exitCode = result.exitCode;
|
|
185
|
+
} catch (error) {
|
|
186
|
+
console.error(`[tsc.safety-net] unmeasured: ${error instanceof Error ? error.message : String(error)}`);
|
|
187
|
+
process.exitCode = 2;
|
|
188
|
+
}
|
|
189
|
+
}
|
package/scripts/usage-rollup.ts
CHANGED
|
@@ -2,14 +2,14 @@
|
|
|
2
2
|
// 실행 칸(Pod 등)이 사라지기 «전»에 자기 llm.usage 를 한 줄로 요약해 stdout 에 — 슈퍼바이저가 호스트로 가져간다.
|
|
3
3
|
// RFC-fleet-supervisor-substrates-benchmark-and-token-accounting §A2·F2 · 2026-09-25.
|
|
4
4
|
// bun scripts/usage-rollup.ts [--since 6h]
|
|
5
|
-
// 출력: ELANOUS_USAGE_ROLLUP {"substrate","runId","armId","truncated","rows":[{site,provider,model,calls,inputTokens,outputTokens,cacheReadInputTokens,usdKnown,unknownCostCalls}],"total":{…}}
|
|
5
|
+
// 출력: ELANOUS_USAGE_ROLLUP {"substrate","runId","armId","truncated","rows":[{site,provider,model,calls,inputTokens,outputTokens,cacheReadInputTokens,cacheCreationInputTokens,usdKnown,unknownCostCalls}],"total":{…}}
|
|
6
6
|
// ⛔ 의존성 없음(설치본 `elanous` 만 부른다) — clone 에 node_modules 가 없어도 돈다.
|
|
7
7
|
// ⛔ 비용을 모르는 호출(cost.kind≠known)은 0 으로 합치지 않고 따로 센다.
|
|
8
8
|
// ⛔ `--all --include-test` 로 «그 기계의 모든 우주»를 읽는다 — Pod(자기 스토어뿐)에서는 그것이 곧 그 칸의 사용량이지만,
|
|
9
9
|
// 호스트(맥)에서 돌리면 테스트 우주·워크트리·다른 트랙의 런까지 섞인다(📏 09-25: 운영만 16회 vs 전체 124회). 호스트 집계용이 아니다.
|
|
10
10
|
import { spawnSync } from 'node:child_process';
|
|
11
11
|
|
|
12
|
-
export interface UsageRow { site: string; provider: string; model: string; calls: number; inputTokens: number; outputTokens: number; cacheReadInputTokens: number; usdKnown: number; unknownCostCalls: number; includedCalls: number; apiEquivalentUsd: number }
|
|
12
|
+
export interface UsageRow { site: string; provider: string; model: string; calls: number; inputTokens: number; outputTokens: number; cacheReadInputTokens: number; cacheCreationInputTokens: number; cacheCreationUnmeasuredCalls: number; usdKnown: number; unknownCostCalls: number; includedCalls: number; apiEquivalentUsd: number }
|
|
13
13
|
|
|
14
14
|
export function rollup(lines: readonly string[]): { rows: UsageRow[]; truncated: boolean } {
|
|
15
15
|
const by = new Map<string, UsageRow>();
|
|
@@ -20,14 +20,18 @@ export function rollup(lines: readonly string[]): { rows: UsageRow[]; truncated:
|
|
|
20
20
|
let r: { event?: string; data?: Record<string, unknown> };
|
|
21
21
|
try { r = JSON.parse(line); } catch { continue; }
|
|
22
22
|
if (r.event !== 'llm-usage' || !r.data) continue;
|
|
23
|
-
const d = r.data as { site?: string; provider?: string; billingProvider?: string; model?: string; inputTokens?: number; outputTokens?: number; cacheReadInputTokens?: number; cost?: { kind?: string; usd?: number } };
|
|
23
|
+
const d = r.data as { site?: string; provider?: string; billingProvider?: string; model?: string; inputTokens?: number; outputTokens?: number; cacheReadInputTokens?: number; cacheCreationInputTokens?: number; cost?: { kind?: string; usd?: number } };
|
|
24
24
|
const provider = d.billingProvider ?? d.provider ?? '?'; // ⭐ 과금 주체 우선(B10)
|
|
25
25
|
const key = `${d.site ?? '?'}|${provider}|${d.model ?? '?'}`;
|
|
26
|
-
const row = by.get(key) ?? { site: d.site ?? '?', provider, model: d.model ?? '?', calls: 0, inputTokens: 0, outputTokens: 0, cacheReadInputTokens: 0, usdKnown: 0, unknownCostCalls: 0, includedCalls: 0, apiEquivalentUsd: 0 };
|
|
26
|
+
const row = by.get(key) ?? { site: d.site ?? '?', provider, model: d.model ?? '?', calls: 0, inputTokens: 0, outputTokens: 0, cacheReadInputTokens: 0, cacheCreationInputTokens: 0, cacheCreationUnmeasuredCalls: 0, usdKnown: 0, unknownCostCalls: 0, includedCalls: 0, apiEquivalentUsd: 0 };
|
|
27
27
|
row.calls++;
|
|
28
28
|
row.inputTokens += Number(d.inputTokens ?? 0);
|
|
29
29
|
row.outputTokens += Number(d.outputTokens ?? 0);
|
|
30
30
|
row.cacheReadInputTokens += Number(d.cacheReadInputTokens ?? 0);
|
|
31
|
+
// ⭐ 캐시 «쓰기»(Anthropic cache_creation_input_tokens) — 빠지면 호스트 원장이 0 으로 보고 재매김 $ 가 쓰기 비용을 잃는다.
|
|
32
|
+
row.cacheCreationInputTokens += Number(d.cacheCreationInputTokens ?? 0);
|
|
33
|
+
// 캐시 읽기는 보고했는데 쓰기 칸이 없는 호출은 쓰기량을 «모른다» — 0 으로 접지 않고 따로 센다(호스트 재매김이 이 수를 보고 멈춘다).
|
|
34
|
+
if (d.cacheReadInputTokens !== undefined && d.cacheCreationInputTokens === undefined) row.cacheCreationUnmeasuredCalls++;
|
|
31
35
|
// ⛔ «모름»을 0 으로 접지 않는다 — partial 의 «알려진 몫»은 더하고, 모르는 호출은 따로 센다(BACKLOG C5).
|
|
32
36
|
// ⭐ 구독·local(`included`)은 청구 0 이고 «모름»이 아니다 — 따로 세고 API 환산가는 별도 합(BACKLOG C6).
|
|
33
37
|
if (d.cost?.kind === 'included') { row.includedCalls++; if (typeof (d.cost as { apiEquivalentUsd?: number }).apiEquivalentUsd === 'number') row.apiEquivalentUsd += (d.cost as { apiEquivalentUsd: number }).apiEquivalentUsd; }
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import { readFile } from 'node:fs/promises';
|
|
2
|
+
import { fetchLinearProjectIssues, type LinearProjectIssue } from '../src/connectors/linear.js';
|
|
3
|
+
|
|
4
|
+
type RecordedIssue = {
|
|
5
|
+
identifier: string; title: string; url: string; createdAt: string; updatedAt: string;
|
|
6
|
+
existingDueDate: string | null; priority: number;
|
|
7
|
+
};
|
|
8
|
+
type Evidence = {
|
|
9
|
+
project: string;
|
|
10
|
+
verifiedIssues: RecordedIssue[];
|
|
11
|
+
cohort: { excludedCurrentIssues: Array<{identifier: string; url: string; dueDate: string | null; priority: number; createdAt: string}> };
|
|
12
|
+
};
|
|
13
|
+
type LiveIssue = LinearProjectIssue & { createdAt: string };
|
|
14
|
+
|
|
15
|
+
export function compareCooEvidence(record: Evidence, live: LiveIssue[], truncated: boolean): string[] {
|
|
16
|
+
const errors: string[] = [];
|
|
17
|
+
if (truncated) errors.push('Linear result truncated');
|
|
18
|
+
if (live.length !== 33) errors.push(`current open count: ${live.length} != 33`);
|
|
19
|
+
if (record.verifiedIssues.length !== 29) errors.push(`recorded count: ${record.verifiedIssues.length} != 29`);
|
|
20
|
+
const sorted = [...live].sort((a, b) => a.createdAt.localeCompare(b.createdAt));
|
|
21
|
+
const selected = sorted.slice(0, 29);
|
|
22
|
+
const excluded = sorted.slice(29);
|
|
23
|
+
const actual = new Map(live.map(issue => [issue.identifier, issue]));
|
|
24
|
+
if (actual.size !== live.length) errors.push('duplicate Linear identifier');
|
|
25
|
+
const seen = new Set<string>();
|
|
26
|
+
for (const row of record.verifiedIssues) {
|
|
27
|
+
if (seen.has(row.identifier)) errors.push(`duplicate recorded identifier: ${row.identifier}`);
|
|
28
|
+
seen.add(row.identifier);
|
|
29
|
+
const issue = actual.get(row.identifier);
|
|
30
|
+
if (!issue) { errors.push(`not in Linear: ${row.identifier}`); continue; }
|
|
31
|
+
for (const [field, expected, value] of [
|
|
32
|
+
['title', row.title, issue.title], ['url', row.url, issue.url],
|
|
33
|
+
['createdAt', row.createdAt, issue.createdAt], ['updatedAt', row.updatedAt, issue.updatedAt],
|
|
34
|
+
['dueDate', row.existingDueDate, issue.dueDate], ['priority', row.priority, issue.priority],
|
|
35
|
+
] as const) if (expected !== value) errors.push(`${row.identifier} ${field}: recorded=${String(expected)} Linear=${String(value)}`);
|
|
36
|
+
}
|
|
37
|
+
const selectedIds = selected.map(issue => issue.identifier).sort().join(',');
|
|
38
|
+
if ([...seen].sort().join(',') !== selectedIds) errors.push('recorded identifiers differ from oldest 29 currently open by createdAt');
|
|
39
|
+
if (selected.filter(issue => issue.dueDate !== null).length !== 4) errors.push('Linear selected dueDate count != 4');
|
|
40
|
+
if (selected.filter(issue => issue.priority !== 0).length !== 7) errors.push('Linear selected priority count != 7');
|
|
41
|
+
const excludedRecorded = record.cohort.excludedCurrentIssues;
|
|
42
|
+
if (excludedRecorded.map(issue => issue.identifier).sort().join(',') !== excluded.map(issue => issue.identifier).sort().join(',')) errors.push('excluded identifiers differ from Linear');
|
|
43
|
+
for (const row of excludedRecorded) {
|
|
44
|
+
const issue = actual.get(row.identifier);
|
|
45
|
+
if (!issue) continue;
|
|
46
|
+
if (row.url !== issue.url || row.createdAt !== issue.createdAt || row.dueDate !== issue.dueDate || row.priority !== issue.priority) errors.push(`excluded ${row.identifier} differs from Linear`);
|
|
47
|
+
}
|
|
48
|
+
return errors;
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
// Linear GraphQL read-only fetchLinearProjectIssues resolves the project and paginates the open issues.
|
|
52
|
+
// createdAt is queried separately because the shared COO tool's projection does not include it.
|
|
53
|
+
export async function readLiveCooIssues(apiKey: string, project: string): Promise<{ issues: LiveIssue[]; truncated: boolean }> {
|
|
54
|
+
const issues = await fetchLinearProjectIssues({apiKey, project});
|
|
55
|
+
const identifiers = issues.map(issue => issue.identifier);
|
|
56
|
+
if (new Set(identifiers).size !== identifiers.length) throw new Error('duplicate Linear identifier');
|
|
57
|
+
const query = 'query CooIssueCreation($id: String!) { issue(id: $id) { identifier createdAt } }';
|
|
58
|
+
const creations = await Promise.all(identifiers.map(async identifier => {
|
|
59
|
+
const response = await fetch('https://api.linear.app/graphql', {
|
|
60
|
+
method: 'POST', headers: {Authorization: apiKey, 'Content-Type': 'application/json'},
|
|
61
|
+
body: JSON.stringify({query, variables: {id: identifier}}),
|
|
62
|
+
});
|
|
63
|
+
if (!response.ok) throw new Error(`Linear creation read HTTP ${response.status}`);
|
|
64
|
+
const body = await response.json() as { errors?: unknown[]; data?: {issue?: {identifier: string; createdAt: string}} };
|
|
65
|
+
if (body.errors?.length || body.data?.issue?.identifier !== identifier || !body.data.issue.createdAt) throw new Error(`Linear creation read failed: ${identifier}`);
|
|
66
|
+
return body.data.issue.createdAt;
|
|
67
|
+
}));
|
|
68
|
+
return {issues: issues.map((issue, index) => ({...issue, createdAt: creations[index]!})), truncated: issues.truncated};
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
if (import.meta.main) {
|
|
72
|
+
const apiKey = process.env.LINEAR_API_KEY?.trim();
|
|
73
|
+
if (!apiKey) throw new Error('LINEAR_API_KEY absent; cannot compare recorded evidence to live Linear');
|
|
74
|
+
const record = JSON.parse(await readFile(new URL('../src/domains/coo-admin-dates.evidence.json', import.meta.url), 'utf8')) as Evidence;
|
|
75
|
+
const {issues, truncated} = await readLiveCooIssues(apiKey, record.project);
|
|
76
|
+
const errors = compareCooEvidence(record, issues, truncated);
|
|
77
|
+
if (errors.length) {
|
|
78
|
+
for (const error of errors) console.error(error);
|
|
79
|
+
process.exitCode = 1;
|
|
80
|
+
} else {
|
|
81
|
+
console.log(`PASS Linear live comparison: open=${issues.length} selected=${record.verifiedIssues.length} dueDates=${record.verifiedIssues.filter(issue => issue.existingDueDate !== null).length} priorities=${record.verifiedIssues.filter(issue => issue.priority !== 0).length} excluded=${record.cohort.excludedCurrentIssues.length}`);
|
|
82
|
+
}
|
|
83
|
+
}
|
package/src/acp/client.ts
CHANGED
|
@@ -371,6 +371,8 @@ export function readClientInfo(
|
|
|
371
371
|
export interface AcpAgentOpts {
|
|
372
372
|
/** Backend id from ACP_BACKENDS. */
|
|
373
373
|
backendId: string;
|
|
374
|
+
/** Review-owned ACP executable override; never changes the shared backend registry. */
|
|
375
|
+
backendSpec?: AcpBackendSpec;
|
|
374
376
|
/** Working directory the agent runs in (cwd argument to spawn).
|
|
375
377
|
* Affects file-tool resolution. Default: getSessionCwd() so a
|
|
376
378
|
* Ctrl+W / /wd in the dashboard retargets new ACP agents. */
|
|
@@ -443,7 +445,7 @@ export class AcpAgent {
|
|
|
443
445
|
private authMethods: string[] = [];
|
|
444
446
|
|
|
445
447
|
constructor(opts: AcpAgentOpts) {
|
|
446
|
-
this.spec = getAcpBackend(opts.backendId);
|
|
448
|
+
this.spec = opts.backendSpec ?? getAcpBackend(opts.backendId);
|
|
447
449
|
// WD7 — default to the session working directory; ACP agents
|
|
448
450
|
// inherit the "active project" concept.
|
|
449
451
|
this.cwd = opts.cwd ?? getSessionCwd();
|
|
@@ -456,7 +458,7 @@ export class AcpAgent {
|
|
|
456
458
|
// proactively. Mirrors zed's env-strip pattern for provider
|
|
457
459
|
// tokens (acp.rs:232-243), generalized here for any env that
|
|
458
460
|
// breaks nested agents.
|
|
459
|
-
const cleanEnv: NodeJS.ProcessEnv = { ...process.env, ...opts.env };
|
|
461
|
+
const cleanEnv: NodeJS.ProcessEnv = opts.backendSpec && opts.env ? { ...opts.env, NODE_ENV: process.env.NODE_ENV } : { ...process.env, ...opts.env };
|
|
460
462
|
for (const key of Object.keys(cleanEnv)) {
|
|
461
463
|
if (NESTED_AGENT_ENV_BLOCKLIST.has(key) || /^CLAUDE_CODE_/.test(key)) {
|
|
462
464
|
delete cleanEnv[key];
|
package/src/acp/codex-plugins.ts
CHANGED
|
@@ -15,7 +15,7 @@
|
|
|
15
15
|
// installations don't churn quickly and a BackendPickerChip re-render
|
|
16
16
|
// should not trigger a fresh RPC roundtrip every time.
|
|
17
17
|
|
|
18
|
-
import type
|
|
18
|
+
import { spawnCodexAppServer, type CodexAppServerClient } from './codex-app-server-client.js';
|
|
19
19
|
|
|
20
20
|
export interface CodexPlugin {
|
|
21
21
|
/** Plugin slug as reported by codex (e.g. "gmail", "google-calendar"). */
|
|
@@ -43,13 +43,55 @@ export interface FetchCodexPluginsOpts {
|
|
|
43
43
|
noCache?: boolean;
|
|
44
44
|
}
|
|
45
45
|
|
|
46
|
+
/** Uncached inventory probe: distinguish no session / RPC failure from an empty installed list. */
|
|
47
|
+
export async function readCodexPluginsObservation(client: CodexAppServerClient | null | undefined): Promise<
|
|
48
|
+
{ status: 'ok'; plugins: ReadonlyArray<CodexPlugin> } | { status: 'unknown'; plugins: readonly [] }
|
|
49
|
+
> {
|
|
50
|
+
if (!client) return { status: 'unknown', plugins: [] };
|
|
51
|
+
try {
|
|
52
|
+
const response = await client.request<Record<string, never>, unknown>('plugin/list', {});
|
|
53
|
+
if (!isWellFormedPluginList(response)) return { status: 'unknown', plugins: [] };
|
|
54
|
+
return { status: 'ok', plugins: parseCodexPluginsResponse(response) };
|
|
55
|
+
} catch { return { status: 'unknown', plugins: [] }; }
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
/** Every marketplace and plugin row must have the shape the projector reads; a damaged or changed
|
|
59
|
+
* RPC response is unknown, never a confirmed empty install list. */
|
|
60
|
+
function isWellFormedPluginList(response: unknown): boolean {
|
|
61
|
+
if (!response || typeof response !== 'object') return false;
|
|
62
|
+
const marketplaces = (response as { marketplaces?: unknown }).marketplaces;
|
|
63
|
+
if (!Array.isArray(marketplaces)) return false;
|
|
64
|
+
return marketplaces.every(market => !!market && typeof market === 'object'
|
|
65
|
+
&& typeof (market as { name?: unknown }).name === 'string' && (market as { name: string }).name.length > 0
|
|
66
|
+
&& Array.isArray((market as { plugins?: unknown }).plugins)
|
|
67
|
+
&& ((market as { plugins: unknown[] }).plugins).every(plugin => !!plugin && typeof plugin === 'object'
|
|
68
|
+
&& typeof (plugin as { name?: unknown }).name === 'string' && (plugin as { name: string }).name.length > 0));
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
export type CodexPluginObservation = Awaited<ReturnType<typeof readCodexPluginsObservation>>;
|
|
72
|
+
|
|
73
|
+
/** Isolated read-only RPC probe; always closes its own app-server process. */
|
|
74
|
+
export async function readCodexPluginsFromAppServer(
|
|
75
|
+
spawn: typeof spawnCodexAppServer = spawnCodexAppServer,
|
|
76
|
+
): Promise<CodexPluginObservation> {
|
|
77
|
+
let server: ReturnType<typeof spawnCodexAppServer>;
|
|
78
|
+
try { server = spawn({ requestTimeoutMs: 5000 }); }
|
|
79
|
+
catch { return { status: 'unknown', plugins: [] }; }
|
|
80
|
+
try {
|
|
81
|
+
await server.client.request('initialize', {
|
|
82
|
+
clientInfo: { name: 'elanous', version: '0.x' }, capabilities: { experimentalApi: true },
|
|
83
|
+
});
|
|
84
|
+
return await readCodexPluginsObservation(server.client);
|
|
85
|
+
} catch { return { status: 'unknown', plugins: [] }; }
|
|
86
|
+
finally {
|
|
87
|
+
try { await server.client.close(); }
|
|
88
|
+
finally { server.child.kill(); }
|
|
89
|
+
}
|
|
90
|
+
}
|
|
91
|
+
|
|
46
92
|
/** Query codex `plugin/list` and project the response into the
|
|
47
93
|
* BackendPickerChip-ready shape. Cached per client for 5 min.
|
|
48
|
-
*
|
|
49
|
-
* Returns an empty array when:
|
|
50
|
-
* - `client` is null/undefined (no active codex session)
|
|
51
|
-
* - the RPC throws (timeout / closed / codex error) — soft-fail
|
|
52
|
-
* with stale cache if available, otherwise [] */
|
|
94
|
+
* Returns [] for no client or RPC failure (stale cache when available). */
|
|
53
95
|
export async function fetchCodexPlugins(
|
|
54
96
|
client: CodexAppServerClient | null | undefined,
|
|
55
97
|
opts: FetchCodexPluginsOpts = {},
|
|
@@ -16,7 +16,7 @@
|
|
|
16
16
|
|
|
17
17
|
import { existsSync } from 'node:fs';
|
|
18
18
|
import type { UserConfig } from '../user-config.js';
|
|
19
|
-
import { runTurn } from '../session/chat.js';
|
|
19
|
+
import { runTurn, type RunTurnOpts } from '../session/chat.js';
|
|
20
20
|
import type { SessionSource } from '../session/index.js';
|
|
21
21
|
import { buildContinuationAgentTools } from '../dispatch/continuation-turn-runner.js';
|
|
22
22
|
import { buildTerminalCapableTurn } from './terminal-surface.js';
|
|
@@ -56,6 +56,54 @@ function recentSentContext(): string {
|
|
|
56
56
|
} catch { return ''; }
|
|
57
57
|
}
|
|
58
58
|
|
|
59
|
+
interface ToolRun { id: string; name: string; result?: unknown }
|
|
60
|
+
|
|
61
|
+
const TOOL_RESULT_CLIP_CHARS = 1500;
|
|
62
|
+
const TOOL_RESULT_MAX_RUNS = 12;
|
|
63
|
+
|
|
64
|
+
function clipToolResult(result: unknown): string {
|
|
65
|
+
if (result === undefined) return '(결과 없음)';
|
|
66
|
+
let text: string;
|
|
67
|
+
try { text = typeof result === 'string' ? result : JSON.stringify(result) ?? String(result); } catch { text = String(result); }
|
|
68
|
+
return text.length > TOOL_RESULT_CLIP_CHARS ? `${text.slice(0, TOOL_RESULT_CLIP_CHARS)}…` : text;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
/** 툴만 부르고 최종 텍스트가 빈 턴 — 관측을 남기고 툴 결과 요약 재턴을 한 번 돌린다. 재턴도 비면 바닥줄이 아니라
|
|
72
|
+
* 실패 문구를 돌려준다. 세션 재생은 role:'tool' 기록을 빼므로 재턴 프롬프트가 툴 결과를 직접 싣는다. */
|
|
73
|
+
async function recoverEmptyAnswer(args: {
|
|
74
|
+
runTurnImpl: typeof runTurn;
|
|
75
|
+
opts: RunTurnOpts;
|
|
76
|
+
llmOpts: RunTurnOpts['llmOpts'];
|
|
77
|
+
systemPrompt: string;
|
|
78
|
+
toolRuns: ToolRun[];
|
|
79
|
+
surface: SessionSource;
|
|
80
|
+
}): Promise<string> {
|
|
81
|
+
const { runTurnImpl, opts, llmOpts, systemPrompt, toolRuns, surface } = args;
|
|
82
|
+
let message = '';
|
|
83
|
+
let sawToolCall = false;
|
|
84
|
+
let retryText = '';
|
|
85
|
+
try {
|
|
86
|
+
const summary = toolRuns.slice(-TOOL_RESULT_MAX_RUNS)
|
|
87
|
+
.map((run) => `- ${run.name}: ${clipToolResult(run.result)}`).join('\n');
|
|
88
|
+
const retry = await runTurnImpl({
|
|
89
|
+
...opts,
|
|
90
|
+
userText: `[툴 결과 요약 재턴] 아래 툴 실행 결과를 근거로 사용자 질문에 대한 최종 답을 텍스트로 작성하세요. 툴은 더 부르지 마세요.\n\n사용자 질문: ${opts.userText}\n\n툴 결과:\n${summary}`,
|
|
91
|
+
onDelta: (delta) => { message += delta; },
|
|
92
|
+
onToolCall: () => { message = ''; sawToolCall = true; },
|
|
93
|
+
onToolResult: () => {},
|
|
94
|
+
skipMemoryInjection: true,
|
|
95
|
+
llmOpts,
|
|
96
|
+
systemPrompt,
|
|
97
|
+
tools: [],
|
|
98
|
+
});
|
|
99
|
+
retryText = (sawToolCall ? message : retry.text)?.trim() ?? '';
|
|
100
|
+
} catch { /* 재턴 실패는 아래 실패 문구로 */ }
|
|
101
|
+
debug.log('agent.turn', 'empty-answer', {
|
|
102
|
+
surface, sessionId: opts.sessionId, toolCalls: toolRuns.length, recovered: retryText !== '',
|
|
103
|
+
});
|
|
104
|
+
return retryText || `⚠️ 답을 만들지 못했다 — 툴 ${toolRuns.length}개 실행`;
|
|
105
|
+
}
|
|
106
|
+
|
|
59
107
|
/** Build the tool-enabled elanous self runTurn for a messenger surface:
|
|
60
108
|
* the full agent tool surface (Read/Grep/Glob/ListDir/Edit/Write +
|
|
61
109
|
* Bash + PtyShell + search), plus — when the finance domain pack is
|
|
@@ -229,6 +277,8 @@ export function makeElanousAgentRunTurn(cfg: UserConfig, surface: SessionSource,
|
|
|
229
277
|
llmOpts = terminal.llmOpts;
|
|
230
278
|
let currentMessage = '';
|
|
231
279
|
let sawToolCall = false;
|
|
280
|
+
const toolRuns: ToolRun[] = [];
|
|
281
|
+
const systemPrompt = terminal.systemPromptParts.join('\n\n');
|
|
232
282
|
return runTurnImpl({
|
|
233
283
|
...opts,
|
|
234
284
|
onDelta: (delta) => {
|
|
@@ -238,21 +288,33 @@ export function makeElanousAgentRunTurn(cfg: UserConfig, surface: SessionSource,
|
|
|
238
288
|
onToolCall: (call) => {
|
|
239
289
|
currentMessage = '';
|
|
240
290
|
sawToolCall = true;
|
|
291
|
+
toolRuns.push({ id: call.id, name: call.name });
|
|
241
292
|
opts.onToolCall?.(call);
|
|
242
293
|
},
|
|
294
|
+
onToolResult: (call) => {
|
|
295
|
+
const run = toolRuns.find((candidate) => candidate.id === call.id);
|
|
296
|
+
if (run) run.result = call.result;
|
|
297
|
+
opts.onToolResult?.(call);
|
|
298
|
+
},
|
|
243
299
|
llmOpts,
|
|
244
|
-
systemPrompt
|
|
300
|
+
systemPrompt,
|
|
245
301
|
tools: terminal.specs,
|
|
246
302
|
dispatchTool: terminal.dispatch,
|
|
247
|
-
}).then((result) => {
|
|
303
|
+
}).then(async (result) => {
|
|
248
304
|
// /cancel self-awareness — when the turn was aborted mid-run (user hit
|
|
249
305
|
// `/cancel`), the tool loop returns with little/no final text. Substitute
|
|
250
306
|
// a CLEAR cancellation marker so (a) the user gets an ack, and (b) it is
|
|
251
307
|
// the text recorded to cross-surface memory (recordInboundTurn) — so the
|
|
252
308
|
// NEXT turn's memory_recall knows the task was CANCELLED, not silently
|
|
253
309
|
// dropped or still running. Only turnAbort (=/cancel) aborts this signal.
|
|
254
|
-
|
|
255
|
-
|
|
310
|
+
let wasAborted = opts.signal?.aborted === true;
|
|
311
|
+
let answer = sawToolCall ? currentMessage.trim() : result.text;
|
|
312
|
+
// Telegram only: other messenger surfaces (Discord …) keep their current final-answer behaviour.
|
|
313
|
+
if (!wasAborted && sawToolCall && !answer && surface === 'telegram') {
|
|
314
|
+
answer = await recoverEmptyAnswer({ runTurnImpl, opts, llmOpts, systemPrompt, toolRuns, surface });
|
|
315
|
+
// A /cancel that lands during the retry turn still wins over the retry answer or the failure sentence.
|
|
316
|
+
if (opts.signal?.aborted === true) { wasAborted = true; answer = ''; }
|
|
317
|
+
}
|
|
256
318
|
const responseText = wasAborted
|
|
257
319
|
? (answer?.trim()
|
|
258
320
|
? `${answer}\n\n⏹️ 이 작업은 /cancel 로 취소되었습니다 (실행 중이던 Bash/PTY 종료됨).`
|
package/src/agent/run-context.ts
CHANGED
|
@@ -9,6 +9,7 @@
|
|
|
9
9
|
|
|
10
10
|
import { normalizeChildLlmProvider } from '../self-dev/dev-cli.js';
|
|
11
11
|
import { providerEnvKey } from '../llm/provider-credentials.js';
|
|
12
|
+
import { bedrockChildRelayEnv } from '../llm/bedrock.js';
|
|
12
13
|
|
|
13
14
|
export type RunContext = 'production' | 'benchmark' | 'simulator' | 'self-build';
|
|
14
15
|
|
|
@@ -54,6 +55,8 @@ export interface ChildLlmSelection {
|
|
|
54
55
|
effort?: ChildLlmEffort;
|
|
55
56
|
/** 선택이 CLI 플래그에서 왔나, self-dev 설정에서 왔나. 같은 모델이라도 다른 사실이다. */
|
|
56
57
|
source: 'flag' | 'config';
|
|
58
|
+
/** Grok weekly cap rerouted this run to Codex: allow prepaid credits even when subscription quota is exhausted. */
|
|
59
|
+
codexQuotaPolicy?: 'credits';
|
|
57
60
|
}
|
|
58
61
|
|
|
59
62
|
/** ⭐⭐ **가르는 축은 「키냐 주소냐」가 «아니라» 「그 자격이 «파일»에 사나 «env»에 사나」다**
|
|
@@ -76,6 +79,12 @@ function childLocalEndpointEnv(provider: string): Record<string, string> {
|
|
|
76
79
|
return url ? { LOCAL_LLM_URL: url } : {};
|
|
77
80
|
}
|
|
78
81
|
|
|
82
|
+
/** BEDROCK-PROVIDER — Bedrock 자격은 «파일»(~/.aws · HOME 으로 자식이 그대로 읽는다)과 «env»(AWS_*) 둘 다에 산다.
|
|
83
|
+
* env 쪽은 replace env 라 상속이 없으므로 이름 목록대로 릴레이한다(값은 싣기만 하고 어디에도 찍지 않는다). */
|
|
84
|
+
function childBedrockEnv(provider: string): Record<string, string> {
|
|
85
|
+
return provider === 'bedrock' ? bedrockChildRelayEnv() : {};
|
|
86
|
+
}
|
|
87
|
+
|
|
79
88
|
/** The family classifier is model-id based, so preserve local-provider identity
|
|
80
89
|
* across the replace-env child boundary without changing non-local model IDs. */
|
|
81
90
|
function childRelayModel(provider: string, model: string): string {
|
|
@@ -91,6 +100,8 @@ export function childLlmSelectionEnv(selection?: ChildLlmSelection): Record<stri
|
|
|
91
100
|
return {
|
|
92
101
|
ELANOUS_LLM_PROVIDER: provider,
|
|
93
102
|
ELANOUS_LLM_MODEL: childRelayModel(provider, selection.model),
|
|
103
|
+
...(selection.codexQuotaPolicy === 'credits' && provider === 'openai-codex'
|
|
104
|
+
? { ELANOUS_CODEX_QUOTA_POLICY: 'credits' } : {}),
|
|
94
105
|
// ⛔⭐ 새 env 이름을 «짓지 않는다» — `ELANOUS_ESCALATE_EFFORT` 가 «이미» 있고
|
|
95
106
|
// `user-config.ts` 가 그것으로 `reasoningLevel`(anthropic)과
|
|
96
107
|
// `codexReasoning.effort`(openai-codex/sol) 를 ***둘 다*** 덮는다.
|
|
@@ -98,6 +109,7 @@ export function childLlmSelectionEnv(selection?: ChildLlmSelection): Record<stri
|
|
|
98
109
|
...(selection.effort ? { ELANOUS_ESCALATE_EFFORT: selection.effort } : {}),
|
|
99
110
|
...childProviderKeyEnv(provider),
|
|
100
111
|
...childLocalEndpointEnv(provider),
|
|
112
|
+
...childBedrockEnv(provider),
|
|
101
113
|
};
|
|
102
114
|
}
|
|
103
115
|
// ⛔⭐ 상속 갈래도 local 이면 «주소»를 같이 넘긴다(BACKLOG B12 · 2026-09-25).
|
|
@@ -108,5 +120,7 @@ export function childLlmSelectionEnv(selection?: ChildLlmSelection): Record<stri
|
|
|
108
120
|
...(process.env.ELANOUS_LLM_PROVIDER !== undefined ? { ELANOUS_LLM_PROVIDER: process.env.ELANOUS_LLM_PROVIDER } : {}),
|
|
109
121
|
...(process.env.ELANOUS_LLM_MODEL !== undefined ? { ELANOUS_LLM_MODEL: process.env.ELANOUS_LLM_MODEL } : {}),
|
|
110
122
|
...(inheritedProvider ? childLocalEndpointEnv(inheritedProvider) : {}),
|
|
123
|
+
// 상속 갈래도 bedrock 이면 AWS_* 를 같이 넘긴다(명시 갈래와 같은 규칙 — replace env 라 자동 상속이 없다).
|
|
124
|
+
...(inheritedProvider ? childBedrockEnv(inheritedProvider) : {}),
|
|
111
125
|
};
|
|
112
126
|
}
|
|
@@ -15,11 +15,27 @@
|
|
|
15
15
|
// ELANOUS_CHILD_TOOL_PROFILE=full 전부
|
|
16
16
|
// ELANOUS_CHILD_TOOL_PROFILE=finance,ops 기본 ⊕ 고른 묶음
|
|
17
17
|
// (없음) coding(기본)
|
|
18
|
+
//
|
|
19
|
+
// 🩸 CHILD-TOOL-PROFILE-TRIM(10-10 실측 · base 0317d73034 · Plan 켬): `coding` 이 33개 중 27개(스키마 26,742자)를
|
|
20
|
+
// 남겼다 — 판·자리 운영·회수·스킬·서브에이전트 도구가 «어느 묶음에도 안 들어서» 기본으로 갔을 뿐이다.
|
|
21
|
+
// ⇒ 화이트리스트를 따로 두지 않고(09-25 설계 유지) 그것들을 새 묶음 넷(admin · recall · skills · subagent)으로 옮긴다.
|
|
22
|
+
// ⇒ `coding` 의 기대 집합 = Read · Grep · Glob · ListDir · Edit · Write · Bash · Plan · MarkStepDone(9개).
|
|
23
|
+
// 빠진 묶음은 상황 신호(골 문면)와 ToolSearch(전체 목록에서 찾는다)로 계속 닿는다.
|
|
24
|
+
|
|
25
|
+
import { debug } from '../debug/log.js';
|
|
18
26
|
|
|
19
27
|
/** 추가 묶음 — 코딩 기본에서 빠지고 «고르면 더해지는» 도구들. 접두 ⊕ 정확한 이름. */
|
|
20
28
|
export const TOOL_EXTRA_GROUPS = {
|
|
21
29
|
finance: { prefixes: ['finance_', 'conatus_'], names: [] as string[] },
|
|
22
30
|
ops: { prefixes: [] as string[], names: ['schedule_manage', 'session_manage', 'autopilot_missions', 'ops_status', 'se_build', 'mission_decide'] },
|
|
31
|
+
/** 판·자리·결정 운영 — 코딩 일에는 안 쓴다. */
|
|
32
|
+
admin: { prefixes: ['release_'], names: ['coo_admin', 'ops_seats', 'decisions_pending', 'proact_meter'] },
|
|
33
|
+
/** 기억·회수·관측 조회. */
|
|
34
|
+
recall: { prefixes: [] as string[], names: ['memory_recall', 'fact_check', 'self_recall', 'context_now', 'logs_query'] },
|
|
35
|
+
/** 스킬 목록·실행. */
|
|
36
|
+
skills: { prefixes: [] as string[], names: ['elanous_skills_list', 'skill_exec'] },
|
|
37
|
+
/** 서브에이전트 — ⚠️ 기본에서 빼도 완주율이 안 떨어지는지는 아직 안 쟀다(SMALL-MODEL-BENCH 가 잰다). 신호·ToolSearch 로 되살린다. */
|
|
38
|
+
subagent: { prefixes: [] as string[], names: ['Agent', 'AgentOutput', 'AgentReply', 'AgentStop', 'AgentList'] },
|
|
23
39
|
} as const;
|
|
24
40
|
export type ToolExtraGroup = keyof typeof TOOL_EXTRA_GROUPS;
|
|
25
41
|
const ALL_GROUPS = Object.keys(TOOL_EXTRA_GROUPS) as ToolExtraGroup[];
|
|
@@ -45,6 +61,10 @@ export function activeToolProfile(env: NodeJS.ProcessEnv = process.env): ToolPro
|
|
|
45
61
|
export const SITUATIONAL_GROUP_SIGNALS: Record<ToolExtraGroup, RegExp> = {
|
|
46
62
|
finance: /금융|주식|종목|주가|시세|매매|포트폴리오|포지션|투자|백테스트|13F|재무|finance_|conatus|stock|ticker|portfolio|backtest|trading/i,
|
|
47
63
|
ops: /스케줄|크론|예약 실행|오토파일럿|미션 결정|운영 상태|schedule_manage|autopilot|ops_status|mission_decide|cron/i,
|
|
64
|
+
admin: /release_(status|change)|coo_admin|ops_seats|decisions_pending|proact_meter|판 칸|칸 근거|칸 상태|체크리스트 칸|checklist (set|status)|결정 대기|자리 현황/i,
|
|
65
|
+
recall: /memory_recall|fact_check|self_recall|context_now|logs_query|기억 조회|기억을 (찾|조회|회수)|자기 이력|사실 확인|팩트 ?체크/i,
|
|
66
|
+
skills: /elanous_skills_list|skill_exec|스킬(을)? 실행|스킬 목록|run (a|the) skill/i,
|
|
67
|
+
subagent: /서브\s?에이전트|하위\s?에이전트|sub-?agents?|에이전트를 (띄|병렬)|병렬 에이전트|Agent(Output|Reply|Stop|List)\b|Agent 도구/i,
|
|
48
68
|
};
|
|
49
69
|
|
|
50
70
|
export function situationalToolGroups(goalText: string | undefined): ToolExtraGroup[] {
|
|
@@ -58,9 +78,15 @@ export function situationalToolGroups(goalText: string | undefined): ToolExtraGr
|
|
|
58
78
|
* ③ 둘 다 없으면 `coding`(다이어트) */
|
|
59
79
|
export function childToolProfile(env: NodeJS.ProcessEnv = process.env, goalText?: string): string {
|
|
60
80
|
const explicit = env.ELANOUS_CHILD_TOOL_PROFILE?.trim();
|
|
61
|
-
if (explicit)
|
|
81
|
+
if (explicit) {
|
|
82
|
+
const parsed = parseToolProfile(explicit);
|
|
83
|
+
debug.log('agent.tool-profile', 'child-profile-chosen', { source: 'env', raw: explicit, profile: parsed?.name ?? 'coding', groups: parsed ? [...parsed.groups] : [] });
|
|
84
|
+
return explicit;
|
|
85
|
+
}
|
|
62
86
|
const groups = situationalToolGroups(goalText);
|
|
63
|
-
|
|
87
|
+
const profile = groups.length ? groups.join(',') : 'coding';
|
|
88
|
+
debug.log('agent.tool-profile', 'child-profile-chosen', { source: groups.length ? 'situational' : 'default', profile, groups, goalChars: goalText?.length ?? 0 });
|
|
89
|
+
return profile;
|
|
64
90
|
}
|
|
65
91
|
|
|
66
92
|
/** 기본 모드에서 뺀 묶음을 자식에게 «한 줄»로 알린다 — 필요하면 ToolSearch 로 불러 쓴다(스키마는 안 싣는다). */
|