elanous 0.2.22 → 0.2.24
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/{aBi6EyMtLsrl7J8eH4kF7 → Q-7iofoxOEv1WX18S35of}/_buildManifest.js +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-0eed0fb0aab716b6.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-aaae04ed1d32622f.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-3b9fc39362473ae7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/autopilot/page-f2b62c19ca68fef8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/board/page-d7602d489edf5f37.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/botlab/page-24282bf9f90031a5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/bots/page-8b7c5ab6b5bc8d64.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ceo/page-4eb84d454f8c3415.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/chat/page-b2e494bdad57fcb5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/consult/{page-80ed511e02c81412.js → page-c0ab229673a8b0eb.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/control/page-3e2b45f3c36dbac4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/decisions/page-c22aa511b28743ad.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/design-check/page-26345242e4049f55.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/editor/page-bf88c0f558d8ef54.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/exec/page-52fec523e5b5d3ad.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/field/page-67723dfdcde92b31.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-22725e2570f1126b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/intake/page-1891335950d68b70.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/layout-3267af1ebdc73cf5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/live/page-c314b75c11234998.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/live-run/page-9f9c85415f61782b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/loops/page-c1d4276059085587.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/market/page-833aab587f26ad4c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-8526c17ae38e6a50.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/morning/page-f998637a8402115c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/not-found-b7bb53828b17b335.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/observatory/page-1b1850de0257e46d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-6f23159fedb41f67.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/release/page-1d809a87139dd024.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-da9e570234d481fd.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/outputs/page-b92caddb5c715f30.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/page-8ce3a38e210b810a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/reflection/page-57ffeeb6019440fd.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/scheduler/page-abbb417bf514630b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/sessions/page-2c2b3f29cec1efa4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-9369279f72fc7b51.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/settings/page-64861f14039499c3.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/done/page-ddc4c93efd8ab94b.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-901a1391b81053bc.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/share/page-68d9bbaac9841a58.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/showroom/page-b5c0c996f329371e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/tasks/page-89881ccbcf728978.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/term/page-0e87a803b3d7165e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/today/page-58d4e5cb30ef4871.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/trace/page-02ce4c3b5f39e4d2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/vault/page-e620d1bb8eadcec2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-acf868c64d77f950.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workflows/page-54fa605fa6dba457.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workspace/page-bc79f0833533fa84.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/worktrees/page-d5c4398eea03d8f3.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/72becfd42807b50d.css +1 -0
- package/apps/pwa/out/_next/static/css/d0a48dc099ed86cf.css +1 -0
- 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/catalog/models/openrouter/deepseek-v4-pro-0813.yaml +39 -0
- package/catalog/models/openrouter/deepseek-v4.1-flash.yaml +38 -0
- package/catalog/models/openrouter/glm-5.3-flash.yaml +35 -0
- package/catalog/providers/openrouter.yaml +2 -0
- package/graphs/implement-loop.yaml +31 -0
- package/graphs/log-horizon/log-horizon-watch.yaml +25 -0
- package/graphs/log-horizon/recipes.yaml +3 -0
- package/graphs/ops/harness-gc.yaml +17 -0
- package/graphs/ops/recipes.yaml +3 -0
- package/graphs/overlays/README.md +1 -1
- package/graphs/overlays/stop-heal-ladder.yaml +105 -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/package.json +4 -1
- package/scripts/add-api-key.sh +1 -1
- package/scripts/bench-report.ts +82 -3
- package/scripts/ci-typecheck-changed.ts +80 -14
- package/scripts/fleet/bedrock-pod-secret.ts +122 -0
- package/scripts/fleet/node-setup-linux.sh +97 -0
- package/scripts/fleet/node-setup.sh +11 -0
- package/scripts/fleet/zai-pod-secret.ts +86 -0
- package/scripts/hq/hq-fence-wrapper.sh +148 -0
- package/scripts/land-global-checks.ts +3 -0
- package/scripts/lib/typecheck-ratchet.ts +51 -0
- package/scripts/measure-log-diet-2.ts +213 -0
- package/scripts/measure-tsc-affected-roots.ts +289 -0
- package/scripts/openai-relay-server.ts +5 -1
- package/scripts/release-loop/docs-node.ts +258 -43
- package/scripts/release-loop/gate-executor.ts +28 -0
- package/scripts/release-loop/gate-method.ts +59 -0
- package/scripts/release-loop/gate-node.ts +335 -33
- 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 +40 -4
- package/scripts/release-loop/resume.ts +94 -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 +29 -7
- package/scripts/rhythm/daily.ts +51 -2
- package/scripts/rhythm/weekly.ts +3 -2
- package/scripts/tsc-baseline-cache.ts +147 -0
- package/scripts/tsc-main-safety-net.ts +189 -0
- package/scripts/usage-rollup.ts +64 -8
- package/src/acp/codex-plugins.ts +48 -6
- package/src/agent/monad-agent-turn.ts +67 -5
- package/src/agent/run-context.ts +20 -0
- package/src/agent/tool-profile.ts +28 -2
- package/src/agent-mission/acp-judge.ts +8 -2
- package/src/agent-mission/capabilities-cli.ts +16 -1
- package/src/agent-mission/driver.ts +19 -4
- package/src/agent-mission/pr-review-watch.ts +6 -2
- package/src/agent-mission/resource-ladder.ts +8 -3
- package/src/agent-mission/review-loop.ts +41 -7
- package/src/agent-substrate/acp-implementer.ts +139 -0
- package/src/agent-substrate/acp-reviewer.ts +17 -8
- package/src/agent-substrate/pr-reviewer.ts +191 -28
- package/src/agent-substrate/review-intent.ts +6 -4
- package/src/agent-substrate/self-review-cli.ts +155 -21
- 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 +216 -12
- 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/mission-critique.ts +18 -5
- package/src/autopilot/mission-feasibility-negotiate.ts +11 -10
- package/src/autopilot/mission-trace.ts +12 -1
- package/src/autopilot/pr-manager.ts +12 -3
- package/src/autopilot/system-lookback-run.ts +16 -10
- package/src/bench/bench.ts +183 -0
- package/src/boot/acp-server.ts +4 -7
- package/src/boot/acp-socket-path.ts +7 -0
- package/src/briefing/brief-items.ts +21 -13
- package/src/budget/fetchers/grok.ts +15 -5
- package/src/budget/llm-cost.ts +37 -5
- package/src/budget/types.ts +8 -2
- package/src/budget/unified-usage.ts +88 -6
- package/src/chat/index.ts +12 -3
- package/src/cli/agent-cli.ts +20 -0
- package/src/cli/bench-cli.ts +34 -0
- package/src/cli/brief-cli.ts +27 -21
- package/src/cli/cli-user-error.ts +9 -2
- package/src/cli/guardian-cli.ts +26 -1
- package/src/cli/image-cli.ts +101 -0
- package/src/cli/log-event-names.ts +7 -0
- package/src/cli/logs-cli.ts +1 -0
- 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 +90 -5
- package/src/cli/pr-land-overlap-evidence.ts +279 -0
- package/src/cli/release-cli.ts +63 -12
- package/src/cli/rfc-status.ts +52 -2
- package/src/cli/self-update.ts +277 -10
- package/src/cli/skills-cli.ts +12 -3
- package/src/cli/tasks-cli.ts +241 -30
- package/src/cli/usage-cli.ts +91 -8
- package/src/context-bus/context-first.ts +51 -2
- package/src/context-bus/context-now-surfaces.ts +13 -2
- package/src/context-bus/long-term-memory.ts +3 -1
- package/src/context-bus/nightly-condense.ts +3 -2
- package/src/core-turn/run-goal-loop.ts +87 -2
- package/src/dashboard/ad-run-setup-bindings.ts +279 -0
- package/src/dashboard/chat-fold.ts +20 -0
- package/src/dashboard/first-screen-band.ts +151 -1
- package/src/dashboard/index.ts +45 -281
- package/src/dashboard/slash-runtime/dashboard-handlers.ts +5 -3
- package/src/dashboard/stale-install-check.ts +24 -2
- package/src/dashboard/turn-stream-formatter.ts +25 -0
- package/src/debug/log-diet.ts +190 -0
- package/src/debug/log.ts +70 -17
- package/src/display/coordinator.ts +25 -2
- package/src/domains/coo-admin-tool.ts +27 -0
- package/src/domains/cron-match.ts +1 -0
- package/src/domains/outbound-alert.ts +17 -6
- package/src/domains/release-tool.ts +158 -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/error-report/report.ts +21 -4
- 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 +2 -0
- package/src/graph-runner/graph-cli.ts +42 -1
- package/src/graph-runner/runner.ts +218 -8
- package/src/grok/usage.ts +23 -2
- package/src/grounding/ref-index.ts +253 -0
- package/src/harness/dispatch-backpressure.ts +267 -0
- package/src/harness/harness-clean.ts +199 -78
- package/src/harness/harness-cli-command.ts +229 -35
- package/src/harness/harness-gc.ts +331 -0
- package/src/harness/harness-seams.ts +2 -20
- package/src/harness/harness-stop.ts +4 -2
- package/src/harness/harness-substrate-default.ts +214 -8
- package/src/harness/launch-registry.ts +6 -0
- package/src/harness/nested-elanous-policy.ts +4 -2
- package/src/harness/worktree-branch-prefix.ts +9 -0
- package/src/hq/fence-wrapper.ts +7 -0
- package/src/hq/fence.ts +187 -0
- package/src/hq/hq.ts +33 -2
- package/src/hq/lease.ts +13 -0
- package/src/hq/seats.ts +133 -21
- package/src/images/image-ledger.ts +179 -0
- package/src/index.ts +250 -69
- package/src/instance/child-scope.ts +32 -1
- package/src/instance/dev-project.ts +133 -0
- package/src/instance/resolve.ts +24 -0
- package/src/instance/spawn-elanous.ts +45 -0
- 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/intake-plane/ref-prefetch.ts +110 -0
- package/src/intelligence-map/model-alias.ts +6 -0
- package/src/intelligence-map/model-catalog.ts +113 -0
- package/src/knowledge/kgs/pack.ts +5 -2
- package/src/knowledge/kgs/sqlite-store.ts +15 -0
- package/src/knowledge/tools/knowledge-query.ts +20 -2
- package/src/knowledge/write.ts +234 -2
- package/src/llm/bedrock-eventstream.ts +215 -0
- package/src/llm/bedrock-provider.ts +248 -0
- package/src/llm/bedrock.ts +491 -0
- package/src/llm/openrouter-byok-cost.ts +96 -0
- package/src/llm/openrouter-deepseek.ts +151 -0
- package/src/llm/openrouter-upstream-pins.config.ts +25 -0
- package/src/llm/provider-credentials.ts +3 -1
- package/src/llm/zai-coding-plan.ts +700 -0
- package/src/llm.ts +383 -41
- package/src/loops/budget.ts +150 -0
- package/src/loops/checker.ts +148 -9
- package/src/loops/orchestrator/resync-shadow.ts +34 -7
- package/src/loops/orchestrator/seat-share.ts +6 -49
- package/src/loops/orchestrator/traffic.ts +5 -81
- package/src/market/signed-index.ts +42 -0
- package/src/maturity/feature-maturity.ts +2 -2
- package/src/mcp/mcp-oauth.ts +136 -17
- package/src/model-tier/llm-tier-map.ts +52 -4
- package/src/models/prompts.ts +23 -1
- package/src/mss/logging/horizon-watch.ts +168 -0
- package/src/mss/logging/log-store.ts +262 -26
- 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/error-reports.ts +30 -8
- package/src/nexus/api/http-server.ts +8 -0
- package/src/nexus/api/loop-resources.ts +42 -0
- package/src/nexus/api/missions.ts +73 -2
- package/src/nexus/api/ops-api.ts +18 -0
- package/src/nexus/api/outbound-report.ts +8 -3
- package/src/nexus/api/telegram-trigger-bot.ts +6 -3
- package/src/nexus/index.ts +17 -75
- package/src/nexus/outbound/format.ts +2 -0
- package/src/nexus/outbound/router.ts +198 -13
- package/src/nexus/tools-kind.ts +78 -0
- package/src/oauth/codex-account-rotation.ts +55 -20
- package/src/oauth/codex-account-store.ts +451 -23
- package/src/oauth/fallback-chain.ts +75 -15
- package/src/onboarding/first-run.ts +37 -18
- package/src/onboarding/web-first.ts +20 -2
- package/src/onboarding.ts +2 -1
- package/src/ops/machine-heartbeat.ts +185 -0
- package/src/ops/overview-cache.ts +175 -0
- package/src/ops/overview.ts +8 -0
- 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/plugin-maker.ts +25 -20
- package/src/plugins/maker/wizard-generate.ts +16 -2
- package/src/policy/llm-policy.ts +14 -1
- package/src/process/pid-liveness.ts +1 -1
- package/src/prompt-cache/openai.ts +13 -6
- package/src/prompt-cache/openrouter.ts +94 -0
- package/src/prompt-cache/types.ts +5 -0
- package/src/prompt-enhance/enhance.ts +69 -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.ts +24 -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 +107 -23
- 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/requirements/requirement-ledger.ts +536 -0
- package/src/retro/daily.ts +26 -12
- package/src/seat-loop/seat-loop.ts +66 -11
- 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 +109 -11
- package/src/self-dev/dev-pipeline.ts +11 -8
- package/src/self-dev/draft-residue.ts +475 -0
- package/src/self-dev/draft-sweep.ts +254 -10
- package/src/self-dev/draft-triage-rules.ts +27 -1
- package/src/self-dev/graph-journey-route.ts +6 -0
- 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 +82 -5
- package/src/self-dev/orchestrate-summary-line.ts +13 -0
- package/src/self-dev/orchestrate.ts +49 -141
- package/src/self-dev/review-provider-fallback.ts +115 -19
- package/src/self-dev/run-store.ts +1 -3
- package/src/self-dev/run-supervisor.ts +190 -36
- package/src/self-dev/run-types.ts +191 -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 +3 -4
- package/src/self-implement/blocked-draft-policy.ts +3 -19
- package/src/self-implement/budget-gate.ts +53 -13
- package/src/self-implement/child-context-composition.ts +139 -0
- package/src/self-implement/child-llm-preference.ts +13 -5
- package/src/self-implement/claude-acp-implement.ts +67 -0
- package/src/self-implement/draft-on-stop-mode.ts +18 -0
- package/src/self-implement/flex-signals.ts +59 -0
- package/src/self-implement/follow-up-goals.ts +114 -38
- package/src/self-implement/frozen-merges.ts +8 -3
- 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-decompose.ts +10 -2
- package/src/self-implement/goal-author.ts +48 -13
- package/src/self-implement/goal-digest.ts +19 -0
- package/src/self-implement/graph-overlay-condition.ts +32 -0
- package/src/self-implement/graph-overlay-yaml.ts +41 -7
- package/src/self-implement/graph-templates.ts +33 -1
- package/src/self-implement/graph-yaml.ts +56 -0
- package/src/self-implement/headless-elanous-driver.ts +11 -9
- package/src/self-implement/heal-intake.ts +5 -1
- package/src/self-implement/host-regate.ts +120 -29
- package/src/self-implement/l8-merge-queue.ts +67 -5
- 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 +271 -25
- 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/running-runs.ts +75 -5
- package/src/self-implement/seams.ts +83 -4
- package/src/self-implement/self-implement-cli.ts +12 -5
- package/src/self-implement/stop-autoheal.ts +69 -2
- 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/session-runtime/retry-policy.ts +2 -1
- 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 +22 -10
- package/src/steward/triage-budget.ts +62 -0
- package/src/steward/triage.ts +87 -24
- package/src/storage/file-lock.ts +8 -1
- package/src/task-agent/actions.ts +66 -5
- package/src/task-agent/card-evidence.ts +59 -13
- package/src/task-agent/completion-evidence.ts +5 -0
- package/src/task-agent/cover.ts +101 -3
- package/src/task-agent/judge.ts +20 -3
- package/src/task-agent/land-order-ledger.ts +95 -0
- package/src/task-agent/land-worktree.ts +201 -0
- package/src/task-agent/live-move-history.ts +219 -0
- package/src/task-agent/live-moves.ts +451 -34
- package/src/task-agent/parent-host.ts +117 -8
- package/src/task-agent/rejudge-on-head.ts +352 -0
- package/src/task-agent/review-prior-fix.ts +146 -0
- package/src/task-agent/review-result-capture.ts +218 -0
- package/src/task-agent/run-adopt.ts +136 -0
- package/src/task-agent/shadow.ts +154 -14
- package/src/task-agent/task-hand.ts +186 -14
- package/src/task-orchestrator/surfaces/pod-account-broker.ts +38 -5
- package/src/task-orchestrator/surfaces/pod-bedrock-child.ts +74 -0
- package/src/task-orchestrator/surfaces/pod-child-default.ts +50 -0
- package/src/task-orchestrator/surfaces/pod-child-providers.ts +42 -0
- package/src/task-orchestrator/surfaces/pod-command-job.ts +6 -3
- package/src/task-orchestrator/surfaces/pod-failure-reason.ts +94 -7
- package/src/task-orchestrator/surfaces/pod-image-source.ts +212 -0
- package/src/task-orchestrator/surfaces/pod-lease.ts +110 -17
- package/src/task-orchestrator/surfaces/pod-ledger-collect.ts +32 -3
- package/src/task-orchestrator/surfaces/pod-pool.ts +86 -18
- package/src/task-orchestrator/surfaces/pod-zai-child.ts +101 -0
- package/src/task-orchestrator/surfaces/self-implement-pod.ts +463 -50
- package/src/task-orchestrator/surfaces/self-implement.ts +25 -3
- 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 +1 -0
- package/src/user-config.ts +180 -32
- 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/triggers/registry.ts +59 -0
- package/src/workflow-runtime/triggers/scheduler.ts +1 -0
- package/src/workflow-runtime/triggers/webhook-source.ts +35 -5
- 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-08b716476f1d50af.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-d238d3e2eb5b2bf5.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-5985236d9307f676.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/5633-d6852385000738ef.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-5b9e8a45a5b0c823.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-aa1cc4ac90af4d40.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-55bcfbb0e8057f59.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/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-88459e0903da2803.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/autopilot/page-d85c43f46f58716b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/board/page-4e645600579ae952.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/botlab/page-87edbfd19117823b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/bots/page-7f0c2b7801ac6a54.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ceo/page-bf1f030a9d1adffd.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/chat/page-cbaf66b1e1804adf.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/control/page-9f5610caaa06178c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/decisions/page-ec8f3575e339de74.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/design-check/page-86d753e460f1a989.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/editor/page-4166a7d51cf0a57d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/exec/page-2a19c5cd3b562580.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/field/page-b6a09cde2e07521a.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-f7eae1518ca0c353.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/intake/page-456a8573ad811381.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/layout-8462d6a543cbb2d9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/live/page-2974cdfb87c0f9c9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/live-run/page-f927ffa25f3c86d1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/loops/page-abd86cd832aaa011.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/market/page-79daf68f6256adaa.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-8c3f168fc3f91939.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/morning/page-786fb4504d0f2fa9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/not-found-75209f14597dcb8f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/observatory/page-bf30affe3a85af7e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-1187a44b7515434b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/release/page-3d0910185a66ed54.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-f401ee1dd5a26e25.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/outputs/page-5dfe7604fd842784.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/page-76cf838050a8d681.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/reflection/page-7ec8e289b4c14df6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/scheduler/page-8c8ac17d52be2a79.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/sessions/page-d359ab048d63a9d9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-b8b345c880bf78d1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/settings/page-f151cc10ad026940.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/done/page-9875f103057da433.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-9789328af9a9aa62.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/share/page-bf495a1e284f4e00.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/showroom/page-a263d94bca4be22a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/tasks/page-3962eab8ec58d16e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/term/page-9abcfac07e02a542.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/today/page-bee49f927c333abb.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/trace/page-bac2d56dcb02d955.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/vault/page-937cbcc13176295c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-d09495594f7f480d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workflows/page-69cb93d1a2e57e0e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workspace/page-72ec543928d67c3e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/worktrees/page-82906eeda0186a7b.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/f2bd5257e6af88d8.css +0 -1
- /package/apps/pwa/out/_next/static/{aBi6EyMtLsrl7J8eH4kF7 → Q-7iofoxOEv1WX18S35of}/_ssgManifest.js +0 -0
|
@@ -1,7 +1,10 @@
|
|
|
1
1
|
import { CLAIM_IDLE_HOURS, PR_LABELS, STALLED_DRAFT_HOURS } from '../github/pr-labels.js';
|
|
2
2
|
import { debug } from '../debug/log.js';
|
|
3
|
-
import { decideDraft, laterMergedTwins, sameGoalPr, type DraftTriagePr } from './draft-triage-rules.js';
|
|
3
|
+
import { decideDraft, draftClaimComment, draftClaimState, draftReleaseComment, laterMergedTwins, sameGoalPr, type DraftTriagePr } from './draft-triage-rules.js';
|
|
4
|
+
import { cardPrNumber, draftTaskOwner, type TaskCard } from '../task-agent/task-hand.js';
|
|
5
|
+
import type { PrTerminalRecord } from './draft-residue.js';
|
|
4
6
|
import { branchLineageSlug } from '../cli/pr-lineage.js';
|
|
7
|
+
import { branchLineageKey } from '../harness/worktree-branch-prefix.js';
|
|
5
8
|
|
|
6
9
|
export interface SweepDraft extends DraftTriagePr {
|
|
7
10
|
readonly title: string;
|
|
@@ -35,6 +38,16 @@ export interface DraftSweepAdapters {
|
|
|
35
38
|
getClaimOwner?(repository: string, number: number): Promise<string | undefined>;
|
|
36
39
|
/** Current owner, accounting for a later claim release; only draft metrics need this distinction. */
|
|
37
40
|
getActiveClaimOwner?(repository: string, number: number): Promise<string | undefined>;
|
|
41
|
+
/** Last active claim's run id; undefined for manual claims or after a release. */
|
|
42
|
+
getActiveClaimRunId?(repository: string, number: number): Promise<string | undefined>;
|
|
43
|
+
/** When the latest claim marker is a release, its timestamp ('' if unreadable); undefined when no release is latest. */
|
|
44
|
+
getLastClaimReleaseAt?(repository: string, number: number): Promise<string | undefined>;
|
|
45
|
+
/** A complete card source; undefined means ownership is unobserved. */
|
|
46
|
+
listTaskCards?(): Promise<readonly TaskCard[] | undefined>;
|
|
47
|
+
/** Host ledger terminal records; undefined means the ledger could not be read. */
|
|
48
|
+
listPrTerminals?(): Promise<readonly PrTerminalRecord[] | undefined>;
|
|
49
|
+
commentDraft?(repository: string, number: number, body: string): Promise<void>;
|
|
50
|
+
removeLabel?(repository: string, number: number, label: string): Promise<void>;
|
|
38
51
|
/** Whether the current owned run has a self-implement.result final observation, even if its worktree remains. */
|
|
39
52
|
hasFinalRunResult?(draft: SweepDraft, repository: string): Promise<boolean | undefined>;
|
|
40
53
|
/** Per-file last change on the draft branch; undefined means file coverage is unverified. */
|
|
@@ -48,6 +61,12 @@ export interface DraftSweepAdapters {
|
|
|
48
61
|
getReviewGate?(draft: SweepDraft, repository: string): Promise<SweepReviewGate | undefined>;
|
|
49
62
|
/** One PR by number (any state); undefined means it could not be read. Only overlap metrics need it. */
|
|
50
63
|
getPr?(repository: string, number: number): Promise<SweepMergedPr | undefined>;
|
|
64
|
+
/**
|
|
65
|
+
* Stops the still-live run behind a draft that a newer, also live, same-lineage run supersedes (`--apply` only).
|
|
66
|
+
* Must reject when the run could not be stopped — the draft is then neither labelled nor closed.
|
|
67
|
+
* Absent ⇒ a live duplicate is kept, never closed.
|
|
68
|
+
*/
|
|
69
|
+
supersedeRun?(draft: SweepDraft, repository: string, newer: SweepDraft): Promise<void>;
|
|
51
70
|
}
|
|
52
71
|
|
|
53
72
|
/** Review PASS and gate posture used only by the daily old-draft count. */
|
|
@@ -65,6 +84,8 @@ export interface DraftSweepOptions {
|
|
|
65
84
|
/** Per-tick close cap; resolve it with resolveDraftSweepCloseCap. Absent or invalid ⇒ DRAFT_SWEEP_CLOSE_CAP. */
|
|
66
85
|
closeCap?: number;
|
|
67
86
|
closeCapSource?: DraftSweepCloseCapSource;
|
|
87
|
+
/** Closes already made this tick by the pod-terminal replay — they count against the same cap. */
|
|
88
|
+
alreadyClosed?: number;
|
|
68
89
|
}
|
|
69
90
|
|
|
70
91
|
export interface DraftSweepEntry {
|
|
@@ -117,11 +138,26 @@ export interface DraftMetrics {
|
|
|
117
138
|
readonly inventory: number;
|
|
118
139
|
readonly oldestAgeHours: number | null;
|
|
119
140
|
readonly needsOwner: number;
|
|
141
|
+
/** Open running claims whose last update cannot be read; neither owned nor needs-owner. */
|
|
142
|
+
readonly claimUnobserved?: number;
|
|
120
143
|
readonly converted48h: number;
|
|
121
144
|
readonly cohort48h: number;
|
|
122
145
|
readonly conversion48h: number | null;
|
|
123
146
|
}
|
|
124
147
|
|
|
148
|
+
/** Default maximum unclaimed open harness drafts for one seat. */
|
|
149
|
+
export const DRAFT_NEEDS_OWNER_SEAT_CAP = 15;
|
|
150
|
+
|
|
151
|
+
/** Compare one seat's observed needsOwner count; the caller supplies counts of open drafts by seat. */
|
|
152
|
+
export function isSeatDraftNeedsOwnerOverCap(
|
|
153
|
+
seat: string,
|
|
154
|
+
needsOwnerBySeat: Readonly<Record<string, number>>,
|
|
155
|
+
cap = DRAFT_NEEDS_OWNER_SEAT_CAP,
|
|
156
|
+
): boolean {
|
|
157
|
+
const count = Object.hasOwn(needsOwnerBySeat, seat) ? needsOwnerBySeat[seat] : undefined;
|
|
158
|
+
return typeof count === 'number' && Number.isFinite(count) && count > cap;
|
|
159
|
+
}
|
|
160
|
+
|
|
125
161
|
export async function collectDraftMetrics(repository: string, adapters: Pick<DraftSweepAdapters, 'listDrafts' | 'listRecentClosed' | 'getActiveClaimOwner'>, now: Date): Promise<DraftMetrics> {
|
|
126
162
|
const clock = now.getTime();
|
|
127
163
|
if (!Number.isFinite(clock)) throw new Error('Invalid draft metric clock');
|
|
@@ -160,7 +196,11 @@ export async function collectDraftMetrics(repository: string, adapters: Pick<Dra
|
|
|
160
196
|
return {
|
|
161
197
|
inventory: open.length,
|
|
162
198
|
oldestAgeHours: open.length ? Math.max(...open.map((pr) => Math.max(0, (clock - Date.parse(pr.createdAt)) / 3_600_000))) : null,
|
|
163
|
-
needsOwner:
|
|
199
|
+
needsOwner: open.filter((draft, index) => {
|
|
200
|
+
const state = draftClaimState(draft, now);
|
|
201
|
+
return state !== 'unobserved' && (state !== 'claimed' || !owners[index]?.trim());
|
|
202
|
+
}).length,
|
|
203
|
+
claimUnobserved: open.filter((draft) => draftClaimState(draft, now) === 'unobserved').length,
|
|
164
204
|
converted48h,
|
|
165
205
|
cohort48h: cohort.length,
|
|
166
206
|
conversion48h: cohort.length ? converted48h / cohort.length : null,
|
|
@@ -424,7 +464,9 @@ const stalledLabel = label('close', 'stalled');
|
|
|
424
464
|
const supersededLabel = label('close', 'superseded');
|
|
425
465
|
const approvalLabel = PR_LABELS.find((entry) => entry.axis === 'state' && entry.sweep.action === 'none')?.name;
|
|
426
466
|
const keepLabel = PR_LABELS.find((entry) => entry.sweep.action === 'exclude')?.name;
|
|
467
|
+
const benchLabel = PR_LABELS.find((entry) => entry.name === 'elanous:bench')!.name;
|
|
427
468
|
const releaseHoldLabel = PR_LABELS.find((entry) => entry.axis === 'addon' && entry.sweep.action === 'none')?.name;
|
|
469
|
+
const harvestableLabel = PR_LABELS.find((entry) => entry.name === 'elanous:harvestable')!.name;
|
|
428
470
|
const PAGE_SIZE = 100;
|
|
429
471
|
/** At most this many closes per tick, so a wrong rule cannot close everything at once. Default for `tools.selfImplement.draftSweepCloseCap`. */
|
|
430
472
|
export const DRAFT_SWEEP_CLOSE_CAP = 10;
|
|
@@ -575,9 +617,26 @@ export async function mapBounded<T, R>(items: readonly T[], limit: number, work:
|
|
|
575
617
|
}
|
|
576
618
|
|
|
577
619
|
function harnessDraft(draft: SweepDraft): boolean {
|
|
620
|
+
// BENCH-ISOLATED-ARMS — a bench arm PR is comparison material: the sweep never marks, supersedes or closes it.
|
|
621
|
+
if (draft.labels.includes(benchLabel)) return false;
|
|
578
622
|
return draft.branch.startsWith('self-impl/') || draft.labels.some((name) => name.startsWith('elanous:'));
|
|
579
623
|
}
|
|
580
624
|
|
|
625
|
+
/**
|
|
626
|
+
* The newest open draft of the same goal lineage that was created strictly after `draft` — a rerun
|
|
627
|
+
* (e.g. a forced requeue) of the same goal. Reads only the branch, so a draft with no task card still has a lineage.
|
|
628
|
+
* ⛔ A branch without a goal id has no lineage key and never matches.
|
|
629
|
+
*/
|
|
630
|
+
export function newerLineageDraft(draft: SweepDraft, openDrafts: readonly SweepDraft[]): SweepDraft | undefined {
|
|
631
|
+
const key = branchLineageKey(draft.branch);
|
|
632
|
+
const created = Date.parse(draft.createdAt);
|
|
633
|
+
if (key === null || !Number.isFinite(created)) return undefined;
|
|
634
|
+
return openDrafts
|
|
635
|
+
.filter((pr) => pr.number !== draft.number && branchLineageKey(pr.branch) === key
|
|
636
|
+
&& Number.isFinite(Date.parse(pr.createdAt)) && Date.parse(pr.createdAt) > created)
|
|
637
|
+
.sort((a, b) => Date.parse(b.createdAt) - Date.parse(a.createdAt) || b.number - a.number)[0];
|
|
638
|
+
}
|
|
639
|
+
|
|
581
640
|
/**
|
|
582
641
|
* Census of harness drafts older than 24h. Same-goal landing uses `sameGoalPr` unchanged.
|
|
583
642
|
* A draft counts as closable when a same-goal merged PR exists, harvestable when review PASS and the gate passed,
|
|
@@ -605,15 +664,20 @@ export function draftSweepDaily(
|
|
|
605
664
|
}
|
|
606
665
|
|
|
607
666
|
/** A failed inventory or liveness lookup is never treated as proof that a draft can be closed. */
|
|
608
|
-
export async function runDraftSweep({ repository, adapters, apply = false, now = new Date(), closeCap: requestedCap, closeCapSource: requestedSource }: DraftSweepOptions): Promise<DraftSweepResult> {
|
|
667
|
+
export async function runDraftSweep({ repository, adapters, apply = false, now = new Date(), closeCap: requestedCap, closeCapSource: requestedSource, alreadyClosed = 0 }: DraftSweepOptions): Promise<DraftSweepResult> {
|
|
609
668
|
const validCap = validCloseCap(requestedCap);
|
|
610
669
|
const closeCap = validCap ?? DRAFT_SWEEP_CLOSE_CAP;
|
|
611
670
|
const closeCapSource: DraftSweepCloseCapSource = validCap === undefined ? 'default' : requestedSource ?? 'flag';
|
|
612
671
|
const result: DraftSweepResult = { repository, apply, complete: false, entries: [], counts: {}, closeCap, closeCapSource };
|
|
672
|
+
// Built once after the inventory (review r4: no per-decision scan of the draft list).
|
|
673
|
+
const runIdByNumber = new Map<number, string>();
|
|
613
674
|
const record = (entry: DraftSweepEntry): void => {
|
|
614
675
|
result.entries.push(entry);
|
|
615
676
|
result.counts[entry.reason] = (result.counts[entry.reason] ?? 0) + 1;
|
|
616
677
|
debug.log('drafts.cleanup', 'decided', { number: entry.number, action: entry.action, reason: entry.reason });
|
|
678
|
+
debug.log('draft.residue', 'sweep-decided', { childRunId: runIdByNumber.get(entry.number) ?? null,
|
|
679
|
+
number: entry.number, prNumber: entry.number, terminalClass: null, owner: 'unknown', ownerSource: 'unknown',
|
|
680
|
+
action: entry.action, reason: entry.reason });
|
|
617
681
|
};
|
|
618
682
|
const finish = (): DraftSweepResult => {
|
|
619
683
|
debug.log('drafts.cleanup', 'summary', result.counts);
|
|
@@ -651,6 +715,7 @@ export async function runDraftSweep({ repository, adapters, apply = false, now =
|
|
|
651
715
|
return finish();
|
|
652
716
|
}
|
|
653
717
|
timing('inventory', drafts.length + merged.length);
|
|
718
|
+
for (const pr of drafts) if (pr.runId) runIdByNumber.set(pr.number, pr.runId);
|
|
654
719
|
const statuses = new Map<number, string | undefined>();
|
|
655
720
|
const finality = new Map<number, boolean | undefined>();
|
|
656
721
|
const latestFileChanges = new Map<number, Readonly<Record<string, string>> | undefined>();
|
|
@@ -690,26 +755,196 @@ export async function runDraftSweep({ repository, adapters, apply = false, now =
|
|
|
690
755
|
timing('review-gate', censused.length);
|
|
691
756
|
}
|
|
692
757
|
result.daily = draftSweepDaily(drafts, merged, now, reviewGate);
|
|
758
|
+
// Card and terminal inventories are observations, not closing authority. An unreadable source cannot mint a claim.
|
|
759
|
+
let cards: readonly TaskCard[] | undefined;
|
|
760
|
+
let terminals: readonly PrTerminalRecord[] | undefined;
|
|
761
|
+
if (apply) {
|
|
762
|
+
try { cards = await adapters.listTaskCards?.(); if (cards && !Array.isArray(cards)) cards = undefined; }
|
|
763
|
+
catch (error) { debug.log('draft.residue', 'claim-skipped', { prNumber: null, owner: null, runId: null, reason: `cards-unreadable: ${sweepFailureReason(error)}` }); }
|
|
764
|
+
try { terminals = await adapters.listPrTerminals?.(); if (terminals && !Array.isArray(terminals)) terminals = undefined; }
|
|
765
|
+
catch (error) { debug.log('draft.residue', 'claim-skipped', { prNumber: null, owner: null, runId: null, reason: `terminals-unreadable: ${sweepFailureReason(error)}` }); }
|
|
766
|
+
}
|
|
693
767
|
result.complete = true;
|
|
694
|
-
let closes = 0;
|
|
768
|
+
let closes = Number.isSafeInteger(alreadyClosed) && alreadyClosed > 0 ? alreadyClosed : 0;
|
|
695
769
|
let unobserved = 0;
|
|
696
770
|
let claimed = 0;
|
|
697
771
|
let claimExpired = 0;
|
|
698
772
|
for (const listedDraft of drafts) {
|
|
699
|
-
const draft = { ...listedDraft, latestFileChanges: latestFileChanges.get(listedDraft.number) };
|
|
773
|
+
const draft = { ...listedDraft, labels: [...listedDraft.labels], latestFileChanges: latestFileChanges.get(listedDraft.number) };
|
|
774
|
+
let releasedThisTick = false;
|
|
775
|
+
let claimWriteFailed = false;
|
|
776
|
+
let claimWriteError: string | undefined;
|
|
777
|
+
let claimPartialApplied = false;
|
|
778
|
+
let partialClaimUnowned = false;
|
|
779
|
+
let releasePending = false;
|
|
780
|
+
if (apply && harnessDraft(draft) && !draft.labels.some((name) => name === approvalLabel || name === keepLabel || name === releaseHoldLabel)
|
|
781
|
+
&& stateLabels.filter((state) => draft.labels.includes(state.name)).length <= 1
|
|
782
|
+
&& !draft.labels.includes(supersededLabel)) {
|
|
783
|
+
const logClaim = (event: 'claim-marked' | 'claim-released' | 'claim-skipped', owner: string | null, runId: string | null, reason: string) =>
|
|
784
|
+
debug.log('draft.residue', event, { prNumber: draft.number, owner, runId, reason });
|
|
785
|
+
try {
|
|
786
|
+
const hasTerminal = terminals?.some((record) => record.prNumber === draft.number
|
|
787
|
+
&& record.repository?.toLowerCase() === repository.toLowerCase());
|
|
788
|
+
const claimRunId = hasTerminal || cards?.length || draft.labels.includes(runningLabel)
|
|
789
|
+
? await adapters.getActiveClaimRunId?.(repository, draft.number) : undefined;
|
|
790
|
+
// A label write can succeed before the claim comment fails. Read the comment too: the label alone
|
|
791
|
+
// cannot prove ownership, and a manual claim (without a run id) must not be overwritten.
|
|
792
|
+
const claimOwner = claimRunId || cards?.length || draft.labels.includes(runningLabel)
|
|
793
|
+
? await adapters.getActiveClaimOwner?.(repository, draft.number) : undefined;
|
|
794
|
+
const runTerminal = claimRunId && terminals?.find((record) => record.prNumber === draft.number
|
|
795
|
+
&& record.repository?.toLowerCase() === repository.toLowerCase()
|
|
796
|
+
&& (record.childRunId === claimRunId || cards?.some((card) => card.runId === claimRunId
|
|
797
|
+
&& card.runChildId === record.childRunId
|
|
798
|
+
&& (cardPrNumber(card) === draft.number || (draft.runId && (draft.runId === card.runId || draft.runId === card.runChildId))))));
|
|
799
|
+
// A seat-attributed terminal releases only its own seat's claim; another owner's claim naming the run is kept.
|
|
800
|
+
const ownerMismatch = Boolean(runTerminal && runTerminal.ownerSource === 'seat' && claimOwner && runTerminal.owner !== claimOwner);
|
|
801
|
+
if (ownerMismatch) logClaim('claim-skipped', claimOwner ?? null, claimRunId ?? null, 'terminal-owner-mismatch');
|
|
802
|
+
const terminal = ownerMismatch ? undefined : runTerminal;
|
|
803
|
+
releasePending = Boolean(terminal);
|
|
804
|
+
if (terminal && adapters.commentDraft && (!draft.labels.includes(runningLabel) || adapters.removeLabel)) {
|
|
805
|
+
if (draft.labels.includes(runningLabel)) {
|
|
806
|
+
await adapters.removeLabel!(repository, draft.number, runningLabel);
|
|
807
|
+
draft.labels.splice(draft.labels.indexOf(runningLabel), 1);
|
|
808
|
+
claimPartialApplied = true;
|
|
809
|
+
}
|
|
810
|
+
await adapters.commentDraft(repository, draft.number, draftReleaseComment(now, `run ${claimRunId} · ${terminal.terminalClass}`));
|
|
811
|
+
releasedThisTick = true;
|
|
812
|
+
draft.updatedAt = now.toISOString();
|
|
813
|
+
logClaim('claim-released', terminal.owner, claimRunId ?? null, terminal.terminalClass);
|
|
814
|
+
} else if (!releasePending && !draft.labels.includes(harvestableLabel)
|
|
815
|
+
&& (draftClaimState(draft, now) === 'unclaimed'
|
|
816
|
+
|| (draft.labels.includes(runningLabel) && adapters.getActiveClaimOwner && adapters.getActiveClaimRunId
|
|
817
|
+
&& !claimOwner && !claimRunId))) {
|
|
818
|
+
partialClaimUnowned = draft.labels.includes(runningLabel) && !claimOwner && !claimRunId;
|
|
819
|
+
const owner = cards && draftTaskOwner(cards, draft);
|
|
820
|
+
const runId = owner?.runChildId ?? owner?.runId;
|
|
821
|
+
const ownerTerminal = owner ? terminals?.find((record) => record.prNumber === draft.number
|
|
822
|
+
&& record.repository?.toLowerCase() === repository.toLowerCase()
|
|
823
|
+
&& (record.childRunId === runId || record.childRunId === owner.runId)) : undefined;
|
|
824
|
+
// An explicit release (manual `drafts claim --release` or an earlier automatic one) is respected unless the
|
|
825
|
+
// owning card was created after it — that card is a resume, not the run the release ended.
|
|
826
|
+
const releasedAt = owner?.seat && runId && !claimOwner && !claimRunId
|
|
827
|
+
? await adapters.getLastClaimReleaseAt?.(repository, draft.number) : undefined;
|
|
828
|
+
const releaseRespected = releasedAt !== undefined
|
|
829
|
+
&& !(Date.parse(owner!.createdAt) > Date.parse(releasedAt));
|
|
830
|
+
if (partialClaimUnowned && owner?.seat && runId && ownerTerminal && adapters.removeLabel && adapters.commentDraft
|
|
831
|
+
&& !(ownerTerminal.ownerSource === 'seat' && ownerTerminal.owner !== owner.seat)) {
|
|
832
|
+
// Label-only partial claim (comment write failed) whose run has since ended: undo the label and say so.
|
|
833
|
+
await adapters.removeLabel(repository, draft.number, runningLabel);
|
|
834
|
+
draft.labels.splice(draft.labels.indexOf(runningLabel), 1);
|
|
835
|
+
claimPartialApplied = true;
|
|
836
|
+
await adapters.commentDraft(repository, draft.number, draftReleaseComment(now, `run ${runId} · ${ownerTerminal.terminalClass}`));
|
|
837
|
+
releasedThisTick = true;
|
|
838
|
+
draft.updatedAt = now.toISOString();
|
|
839
|
+
logClaim('claim-released', owner.seat, runId, `partial-claim:${ownerTerminal.terminalClass}`);
|
|
840
|
+
} else if (owner?.seat && runId && terminals && !claimOwner && !claimRunId
|
|
841
|
+
&& !merged.some((pr) => pr.number !== draft.number && sameGoalPr(draft, pr))
|
|
842
|
+
&& !ownerTerminal && !releaseRespected && adapters.commentDraft) {
|
|
843
|
+
if (!draft.labels.includes(runningLabel)) {
|
|
844
|
+
await adapters.setLabels(repository, draft.number, { add: runningLabel,
|
|
845
|
+
remove: stateLabels.filter((state) => draft.labels.includes(state.name)).map((state) => state.name) });
|
|
846
|
+
draft.labels.splice(0, draft.labels.length, ...draft.labels.filter((name) => !stateLabels.some((state) => state.name === name)), runningLabel);
|
|
847
|
+
claimPartialApplied = true;
|
|
848
|
+
}
|
|
849
|
+
await adapters.commentDraft(repository, draft.number, draftClaimComment(owner.seat, now, `run ${runId}`));
|
|
850
|
+
draft.updatedAt = now.toISOString();
|
|
851
|
+
logClaim('claim-marked', owner.seat, runId, 'unique-card');
|
|
852
|
+
} else logClaim('claim-skipped', owner?.seat ?? null, runId ?? null,
|
|
853
|
+
!cards ? 'cards-unobserved' : !owner ? 'owner-ambiguous-or-missing' : !terminals ? 'terminals-unobserved'
|
|
854
|
+
: claimRunId || claimOwner ? 'claim-already-owned' : ownerTerminal ? 'run-terminal'
|
|
855
|
+
: releaseRespected ? 'release-respected' : 'run-not-live-or-write-unavailable');
|
|
856
|
+
}
|
|
857
|
+
} catch (error) {
|
|
858
|
+
claimWriteFailed = true;
|
|
859
|
+
claimWriteError = String(error);
|
|
860
|
+
logClaim('claim-skipped', null, null, `claim-write-failed: ${sweepFailureReason(error)}`);
|
|
861
|
+
}
|
|
862
|
+
}
|
|
700
863
|
const runStatus = statuses.get(draft.number);
|
|
701
864
|
const finalRunResult = finality.get(draft.number);
|
|
702
865
|
const states = stateLabels.filter((state) => draft.labels.includes(state.name));
|
|
703
866
|
const contradiction = states.length > 1 || draft.labels.includes(approvalLabel ?? '');
|
|
867
|
+
if (releasedThisTick || claimWriteFailed || partialClaimUnowned || releasePending) {
|
|
868
|
+
record({ number: draft.number, action: 'keep', reason: releasedThisTick ? 'claim-released'
|
|
869
|
+
: claimWriteFailed ? 'claim-write-unobserved' : releasePending ? 'claim-release-unobserved' : 'claim-owner-unobserved', applied: releasedThisTick,
|
|
870
|
+
...(claimWriteFailed ? { error: claimWriteError, ...(claimPartialApplied ? { partialApplied: true } : {}) } : {}) });
|
|
871
|
+
continue;
|
|
872
|
+
}
|
|
704
873
|
if (draft.labels.includes(releaseHoldLabel ?? '') || (!contradiction && draft.labels.includes(keepLabel ?? ''))) {
|
|
705
874
|
const held = draft.labels.includes(keepLabel ?? '') ? keepLabel : releaseHoldLabel;
|
|
706
875
|
record({ number: draft.number, action: 'keep', reason: `label:${held}`, applied: false });
|
|
707
876
|
continue;
|
|
708
877
|
}
|
|
709
|
-
const
|
|
878
|
+
const claimState = contradiction ? 'unclaimed' : draftClaimState(draft, now);
|
|
879
|
+
const isClaimed = claimState !== 'unclaimed';
|
|
710
880
|
const ageHours = (now.getTime() - Date.parse(draft.createdAt)) / 3_600_000;
|
|
711
881
|
const idleHours = typeof draft.updatedAt === 'string' && Number.isFinite(Date.parse(draft.updatedAt))
|
|
712
882
|
? (now.getTime() - Date.parse(draft.updatedAt)) / 3_600_000 : NaN;
|
|
883
|
+
// A newer open draft of the same goal lineage (a rerun, e.g. a forced requeue) supersedes this one even when
|
|
884
|
+
// its running claim is fresh or its run is still live. Holds, merged twins and the title-based duplicate rule keep their priority.
|
|
885
|
+
const lineageNewer = contradiction || draft.labels.includes(harvestableLabel) ? undefined : newerLineageDraft(draft, drafts);
|
|
886
|
+
if (lineageNewer) {
|
|
887
|
+
const base = decideDraft({ draft, runStatus, mergedTwins: merged, openDrafts: drafts, liveBranches,
|
|
888
|
+
finalRunResult, ageHours: runStatus ? ageHours : idleHours });
|
|
889
|
+
if (!base.reason.startsWith('label:') && !base.reason.startsWith('superseded-by #') && !base.reason.startsWith('duplicate-of-open #')) {
|
|
890
|
+
const live = (status: string | undefined, branch: string) => status === 'running' || status === 'probable-running'
|
|
891
|
+
|| (status !== 'self-implement.result final' && liveBranches.has(branch));
|
|
892
|
+
const runLive = live(runStatus, draft.branch);
|
|
893
|
+
const lineageKey = branchLineageKey(draft.branch);
|
|
894
|
+
const reason = `duplicate-of-open #${lineageNewer.number} (lineage ${lineageKey})${runLive ? ` · stop run ${draft.runId ?? 'unknown'}` : ''}`;
|
|
895
|
+
// Every lineage outcome that does not close falls through to the existing rules (preservation contract):
|
|
896
|
+
// a duplicate this rule cannot settle is decided exactly as it was before this rule existed.
|
|
897
|
+
const fallThrough = (why: string) => {
|
|
898
|
+
try { debug.log('self-dev.draft-sweep', 'lineage-fall-through', { number: draft.number, newer: lineageNewer.number, lineageKey, why }); } catch { /* fail-soft */ }
|
|
899
|
+
};
|
|
900
|
+
if (runLive && !adapters.supersedeRun) fallThrough('lineage-duplicate-run-live');
|
|
901
|
+
// Safety (OP 10-11): a live run is stopped only when the newer run of the same lineage is itself live —
|
|
902
|
+
// never trade a running attempt for one that already ended or was never observed running.
|
|
903
|
+
else if (runLive && !live(statuses.get(lineageNewer.number), lineageNewer.branch)) fallThrough('lineage-newer-run-not-live');
|
|
904
|
+
else if (closes >= closeCap) {
|
|
905
|
+
record({ number: draft.number, action: 'keep', reason: 'close-cap', applied: false });
|
|
906
|
+
continue;
|
|
907
|
+
} else {
|
|
908
|
+
let stopFailed = false;
|
|
909
|
+
// --apply only: the run is stopped before anything is written; a stop that cannot be confirmed writes nothing.
|
|
910
|
+
if (apply && runLive) {
|
|
911
|
+
const observed = { number: draft.number, newer: lineageNewer.number, runId: draft.runId ?? null, newerRunId: lineageNewer.runId ?? null, lineageKey };
|
|
912
|
+
try {
|
|
913
|
+
await adapters.supersedeRun!(draft, repository, lineageNewer);
|
|
914
|
+
try { debug.log('self-dev.draft-sweep', 'supersede-run', observed); } catch { /* fail-soft */ }
|
|
915
|
+
} catch (error) {
|
|
916
|
+
stopFailed = true;
|
|
917
|
+
try { debug.log('self-dev.draft-sweep', 'supersede-run-failed', { ...observed, reason: sweepFailureReason(error) }, { level: 'warn' }); } catch { /* fail-soft */ }
|
|
918
|
+
}
|
|
919
|
+
}
|
|
920
|
+
if (stopFailed) fallThrough('supersede-run-failed');
|
|
921
|
+
else {
|
|
922
|
+
// A close is counted against the cap only once it is decided here; a failed write gives the slot back.
|
|
923
|
+
closes += 1;
|
|
924
|
+
const entry: DraftSweepEntry = { number: draft.number, action: 'close', reason, statusLabel: supersededLabel, applied: false };
|
|
925
|
+
record(entry);
|
|
926
|
+
if (!apply) continue;
|
|
927
|
+
let labelsChanged = false;
|
|
928
|
+
try {
|
|
929
|
+
if (!draft.labels.includes(supersededLabel)) {
|
|
930
|
+
await adapters.setLabels(repository, draft.number, {
|
|
931
|
+
add: supersededLabel, remove: states.map((state) => state.name).filter((name) => name !== supersededLabel),
|
|
932
|
+
});
|
|
933
|
+
labelsChanged = true;
|
|
934
|
+
}
|
|
935
|
+
await adapters.closeDraft(repository, draft.number,
|
|
936
|
+
`Draft sweep: ${reason} (https://github.com/${repository}/pull/${lineageNewer.number}). Branch preserved.`);
|
|
937
|
+
entry.applied = true;
|
|
938
|
+
} catch (error) {
|
|
939
|
+
if (labelsChanged) entry.partialApplied = true;
|
|
940
|
+
else closes -= 1;
|
|
941
|
+
entry.error = String(error);
|
|
942
|
+
}
|
|
943
|
+
continue;
|
|
944
|
+
}
|
|
945
|
+
}
|
|
946
|
+
}
|
|
947
|
+
}
|
|
713
948
|
// An unobserved claim may still have a merged twin: liveness/holds retain their priority,
|
|
714
949
|
// but a superseded draft must not be hidden by the six-hour claim window.
|
|
715
950
|
const mergedDecision = isClaimed ? decideDraft({ draft, runStatus, mergedTwins: merged, openDrafts: drafts, liveBranches,
|
|
@@ -722,16 +957,16 @@ export async function runDraftSweep({ repository, adapters, apply = false, now =
|
|
|
722
957
|
}
|
|
723
958
|
// Without an observed update time, neither expiration nor a fallback to creation time can authorize mutation —
|
|
724
959
|
// but a merged twin does not need the update time, so superseded keeps its priority over the unobserved claim.
|
|
725
|
-
if (
|
|
960
|
+
if (claimState === 'unobserved' && !supersededClaim) {
|
|
726
961
|
record({ number: draft.number, action: 'keep', reason: 'claim-update-unobserved', applied: false });
|
|
727
962
|
continue;
|
|
728
963
|
}
|
|
729
|
-
if (
|
|
964
|
+
if (claimState === 'claimed' && !supersededClaim) {
|
|
730
965
|
claimed += 1;
|
|
731
966
|
record({ number: draft.number, action: 'keep', reason: `label:running(<${CLAIM_IDLE_HOURS}h)`, applied: false });
|
|
732
967
|
continue;
|
|
733
968
|
}
|
|
734
|
-
if (
|
|
969
|
+
if (claimState === 'expired' && !supersededClaim) {
|
|
735
970
|
claimExpired += 1;
|
|
736
971
|
if (liveBranches.has(draft.branch) && finalRunResult === undefined
|
|
737
972
|
&& runStatus !== 'running' && runStatus !== 'probable-running') {
|
|
@@ -772,6 +1007,12 @@ export async function runDraftSweep({ repository, adapters, apply = false, now =
|
|
|
772
1007
|
}
|
|
773
1008
|
let decision = supersededClaim ? mergedDecision! : decideDraft({ draft, runStatus, mergedTwins: merged, openDrafts: drafts, liveBranches,
|
|
774
1009
|
finalRunResult, ageHours: runStatus ? ageHours : idleHours });
|
|
1010
|
+
const fallback = decision.reason === 'unobserved' || decision.reason === 'stale-unobserved'
|
|
1011
|
+
|| decision.reason === 'recent' || decision.reason.startsWith('recent (') || decision.reason.startsWith('stale-ended-run');
|
|
1012
|
+
if (!contradiction && draft.labels.includes(harvestableLabel) && fallback) {
|
|
1013
|
+
decision = Number.isFinite(idleHours) && idleHours >= STALLED_DRAFT_HOURS
|
|
1014
|
+
? { action: 'close', reason: 'harvest-expired' } : { action: 'keep', reason: 'harvestable' };
|
|
1015
|
+
}
|
|
775
1016
|
if (!runStatus && (decision.reason === 'unobserved' || decision.reason === 'stale-unobserved')) unobserved += 1;
|
|
776
1017
|
if (!contradiction && decision.action === 'close') {
|
|
777
1018
|
if (closes >= closeCap) decision = { action: 'keep', reason: 'close-cap' };
|
|
@@ -799,6 +1040,8 @@ export async function runDraftSweep({ repository, adapters, apply = false, now =
|
|
|
799
1040
|
if (action === 'close') {
|
|
800
1041
|
await adapters.closeDraft(repository, draft.number, decision.reason === 'stale-unobserved'
|
|
801
1042
|
? `Draft sweep: run unobserved — no run record reachable here, no host worktree for this branch, idle ≥${STALLED_DRAFT_HOURS}h. Closed as stalled. Branch preserved; reopen to restore.`
|
|
1043
|
+
: decision.reason === 'harvest-expired'
|
|
1044
|
+
? `Draft sweep: harvest-expired — 종단이 수확 대상으로 표시한 뒤 ${STALLED_DRAFT_HOURS}h 동안 수확 없음. Branch preserved; reopen to restore.`
|
|
802
1045
|
: `Draft sweep: ${decision.reason}${decision.reason.startsWith('superseded-by #')
|
|
803
1046
|
? ` (https://github.com/${repository}/pull/${decision.reason.slice('superseded-by #'.length).match(/^\d+/)![0]})` : ''}. Branch preserved.`);
|
|
804
1047
|
}
|
|
@@ -811,7 +1054,8 @@ export async function runDraftSweep({ repository, adapters, apply = false, now =
|
|
|
811
1054
|
timing('decide', drafts.length);
|
|
812
1055
|
try { debug.log('self-dev.draft-sweep', 'timing', { phase: 'total', ms: Date.now() - started, count: drafts.length, closed: closes, closeCap, closeCapSource }); } catch { /* fail-soft */ }
|
|
813
1056
|
result.unobserved = unobserved;
|
|
814
|
-
|
|
1057
|
+
// `closed` stays «closed by this sweep»; replay closes only consume the shared cap (alreadyClosed).
|
|
1058
|
+
result.closed = closes - (Number.isSafeInteger(alreadyClosed) && alreadyClosed > 0 ? alreadyClosed : 0);
|
|
815
1059
|
result.claimed = claimed;
|
|
816
1060
|
result.claimExpired = claimExpired;
|
|
817
1061
|
return finish();
|
|
@@ -1,6 +1,22 @@
|
|
|
1
|
-
import { PR_LABELS, STALLED_DRAFT_HOURS } from '../github/pr-labels.js';
|
|
1
|
+
import { CLAIM_IDLE_HOURS, PR_LABELS, STALLED_DRAFT_HOURS } from '../github/pr-labels.js';
|
|
2
2
|
import { RELEASE_PATH_LABEL } from './release-path-guard.js';
|
|
3
3
|
|
|
4
|
+
export function draftClaimComment(owner: string, at: Date, note?: string): string {
|
|
5
|
+
return `🔧 처리 중 — owner ${owner} · ${at.toISOString()}${note?.trim() ? ` · ${note.trim()}` : ''}`;
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
export function draftReleaseComment(at: Date, note?: string): string {
|
|
9
|
+
return `🔧 처리 끝 — ${at.toISOString()}${note?.trim() ? ` · ${note.trim()}` : ''}`;
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
/** No timestamp is an observation gap, not an expired claim. */
|
|
13
|
+
export function draftClaimState(draft: { labels: readonly string[]; updatedAt?: string }, now: Date): 'claimed' | 'expired' | 'unclaimed' | 'unobserved' {
|
|
14
|
+
if (!draft.labels.includes('elanous:running') || draft.labels.includes('elanous:harvestable')) return 'unclaimed';
|
|
15
|
+
const updated = typeof draft.updatedAt === 'string' ? Date.parse(draft.updatedAt) : NaN;
|
|
16
|
+
if (!Number.isFinite(updated)) return 'unobserved';
|
|
17
|
+
return (now.getTime() - updated) / 3_600_000 < CLAIM_IDLE_HOURS ? 'claimed' : 'expired';
|
|
18
|
+
}
|
|
19
|
+
|
|
4
20
|
export interface DraftTriagePr {
|
|
5
21
|
number: number;
|
|
6
22
|
title?: string;
|
|
@@ -44,6 +60,16 @@ export const isAutoTitle = (title: string): boolean =>
|
|
|
44
60
|
/^[\w./-]+:\s*[^\s,]+\.[a-z0-9]+(?:\s*,\s*[^\s,]+\.[a-z0-9]+)*$/i.test(title.trim());
|
|
45
61
|
|
|
46
62
|
/** Same goal (TC 10-05): ① both carry a goal identifier → compare it ② otherwise exact title ⊕ both harness drafts ⊕ same branch stem, never an auto title ③ else false. */
|
|
63
|
+
/** Same goal only when a verified goal identifier matches on both sides (branch goal id, else the body's «골:» line).
|
|
64
|
+
* Unlike sameGoalPr it never falls back to titles or branch stems — used where a match closes a PR. */
|
|
65
|
+
export function sameVerifiedGoal(a: DraftTriagePr, b: DraftTriagePr): boolean {
|
|
66
|
+
const idA = goalId(a.branch), idB = goalId(b.branch);
|
|
67
|
+
if (idA && idB) return idA === idB;
|
|
68
|
+
// Review r7: a branch goal id on only one side cannot be checked against the other — never close on body text then.
|
|
69
|
+
if (idA || idB) return false;
|
|
70
|
+
const textA = goalText(a.body), textB = goalText(b.body);
|
|
71
|
+
return Boolean(textA && textB && textA === textB);
|
|
72
|
+
}
|
|
47
73
|
export function sameGoalPr(a: DraftTriagePr, b: DraftTriagePr): boolean {
|
|
48
74
|
const idA = goalId(a.branch), idB = goalId(b.branch);
|
|
49
75
|
if (idA && idB) return idA === idB;
|
|
@@ -103,3 +103,9 @@ export function intakeTakesQueue(label: 'queued' | 'direct', route: Pick<Journey
|
|
|
103
103
|
const graphQueues = route.source === 'graph' ? route.to === 'queue' : label === 'queued';
|
|
104
104
|
return graphQueues && eligible;
|
|
105
105
|
}
|
|
106
|
+
|
|
107
|
+
/** 병합 직전 동결 검사의 «승인 요구» — 동결이 아닌(open) 병합을 그래프가 hold 로 보내면 true.
|
|
108
|
+
* ⛔ 그래프가 답을 못 내면(code-default) false — 오늘의 입장 판정 그대로. 동결·선점(frozen·taken)은 이미 코드가 정했다. */
|
|
109
|
+
export function freezeCheckHolds(label: 'open' | 'frozen' | 'taken', route: Pick<JourneyRoute, 'source' | 'to'>): boolean {
|
|
110
|
+
return label === 'open' && route.source === 'graph' && route.to === 'hold';
|
|
111
|
+
}
|