elanous 0.2.28 → 0.2.29
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/apps/pwa/out/404/index.html +1 -1
- package/apps/pwa/out/404.html +1 -1
- package/apps/pwa/out/_next/static/{y1ltt7oCZxVpC6zVPhZ2O → cIpv5nU9AycwYWZI9H589}/_buildManifest.js +1 -1
- package/apps/pwa/out/_next/static/chunks/{ab4d57c2.e90bc2cb31949045.js → 058a98ba.7eb28d5e6dc03565.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{4565-67e4c620597965c8.js → 1015-9cba22a5a4554797.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/1084-4e66af7376a18db7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1106.3a6410b7b0c70ad4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1127.32fc642f70423506.js +8 -0
- package/apps/pwa/out/_next/static/chunks/{1516.83dd2c1b86b4e507.js → 1142.65d002789ab3af7d.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/1189-d9b8e1995a831fae.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1224.6da98c7ad0eb7dd8.js +34 -0
- package/apps/pwa/out/_next/static/chunks/1370.4e3e2558f111fd5d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1514-b7da377fdc4eb17a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1516.dfaceff3fd2d0e0d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1577.3c24c32584e10d70.js +286 -0
- package/apps/pwa/out/_next/static/chunks/161.130a569855c4d68c.js +24 -0
- package/apps/pwa/out/_next/static/chunks/1782-59db1b5aa06df38a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{1743.563d3168e95825ef.js → 1852.7f7b53991fcb99ef.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/1864.16da9556e78a9236.js +1 -0
- package/apps/pwa/out/_next/static/chunks/1b6f6b2a.aff090122be3726e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2341.e8a9135e5b910dd5.js +36 -0
- package/apps/pwa/out/_next/static/chunks/257.10afdbe3520f2fc2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2658.87550e692dc493f6.js +64 -0
- package/apps/pwa/out/_next/static/chunks/2673.85e2f02efae7a85f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2766-bee623b37472ed63.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2794.6d836872b0bf43e2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2806.eb57ced1a528ed39.js +1 -0
- package/apps/pwa/out/_next/static/chunks/283.7a121c4910e6dad7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{65ebff95.081daeff622d238e.js → 285adb1a.5654e605dddf86d2.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/2870.1dc29aa5fc01f09f.js +115 -0
- package/apps/pwa/out/_next/static/chunks/293.fd38e77ce5d48103.js +1 -0
- package/apps/pwa/out/_next/static/chunks/2993-5952a1cd3fd5d441.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3160-95c96f4d2a21dd26.js +1 -0
- package/apps/pwa/out/_next/static/chunks/32-a523427c5bd5ed00.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3280.af38002a6424a905.js +90 -0
- package/apps/pwa/out/_next/static/chunks/328bb3ab-6628a1114fe3fb3b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3292-5ddffdb2f517b44f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{9917-9e26abc5f7772735.js → 3396-97b97928c49190c9.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{6196.34d6b229079e9e28.js → 3403.7199205e65124486.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/3523.d3231daaf7aba993.js +1 -0
- package/apps/pwa/out/_next/static/chunks/3763.577de3181e1e6ea0.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4138-cc56b0938ef72783.js +1 -0
- package/apps/pwa/out/_next/static/chunks/419.736c0d6f426249a7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4255-8350c43d307a8875.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{6def8a8e.c81f9ca41028eccf.js → 425cfc4d.fb91158e3971c39f.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/4352.a4954693499c2714.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4421-f2dcbc6fd80ec013.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4513-51b94aeee37c9905.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{16e57f67.3ea19e893461e611.js → 46bd8bea.2f4b4099172fcdb7.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{5081.a240b63fad28663a.js → 4759.1f76713aefb87db5.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/4928-c3b72f99aa588699.js +1 -0
- package/apps/pwa/out/_next/static/chunks/4986-f9fc0283fb325219.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5014.671a7b9f69c2b7b1.js +94 -0
- package/apps/pwa/out/_next/static/chunks/5137.d398e24710b3feb6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5298.0bea74885cabe754.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5315.74c53a39739b11c4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5317-8b1df8d02105cd07.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5358-33051f41a2b239af.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5388.a2ec02501f714ad5.js +62 -0
- package/apps/pwa/out/_next/static/chunks/5395.e6ac948a2d15058d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5409-f282bf533c151849.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5466.d0f4aba9d52acfa8.js +27 -0
- package/apps/pwa/out/_next/static/chunks/5564.3d28b353470fe305.js +104 -0
- package/apps/pwa/out/_next/static/chunks/{9974.e77b4ff4884557b3.js → 5591.a35e7a217734a8b9.js} +2 -2
- package/apps/pwa/out/_next/static/chunks/569.b0cbfb4dee4a167a.js +93 -0
- package/apps/pwa/out/_next/static/chunks/5835-72465b73a8bb8d74.js +1 -0
- package/apps/pwa/out/_next/static/chunks/5941.045d6093139e1f7a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{5492-e05e26a033ba80d2.js → 6013-2f769370d8b4c2c6.js} +3 -3
- package/apps/pwa/out/_next/static/chunks/6228.47cabb83564dfe54.js +24 -0
- package/apps/pwa/out/_next/static/chunks/6457-8d1993002a87d0fe.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6513.ef54cfae52351982.js +2 -0
- package/apps/pwa/out/_next/static/chunks/{5408.377c8c543635b81f.js → 6534.1ab00f370db7b105.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/6582.13d245bf87df69f1.js +148 -0
- package/apps/pwa/out/_next/static/chunks/6655.c33f6acc2c61bb89.js +149 -0
- package/apps/pwa/out/_next/static/chunks/6731-9d7195af289c8d4c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6733.0be05b1db9279fc5.js +79 -0
- package/apps/pwa/out/_next/static/chunks/6742-90937146253a8b9e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{8578.dff22d988cc2b106.js → 6767.1fcfc9b8be83975f.js} +16 -16
- package/apps/pwa/out/_next/static/chunks/6776.06ff1e3b464cc607.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{9311.24c8f5ea793253dd.js → 6853.cc5174a9dee59593.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/687-816858f77a396a4e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6888.72c7b8cfb02a7e61.js +1 -0
- package/apps/pwa/out/_next/static/chunks/6993.c17c828ac3ef3253.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7076.9f27ef666b0cefdd.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7113.1403c5d451804e8c.js +287 -0
- package/apps/pwa/out/_next/static/chunks/7169.9dd603c726c2cd7c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7247-e3ec21f761f86710.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7261-a47b72f96f5199df.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7335-5cda81ac90310077.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7356-c2e4af090546e2d4.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{94.4cfed21c0b781a06.js → 7375.050ea0d72968e49f.js} +16 -16
- package/apps/pwa/out/_next/static/chunks/738-59518742078fda71.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7385.a7375f10db73243a.js +77 -0
- package/apps/pwa/out/_next/static/chunks/7445.cf1cf2fe109bcd96.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7505.a2057432ab6ef99a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7515.31f45fac1f9c70cb.js +74 -0
- package/apps/pwa/out/_next/static/chunks/7658-d4ce8c72a9548a91.js +1 -0
- package/apps/pwa/out/_next/static/chunks/7725-4f83d5541fbdb81b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8107-0b1ae46bc5bcb788.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8132.bfea2f016ce8d992.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8332.6f0f49df772e163b.js +23 -0
- package/apps/pwa/out/_next/static/chunks/{7483.ba01c6c209b81bba.js → 8398.73a19b39715eda04.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/{2846.d6a433b8663819a5.js → 8471.8d2a8c74f09c36ff.js} +3 -3
- package/apps/pwa/out/_next/static/chunks/8672.e299832bc7d18ee2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8735.f1ef798a5f260f6f.js +226 -0
- package/apps/pwa/out/_next/static/chunks/{5785-ea8d2c633b6688e3.js → 8767-2f6a634f5abeaa01.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/8774-88f67f7d8d53d299.js +1 -0
- package/apps/pwa/out/_next/static/chunks/8782.252e5a405d86e4ed.js +32 -0
- package/apps/pwa/out/_next/static/chunks/8795.32573a185af18c7b.js +41 -0
- package/apps/pwa/out/_next/static/chunks/909-9ed7aa0dba804316.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9100.22b0301256827007.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9140-dde77575570bc71e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{4593.10f5b9bd702d4a6c.js → 9143.ff14585db1d275ff.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/9292-a7ad9a01c7044b93.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9517.00627dc51b02821c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9725.dcbb585652d8e9c5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9761.a3ebf5c389c24ddc.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{4204.a409ab6250c0f6a8.js → 9907.49be0fcadaf214b5.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/9972.834d2b2b7d48f1ed.js +1 -0
- package/apps/pwa/out/_next/static/chunks/9995-1a90486f5ae01546.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{973cbf1b.3bbcf2b41548eca7.js → a435ad95.577add051b4facb2.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/_not-found/page-83372d8b5863ebf7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/approvals/page-d69256d7613c140a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/autopilot/page-352c5e9ba3f9b858.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/board/page-69f1d725524201a8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/botlab/{page-fa46d4588e8442c2.js → page-a5635eba0d73b84e.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/bots/page-ad9181d84285e4ea.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ceo/{page-66ad46ed0279feb9.js → page-86feb08080261a2f.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/chat/page-ffa15987e4756d03.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/consult/page-11a3ab44ac327cc1.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/control/page-6309b11c4264d24d.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/decisions/page-8800472079612e87.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/design-check/page-d387bf3f2301882a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/editor/page-048f88d8c8658da6.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/exec/page-6c14f9739b7f6880.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/field/page-2834f44f64e98d74.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/healthz/route-83372d8b5863ebf7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/inside/page-a13df6f88e824887.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/intake/page-8a4397248754cf2b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/layout-daf0bd329360a336.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/live/page-f7ef1c28764cb476.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/live-run/page-61e74f28b9353dac.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/loops/{page-646b50f63b6fe732.js → page-8aaa6dedc4c10dfb.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/market/page-294602ba649be829.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-5fa5f41ed3fce323.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/morning/{page-6f131b51193a36f9.js → page-33bf667a5fb297bf.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/app/not-found-5ae3cbd6e5dba515.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/observatory/page-eb867d16ad6fdede.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-1ab789fa68682f7e.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/release/page-6fd41b5b6ff13a71.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-fb3d5f7642c99fba.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/outputs/page-70f705b2b5ed42ca.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/page-c9c93b358a7667b5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/reflection/page-1563c556b81c96ed.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/scheduler/page-ce89c20c45b3a673.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/sessions/page-423ae63d786f4ee9.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-591a5378a4c4447c.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/settings/page-a250496b19a5824b.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/done/page-c36a9277febc5911.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/layout-83372d8b5863ebf7.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/setup/page-29900ed0011b2c83.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/share/page-a5de57edc6d7f942.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/showroom/page-16bdd4c9f40498df.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/tasks/page-75e946e6e71cc6d8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/term/page-9eb56166774eb256.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/today/page-1c5f9ef35dbb22c5.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/trace/page-657ff9985e508498.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/vault/page-22dc72499da68fb2.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-9f92737b8766009a.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workflows/page-094ad334e40f8169.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/workspace/page-8bcd379852ff6287.js +1 -0
- package/apps/pwa/out/_next/static/chunks/app/worktrees/page-6b04413f280cd344.js +1 -0
- package/apps/pwa/out/_next/static/chunks/{f4dfbfc0.a69fb12f854882aa.js → bc324b7c.02a09dd93f6a399b.js} +1 -1
- package/apps/pwa/out/_next/static/chunks/de70ab42-d28d47437208d458.js +1 -0
- package/apps/pwa/out/_next/static/chunks/f800c5e3.46dbd7f2af8c3fce.js +1 -0
- package/apps/pwa/out/_next/static/chunks/f8bc19ad.47579f6d684b0760.js +122 -0
- package/apps/pwa/out/_next/static/chunks/framework-ca9ac4609fb9fed8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/main-app-0dd08d32d15a030f.js +1 -0
- package/apps/pwa/out/_next/static/chunks/main-f0399d33955c4e01.js +1 -0
- package/apps/pwa/out/_next/static/chunks/pages/_app-d42caca6f8ac2211.js +1 -0
- package/apps/pwa/out/_next/static/chunks/pages/_error-42e713c13aa41ca8.js +1 -0
- package/apps/pwa/out/_next/static/chunks/webpack-8fbf8f61a377aa16.js +1 -0
- package/apps/pwa/out/approvals/index.html +1 -1
- package/apps/pwa/out/approvals/index.txt +22 -22
- package/apps/pwa/out/autopilot/index.html +1 -1
- package/apps/pwa/out/autopilot/index.txt +22 -22
- package/apps/pwa/out/board/index.html +1 -1
- package/apps/pwa/out/board/index.txt +22 -22
- package/apps/pwa/out/botlab/index.html +1 -1
- package/apps/pwa/out/botlab/index.txt +21 -21
- package/apps/pwa/out/bots/index.html +1 -1
- package/apps/pwa/out/bots/index.txt +21 -21
- package/apps/pwa/out/ceo/index.html +1 -1
- package/apps/pwa/out/ceo/index.txt +22 -22
- package/apps/pwa/out/chat/index.html +1 -1
- package/apps/pwa/out/chat/index.txt +21 -21
- package/apps/pwa/out/consult/index.html +1 -1
- package/apps/pwa/out/consult/index.txt +22 -22
- package/apps/pwa/out/control/index.html +1 -1
- package/apps/pwa/out/control/index.txt +22 -22
- package/apps/pwa/out/decisions/index.html +1 -1
- package/apps/pwa/out/decisions/index.txt +21 -21
- package/apps/pwa/out/design-check/index.html +1 -1
- package/apps/pwa/out/design-check/index.txt +22 -22
- package/apps/pwa/out/editor/index.html +1 -1
- package/apps/pwa/out/editor/index.txt +22 -22
- package/apps/pwa/out/exec/index.html +1 -1
- package/apps/pwa/out/exec/index.txt +22 -22
- package/apps/pwa/out/field/index.html +1 -1
- package/apps/pwa/out/field/index.txt +22 -22
- package/apps/pwa/out/healthz +1 -1
- package/apps/pwa/out/index.html +1 -1
- package/apps/pwa/out/index.txt +21 -21
- package/apps/pwa/out/inside/index.html +1 -1
- package/apps/pwa/out/inside/index.txt +21 -21
- package/apps/pwa/out/intake/index.html +1 -1
- package/apps/pwa/out/intake/index.txt +22 -22
- package/apps/pwa/out/live/index.html +1 -1
- package/apps/pwa/out/live/index.txt +22 -22
- package/apps/pwa/out/live-run/index.html +1 -1
- package/apps/pwa/out/live-run/index.txt +22 -22
- package/apps/pwa/out/loops/index.html +1 -1
- package/apps/pwa/out/loops/index.txt +21 -21
- package/apps/pwa/out/market/index.html +1 -1
- package/apps/pwa/out/market/index.txt +21 -21
- package/apps/pwa/out/missions/placeholder/index.html +1 -1
- package/apps/pwa/out/missions/placeholder/index.txt +21 -21
- package/apps/pwa/out/morning/index.html +1 -1
- package/apps/pwa/out/morning/index.txt +22 -22
- package/apps/pwa/out/observatory/index.html +1 -1
- package/apps/pwa/out/observatory/index.txt +22 -22
- package/apps/pwa/out/ops/checklist/index.html +1 -1
- package/apps/pwa/out/ops/checklist/index.txt +21 -21
- package/apps/pwa/out/ops/release/index.html +1 -1
- package/apps/pwa/out/ops/release/index.txt +21 -21
- package/apps/pwa/out/ops/seats/index.html +1 -1
- package/apps/pwa/out/ops/seats/index.txt +21 -21
- package/apps/pwa/out/outputs/index.html +1 -1
- package/apps/pwa/out/outputs/index.txt +21 -21
- package/apps/pwa/out/reflection/index.html +1 -1
- package/apps/pwa/out/reflection/index.txt +22 -22
- package/apps/pwa/out/scheduler/index.html +1 -1
- package/apps/pwa/out/scheduler/index.txt +22 -22
- package/apps/pwa/out/sessions/index.html +1 -1
- package/apps/pwa/out/sessions/index.txt +21 -21
- package/apps/pwa/out/settings/devices/index.html +1 -1
- package/apps/pwa/out/settings/devices/index.txt +22 -22
- package/apps/pwa/out/settings/index.html +1 -1
- package/apps/pwa/out/settings/index.txt +22 -22
- package/apps/pwa/out/setup/done/index.html +1 -1
- package/apps/pwa/out/setup/done/index.txt +22 -22
- package/apps/pwa/out/setup/index.html +1 -1
- package/apps/pwa/out/setup/index.txt +22 -22
- package/apps/pwa/out/share/index.html +1 -1
- package/apps/pwa/out/share/index.txt +22 -22
- package/apps/pwa/out/showroom/index.html +1 -1
- package/apps/pwa/out/showroom/index.txt +21 -21
- package/apps/pwa/out/tasks/index.html +1 -1
- package/apps/pwa/out/tasks/index.txt +22 -22
- package/apps/pwa/out/term/index.html +1 -1
- package/apps/pwa/out/term/index.txt +22 -22
- package/apps/pwa/out/today/index.html +1 -1
- package/apps/pwa/out/today/index.txt +22 -22
- package/apps/pwa/out/trace/index.html +1 -1
- package/apps/pwa/out/trace/index.txt +22 -22
- package/apps/pwa/out/vault/index.html +1 -1
- package/apps/pwa/out/vault/index.txt +22 -22
- package/apps/pwa/out/workflows/chat-ui/index.html +1 -1
- package/apps/pwa/out/workflows/chat-ui/index.txt +22 -22
- package/apps/pwa/out/workflows/index.html +1 -1
- package/apps/pwa/out/workflows/index.txt +22 -22
- package/apps/pwa/out/workspace/index.html +1 -1
- package/apps/pwa/out/workspace/index.txt +22 -22
- package/apps/pwa/out/worktrees/index.html +1 -1
- package/apps/pwa/out/worktrees/index.txt +22 -22
- package/graphs/release/release-loop.yaml +6 -2
- package/package.json +1 -1
- package/plugins/agent-team/agents/research.md +1 -0
- package/scripts/ci-typecheck-changed.ts +3 -2
- package/scripts/coord-channel-watch.sh +26 -6
- package/scripts/coord-role-pack.ts +143 -0
- package/scripts/lib/morning-report-options.ts +41 -0
- package/scripts/pr-land-extra-remote-gates.ts +49 -0
- package/scripts/release-loop/gate-batch-safe.ts +23 -0
- package/scripts/release-loop/gate-history.ts +422 -0
- package/scripts/release-loop/gate-node.ts +310 -46
- package/scripts/release-loop/gate-triage-node.ts +190 -0
- package/scripts/release-loop/spawn-lane.ts +68 -0
- package/scripts/release-loop/tui-node-checks.ts +23 -0
- package/scripts/release-loop/version-node.ts +62 -4
- package/scripts/test-deterministic.ts +41 -12
- package/scripts/usage-rollup.ts +11 -3
- package/src/acp/core-turn-bridge.ts +98 -22
- package/src/acp/elanous-extensions.ts +2 -0
- package/src/acp/server.ts +2 -0
- package/src/agent/ref-grounding.ts +18 -0
- package/src/agent-substrate/pr-reviewer.ts +29 -21
- package/src/budget/pty-usage-reemit.ts +7 -0
- package/src/budget/run-usage-rollup.ts +9 -0
- package/src/budget/usage-daily-store.ts +98 -0
- package/src/capture/tui-self-report.ts +22 -4
- package/src/chat/index.ts +31 -10
- package/src/chat/pickers/modal-runtime.ts +1 -0
- package/src/chat/pickers/modals.ts +3 -1
- package/src/chat/turn-typeahead.ts +123 -16
- package/src/cli/dashboard-name-flag.ts +48 -0
- package/src/cli/doctor-cli.ts +80 -0
- package/src/cli/log-event-names.ts +12 -0
- package/src/cli/msg-cli.ts +45 -2
- package/src/cli/pr-cli.ts +382 -105
- package/src/cli/pr-land-heavy-remote.ts +233 -0
- package/src/cli/pr-land-overlap-evidence.ts +104 -5
- package/src/cli/pty-takeover-cli.ts +125 -16
- package/src/cli/release-cli.ts +44 -2
- package/src/cli/remote-resolve.ts +2 -1
- package/src/cli/seat-cli.ts +26 -16
- package/src/cli/tasks-cli.ts +8 -2
- package/src/cli/usage-cli.ts +146 -12
- package/src/cli/usage-daily-cli.ts +84 -0
- package/src/context-bus/context-now.ts +82 -5
- package/src/core-turn/auth-rejected-notice.ts +41 -0
- package/src/core-turn/run-core-turn.ts +13 -2
- package/src/core-turn/run-goal-loop.ts +17 -1
- package/src/core-turn/short-question.ts +45 -12
- package/src/core-turn/types.ts +7 -0
- package/src/dashboard/acp-active-model.ts +40 -0
- package/src/dashboard/auto-compact-runtime.ts +2 -0
- package/src/dashboard/boot-banner.ts +80 -0
- package/src/dashboard/dashboard-status-lines.ts +11 -0
- package/src/dashboard/detail-viewer-runtime.ts +15 -2
- package/src/dashboard/event-loop-stall-monitor.ts +4 -0
- package/src/dashboard/goal-loop-thinking.ts +16 -0
- package/src/dashboard/hitl-boot.ts +9 -4
- package/src/dashboard/index.ts +228 -387
- package/src/dashboard/input/chat-main-entry-runtime.ts +2 -0
- package/src/dashboard/input/chat-main-log-actions.ts +4 -0
- package/src/dashboard/input/chat-main-log-command.ts +12 -1
- package/src/dashboard/input/chat-main-plain-turn-runtime.ts +172 -3
- package/src/dashboard/input/chat-main-session.ts +6 -2
- package/src/dashboard/input/chat-main-slash-command.ts +7 -0
- package/src/dashboard/input/chat-main-turn.ts +2 -1
- package/src/dashboard/input/compact-prepass-recovery.ts +97 -0
- package/src/dashboard/input/dashboard-chord-actions.ts +10 -1
- package/src/dashboard/input/dashboard-chord-runtime.ts +2 -0
- package/src/dashboard/input/external-input-host.ts +45 -0
- package/src/dashboard/input/log-fold-binding.ts +18 -0
- package/src/dashboard/input/mouse-wiring.ts +17 -4
- package/src/dashboard/input/turn-steer-bridge.ts +94 -0
- package/src/dashboard/log-click-runtime.ts +5 -3
- package/src/dashboard/running-build-status.ts +74 -0
- package/src/dashboard/seat-boot-preamble.ts +113 -0
- package/src/dashboard/seat-local-instructions.ts +305 -0
- package/src/dashboard/slash-runtime/dashboard-handlers.ts +100 -28
- package/src/dashboard/slash-runtime/model-choices.ts +35 -0
- package/src/dashboard/term-slash-runtime.ts +15 -0
- package/src/dashboard/turn-preamble.ts +30 -2
- package/src/dashboard/turn-session-layers.ts +176 -0
- package/src/dashboard/turn-stream-formatter.ts +14 -6
- package/src/dashboard/turn-stream-presentation-applier.ts +8 -0
- package/src/domains/release-tool.ts +8 -9
- package/src/domains/surface-events.ts +4 -1
- package/src/domains/watch-default-scheduler.ts +8 -9
- package/src/fold-stack.ts +24 -1
- package/src/git-fs/dirty.ts +32 -4
- package/src/git-fs/index.ts +43 -1
- package/src/graph-runner/runner.ts +1 -0
- package/src/harness/harness-gc.ts +32 -5
- package/src/index.ts +14 -1
- package/src/input/external-input-queue.ts +219 -0
- package/src/interactive-terminal-modal.ts +13 -0
- package/src/llm/route-decision.ts +25 -0
- package/src/llm-stream-retry-display.ts +59 -0
- package/src/llm.ts +253 -55
- package/src/log-entry.ts +3 -3
- package/src/log-pane/search.ts +29 -4
- package/src/loops/agent-reply.ts +256 -0
- package/src/loops/budget.ts +37 -7
- package/src/loops/loop-cli.ts +3 -2
- package/src/loops/msg-address.ts +57 -0
- package/src/loops/msg-wake.ts +282 -0
- package/src/loops/orchestrator/inbox.ts +60 -3
- package/src/loops/orchestrator/tick.ts +24 -4
- package/src/loops/registry.ts +42 -4
- package/src/memory.ts +20 -5
- package/src/native-tool-catalog.ts +125 -0
- package/src/nexus/api/http-server.ts +5 -0
- package/src/nexus/api/ops-api.ts +2 -0
- package/src/nexus/api/project-autopsy.ts +127 -0
- package/src/nexus/api/terminals.ts +3 -0
- package/src/nexus/api/workflow-approvals.ts +2 -0
- package/src/nexus/onboarding/first-boot-wizard.ts +56 -2
- package/src/oauth/codex-account-store.ts +15 -3
- package/src/oauth/codex-billing-route.ts +31 -0
- package/src/ops/overview-collect.ts +19 -2
- package/src/panes/log-pane.ts +67 -8
- package/src/persona/presets.ts +44 -0
- package/src/plugins/maker/wizard-generate.ts +6 -4
- package/src/preview/terminal.ts +14 -1
- package/src/prompt-cache/types.ts +2 -0
- package/src/prompt-enhance/enhance.ts +24 -8
- package/src/prompt-library/universal-preamble.ts +273 -56
- package/src/pty-shell/pty-control-ipc.ts +4 -1
- package/src/pty-shell/pty-manifest.ts +77 -5
- package/src/pty-shell/registry.ts +19 -2
- package/src/pty-shell/tui-run-state.ts +253 -0
- package/src/release-loop/light-rc.ts +28 -3
- package/src/release-loop/rehearsal.ts +1 -1
- package/src/render.ts +5 -1
- package/src/seat-loop/seat-report.ts +42 -2
- package/src/self-dev/run-supervisor.ts +71 -5
- package/src/self-dev/shard-aggregate.ts +2 -0
- package/src/self-dev/shard-run.ts +23 -2
- package/src/self-health/signatures.ts +132 -0
- package/src/self-implement/doctor-visit.ts +118 -0
- package/src/self-implement/gate-cli.ts +11 -2
- package/src/self-implement/goal-author-decompose.ts +80 -16
- package/src/self-implement/goal-author.ts +114 -72
- package/src/self-implement/goal-authoring-grounding.ts +1 -1
- package/src/self-implement/goal-file-name.ts +65 -0
- package/src/self-implement/ground-goal.ts +2 -1
- package/src/self-implement/host-regate.ts +14 -0
- package/src/self-implement/review-mustfix-class.ts +115 -0
- package/src/self-implement/run-ledger.ts +111 -7
- package/src/self-implement/running-runs.ts +10 -6
- package/src/self-implement/self-implement-runtime.ts +32 -0
- package/src/session/pending-input.ts +62 -11
- package/src/session-runtime/index.ts +7 -1
- package/src/skills/tools/ops-ledger.ts +707 -0
- package/src/skills/tools/persistent-grounding.ts +47 -7
- package/src/skills/tools/shell.ts +117 -1
- package/src/status/bar.ts +32 -2
- package/src/status/status-provider-info.ts +58 -0
- package/src/task-agent/rejudge-on-head.ts +4 -1
- package/src/task-agent/remote-rejudge-bind.ts +34 -5
- package/src/task-agent/repair-cycle.ts +13 -0
- package/src/task-orchestrator/surfaces/kubectl-transient-retry.ts +51 -0
- package/src/task-orchestrator/surfaces/pod-command-job.ts +63 -7
- package/src/task-orchestrator/surfaces/pod-install-slots.ts +6 -11
- package/src/task-orchestrator/surfaces/pod-mirror-seed.ts +76 -0
- package/src/task-orchestrator/surfaces/self-implement-pod.ts +107 -33
- package/src/terminal/session-registry.ts +6 -0
- package/src/thinking-line.ts +12 -3
- package/src/tool-runtime/index.ts +4 -0
- package/src/tool-runtime/ops-ledger-runtimes.ts +84 -0
- package/src/tool-runtime/ref-consult-runtime.ts +17 -2
- package/src/tool-runtime/run-shell-runtime.ts +4 -1
- package/src/tool-runtime/self-cognition-runtimes.ts +5 -1
- package/src/tui.ts +5 -0
- package/src/user-config.ts +54 -6
- package/src/ux-sim/fake-llm.ts +29 -0
- package/src/ux-sim/in-process-cli.ts +175 -0
- package/src/version/packed-revision.json +1 -1
- package/apps/pwa/out/_next/static/chunks/1027.a0f04663d24c2779.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1038.676007ae505822e7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1113.a37eadf7f740d955.js +0 -1
- package/apps/pwa/out/_next/static/chunks/112-fa7c526c20ce1405.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1144.5fa1fa1d48dbcd12.js +0 -36
- package/apps/pwa/out/_next/static/chunks/1146.80d15ea7c6e6ee95.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1157.f08bf2b70915e176.js +0 -148
- package/apps/pwa/out/_next/static/chunks/119b405e.8fdd0e44d1ff37aa.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1296.04560d98e73fbf51.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1314-f604ba013ec535b0.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1454-29d1d773d5996a49.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1464.f3209af0d8ae4ff2.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1729-d73dd25e564679d4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/1843.5924c24295243261.js +0 -27
- package/apps/pwa/out/_next/static/chunks/1987.e28149724b92918b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2066-5ca18ffa5a4be68b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2240.d10a66695155fd93.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2391.e2cbc98d4abbb41a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2528.3868070ef1be69f9.js +0 -24
- package/apps/pwa/out/_next/static/chunks/2566-734cb83bbd405886.js +0 -1
- package/apps/pwa/out/_next/static/chunks/2697.76ca2ac3efef6f3b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/275.0e6bad414729bfa0.js +0 -32
- package/apps/pwa/out/_next/static/chunks/2803-33bdae771855a8d1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3143.257997a5f1ed79df.js +0 -34
- package/apps/pwa/out/_next/static/chunks/3259-86f3be56e43eaf6a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3280-e177c33bfbdcfb0a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3294-2b6a6d45a46a6c1c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3309.364573ceedbdfd5f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3522.758840fc5e7fe630.js +0 -287
- package/apps/pwa/out/_next/static/chunks/3525-a7c989c1a661e880.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3694.b1a66387756458c0.js +0 -1
- package/apps/pwa/out/_next/static/chunks/370.124f9e678a76fc01.js +0 -1
- package/apps/pwa/out/_next/static/chunks/3797-9643105335e660fe.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4084.15ecaf4240bd9e77.js +0 -286
- package/apps/pwa/out/_next/static/chunks/4089-b3382b8843114eee.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4293.928a8d573c16aab7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4402.f9238a3b18a7bd43.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4490-9b090b0f9427f902.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4548.13502d0ca3b4f862.js +0 -8
- package/apps/pwa/out/_next/static/chunks/4599-548bc96cda44a5a7.js +0 -1
- package/apps/pwa/out/_next/static/chunks/4625.206574e33a9e7ae8.js +0 -104
- package/apps/pwa/out/_next/static/chunks/4862-392c9a71f0d8dfb4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5054.2906d1b02542edc5.js +0 -149
- package/apps/pwa/out/_next/static/chunks/5102-c822bbbee5a022a4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5194-8c93f2e7e4b6f717.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5305-bacd7eca0b9a5848.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5311.9071ee3f44fd7ff5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5369.9f34353442daa421.js +0 -1
- package/apps/pwa/out/_next/static/chunks/589-49d730cb8138b397.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5904-264a6412ae3c9028.js +0 -1
- package/apps/pwa/out/_next/static/chunks/5980.728531d5c566535c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/599-56f2c0a5cc4a7295.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6011.f525002e21bef0ac.js +0 -23
- package/apps/pwa/out/_next/static/chunks/6132.4381ab93683f1acf.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6149.2e698635e454d8f6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6356-0afafc4230cf9767.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6406.64756073f7df35b8.js +0 -77
- package/apps/pwa/out/_next/static/chunks/6479-16e62aedafa0e310.js +0 -1
- package/apps/pwa/out/_next/static/chunks/6599.b5246b46a2453329.js +0 -64
- package/apps/pwa/out/_next/static/chunks/6610.5c26eec011565acb.js +0 -1
- package/apps/pwa/out/_next/static/chunks/666.37d18474edc1c552.js +0 -2
- package/apps/pwa/out/_next/static/chunks/6904.a0b5b1ed4f2d2c20.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7247-1f4aba94aba50d9f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7274-e71a7c5b7760cd02.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7290.1fcaeef3adb5d0d4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7477-2c64e42760f82f33.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7505-47002b76ff1aef6c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7600-11884ca4da68e5d9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7607.40d8bb3689697ccb.js +0 -62
- package/apps/pwa/out/_next/static/chunks/7752.5cbdd0b433c54af9.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7763.f51fcc19ca1414ec.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7785.846140c859b1adf6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7807-a0fdac6393e0bf36.js +0 -1
- package/apps/pwa/out/_next/static/chunks/7837-20a63b4b7e9342b1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/800.7815414cf280545d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8085-1e5fce59500a2cc2.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8100.415f2105faa63e97.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8290.701aa42ed13aa767.js +0 -226
- package/apps/pwa/out/_next/static/chunks/83a80514-b897b64df43ce108.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8444.d9c74214a3145a43.js +0 -93
- package/apps/pwa/out/_next/static/chunks/8569.98c915534928c7f9.js +0 -24
- package/apps/pwa/out/_next/static/chunks/8591.b1c7f876e5ec7cfb.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8715-f63756021d3ab989.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8879.776c2ec7732aa114.js +0 -115
- package/apps/pwa/out/_next/static/chunks/8881.ddca15b3c82c490c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/8946.5da5c87f32a2e1a8.js +0 -41
- package/apps/pwa/out/_next/static/chunks/9117.080b9b75be90e14d.js +0 -74
- package/apps/pwa/out/_next/static/chunks/9167.f3ecb28f367d6e69.js +0 -94
- package/apps/pwa/out/_next/static/chunks/9224.66095370ee28c93b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9238-0682b013c83d6449.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9449.d3ed795da4befb1c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/949.1e7d45ccb71580aa.js +0 -90
- package/apps/pwa/out/_next/static/chunks/9638-d268329f2c6f4f8d.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9842-d6644eb53d3dc6bf.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9863.94ca3263e760696e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/9938.b23e4d4dfa0114cd.js +0 -79
- package/apps/pwa/out/_next/static/chunks/app/_not-found/page-d9babd8795f396a5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/approvals/page-5ab1e47978577c5e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/autopilot/page-24453f6a302816b4.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/board/page-6c131d30bb1cf871.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/bots/page-dc0772b11861af51.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/chat/page-5159dc8752c6cd29.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/consult/page-c5a2478861c08b87.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/control/page-f722a9dec084e08b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/decisions/page-256ffd365d32e100.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/design-check/page-e0de78ae7b99f01c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/editor/page-cfbdc44b708d9801.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/exec/page-4c741eb760f2f77c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/field/page-e9ba98f5f1440a21.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/healthz/route-d9babd8795f396a5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/inside/page-dafc901bb1b72b5f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/intake/page-2f6f303fa114ec24.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/layout-1634081c5272006c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/live/page-ced0bcfc6542b3fc.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/live-run/page-bb1f05cd51c38944.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/market/page-db069b48a59c8c00.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-f736324afa2117c1.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/not-found-435f5e2faf02bc01.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/observatory/page-497e0eedf20e7890.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-a8d28fdf995e16ea.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/release/page-8966452228753c5e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-fd5d18656cb432b6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/outputs/page-5663779cb1a37609.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/page-66a67eb19ebd976b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/reflection/page-3b492aa78cf3c4a6.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/scheduler/page-c71267e7681da982.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/sessions/page-a21d1e1797172692.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-cb249e81ed339318.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/settings/page-781cfc5114e097da.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/done/page-478157214db6a023.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/layout-d9babd8795f396a5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/setup/page-86141f12cf090b7f.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/share/page-7256c73bb1c36751.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/showroom/page-5c738ca7adef3de5.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/tasks/page-0138c8091ec17224.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/term/page-cc2f24f16d85e735.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/today/page-979d318a534e92da.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/trace/page-182d394f7e6e096b.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/vault/page-21050928a697ed7a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-44b9d807005a9030.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workflows/page-601fb77340e63c9a.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/workspace/page-75d3fb5d47af0edf.js +0 -1
- package/apps/pwa/out/_next/static/chunks/app/worktrees/page-11bf9e5725a72c22.js +0 -1
- package/apps/pwa/out/_next/static/chunks/dcf24383-2f82e35f2d827393.js +0 -1
- package/apps/pwa/out/_next/static/chunks/e117f801.e92bf10242653497.js +0 -1
- package/apps/pwa/out/_next/static/chunks/e87d89b9.2e71c0ae475d28a1.js +0 -122
- package/apps/pwa/out/_next/static/chunks/framework-bf135b997155e90e.js +0 -1
- package/apps/pwa/out/_next/static/chunks/main-5571537543bea91c.js +0 -1
- package/apps/pwa/out/_next/static/chunks/main-app-25c51c7df7f3a442.js +0 -1
- package/apps/pwa/out/_next/static/chunks/pages/_app-e3b2c1f5d82abd65.js +0 -1
- package/apps/pwa/out/_next/static/chunks/pages/_error-083f2e23e9bc3641.js +0 -1
- package/apps/pwa/out/_next/static/chunks/webpack-e94d22b7a028217b.js +0 -1
- package/src/dashboard/bench-slash-runtime.ts +0 -40
- package/src/dashboard/input/search-modal-router.ts +0 -9
- package/src/dashboard/modals/pane-key-router.ts +0 -27
- package/src/dashboard/view-slash-runtime.ts +0 -48
- /package/apps/pwa/out/_next/static/{y1ltt7oCZxVpC6zVPhZ2O → cIpv5nU9AycwYWZI9H589}/_ssgManifest.js +0 -0
|
@@ -371,6 +371,12 @@ export interface StartOpts {
|
|
|
371
371
|
kind?: string;
|
|
372
372
|
/** 휴먼 리더블 닉네임 — 고유 id 와 함께 같은 PTY 를 부르는 다른 이름(나중에 goto 로 기억·접근). */
|
|
373
373
|
nickname?: string;
|
|
374
|
+
/** Explicit origin for a host-owned PTY when the host process has no origin marker. */
|
|
375
|
+
origin?: { originRoot: string; controller?: string };
|
|
376
|
+
/** Explicit purpose for a host-owned PTY with no worktree goal. */
|
|
377
|
+
purpose?: string;
|
|
378
|
+
/** Seat that owns this PTY; absent for callers without a seat. */
|
|
379
|
+
seat?: string;
|
|
374
380
|
/** 접근 모드 초기값(관찰 read/인터랙션 write/자율 auto). 기본 'write'(미션 등 헤드리스 자율은 'auto' 지정). */
|
|
375
381
|
accessMode?: PtyAccessMode;
|
|
376
382
|
/** 전환 정책 초기값(전환불가 locked/전환허용 open). 기본 'open'. */
|
|
@@ -766,6 +772,9 @@ export function startPty(opts: StartOpts): PtyHandle {
|
|
|
766
772
|
id, kind: handle.kind, cmd: handle.cmd, ptyPid: adapter.pid,
|
|
767
773
|
...(handle.nickname ? { nickname: handle.nickname } : {}),
|
|
768
774
|
...(handle.workdir ? { workdir: handle.workdir } : {}),
|
|
775
|
+
...(opts.origin ? { origin: opts.origin } : {}),
|
|
776
|
+
...(opts.purpose ? { purpose: opts.purpose } : {}),
|
|
777
|
+
...(opts.seat ? { seat: opts.seat } : {}),
|
|
769
778
|
startedAt: handle.startedAt, now: Date.now(),
|
|
770
779
|
identity: {
|
|
771
780
|
...(childSpaceId === undefined ? {} : { spaceId: childSpaceId }),
|
|
@@ -887,8 +896,16 @@ export function listPty(): PtyHandle[] {
|
|
|
887
896
|
/** 닉네임 부여/변경 — 나중에 goto 로 기억·접근 쉽게. 없는 id 면 false. */
|
|
888
897
|
export function renamePty(id: string, nickname: string): boolean {
|
|
889
898
|
const h = getPty(id);
|
|
890
|
-
if (
|
|
891
|
-
|
|
899
|
+
if (h) {
|
|
900
|
+
h.setNickname(nickname);
|
|
901
|
+
return true;
|
|
902
|
+
}
|
|
903
|
+
// ⭐ 자식이 아닌 제어 대상(맨 `elanous` TUI 의 `tui:<pid>` 행 등)은 PtyHandle 이 없다 —
|
|
904
|
+
// 별명은 manifest 행에만 산다. 여기서 받지 않으면 IPC rename 이 그 행에 `unknown-pty` 로 진다.
|
|
905
|
+
const target = controlTargets.get(id);
|
|
906
|
+
if (!target || !target.isAlive()) return false;
|
|
907
|
+
if (PTY_MANIFEST_ENABLED) updatePtyManifestNickname(id, nickname.trim() || undefined, Date.now());
|
|
908
|
+
debug.log('pty.rename', 'control-target-renamed', { ptyId: id, nickname: nickname.trim() });
|
|
892
909
|
return true;
|
|
893
910
|
}
|
|
894
911
|
|
|
@@ -0,0 +1,253 @@
|
|
|
1
|
+
// ── TUI 실행 상태 — 턴(busy/idle) ⊕ 기동 판 ⊕ stale 판정 ──
|
|
2
|
+
//
|
|
3
|
+
// 바깥 제어자(`elanous pty state <ref>`)가 «지금 턴 중인가»와 «이 프로세스가 어느 판 코드로 도는가»를
|
|
4
|
+
// 화면 글자 grep 없이 알게 한다(대표 TUI OP 도그푸드 결함 #13).
|
|
5
|
+
//
|
|
6
|
+
// ⛔ 화면 하단 `⌥ HEAD@<sha>` 는 «세션 cwd 트리»의 HEAD 다 — 프로세스가 실은 코드가 아니다.
|
|
7
|
+
// 10-14 실측: 15:19 에 뜬 TUI 가 15:4x 설치 갱신(5c0f98f) 뒤에도 새 판처럼 보였다.
|
|
8
|
+
// ⇒ 기동 판은 «기동 때 한 번» 잡아 manifest 행에 적고, 비교 대상(설치본 · 체크아웃 HEAD)은 «읽을 때» 잰다.
|
|
9
|
+
//
|
|
10
|
+
// 기록(TUI 쪽): 행 등록 직후 `startTuiRunStateRecorder` 가 판 ⊕ idle 을 적고, 대시보드가 턴 시작·끝에
|
|
11
|
+
// `reportTuiTurn` 을 부른다. 기록 실패는 `debug.log('pty.tui-state', …)` — 조용히 삼키지 않는다.
|
|
12
|
+
// 판독(CLI 쪽): `describePtyRunState` 가 행 ⊕ 설치본 기록 ⊕ (체크아웃이면) 그 뿌리의 HEAD 로 판정한다.
|
|
13
|
+
|
|
14
|
+
import { readFileSync } from 'node:fs';
|
|
15
|
+
import { homedir } from 'node:os';
|
|
16
|
+
import { dirname, join, resolve } from 'node:path';
|
|
17
|
+
import { fileURLToPath } from 'node:url';
|
|
18
|
+
|
|
19
|
+
import { debug } from '../debug/log.js';
|
|
20
|
+
import { runGitCommand } from '../git-fs/runner.js';
|
|
21
|
+
import { codeRevision, packageVersion, readInstallMetadataCommit } from '../version/code-revision.js';
|
|
22
|
+
import { versionedDashboardInstallDir } from '../dashboard/stale-install-check.js';
|
|
23
|
+
import {
|
|
24
|
+
updatePtyManifestBuild, updatePtyManifestTurn,
|
|
25
|
+
type PtyBuildIdentity, type PtyManifestRow, type PtyTurnState,
|
|
26
|
+
} from './pty-manifest.js';
|
|
27
|
+
|
|
28
|
+
const CODE_ROOT = resolve(dirname(fileURLToPath(import.meta.url)), '..', '..');
|
|
29
|
+
|
|
30
|
+
// ── 기동 판 ──
|
|
31
|
+
|
|
32
|
+
export interface RunningBuildDeps {
|
|
33
|
+
readonly codeRoot?: string;
|
|
34
|
+
readonly installRoot?: string;
|
|
35
|
+
readonly versionDirOf?: (codeRoot: string, installRoot?: string) => string | undefined;
|
|
36
|
+
readonly readInstallCommit?: (metadataPath: string) => string | undefined;
|
|
37
|
+
/** 체크아웃 HEAD(설치본 판 폴더가 아닐 때만). */
|
|
38
|
+
readonly revision?: () => string | undefined;
|
|
39
|
+
readonly version?: () => string;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
/** 이 프로세스가 실은 코드의 판. 설치본 판 폴더면 그 폴더의 install.json, 아니면 코드 뿌리의 git HEAD. */
|
|
43
|
+
export function resolveRunningBuild(deps: RunningBuildDeps = {}): PtyBuildIdentity {
|
|
44
|
+
const codeRoot = deps.codeRoot ?? CODE_ROOT;
|
|
45
|
+
const version = (deps.version ?? packageVersion)();
|
|
46
|
+
const versionDir = (deps.versionDirOf ?? versionedDashboardInstallDir)(codeRoot, deps.installRoot);
|
|
47
|
+
if (versionDir) {
|
|
48
|
+
// 판 폴더의 install.json 만이 «실은 판»의 증거다 — 못 읽으면 다른 출처로 메우지 않고 모른다로 둔다.
|
|
49
|
+
const sha = (deps.readInstallCommit ?? readInstallMetadataCommit)(join(versionDir, 'install.json')) ?? '';
|
|
50
|
+
return { version, sha, source: sha ? 'installed' : 'unknown', codeRoot };
|
|
51
|
+
}
|
|
52
|
+
const sha = (deps.revision ?? codeRevision)() ?? '';
|
|
53
|
+
return { version, sha, source: sha ? 'checkout' : 'unknown', codeRoot };
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
let bootBuild: PtyBuildIdentity | undefined;
|
|
57
|
+
/** 기동 판 — 처음 부른 순간 한 번 잡고 그대로 둔다(뒤에 트리 HEAD 가 움직여도 «실은 코드»는 그대로다). */
|
|
58
|
+
export function runningBuild(): PtyBuildIdentity {
|
|
59
|
+
bootBuild ??= resolveRunningBuild();
|
|
60
|
+
return bootBuild;
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
// ── 설치본 기록 ──
|
|
64
|
+
|
|
65
|
+
export interface InstalledRecord {
|
|
66
|
+
readonly sha?: string;
|
|
67
|
+
/** install.json `installedAt`(epoch ms) — 못 읽으면 undefined. */
|
|
68
|
+
readonly installedAt?: number;
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
export function defaultInstallRoot(): string {
|
|
72
|
+
return join(homedir(), '.local', 'share', 'elanous');
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/** 지금 `current` 가 가리키는 설치본의 commit ⊕ 설치 시각. */
|
|
76
|
+
export function readCurrentInstallRecord(installRoot = defaultInstallRoot()): InstalledRecord {
|
|
77
|
+
const path = join(installRoot, 'current', 'install.json');
|
|
78
|
+
const sha = readInstallMetadataCommit(path);
|
|
79
|
+
let installedAt: number | undefined;
|
|
80
|
+
try {
|
|
81
|
+
const parsed = JSON.parse(readFileSync(path, 'utf8')) as { installedAt?: unknown };
|
|
82
|
+
const t = typeof parsed.installedAt === 'string' ? Date.parse(parsed.installedAt) : NaN;
|
|
83
|
+
if (Number.isFinite(t)) installedAt = t;
|
|
84
|
+
} catch { /* 설치본 없음 */ }
|
|
85
|
+
return { ...(sha ? { sha } : {}), ...(installedAt !== undefined ? { installedAt } : {}) };
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
export function readCheckoutHead(codeRoot: string): string | undefined {
|
|
89
|
+
try {
|
|
90
|
+
const r = runGitCommand(codeRoot, ['rev-parse', 'HEAD'], { encoding: 'utf8' });
|
|
91
|
+
const sha = r.status === 0 ? String(r.stdout).trim() : '';
|
|
92
|
+
return sha || undefined;
|
|
93
|
+
} catch {
|
|
94
|
+
return undefined;
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
// ── stale 판정 ──
|
|
99
|
+
|
|
100
|
+
export type BuildStaleReason =
|
|
101
|
+
/** 설치본 판으로 떴고 지금 설치본과 같다. */
|
|
102
|
+
| 'same-as-installed'
|
|
103
|
+
/** 설치본 판으로 떴는데 그 뒤 설치본이 바뀌었다 — 재기동해야 새 판. */
|
|
104
|
+
| 'installed-moved'
|
|
105
|
+
/** 체크아웃에서 떴고 그 뿌리의 HEAD 가 같다. */
|
|
106
|
+
| 'same-as-checkout'
|
|
107
|
+
/** 체크아웃에서 떴는데 그 뿌리의 HEAD 가 움직였다. */
|
|
108
|
+
| 'checkout-moved'
|
|
109
|
+
/** 판 기록이 없는 옛 행인데 설치본이 그 행보다 늦게 깔렸다(추정 — 설치본으로 떴다면 낡았다). */
|
|
110
|
+
| 'started-before-install'
|
|
111
|
+
/** 비교할 값을 못 얻었다 — «안 낡았다»가 아니다. */
|
|
112
|
+
| 'unknown';
|
|
113
|
+
|
|
114
|
+
export interface BuildStaleness {
|
|
115
|
+
/** null = 못 쟀다(⛔ false 로 접지 않는다). */
|
|
116
|
+
readonly stale: boolean | null;
|
|
117
|
+
readonly reason: BuildStaleReason;
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
export function judgeBuildStaleness(input: {
|
|
121
|
+
readonly build?: PtyBuildIdentity;
|
|
122
|
+
readonly installed: InstalledRecord;
|
|
123
|
+
readonly checkoutHead?: string;
|
|
124
|
+
readonly startedAt?: number;
|
|
125
|
+
}): BuildStaleness {
|
|
126
|
+
const { build, installed } = input;
|
|
127
|
+
if (build?.sha && build.source === 'installed') {
|
|
128
|
+
if (!installed.sha) return { stale: null, reason: 'unknown' };
|
|
129
|
+
return installed.sha === build.sha ? { stale: false, reason: 'same-as-installed' } : { stale: true, reason: 'installed-moved' };
|
|
130
|
+
}
|
|
131
|
+
if (build?.sha && build.source === 'checkout') {
|
|
132
|
+
if (!input.checkoutHead) return { stale: null, reason: 'unknown' };
|
|
133
|
+
return input.checkoutHead === build.sha ? { stale: false, reason: 'same-as-checkout' } : { stale: true, reason: 'checkout-moved' };
|
|
134
|
+
}
|
|
135
|
+
if (!build && input.startedAt !== undefined && installed.installedAt !== undefined && installed.installedAt > input.startedAt) {
|
|
136
|
+
return { stale: true, reason: 'started-before-install' };
|
|
137
|
+
}
|
|
138
|
+
return { stale: null, reason: 'unknown' };
|
|
139
|
+
}
|
|
140
|
+
|
|
141
|
+
// ── 판독(CLI) ──
|
|
142
|
+
|
|
143
|
+
export type PtyTurnView = PtyTurnState | 'unknown';
|
|
144
|
+
|
|
145
|
+
export interface PtyRunStateView {
|
|
146
|
+
readonly turn: PtyTurnView;
|
|
147
|
+
readonly turnAt?: number;
|
|
148
|
+
readonly build: PtyBuildIdentity | null;
|
|
149
|
+
readonly installed: string | null;
|
|
150
|
+
readonly stale: boolean | null;
|
|
151
|
+
readonly staleReason: BuildStaleReason;
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
export interface DescribeRunStateDeps {
|
|
155
|
+
readonly readInstalled?: () => InstalledRecord;
|
|
156
|
+
readonly readCheckoutHead?: (codeRoot: string) => string | undefined;
|
|
157
|
+
}
|
|
158
|
+
|
|
159
|
+
/** manifest 행 하나의 턴 ⊕ 판 ⊕ stale. 행이 없거나 죽었으면 턴은 unknown. */
|
|
160
|
+
export function describePtyRunState(
|
|
161
|
+
row: Pick<PtyManifestRow, 'alive' | 'startedAt' | 'kind' | 'turnState' | 'turnAt' | 'build'> | null,
|
|
162
|
+
deps: DescribeRunStateDeps = {},
|
|
163
|
+
): PtyRunStateView {
|
|
164
|
+
let installed: InstalledRecord = {};
|
|
165
|
+
try { installed = (deps.readInstalled ?? readCurrentInstallRecord)(); } catch { /* unknown */ }
|
|
166
|
+
const build = row?.build;
|
|
167
|
+
let checkoutHead: string | undefined;
|
|
168
|
+
// 판독 예외는 «모른다»(stale=null)로 — 조회 명령 자체를 깨지 않는다.
|
|
169
|
+
try {
|
|
170
|
+
if (build?.source === 'checkout' && build.codeRoot) checkoutHead = (deps.readCheckoutHead ?? readCheckoutHead)(build.codeRoot);
|
|
171
|
+
} catch { checkoutHead = undefined; }
|
|
172
|
+
// 판 기록 없는 옛 행의 «설치 뒤에 떴나» 추정은 elanous TUI 행에만 건다(셸 PTY 는 판과 무관하다).
|
|
173
|
+
const staleness = judgeBuildStaleness({
|
|
174
|
+
...(build ? { build } : {}),
|
|
175
|
+
installed,
|
|
176
|
+
...(checkoutHead ? { checkoutHead } : {}),
|
|
177
|
+
...(row && row.kind === 'tui' ? { startedAt: row.startedAt } : {}),
|
|
178
|
+
});
|
|
179
|
+
const turn: PtyTurnView = row?.alive && row.turnState ? row.turnState : 'unknown';
|
|
180
|
+
return {
|
|
181
|
+
turn,
|
|
182
|
+
...(turn !== 'unknown' && row?.turnAt ? { turnAt: row.turnAt } : {}),
|
|
183
|
+
build: build ?? null,
|
|
184
|
+
installed: installed.sha ?? null,
|
|
185
|
+
stale: staleness.stale,
|
|
186
|
+
staleReason: staleness.reason,
|
|
187
|
+
};
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
export function shortSha(sha: string | null | undefined): string {
|
|
191
|
+
return sha ? sha.slice(0, 7) : '-';
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
// ── 기록(TUI) ──
|
|
195
|
+
|
|
196
|
+
export interface TuiRunStateRecorderDeps {
|
|
197
|
+
readonly now?: () => number;
|
|
198
|
+
readonly build?: () => PtyBuildIdentity;
|
|
199
|
+
readonly writeBuild?: (id: string, build: PtyBuildIdentity) => boolean;
|
|
200
|
+
readonly writeTurn?: (id: string, turn: PtyTurnState, at: number) => boolean;
|
|
201
|
+
readonly log?: (event: string, data: Record<string, unknown>) => void;
|
|
202
|
+
}
|
|
203
|
+
|
|
204
|
+
interface ActiveRecorder {
|
|
205
|
+
readonly surfaceId: string;
|
|
206
|
+
readonly now: () => number;
|
|
207
|
+
readonly writeTurn: (id: string, turn: PtyTurnState, at: number) => boolean;
|
|
208
|
+
readonly log: (event: string, data: Record<string, unknown>) => void;
|
|
209
|
+
last?: PtyTurnState;
|
|
210
|
+
}
|
|
211
|
+
|
|
212
|
+
let active: ActiveRecorder | null = null;
|
|
213
|
+
|
|
214
|
+
const defaultLog = (event: string, data: Record<string, unknown>): void => { debug.log('pty.tui-state', event, data); };
|
|
215
|
+
|
|
216
|
+
/** TUI 행 등록 직후 부른다 — 판을 적고 턴을 idle 로 연다. 이후 `reportTuiTurn` 이 이 행에 적는다. */
|
|
217
|
+
export function startTuiRunStateRecorder(surfaceId: string, deps: TuiRunStateRecorderDeps = {}): () => void {
|
|
218
|
+
const now = deps.now ?? Date.now;
|
|
219
|
+
const log = deps.log ?? defaultLog;
|
|
220
|
+
const writeTurn = deps.writeTurn ?? updatePtyManifestTurn;
|
|
221
|
+
let build: PtyBuildIdentity | undefined;
|
|
222
|
+
try { build = (deps.build ?? runningBuild)(); } catch (error) {
|
|
223
|
+
log('build-resolve-failed', { ptyId: surfaceId, error: error instanceof Error ? error.message : String(error) });
|
|
224
|
+
}
|
|
225
|
+
if (build) {
|
|
226
|
+
const ok = (() => { try { return (deps.writeBuild ?? updatePtyManifestBuild)(surfaceId, build); } catch { return false; } })();
|
|
227
|
+
log(ok ? 'build-recorded' : 'build-write-failed', { ptyId: surfaceId, sha: build.sha, version: build.version, source: build.source });
|
|
228
|
+
}
|
|
229
|
+
const recorder: ActiveRecorder = { surfaceId, now, writeTurn, log };
|
|
230
|
+
active = recorder;
|
|
231
|
+
writeTurnState(recorder, 'idle');
|
|
232
|
+
return () => { if (active === recorder) active = null; };
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
/** 대시보드가 턴 시작(busy)·끝(idle)에 부른다. 녹음기가 없으면(자기보고 꺼짐) 아무것도 안 한다. */
|
|
236
|
+
export function reportTuiTurn(turn: PtyTurnState): void {
|
|
237
|
+
if (!active || active.last === turn) return;
|
|
238
|
+
writeTurnState(active, turn);
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
function writeTurnState(recorder: ActiveRecorder, turn: PtyTurnState): void {
|
|
242
|
+
const at = recorder.now();
|
|
243
|
+
let ok = false;
|
|
244
|
+
try { ok = recorder.writeTurn(recorder.surfaceId, turn, at); } catch { ok = false; }
|
|
245
|
+
if (ok) recorder.last = turn;
|
|
246
|
+
// 실패는 관측으로 남긴다 — 바깥 제어자는 그 사이 «unknown/낡은 값»을 본다. 성공은 남기지 않는다(턴마다 두 줄은 소음).
|
|
247
|
+
else recorder.log('turn-write-failed', { ptyId: recorder.surfaceId, turn, at });
|
|
248
|
+
}
|
|
249
|
+
|
|
250
|
+
export function resetTuiRunStateForTesting(): void {
|
|
251
|
+
active = null;
|
|
252
|
+
bootBuild = undefined;
|
|
253
|
+
}
|
|
@@ -11,6 +11,7 @@ import { runSelfGateCli, type SelfGateCliOptions, type SelfGateCliResult } from
|
|
|
11
11
|
import { dispatchHeavyCheck, isValidGateHost, type DispatchDeps, type DispatchOptions } from '../self-implement/gate-remote.js';
|
|
12
12
|
import { latestPublishedPreviousVersion } from '../../scripts/release-loop/unattended-release.js';
|
|
13
13
|
import { baseVersion, isReleaseVersion } from '../../scripts/release-loop/release-version.js';
|
|
14
|
+
import { executeTuiNodeCheck, type ExecutedTuiCheck } from '../../scripts/release-loop/tui-node-checks.js';
|
|
14
15
|
|
|
15
16
|
export const LIGHT_RC_ALWAYS_FILE = 'release/light-rc-always.txt';
|
|
16
17
|
export const LIGHT_RC_DEFAULT_SHARDS = 4;
|
|
@@ -31,6 +32,8 @@ export interface LightRcOptions {
|
|
|
31
32
|
/** Release ledger root for the previous-version lookup (release run's deps.ledgerRoot). */
|
|
32
33
|
ledgerRoot?: string;
|
|
33
34
|
log?: (line: string) => void;
|
|
35
|
+
/** Rehearsal-only TUI screen check; other light-rc callers keep their current defaults. */
|
|
36
|
+
rehearsalTui?: boolean;
|
|
34
37
|
}
|
|
35
38
|
|
|
36
39
|
export interface LightRcResult {
|
|
@@ -57,6 +60,7 @@ export interface LightRcResult {
|
|
|
57
60
|
/** LIGHT-RC-MEASURE ③ — why the gate produced no measurement (e.g. `shard-2`); null = it measured. Carried in the
|
|
58
61
|
* JSON so the reason reaches the caller even when the remote child's human lines (stderr) do not. */
|
|
59
62
|
unmeasured: string | null;
|
|
63
|
+
rehearsalTui?: ExecutedTuiCheck;
|
|
60
64
|
}
|
|
61
65
|
|
|
62
66
|
export interface LightRcDeps {
|
|
@@ -68,6 +72,7 @@ export interface LightRcDeps {
|
|
|
68
72
|
dispatch?: (opts: DispatchOptions, deps?: DispatchDeps) => Promise<number>;
|
|
69
73
|
/** Extra dispatch deps (runner · settings) — tests drive the real dispatch with a fake host. */
|
|
70
74
|
dispatchDeps?: Omit<DispatchDeps, 'write'>;
|
|
75
|
+
tuiCheck?: typeof executeTuiNodeCheck;
|
|
71
76
|
/** Detached checkout of `sha` for a local run whose tree is not at the measured commit (default: git worktree add
|
|
72
77
|
* --detach in a temp dir ⊕ bun install); `cleanup` removes it. */
|
|
73
78
|
checkout?: (sha: string, repo: string, log: (line: string) => void) => { dir: string; cleanup: () => void };
|
|
@@ -180,13 +185,21 @@ export async function runLightRc(version: string, opts: LightRcOptions = {}, dep
|
|
|
180
185
|
let alwaysInclude = readList(cwd);
|
|
181
186
|
|
|
182
187
|
let local: SelfGateCliResult | undefined;
|
|
183
|
-
|
|
188
|
+
let localTui: ExecutedTuiCheck | undefined;
|
|
189
|
+
const runLocal = async () => {
|
|
184
190
|
// ① The gate scopes by its tree's HEAD — so a tree that is not at the measured commit runs in a detached checkout of it.
|
|
185
191
|
const checkout = worktreeHead === measuredCommit ? undefined : (deps.checkout ?? defaultCheckout)(measuredCommit, cwd, log);
|
|
186
192
|
try {
|
|
187
193
|
const dir = checkout?.dir ?? cwd;
|
|
188
194
|
if (checkout) alwaysInclude = readList(dir);
|
|
189
195
|
local = (deps.runGate ?? runSelfGateCli)(dir, { base, shards, alwaysInclude, includeImporterTests: true });
|
|
196
|
+
if (opts.rehearsalTui) {
|
|
197
|
+
const command = async (cmd: string, args: string[], tree: string, limitMs?: number) => {
|
|
198
|
+
const run = spawnSync(cmd, args, { cwd: tree, encoding: 'utf8', timeout: limitMs });
|
|
199
|
+
return { rc: run.status ?? 2, output: `${run.stdout ?? ''}\n${run.stderr ?? ''}` };
|
|
200
|
+
};
|
|
201
|
+
localTui = await (deps.tuiCheck ?? executeTuiNodeCheck)(measuredCommit, dir, command);
|
|
202
|
+
}
|
|
190
203
|
} finally { checkout?.cleanup(); }
|
|
191
204
|
for (const line of local.lines) log(line);
|
|
192
205
|
return local.exitCode;
|
|
@@ -195,7 +208,7 @@ export async function runLightRc(version: string, opts: LightRcOptions = {}, dep
|
|
|
195
208
|
const rc = await (deps.dispatch ?? dispatchHeavyCheck)({
|
|
196
209
|
tool: 'self-gate', repo: cwd, installPwa: true, refs: [base], json: true, commit: measuredCommit,
|
|
197
210
|
// The host re-runs this command with --local (and ELANOUS_GATE_REMOTE_CHILD=1), so it never recurses.
|
|
198
|
-
remoteArgv: (sha) => ['bun', 'bin/elanous.mjs', 'release', 'light-rc', '--version', version, '--base', sha(base), '--head', measuredCommit, '--shards', String(shards), '--local', '--json'],
|
|
211
|
+
remoteArgv: (sha) => ['bun', 'bin/elanous.mjs', 'release', 'light-rc', '--version', version, '--base', sha(base), '--head', measuredCommit, '--shards', String(shards), '--local', '--json', ...(opts.rehearsalTui ? ['--rehearsal-tui'] : [])],
|
|
199
212
|
flags: { remote: opts.local ? undefined : opts.remote ?? true, local: !!opts.local },
|
|
200
213
|
runLocal,
|
|
201
214
|
}, {
|
|
@@ -236,11 +249,22 @@ export async function runLightRc(version: string, opts: LightRcOptions = {}, dep
|
|
|
236
249
|
unmeasured: typeof remote.unmeasured === 'string' && remote.unmeasured
|
|
237
250
|
? remote.unmeasured
|
|
238
251
|
: typeof remote.introduced === 'number' ? null : LIGHT_RC_REASON_NOT_REPORTED,
|
|
252
|
+
...(remote.rehearsalTui ? { rehearsalTui: remote.rehearsalTui } : {}),
|
|
239
253
|
};
|
|
240
254
|
}
|
|
241
255
|
// Unmeasured (null) or unclassified failures are never green; policy-gate findings in the gate output are reported
|
|
242
256
|
// (gate rc), not a regression.
|
|
243
|
-
|
|
257
|
+
if (opts.rehearsalTui) {
|
|
258
|
+
if (local) {
|
|
259
|
+
result.rehearsalTui = localTui ?? { outcome: 'unmeasured', detail: 'local TUI screen result missing' };
|
|
260
|
+
} else {
|
|
261
|
+
const tui = result.rehearsalTui;
|
|
262
|
+
result.rehearsalTui = tui && ['ok', 'fail', 'unmeasured'].includes(tui.outcome) && typeof tui.detail === 'string' && tui.detail.length > 0
|
|
263
|
+
? tui : { outcome: 'unmeasured', detail: 'remote TUI screen result missing' };
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
result.ok = result.introduced === 0 && result.unclassified === 0 && result.unmeasured === null
|
|
267
|
+
&& (!opts.rehearsalTui || result.rehearsalTui?.outcome === 'ok');
|
|
244
268
|
debug.log('release.light-rc', 'done', { version, base, measuredCommit, worktreeHead, importerTests: result.importerTests, introduced: result.introduced, preexisting: result.preexisting, unclassified: result.unclassified, shards, remote: result.remote, unmeasured: result.unmeasured });
|
|
245
269
|
return result;
|
|
246
270
|
}
|
|
@@ -250,5 +274,6 @@ export function formatLightRc(result: LightRcResult): string[] {
|
|
|
250
274
|
`${result.ok ? '✅' : '⛔'} light-rc ${result.version} · base ${result.base.slice(0, 12)} · measured ${result.measuredCommit.slice(0, 12)} · ${result.remote ? `host ${result.remote}` : 'local'} · shards ${result.shards}`,
|
|
251
275
|
` introduced ${result.introduced ?? '못 쟀다'} · preexisting ${result.preexisting ?? '못 쟀다'} · unclassified ${result.unclassified ?? '못 쟀다'} · importer tests ${result.importerTests ?? '못 쟀다'} · always-include ${result.alwaysInclude}${result.alwaysIncludeMissing.length ? ` (missing: ${result.alwaysIncludeMissing.join(', ')})` : ''} · gate rc ${result.gateExitCode}`,
|
|
252
276
|
...(result.unmeasured !== null ? [` shards: unmeasured (${result.unmeasured})`] : []),
|
|
277
|
+
...(result.rehearsalTui ? [` TUI screens: ${result.rehearsalTui.outcome} (${result.rehearsalTui.detail})`] : []),
|
|
253
278
|
];
|
|
254
279
|
}
|
|
@@ -290,7 +290,7 @@ export async function runRehearsalTick(opts: RehearsalOptions = {}, deps: Rehear
|
|
|
290
290
|
stamp.sha = gitResult(git, ['rev-parse', 'HEAD'], checkout);
|
|
291
291
|
if (!stamp.sha) throw new Error('git rev-parse HEAD returned no sha');
|
|
292
292
|
const regressionFiles: string[] = [];
|
|
293
|
-
const result = await (deps.lightRc ?? ((version, cwd) => runLightRc(version, { ledgerRoot: root, head: stamp.sha, log: (line) => {
|
|
293
|
+
const result = await (deps.lightRc ?? ((version, cwd) => runLightRc(version, { ledgerRoot: root, head: stamp.sha, rehearsalTui: true, log: (line) => {
|
|
294
294
|
for (const entry of line.split(/\r?\n/)) {
|
|
295
295
|
const file = /^- introduced: (.+?)(?: > |$)/.exec(entry)?.[1];
|
|
296
296
|
if (file && regressionFiles.length < 3) regressionFiles.push(file);
|
package/src/render.ts
CHANGED
|
@@ -572,6 +572,10 @@ function parseAndRenderTable(lines: string[]): string {
|
|
|
572
572
|
* Render a tool call header like Claude Code:
|
|
573
573
|
* ⏺ ToolName(description)
|
|
574
574
|
*/
|
|
575
|
+
export function singleLineToolHeaderText(text: string): string {
|
|
576
|
+
return text.replace(/[ \t]*(?:\r\n|\r|\n|\u2028|\u2029)[ \t]*/g, ' ↵ ');
|
|
577
|
+
}
|
|
578
|
+
|
|
575
579
|
export function toolHeader(
|
|
576
580
|
toolName: string,
|
|
577
581
|
description: string,
|
|
@@ -585,7 +589,7 @@ export function toolHeader(
|
|
|
585
589
|
case 'error': icon = applyColor(circle, 'error'); break;
|
|
586
590
|
}
|
|
587
591
|
const name = chalk.bold(toolName);
|
|
588
|
-
const desc = description ? chalk.dim(`(${description})`) : '';
|
|
592
|
+
const desc = description ? chalk.dim(`(${singleLineToolHeaderText(description)})`) : '';
|
|
589
593
|
return `${icon} ${name}${desc}`;
|
|
590
594
|
}
|
|
591
595
|
|
|
@@ -8,6 +8,7 @@ import { effectiveInstanceRoot } from '../instance/resolve.js';
|
|
|
8
8
|
import { getUserConfig, type SeatLoopConfig } from '../user-config.js';
|
|
9
9
|
import { collectDraftMetrics, collectOverlapMetrics, countSalvagedToday, type DraftMetrics, type OverlapMetrics } from '../self-dev/draft-sweep.js';
|
|
10
10
|
import { queryRunningRuns } from '../self-implement/running-runs.js';
|
|
11
|
+
import { loadRunLedger } from '../self-implement/run-ledger.js';
|
|
11
12
|
import { readTaskAgentCover } from '../cli/tasks-cli.js';
|
|
12
13
|
import { formatTaskAgentCover } from '../task-agent/cover.js';
|
|
13
14
|
import type { TasksCliDeps } from '../cli/tasks-cli.js';
|
|
@@ -27,6 +28,10 @@ export type SeatReportDeps = {
|
|
|
27
28
|
/** DRAFT-NOT-ARCHIVE salvage branches since the KST day start; null = unreadable. */
|
|
28
29
|
salvagedToday?: (dayStart: Date, now: Date) => Promise<number | null>;
|
|
29
30
|
runningRuns?: (runIds: readonly string[]) => { running: number; unknown: number } | null;
|
|
31
|
+
/** Launched-run 착지 집계; null 이나 예외는 «착지 못 잼»으로 나온다. */
|
|
32
|
+
landedRuns?: (runIds: readonly string[]) => { landed: number; unread: number } | null;
|
|
33
|
+
/** 기본 집계의 runId별 읽기 경로를 시험할 때만 교체한다. */
|
|
34
|
+
loadLedger?: typeof loadRunLedger;
|
|
30
35
|
};
|
|
31
36
|
export type SeatReportResult = { seat: string; date: string; body: string; posted: boolean };
|
|
32
37
|
const repoRoot = resolve(import.meta.dir, '../..');
|
|
@@ -173,10 +178,45 @@ export async function seatReport(seat: string, deps: SeatReportDeps = {}): Promi
|
|
|
173
178
|
: ` · 도는 런 ${counts.running}(불확실 ${counts.unknown})`;
|
|
174
179
|
} catch { runningDetail = ' · 도는 런 못 잼'; }
|
|
175
180
|
}
|
|
176
|
-
|
|
181
|
+
// ⭐ 사다리 ① (#25210 «도는 런» 옆): 발사된 runId 각각의 run 원장을 읽어 착지 수를 센다.
|
|
182
|
+
// 'merged' 사건이 있으면 착지 · 원장이 null(로컬에 없음 — Pod 런 등)이면 «원장 없음»으로 따로 센다.
|
|
183
|
+
let landedDetail = '';
|
|
184
|
+
let landed: number | null = 0;
|
|
185
|
+
let landedUnread: number | null = 0;
|
|
186
|
+
if (runIds.length) {
|
|
187
|
+
try {
|
|
188
|
+
const counts = (deps.landedRuns ?? ((ids: readonly string[]) => {
|
|
189
|
+
let landedCount = 0;
|
|
190
|
+
let unreadCount = 0;
|
|
191
|
+
let unreadable = false;
|
|
192
|
+
for (const runId of ids) {
|
|
193
|
+
try {
|
|
194
|
+
const ledger = (deps.loadLedger ?? loadRunLedger)(runId);
|
|
195
|
+
if (ledger === null) unreadCount += 1;
|
|
196
|
+
else if (ledger.some((entry) => entry.event === 'merged')) landedCount += 1;
|
|
197
|
+
} catch { unreadable = true; }
|
|
198
|
+
}
|
|
199
|
+
return unreadable ? null : { landed: landedCount, unread: unreadCount };
|
|
200
|
+
}))(runIds);
|
|
201
|
+
if (counts === null) {
|
|
202
|
+
landed = null;
|
|
203
|
+
landedUnread = null;
|
|
204
|
+
landedDetail = ' · 착지 못 잼';
|
|
205
|
+
} else {
|
|
206
|
+
landed = counts.landed;
|
|
207
|
+
landedUnread = counts.unread;
|
|
208
|
+
landedDetail = ` · 착지 ${counts.landed}(원장 없음 ${counts.unread})`;
|
|
209
|
+
}
|
|
210
|
+
} catch {
|
|
211
|
+
landed = null;
|
|
212
|
+
landedUnread = null;
|
|
213
|
+
landedDetail = ' · 착지 못 잼';
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
const body = `**[${seat}]** {{TS}} → 보고 ${date}: ${detail.join(' · ') || (classified.length ? 'OP 그림자 판단' : '원장 기록 없음')}${opDetail}${draftDetail}${runningDetail}${landedDetail}`;
|
|
177
217
|
const pr = (deps.config ?? getUserConfig().loops?.seat)?.reportPr;
|
|
178
218
|
const posted = deps.post === true && pr !== undefined;
|
|
179
219
|
if (posted) await (deps.send ?? ((text, id, number) => defaultSend(text, id, number, deps.repo ?? repoRoot)))(body, seat, pr);
|
|
180
|
-
try { debug.log('seat.loop', 'reported', { seat, date, entries: entries.length, posted }); } catch { /* observation is fail-soft */ }
|
|
220
|
+
try { debug.log('seat.loop', 'reported', { seat, date, entries: entries.length, posted, landed, landedUnread }); } catch { /* observation is fail-soft */ }
|
|
181
221
|
return { seat, date, body, posted };
|
|
182
222
|
}
|
|
@@ -11,6 +11,7 @@ import { sweepFrozenMerges } from '../self-implement/frozen-merges.js';
|
|
|
11
11
|
import { routeSupervisorVerdict } from './supervisor-verdict-edges.js';
|
|
12
12
|
import { recordTaskAgentShadowMove, runCardFor, type TaskAgentShadowInput } from '../task-agent/shadow.js';
|
|
13
13
|
import { cardPrNumber, taskAgentStatePath } from '../task-agent/task-hand.js';
|
|
14
|
+
import { classifyMustFixRound, inferMustFixEvidence, type MustFixRoundClassification, type MustFixRoundObservation } from '../self-implement/review-mustfix-class.js';
|
|
14
15
|
|
|
15
16
|
export interface SupervisorRound {
|
|
16
17
|
round: number;
|
|
@@ -46,6 +47,8 @@ export interface SupervisorRound {
|
|
|
46
47
|
* streak pairs rounds by this key. Omitted on older history — the guard then pairs by taskId as before.
|
|
47
48
|
*/
|
|
48
49
|
noPrFeatureKeys?: string[];
|
|
50
|
+
/** REVIEW-MUSTFIX-CLASSIFY — that round's observed must-fix items; pairs the next round's classification. */
|
|
51
|
+
mustFix?: MustFixRoundObservation;
|
|
49
52
|
}
|
|
50
53
|
|
|
51
54
|
/** Failed without a PR — a result that carries either a PR number or a PR URL has one (fixtures and older producers set only one). */
|
|
@@ -116,6 +119,10 @@ export interface SupervisorDecision {
|
|
|
116
119
|
deliverableUnmeasured: boolean;
|
|
117
120
|
deliverableMergeCompleteness: 'unmeasured' | 'complete' | 'incomplete';
|
|
118
121
|
reviewMustFixTrend: ReviewRework['trend'];
|
|
122
|
+
/** REVIEW-MUSTFIX-CLASSIFY — this round's leading must-fix class (② › ③ observed › ①); omitted when unmeasured (지금 동작 그대로). */
|
|
123
|
+
mustFix?: MustFixRoundClassification;
|
|
124
|
+
/** REVIEW-MUSTFIX-CLASSIFY — every oscillating task's measured class, so a mixed round keeps each task's decision. */
|
|
125
|
+
mustFixByTask?: Record<string, MustFixRoundClassification>;
|
|
119
126
|
oscillation?: { taskIds: string[]; helper: 'review-oscillation'; signature: string; repairGoals?: Record<string, string>; heldTaskIds?: string[] };
|
|
120
127
|
pendingDecision?: 'attempt-care-escalation';
|
|
121
128
|
}
|
|
@@ -234,6 +241,41 @@ export function aggregateReviewTrend(results: readonly SelfDevJobResult[]): Revi
|
|
|
234
241
|
return severity[Math.max(...trends.map((trend) => severity.indexOf(trend)))];
|
|
235
242
|
}
|
|
236
243
|
|
|
244
|
+
/**
|
|
245
|
+
* REVIEW-MUSTFIX-CLASSIFY — this round's must-fix observation from the results' verbatim `reviewMustFix`.
|
|
246
|
+
* Each item carries its `taskId` so the next round pairs per task (one task's recurrence never holds another).
|
|
247
|
+
*/
|
|
248
|
+
function mustFixFromResults(results: readonly SupervisorJobResult[]): MustFixRoundObservation {
|
|
249
|
+
const items = results.flatMap((result) => (result.reviewMustFix ?? []).map((text) => {
|
|
250
|
+
const evidence = inferMustFixEvidence(text);
|
|
251
|
+
return { text, taskId: result.taskId, ...(evidence === undefined ? {} : { evidence }) };
|
|
252
|
+
}));
|
|
253
|
+
return items.length > 0 ? { items } : {};
|
|
254
|
+
}
|
|
255
|
+
|
|
256
|
+
/**
|
|
257
|
+
* REVIEW-MUSTFIX-CLASSIFY — per-task class. `prev` is the preceding round's items of the same task or its repair
|
|
258
|
+
* lineage (`oscillationRepairOf`), and only when that preceding round authored a repair for it — «수리 뒤 같은 지적»
|
|
259
|
+
* means a repair ran between the last observation and this one, not «repaired at any time». Lineage items are
|
|
260
|
+
* re-scoped to this task so the pure pairing accepts them; unrelated tasks never pair.
|
|
261
|
+
*/
|
|
262
|
+
function classifyTaskMustFix(result: SupervisorJobResult, preceding: SupervisorRound | undefined): MustFixRoundClassification {
|
|
263
|
+
const pairIds = new Set([result.taskId, ...(result.oscillationRepairOf ? [result.oscillationRepairOf] : [])]);
|
|
264
|
+
const repairedSincePrev = (preceding?.oscillationRepairTaskIds ?? []).some((id) => pairIds.has(id));
|
|
265
|
+
const prevItems = repairedSincePrev
|
|
266
|
+
? (preceding?.mustFix?.items ?? []).filter((item) => item.taskId !== undefined && pairIds.has(item.taskId))
|
|
267
|
+
.map((item) => ({ ...item, taskId: result.taskId }))
|
|
268
|
+
: [];
|
|
269
|
+
return classifyMustFixRound(prevItems.length > 0 ? { items: prevItems } : undefined, mustFixFromResults([result]));
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
/**
|
|
273
|
+
* Classes that hold a task out of this round's same-run repair. Only ② acts in this slice; ③ recurring is
|
|
274
|
+
* observed (decision `mustFix`/`mustFixByTask` · crossReview suggestion) but behaves as ① — acting on it is a
|
|
275
|
+
* follow-up cell (REVIEW-MUSTFIX-CLASSIFY partial landing).
|
|
276
|
+
*/
|
|
277
|
+
const MUST_FIX_HELD = new Set<MustFixRoundClassification['class']>(['post-land-evidence']);
|
|
278
|
+
|
|
237
279
|
export function decideNextRun(input: {
|
|
238
280
|
results: readonly SupervisorJobResult[];
|
|
239
281
|
history?: readonly SupervisorRound[];
|
|
@@ -520,8 +562,27 @@ export function decideNextRun(input: {
|
|
|
520
562
|
|| (entry.oscillationRepairFeatures?.[index] !== undefined && entry.oscillationRepairFeatures[index] === result.feature
|
|
521
563
|
&& Object.values(entry.oscillationRepairGoals ?? {}).includes(result.feature))));
|
|
522
564
|
// Per task: a task that already got its one oscillation repair is held for a human; a fresh one may get it.
|
|
523
|
-
|
|
524
|
-
|
|
565
|
+
// REVIEW-MUSTFIX-CLASSIFY — 슈퍼바이저는 추이 대신 회차 분류를 먼저 본다(대표 10-12 «노하우가 아니라 로직으로» · 임의 임계 없음).
|
|
566
|
+
// ① new-defect — 그대로 수렴(진동 수리 유지).
|
|
567
|
+
// ② post-land-evidence — 증거는 착지 뒤에만 난다 ⇒ 같은 런 재수리 0, «그림자 착지 → 관측 → live» 쪼개기 결정.
|
|
568
|
+
// ③ recurring — 수리 뒤 같은 지적 ⇒ 이 조각에선 관측만(교차 리뷰 제안을 결정에 싣고 동작은 ① 그대로 · 후속 칸).
|
|
569
|
+
// unmeasured — 분류 불가 ⇒ 지금 동작 그대로. 분류는 조각마다 — 한 조각의 분류가 다른 조각의 수리를 끊지 않는다.
|
|
570
|
+
const taskClasses = new Map(oscillating.map((result) => [result.taskId, classifyTaskMustFix(result, preceding)]));
|
|
571
|
+
const fresh = oscillating.filter((result) => !isRepaired(result) && !MUST_FIX_HELD.has(taskClasses.get(result.taskId)!.class));
|
|
572
|
+
const classes = [...taskClasses.values()];
|
|
573
|
+
// Decision-level class: ② (the only acting class) first, then observed ③, else ①.
|
|
574
|
+
const mustFixClass = classes.find((c) => c.class === 'post-land-evidence') ?? classes.find((c) => c.class === 'recurring')
|
|
575
|
+
?? classes.find((c) => c.class === 'new-defect');
|
|
576
|
+
// Held = already repaired once, or classified ② — either way it never rides this round's rerun.
|
|
577
|
+
const classHeld = [...new Set(oscillating.filter((result) => !isRepaired(result)
|
|
578
|
+
&& MUST_FIX_HELD.has(taskClasses.get(result.taskId)!.class)).map((result) => result.taskId))];
|
|
579
|
+
const held = [...new Set([...oscillating.filter(isRepaired).map((result) => result.taskId), ...classHeld])];
|
|
580
|
+
const repairedHeld = held.filter((id) => !classHeld.includes(id));
|
|
581
|
+
// Every task's measured class survives in the decision — a mixed round keeps ② split and the observed ③ cross-review suggestion both.
|
|
582
|
+
const mustFixByTask: Record<string, MustFixRoundClassification> = Object.fromEntries(
|
|
583
|
+
[...taskClasses].filter(([, c]) => c.class !== 'unmeasured'));
|
|
584
|
+
const heldReasons = [...new Set(classes.filter((c) => MUST_FIX_HELD.has(c.class)).map((c) => c.reason))];
|
|
585
|
+
const heldReasonSuffix = heldReasons.length ? ` · ${heldReasons.join(' · ')}` : '';
|
|
525
586
|
const repairGoals: Record<string, string> = Object.fromEntries(fresh.flatMap((result) => {
|
|
526
587
|
const goal = result.prNumber && result.reviewMustFix?.length
|
|
527
588
|
? authorRepairGoal({ pr: result.prNumber, category: 'review-oscillation', originalRequest: result.feature,
|
|
@@ -551,14 +612,16 @@ export function decideNextRun(input: {
|
|
|
551
612
|
} : {}),
|
|
552
613
|
action,
|
|
553
614
|
...(action === 'stop' ? { stopReason: 'review-oscillating' as const } : {}),
|
|
615
|
+
...(mustFixClass ? { mustFix: mustFixClass } : {}),
|
|
616
|
+
...(Object.keys(mustFixByTask).length ? { mustFixByTask } : {}),
|
|
554
617
|
oscillation: { taskIds, helper: 'review-oscillation', signature, ...(Object.keys(repairGoals).length ? { repairGoals } : {}),
|
|
555
618
|
...(action === 'add-repair-task' && held.length ? { heldTaskIds: held } : {}) },
|
|
556
619
|
pendingDecision: 'attempt-care-escalation',
|
|
557
620
|
why: fresh.length === 0
|
|
558
|
-
? `리뷰 진동 반복 — ${signatureOf(oscillating)} · 사람 결정 필요(같은 전략 재발사 금지)`
|
|
621
|
+
? `리뷰 진동 반복 — ${signatureOf(oscillating)} · 사람 결정 필요(같은 전략 재발사 금지)${heldReasonSuffix}`
|
|
559
622
|
: cannotRepair
|
|
560
|
-
? `리뷰 진동 — ${signatureOf(oscillating)} · ${input.repairGoalExecution === false ? '이 감독 경로가 수리 골 실행을 선언하지 않았다(미선언 또는 불가)' : '수리 원문/PR 관측 불가'} · 사람 결정 필요(같은 전략 재발사 금지)`
|
|
561
|
-
: `리뷰 진동 — ${signatureOf(fresh)} · review-oscillation 수리 조각을 한 번 붙인다${input.repairGoalExecution === true ? '' : '(실행 배선 미선언 — 결정 칸만)'}${
|
|
623
|
+
? `리뷰 진동 — ${signatureOf(oscillating)} · ${input.repairGoalExecution === false ? '이 감독 경로가 수리 골 실행을 선언하지 않았다(미선언 또는 불가)' : '수리 원문/PR 관측 불가'} · 사람 결정 필요(같은 전략 재발사 금지)${heldReasonSuffix}`
|
|
624
|
+
: `리뷰 진동 — ${signatureOf(fresh)} · review-oscillation 수리 조각을 한 번 붙인다${input.repairGoalExecution === true ? '' : '(실행 배선 미선언 — 결정 칸만)'}${repairedHeld.length ? ` · 이미 수리한 조각 ${repairedHeld.join(', ')} 은 사람 결정 대기` : ''}${classHeld.length ? ` · 분류로 보류한 조각 ${classHeld.join(', ')}` : ''}${heldReasonSuffix}`,
|
|
562
625
|
};
|
|
563
626
|
}
|
|
564
627
|
|
|
@@ -588,6 +651,8 @@ export function appendRound(
|
|
|
588
651
|
const t = triageRun(results.filter((result) => result.salvage !== 'launched'), undefined, false, undefined, mainSyncRelaunchSpent(history));
|
|
589
652
|
const baseCompleted = countBaseCompleted(results);
|
|
590
653
|
const base = roundBase(results);
|
|
654
|
+
// REVIEW-MUSTFIX-CLASSIFY — 회차 원장에 관측을 실어 다음 회차 짝으로 쓴다(관측 없는 옛 원장은 그대로).
|
|
655
|
+
const mustFix = mustFixFromResults(results.filter((result) => result.salvage !== 'launched'));
|
|
591
656
|
const noPrResults = results.filter(failedWithoutPr);
|
|
592
657
|
const noPrTaskIds = noPrResults.map((result) => result.taskId);
|
|
593
658
|
const noPrFeatureKeys = noPrResults.map((result) => noPrStreakKey(result.feature));
|
|
@@ -597,6 +662,7 @@ export function appendRound(
|
|
|
597
662
|
...(baseCompleted > 0 || base !== undefined ? { baseCompleted, ...(base === undefined ? {} : { base }) } : {}),
|
|
598
663
|
actionable: countActionable(t),
|
|
599
664
|
...(reviewMustFixTrend === undefined ? {} : { reviewMustFixTrend }),
|
|
665
|
+
...((mustFix.items ?? []).length > 0 ? { mustFix } : {}),
|
|
600
666
|
...(results.some((result) => result.rework?.signature)
|
|
601
667
|
? { signatures: Object.fromEntries(results.filter((result) => result.rework?.signature).map((result) => [result.taskId, result.rework!.signature])) } : {}),
|
|
602
668
|
...(decision && decision.action !== 'stop' && decision.relaunchOnMain.length > 0 ? {
|
|
@@ -16,6 +16,8 @@ export interface GateShardAttempt {
|
|
|
16
16
|
baselineExitCode: number | null;
|
|
17
17
|
currentSignal?: string | null;
|
|
18
18
|
baselineSignal?: string | null;
|
|
19
|
+
currentDiagnostic?: string;
|
|
20
|
+
baselineDiagnostic?: string;
|
|
19
21
|
/** LIGHT-RC-MEASURE — the shard files that exist in the baseline tree, i.e. what the baseline side actually ran.
|
|
20
22
|
* Absent = every shard file (the old shape). Empty = the baseline side was not run and contributes zero cases. */
|
|
21
23
|
baselineFiles?: readonly string[];
|