elanous 0.2.38 → 0.2.41

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (712) hide show
  1. package/README.md +7 -7
  2. package/apps/pwa/out/404/index.html +1 -1
  3. package/apps/pwa/out/404.html +1 -1
  4. package/apps/pwa/out/_next/static/{RrjXTwz-urRAbChP1bX02 → GiOLWmt4MqDZePubBjA4Q}/_buildManifest.js +1 -1
  5. package/apps/pwa/out/_next/static/chunks/1115.434ae2ecb0ad986d.js +149 -0
  6. package/apps/pwa/out/_next/static/chunks/1121.667cec0bcdbb3fdb.js +36 -0
  7. package/apps/pwa/out/_next/static/chunks/1178.1aa9cad0e7695427.js +1 -0
  8. package/apps/pwa/out/_next/static/chunks/1197-54da59d250a6e476.js +1 -0
  9. package/apps/pwa/out/_next/static/chunks/{5203.51e5d8b5f1dcfe53.js → 1219.7e17964e0e7cd8e5.js} +3 -3
  10. package/apps/pwa/out/_next/static/chunks/1245.1cfd13b26dbd71d6.js +287 -0
  11. package/apps/pwa/out/_next/static/chunks/1494-f93046ff5c5a124d.js +1 -0
  12. package/apps/pwa/out/_next/static/chunks/1609.2b312797599b8e45.js +1 -0
  13. package/apps/pwa/out/_next/static/chunks/1661.0dd330f3d89f73f3.js +1 -0
  14. package/apps/pwa/out/_next/static/chunks/167-0c121e4b47e0f9da.js +1 -0
  15. package/apps/pwa/out/_next/static/chunks/1700.cdc2bf8cc685e221.js +90 -0
  16. package/apps/pwa/out/_next/static/chunks/1703-78e46acad29f3cfc.js +1 -0
  17. package/apps/pwa/out/_next/static/chunks/{7573.2376e13c9c21f1f8.js → 1765.679b29625c8e88d4.js} +2 -2
  18. package/apps/pwa/out/_next/static/chunks/{3528.e4b8ab70d339f965.js → 1800.f7ff51dc4978a958.js} +1 -1
  19. package/apps/pwa/out/_next/static/chunks/1971-7efb628c471dc5a0.js +1 -0
  20. package/apps/pwa/out/_next/static/chunks/1999-8de7b7bb36801913.js +1 -0
  21. package/apps/pwa/out/_next/static/chunks/2073.689dcb2680113d76.js +1 -0
  22. package/apps/pwa/out/_next/static/chunks/2198-557d49184104d165.js +1 -0
  23. package/apps/pwa/out/_next/static/chunks/221-440ce67fa9f5c839.js +1 -0
  24. package/apps/pwa/out/_next/static/chunks/{8879.ac06755bcf3e44a1.js → 2263.e09b6edea33bad2d.js} +1 -1
  25. package/apps/pwa/out/_next/static/chunks/2427-8ed8e98624cbd664.js +1 -0
  26. package/apps/pwa/out/_next/static/chunks/2457-725c5827bc003795.js +1 -0
  27. package/apps/pwa/out/_next/static/chunks/2491-2718b15a5ccb75a5.js +1 -0
  28. package/apps/pwa/out/_next/static/chunks/2527-5c636a43c7cc5dde.js +1 -0
  29. package/apps/pwa/out/_next/static/chunks/2692-1027cb16fe4ccf49.js +1 -0
  30. package/apps/pwa/out/_next/static/chunks/2743.5d3f76948be32b34.js +41 -0
  31. package/apps/pwa/out/_next/static/chunks/2773.0e80b9d325fb5635.js +32 -0
  32. package/apps/pwa/out/_next/static/chunks/2873-0f3cb56c8e3528ea.js +1 -0
  33. package/apps/pwa/out/_next/static/chunks/{9fe1b809.738da85c8b17e3fb.js → 2fdf2931.b431eee4fb468bc3.js} +1 -1
  34. package/apps/pwa/out/_next/static/chunks/{eaad0cba.771200940c529df7.js → 2fe2c302.41b517f88d6fe502.js} +1 -1
  35. package/apps/pwa/out/_next/static/chunks/3097.864e92bdaa2f4d15.js +79 -0
  36. package/apps/pwa/out/_next/static/chunks/3136-d6870ba63300a93e.js +1 -0
  37. package/apps/pwa/out/_next/static/chunks/3173-0289113d434e83b7.js +1 -0
  38. package/apps/pwa/out/_next/static/chunks/3230-49298c3b73ef2268.js +1 -0
  39. package/apps/pwa/out/_next/static/chunks/325-dd9208a1a0ab7ce4.js +1 -0
  40. package/apps/pwa/out/_next/static/chunks/3283.528f430dd043fb4e.js +74 -0
  41. package/apps/pwa/out/_next/static/chunks/3295.cc8cb13b8f0dae1a.js +1 -0
  42. package/apps/pwa/out/_next/static/chunks/3688-86e3b88abf18cb3b.js +1 -0
  43. package/apps/pwa/out/_next/static/chunks/3804-7220467a5473a8df.js +1 -0
  44. package/apps/pwa/out/_next/static/chunks/3808.3e1e247ce7bdf889.js +1 -0
  45. package/apps/pwa/out/_next/static/chunks/{b7478fef.5917716286213fcc.js → 385e4574.e9886ab32759eda3.js} +3 -3
  46. package/apps/pwa/out/_next/static/chunks/3927.b5473ad109da44c5.js +1 -0
  47. package/apps/pwa/out/_next/static/chunks/3934-98ea94832e194796.js +1 -0
  48. package/apps/pwa/out/_next/static/chunks/4133.2056bb4d78f621af.js +1 -0
  49. package/apps/pwa/out/_next/static/chunks/4156.ba4de4a3664f04b4.js +1 -0
  50. package/apps/pwa/out/_next/static/chunks/4297-239ca82f293faab0.js +1 -0
  51. package/apps/pwa/out/_next/static/chunks/4320-dcc5a7734126f4c9.js +1 -0
  52. package/apps/pwa/out/_next/static/chunks/4434.94b4c552a2d91e69.js +148 -0
  53. package/apps/pwa/out/_next/static/chunks/{8911.bf5e712acb25fb6c.js → 4527.a69f2894d1bc9f4a.js} +1 -1
  54. package/apps/pwa/out/_next/static/chunks/4579.03e4092f73950965.js +226 -0
  55. package/apps/pwa/out/_next/static/chunks/{5307.d7328020227880c2.js → 4667.97e31aa38c95c475.js} +4 -4
  56. package/apps/pwa/out/_next/static/chunks/{6142.913b44e260a3f925.js → 4702.4a4adc1f16d7c93b.js} +1 -1
  57. package/apps/pwa/out/_next/static/chunks/4815.481501c57b3568d9.js +1 -0
  58. package/apps/pwa/out/_next/static/chunks/487-d16e698ef14662d9.js +1 -0
  59. package/apps/pwa/out/_next/static/chunks/4888-7a38bf522c9cc6fe.js +1 -0
  60. package/apps/pwa/out/_next/static/chunks/5034-30e429d6bb086881.js +1 -0
  61. package/apps/pwa/out/_next/static/chunks/5040-35c494e60dadd97d.js +1 -0
  62. package/apps/pwa/out/_next/static/chunks/50c6ab1e.81a96e419350909d.js +1 -0
  63. package/apps/pwa/out/_next/static/chunks/5154.4b6a836179356f30.js +94 -0
  64. package/apps/pwa/out/_next/static/chunks/{8487.291666583bebe640.js → 5159.115f1c2ca471386c.js} +1 -1
  65. package/apps/pwa/out/_next/static/chunks/5228-a8200df486278f2d.js +1 -0
  66. package/apps/pwa/out/_next/static/chunks/530.d26346e18089640a.js +115 -0
  67. package/apps/pwa/out/_next/static/chunks/5379.97af106d09566f69.js +8 -0
  68. package/apps/pwa/out/_next/static/chunks/{89d6c04f-6b8ab341748e468a.js → 53aeb4ee-51c92f8d683f5220.js} +1 -1
  69. package/apps/pwa/out/_next/static/chunks/{3291.f6c1005387d514bd.js → 5471.1e611302ed3a7c53.js} +2 -2
  70. package/apps/pwa/out/_next/static/chunks/5479-b6372e762719f92f.js +1 -0
  71. package/apps/pwa/out/_next/static/chunks/5534-699c5cbcbc96c5d7.js +1 -0
  72. package/apps/pwa/out/_next/static/chunks/{3086.fb14b60ce98b53d3.js → 5574.f35accf4f132b29d.js} +1 -1
  73. package/apps/pwa/out/_next/static/chunks/5701.9c4e8f250312eeee.js +24 -0
  74. package/apps/pwa/out/_next/static/chunks/{1632.7d87f998e714bede.js → 5744.b9415e18ad623100.js} +1 -1
  75. package/apps/pwa/out/_next/static/chunks/{5300.677c97e0393742e6.js → 5892.2526d962339662d8.js} +1 -1
  76. package/apps/pwa/out/_next/static/chunks/5937.c2df9e3447e1f667.js +1 -0
  77. package/apps/pwa/out/_next/static/chunks/5941.8210cc93c9202c0a.js +286 -0
  78. package/apps/pwa/out/_next/static/chunks/{7161-8f22db3ec5ed005e.js → 5947-135e26537d80a6b9.js} +3 -3
  79. package/apps/pwa/out/_next/static/chunks/{3124-561f7f037943cde2.js → 5964-7e21164a8f2cf0ce.js} +1 -1
  80. package/apps/pwa/out/_next/static/chunks/5975.4004f820ae3cecd5.js +1 -0
  81. package/apps/pwa/out/_next/static/chunks/6142-7ccd48795d7abd55.js +1 -0
  82. package/apps/pwa/out/_next/static/chunks/6160.bf9177b8c1bfb243.js +1 -0
  83. package/apps/pwa/out/_next/static/chunks/6398.71ba0690c8027555.js +27 -0
  84. package/apps/pwa/out/_next/static/chunks/6492.2bd5c10edc1a064e.js +1 -0
  85. package/apps/pwa/out/_next/static/chunks/6552.a3840aa7da35ad68.js +62 -0
  86. package/apps/pwa/out/_next/static/chunks/6736.1e36d3ac5fa5e41d.js +24 -0
  87. package/apps/pwa/out/_next/static/chunks/6874.d5cf7eb8edb2cabe.js +2 -0
  88. package/apps/pwa/out/_next/static/chunks/6900.3ccbe069bdd4556a.js +1 -0
  89. package/apps/pwa/out/_next/static/chunks/71327eb4.add50b365f94bf3a.js +122 -0
  90. package/apps/pwa/out/_next/static/chunks/7136.deca3e3a2ddaa374.js +1 -0
  91. package/apps/pwa/out/_next/static/chunks/7139-ee9f8ed2677a40b3.js +1 -0
  92. package/apps/pwa/out/_next/static/chunks/{2415.738b777642a02233.js → 7191.fdc955f7d96064a4.js} +1 -1
  93. package/apps/pwa/out/_next/static/chunks/7423-e0aa5d9e2962120e.js +1 -0
  94. package/apps/pwa/out/_next/static/chunks/7453.afc1ea7e05d56a8c.js +1 -0
  95. package/apps/pwa/out/_next/static/chunks/7503-5e6a3d7fe67e4a0c.js +1 -0
  96. package/apps/pwa/out/_next/static/chunks/7761-476fd7bf768abd34.js +1 -0
  97. package/apps/pwa/out/_next/static/chunks/7975.eafb12097a0a9e62.js +1 -0
  98. package/apps/pwa/out/_next/static/chunks/{1026-44010f405704050c.js → 8050-9b364bdef8f71927.js} +1 -1
  99. package/apps/pwa/out/_next/static/chunks/8152.64e253c35cccfaae.js +1 -0
  100. package/apps/pwa/out/_next/static/chunks/8190.620f0231b3924bcb.js +1 -0
  101. package/apps/pwa/out/_next/static/chunks/83184dcd-0ee6247ff41eb3f2.js +1 -0
  102. package/apps/pwa/out/_next/static/chunks/8448.45b6b1f1a99eeb35.js +104 -0
  103. package/apps/pwa/out/_next/static/chunks/8464-e24f10451b658aac.js +1 -0
  104. package/apps/pwa/out/_next/static/chunks/8477.e4c944bb3aa5d2f3.js +1 -0
  105. package/apps/pwa/out/_next/static/chunks/8710.ca385257d5ca422e.js +1 -0
  106. package/apps/pwa/out/_next/static/chunks/8830.627ccf294ec2465c.js +1 -0
  107. package/apps/pwa/out/_next/static/chunks/8880.64c445592f04acaf.js +1 -0
  108. package/apps/pwa/out/_next/static/chunks/8981.c706964c8ba27aff.js +1 -0
  109. package/apps/pwa/out/_next/static/chunks/{5638.107314dc479e2f37.js → 9048.212083de42d25be3.js} +2 -2
  110. package/apps/pwa/out/_next/static/chunks/9053.bd0fffaff8d3f836.js +1 -0
  111. package/apps/pwa/out/_next/static/chunks/9161-c66e723d7ec9d682.js +1 -0
  112. package/apps/pwa/out/_next/static/chunks/9185.1ecdf9b65c0bb684.js +1 -0
  113. package/apps/pwa/out/_next/static/chunks/9356.fccd5f58086b4ff5.js +1 -0
  114. package/apps/pwa/out/_next/static/chunks/9446.dc0406109371d329.js +1 -0
  115. package/apps/pwa/out/_next/static/chunks/9506.dcf25d467a42627e.js +1 -0
  116. package/apps/pwa/out/_next/static/chunks/{8019.21ca554a821dad01.js → 9507.7026657a2f47eb64.js} +16 -16
  117. package/apps/pwa/out/_next/static/chunks/9541.eb8e2f8480c7feca.js +93 -0
  118. package/apps/pwa/out/_next/static/chunks/9577.ed7582186efa5482.js +1 -0
  119. package/apps/pwa/out/_next/static/chunks/9579.4a8169600fff2058.js +1 -0
  120. package/apps/pwa/out/_next/static/chunks/9642-ff2e039eb62e3b92.js +1 -0
  121. package/apps/pwa/out/_next/static/chunks/9659-8f2323348113ad80.js +1 -0
  122. package/apps/pwa/out/_next/static/chunks/9724.4c5623af2db43153.js +34 -0
  123. package/apps/pwa/out/_next/static/chunks/{6493.27ad77de7aac7966.js → 9834.63ab2bbc3153172e.js} +1 -1
  124. package/apps/pwa/out/_next/static/chunks/{3389.012c70767a872f9b.js → 9869.81a1e24ca682d5a0.js} +1 -1
  125. package/apps/pwa/out/_next/static/chunks/{8994d93e.33ba491f95345fc2.js → a0a01613.6d1cca322238d7fe.js} +1 -1
  126. package/apps/pwa/out/_next/static/chunks/{de8b930d.d94c0f42acf807fc.js → addc2b32.8c4ff8f0aefe987d.js} +1 -1
  127. package/apps/pwa/out/_next/static/chunks/app/_not-found/page-8d9d76ea322d855c.js +1 -0
  128. package/apps/pwa/out/_next/static/chunks/app/approvals/page-ed2c4e59f9f1fe21.js +1 -0
  129. package/apps/pwa/out/_next/static/chunks/app/autopilot/page-2dc99e03c5d76ca0.js +1 -0
  130. package/apps/pwa/out/_next/static/chunks/app/board/page-b5a3a788330e920f.js +1 -0
  131. package/apps/pwa/out/_next/static/chunks/app/botlab/{page-866aac5ff226a7f3.js → page-14949db884bfa672.js} +1 -1
  132. package/apps/pwa/out/_next/static/chunks/app/bots/page-ea76c85b36388a97.js +1 -0
  133. package/apps/pwa/out/_next/static/chunks/app/ceo/page-01716d20af62d325.js +1 -0
  134. package/apps/pwa/out/_next/static/chunks/app/chat/page-62baf6881a64b1e9.js +1 -0
  135. package/apps/pwa/out/_next/static/chunks/app/consult/page-f89ba590c2af8afa.js +1 -0
  136. package/apps/pwa/out/_next/static/chunks/app/control/page-22f8b0f78d9637e5.js +1 -0
  137. package/apps/pwa/out/_next/static/chunks/app/decisions/page-817f9d7e6820be80.js +1 -0
  138. package/apps/pwa/out/_next/static/chunks/app/design-check/page-ffb9bc0d2650249a.js +1 -0
  139. package/apps/pwa/out/_next/static/chunks/app/editor/page-f6d0e64873c0f629.js +1 -0
  140. package/apps/pwa/out/_next/static/chunks/app/exec/page-8bfa0d4ba23a209d.js +1 -0
  141. package/apps/pwa/out/_next/static/chunks/app/field/page-f5060462249e32c7.js +1 -0
  142. package/apps/pwa/out/_next/static/chunks/app/healthz/route-8d9d76ea322d855c.js +1 -0
  143. package/apps/pwa/out/_next/static/chunks/app/inside/page-b2049f8b1ef79117.js +1 -0
  144. package/apps/pwa/out/_next/static/chunks/app/intake/page-1446c5fa93907f11.js +1 -0
  145. package/apps/pwa/out/_next/static/chunks/app/layout-b48a7a07c5204156.js +1 -0
  146. package/apps/pwa/out/_next/static/chunks/app/live/page-e974b8c4ca47614c.js +1 -0
  147. package/apps/pwa/out/_next/static/chunks/app/live-run/page-8a919b869bd28594.js +1 -0
  148. package/apps/pwa/out/_next/static/chunks/app/loops/page-d31b8de6bfcd72ed.js +1 -0
  149. package/apps/pwa/out/_next/static/chunks/app/market/page-64765f817909db29.js +1 -0
  150. package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-d128c8569a36ee9b.js +1 -0
  151. package/apps/pwa/out/_next/static/chunks/app/morning/page-b2679d357e9b9270.js +1 -0
  152. package/apps/pwa/out/_next/static/chunks/app/not-found-6fabec98a9e7b269.js +1 -0
  153. package/apps/pwa/out/_next/static/chunks/app/observatory/page-048f30149dcf1349.js +1 -0
  154. package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-9113181d6b5a2725.js +1 -0
  155. package/apps/pwa/out/_next/static/chunks/app/ops/release/page-40f9e19149024298.js +1 -0
  156. package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-1e7a755a13227611.js +1 -0
  157. package/apps/pwa/out/_next/static/chunks/app/outputs/page-3c8f8b67a203cf07.js +1 -0
  158. package/apps/pwa/out/_next/static/chunks/app/page-18032f5437215062.js +1 -0
  159. package/apps/pwa/out/_next/static/chunks/app/reflection/page-da3b739192fd0ee3.js +1 -0
  160. package/apps/pwa/out/_next/static/chunks/app/scheduler/page-d332545571bd6fd1.js +1 -0
  161. package/apps/pwa/out/_next/static/chunks/app/sessions/page-5237aa5b3f3b8ec5.js +1 -0
  162. package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-a142dfb0331a05f5.js +1 -0
  163. package/apps/pwa/out/_next/static/chunks/app/settings/page-d16e56c3989c147e.js +1 -0
  164. package/apps/pwa/out/_next/static/chunks/app/setup/done/page-6b6593600869e2cd.js +1 -0
  165. package/apps/pwa/out/_next/static/chunks/app/setup/layout-8d9d76ea322d855c.js +1 -0
  166. package/apps/pwa/out/_next/static/chunks/app/setup/page-29e8b8a8396b55cb.js +1 -0
  167. package/apps/pwa/out/_next/static/chunks/app/share/page-b3414d856a1a7e2f.js +1 -0
  168. package/apps/pwa/out/_next/static/chunks/app/showroom/page-c3affa52b7ce961b.js +1 -0
  169. package/apps/pwa/out/_next/static/chunks/app/tasks/page-f21dddf9f95b6fab.js +1 -0
  170. package/apps/pwa/out/_next/static/chunks/app/term/page-f5a30a24745bf088.js +1 -0
  171. package/apps/pwa/out/_next/static/chunks/app/today/page-8c8569a09b4d4e34.js +1 -0
  172. package/apps/pwa/out/_next/static/chunks/app/trace/page-2ce32722c0243483.js +1 -0
  173. package/apps/pwa/out/_next/static/chunks/app/vault/page-4767b0d9c0a98c6c.js +1 -0
  174. package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-116ee1339c387a75.js +1 -0
  175. package/apps/pwa/out/_next/static/chunks/app/workflows/page-35e8c50ca4ef7ffc.js +1 -0
  176. package/apps/pwa/out/_next/static/chunks/app/workspace/page-52e17113356bb891.js +1 -0
  177. package/apps/pwa/out/_next/static/chunks/app/worktrees/page-7458ae05ed2ac1a0.js +1 -0
  178. package/apps/pwa/out/_next/static/chunks/b2271e54.c1de3347976e90b0.js +1 -0
  179. package/apps/pwa/out/_next/static/chunks/{b7459770.6539b11860eb8a9c.js → c0c1a699.0ba79f97005965d4.js} +7 -7
  180. package/apps/pwa/out/_next/static/chunks/framework-ad6c9dd524ad6ef8.js +1 -0
  181. package/apps/pwa/out/_next/static/chunks/main-app-2ddd1f2b44d6aa59.js +1 -0
  182. package/apps/pwa/out/_next/static/chunks/main-e3d82bdc358d20c5.js +1 -0
  183. package/apps/pwa/out/_next/static/chunks/pages/_app-71d5aa3896e1655f.js +1 -0
  184. package/apps/pwa/out/_next/static/chunks/pages/_error-03ffc54e00438546.js +1 -0
  185. package/apps/pwa/out/_next/static/chunks/webpack-56bb89af5a611d0b.js +1 -0
  186. package/apps/pwa/out/approvals/index.html +1 -1
  187. package/apps/pwa/out/approvals/index.txt +22 -22
  188. package/apps/pwa/out/autopilot/index.html +1 -1
  189. package/apps/pwa/out/autopilot/index.txt +22 -22
  190. package/apps/pwa/out/board/index.html +1 -1
  191. package/apps/pwa/out/board/index.txt +22 -22
  192. package/apps/pwa/out/botlab/index.html +1 -1
  193. package/apps/pwa/out/botlab/index.txt +21 -21
  194. package/apps/pwa/out/bots/index.html +1 -1
  195. package/apps/pwa/out/bots/index.txt +21 -21
  196. package/apps/pwa/out/ceo/index.html +1 -1
  197. package/apps/pwa/out/ceo/index.txt +22 -22
  198. package/apps/pwa/out/chat/index.html +1 -1
  199. package/apps/pwa/out/chat/index.txt +21 -21
  200. package/apps/pwa/out/consult/index.html +1 -1
  201. package/apps/pwa/out/consult/index.txt +22 -22
  202. package/apps/pwa/out/control/index.html +1 -1
  203. package/apps/pwa/out/control/index.txt +22 -22
  204. package/apps/pwa/out/decisions/index.html +1 -1
  205. package/apps/pwa/out/decisions/index.txt +21 -21
  206. package/apps/pwa/out/design-check/index.html +1 -1
  207. package/apps/pwa/out/design-check/index.txt +22 -22
  208. package/apps/pwa/out/editor/index.html +1 -1
  209. package/apps/pwa/out/editor/index.txt +22 -22
  210. package/apps/pwa/out/exec/index.html +1 -1
  211. package/apps/pwa/out/exec/index.txt +22 -22
  212. package/apps/pwa/out/field/index.html +1 -1
  213. package/apps/pwa/out/field/index.txt +22 -22
  214. package/apps/pwa/out/healthz +1 -1
  215. package/apps/pwa/out/index.html +1 -1
  216. package/apps/pwa/out/index.txt +21 -21
  217. package/apps/pwa/out/inside/index.html +1 -1
  218. package/apps/pwa/out/inside/index.txt +21 -21
  219. package/apps/pwa/out/intake/index.html +1 -1
  220. package/apps/pwa/out/intake/index.txt +22 -22
  221. package/apps/pwa/out/live/index.html +1 -1
  222. package/apps/pwa/out/live/index.txt +22 -22
  223. package/apps/pwa/out/live-run/index.html +1 -1
  224. package/apps/pwa/out/live-run/index.txt +22 -22
  225. package/apps/pwa/out/loops/index.html +1 -1
  226. package/apps/pwa/out/loops/index.txt +21 -21
  227. package/apps/pwa/out/market/index.html +1 -1
  228. package/apps/pwa/out/market/index.txt +21 -21
  229. package/apps/pwa/out/missions/placeholder/index.html +1 -1
  230. package/apps/pwa/out/missions/placeholder/index.txt +21 -21
  231. package/apps/pwa/out/morning/index.html +1 -1
  232. package/apps/pwa/out/morning/index.txt +22 -22
  233. package/apps/pwa/out/observatory/index.html +1 -1
  234. package/apps/pwa/out/observatory/index.txt +22 -22
  235. package/apps/pwa/out/ops/checklist/index.html +1 -1
  236. package/apps/pwa/out/ops/checklist/index.txt +21 -21
  237. package/apps/pwa/out/ops/release/index.html +1 -1
  238. package/apps/pwa/out/ops/release/index.txt +21 -21
  239. package/apps/pwa/out/ops/seats/index.html +1 -1
  240. package/apps/pwa/out/ops/seats/index.txt +21 -21
  241. package/apps/pwa/out/outputs/index.html +1 -1
  242. package/apps/pwa/out/outputs/index.txt +21 -21
  243. package/apps/pwa/out/reflection/index.html +1 -1
  244. package/apps/pwa/out/reflection/index.txt +22 -22
  245. package/apps/pwa/out/scheduler/index.html +1 -1
  246. package/apps/pwa/out/scheduler/index.txt +22 -22
  247. package/apps/pwa/out/sessions/index.html +1 -1
  248. package/apps/pwa/out/sessions/index.txt +21 -21
  249. package/apps/pwa/out/settings/devices/index.html +1 -1
  250. package/apps/pwa/out/settings/devices/index.txt +22 -22
  251. package/apps/pwa/out/settings/index.html +1 -1
  252. package/apps/pwa/out/settings/index.txt +22 -22
  253. package/apps/pwa/out/setup/done/index.html +1 -1
  254. package/apps/pwa/out/setup/done/index.txt +22 -22
  255. package/apps/pwa/out/setup/index.html +1 -1
  256. package/apps/pwa/out/setup/index.txt +22 -22
  257. package/apps/pwa/out/share/index.html +1 -1
  258. package/apps/pwa/out/share/index.txt +22 -22
  259. package/apps/pwa/out/showroom/index.html +1 -1
  260. package/apps/pwa/out/showroom/index.txt +21 -21
  261. package/apps/pwa/out/tasks/index.html +1 -1
  262. package/apps/pwa/out/tasks/index.txt +22 -22
  263. package/apps/pwa/out/term/index.html +1 -1
  264. package/apps/pwa/out/term/index.txt +22 -22
  265. package/apps/pwa/out/today/index.html +1 -1
  266. package/apps/pwa/out/today/index.txt +22 -22
  267. package/apps/pwa/out/trace/index.html +1 -1
  268. package/apps/pwa/out/trace/index.txt +22 -22
  269. package/apps/pwa/out/vault/index.html +1 -1
  270. package/apps/pwa/out/vault/index.txt +22 -22
  271. package/apps/pwa/out/workflows/chat-ui/index.html +1 -1
  272. package/apps/pwa/out/workflows/chat-ui/index.txt +22 -22
  273. package/apps/pwa/out/workflows/index.html +1 -1
  274. package/apps/pwa/out/workflows/index.txt +22 -22
  275. package/apps/pwa/out/workspace/index.html +1 -1
  276. package/apps/pwa/out/workspace/index.txt +22 -22
  277. package/apps/pwa/out/worktrees/index.html +1 -1
  278. package/apps/pwa/out/worktrees/index.txt +22 -22
  279. package/bin/elanous.mjs +6 -1
  280. package/catalog/models/openai/gpt-6.1-sol.yaml +16 -0
  281. package/catalog/models/openai/gpt-6.1-terra.yaml +16 -0
  282. package/graphs/demo/persona-marketer/fixtures/marketer-scenario.yaml +10 -0
  283. package/graphs/demo/persona-marketer/persona-marketer.yaml +25 -0
  284. package/graphs/demo/persona-marketer/recipes.yaml +19 -0
  285. package/graphs/demo/persona-teacher/lesson-pack.yaml +16 -0
  286. package/graphs/demo/persona-teacher/recipes.yaml +17 -0
  287. package/graphs/demo/persona-teacher/weekly-lesson.yaml +36 -0
  288. package/graphs/overlays/stop-heal-ladder.yaml +23 -2
  289. package/graphs/release/release-loop.yaml +3 -1
  290. package/graphs/units/gate/gate.yaml +20 -0
  291. package/graphs/units/git/git.yaml +26 -0
  292. package/graphs/units/implement/implement.yaml +19 -0
  293. package/graphs/units/landing/landing.yaml +18 -0
  294. package/graphs/units/review/review.yaml +20 -0
  295. package/graphs/units/verbs/recipes.yaml +3 -0
  296. package/graphs/units/verbs/research.yaml +20 -0
  297. package/graphs/video/explainer-line.yaml +4 -1
  298. package/graphs/work/research-report.yaml +11 -1
  299. package/package.json +1 -1
  300. package/scripts/dead-code/report.ts +169 -0
  301. package/scripts/disk-steward.ts +46 -0
  302. package/scripts/fleet/node-setup.sh +50 -0
  303. package/scripts/graph-units/verbs/research.ts +55 -0
  304. package/scripts/lib/morning-report-options.ts +3 -4
  305. package/scripts/lib/tui-regress-evidence.ts +56 -0
  306. package/scripts/llm-cost-ledger.ts +179 -8
  307. package/scripts/measure-nl-routing-corpus.ts +10 -2
  308. package/scripts/morning-report.ts +5 -1
  309. package/scripts/persona-teacher/weekly-lesson-node.ts +172 -0
  310. package/scripts/public-copy-lint.ts +163 -19
  311. package/scripts/public-export.ts +15 -7
  312. package/scripts/ratchets/train-side-invariants.sh +0 -1
  313. package/scripts/release-loop/export-check-node.ts +21 -3
  314. package/scripts/release-loop/gate-autoheal.ts +117 -0
  315. package/scripts/release-loop/gate-baseline-receipt.ts +8 -1
  316. package/scripts/release-loop/gate-diff.ts +22 -3
  317. package/scripts/release-loop/gate-node.ts +583 -64
  318. package/scripts/release-loop/gate-shard-dispatch.ts +128 -0
  319. package/scripts/release-loop/gate-shard-load-flaky.ts +256 -0
  320. package/scripts/release-loop/gate-shard-receipts.ts +89 -0
  321. package/scripts/release-loop/gate-triage-node.ts +70 -10
  322. package/scripts/release-loop/gate-wall.ts +5 -5
  323. package/scripts/release-loop/preflight.ts +6 -2
  324. package/scripts/release-loop/resume-release.ts +267 -20
  325. package/scripts/release-loop/resume.ts +48 -0
  326. package/scripts/release-loop/traffic-node.ts +6 -3
  327. package/scripts/release-loop/unattended-release.ts +4 -2
  328. package/scripts/release-loop/version-node.ts +7 -2
  329. package/scripts/release-story/draft.ts +1 -1
  330. package/scripts/research-bench/README.md +53 -0
  331. package/scripts/research-bench/questions.json +66 -0
  332. package/scripts/research-bench/rubric.md +33 -0
  333. package/scripts/research-bench/run.ts +523 -0
  334. package/scripts/shadow-authoring-probe.ts +20 -0
  335. package/scripts/tui-regress.ts +85 -10
  336. package/scripts/ux-sim.ts +19 -2
  337. package/src/acp/core-turn-bridge.ts +94 -4
  338. package/src/agent/autonomous-tools.ts +10 -3
  339. package/src/agent/monad-agent-turn.ts +4 -1
  340. package/src/agent/registry.ts +26 -2
  341. package/src/agent/shared-app-tools.ts +1 -1
  342. package/src/agent/surface-ux/build.ts +12 -3
  343. package/src/agent/surface-ux/types.ts +1 -1
  344. package/src/agent/task-notification.ts +75 -6
  345. package/src/agent/types.ts +3 -0
  346. package/src/agent-mission/driver.ts +29 -3
  347. package/src/agent-mission/mission-cli.ts +2 -1
  348. package/src/agent-substrate/review-context-pack.ts +365 -0
  349. package/src/agent-substrate/self-review-cli.ts +291 -20
  350. package/src/ask-user-question/index.ts +6 -0
  351. package/src/ask-user-question/inline-resolver.ts +49 -0
  352. package/src/auto-research/question-ladder-contract.ts +22 -3
  353. package/src/auto-research/research-turn.ts +359 -17
  354. package/src/autopilot/agent-loop.ts +1 -1
  355. package/src/autopilot/discovery/wiki-claim-proposer.ts +22 -1
  356. package/src/autopilot/pty-control-loop.ts +8 -1
  357. package/src/boot/daemon-tools/index.ts +4 -3
  358. package/src/boot/daemon-tools/self-implement.ts +312 -7
  359. package/src/boot/daemon-tools/types.ts +2 -0
  360. package/src/budget/llm-cost.ts +44 -5
  361. package/src/budget/shadow-arms.ts +52 -0
  362. package/src/budget/unified-usage.ts +17 -1
  363. package/src/capture/tui-self-report.ts +14 -0
  364. package/src/chat/index.ts +33 -7
  365. package/src/chat/pickers/state.ts +7 -1
  366. package/src/cli/agent-cli.ts +43 -8
  367. package/src/cli/intake-cli.ts +22 -1
  368. package/src/cli/lesson-cli.ts +19 -3
  369. package/src/cli/log-event-names.ts +6 -0
  370. package/src/cli/mcp-login.ts +8 -18
  371. package/src/cli/msg-cli.ts +57 -1
  372. package/src/cli/pod-cli.ts +17 -2
  373. package/src/cli/pr-land-heavy-remote.ts +15 -9
  374. package/src/cli/pty-takeover-cli.ts +67 -7
  375. package/src/cli/release-cli.ts +79 -7
  376. package/src/cli/repo-cli.ts +2 -1
  377. package/src/cli/sim-cli.ts +7 -1
  378. package/src/cli/tasks-cli.ts +41 -13
  379. package/src/codex/models.ts +30 -15
  380. package/src/control-plane/ledger.ts +21 -4
  381. package/src/core-turn/run-core-turn.ts +47 -3
  382. package/src/core-turn/run-goal-loop.ts +240 -10
  383. package/src/core-turn/types.ts +9 -0
  384. package/src/dashboard/acp-boot.ts +72 -3
  385. package/src/dashboard/chat/acp-chat.ts +2 -2
  386. package/src/dashboard/classic-sigquit.ts +16 -0
  387. package/src/dashboard/index.ts +327 -27
  388. package/src/dashboard/input/chat-main-interaction-opts.ts +3 -0
  389. package/src/dashboard/input/chat-main-plain-turn-runtime.ts +7 -2
  390. package/src/dashboard/input/chat-main-slash-command.ts +7 -0
  391. package/src/dashboard/input/dashboard-plain-turn-stream.ts +4 -0
  392. package/src/dashboard/input/dashboard-priority-key-route.ts +21 -5
  393. package/src/dashboard/input/external-input-host.ts +2 -0
  394. package/src/dashboard/sidetab-runtime.ts +228 -0
  395. package/src/dashboard/slash-runtime/ask-clarification.ts +7 -1
  396. package/src/dashboard/slash-runtime/dashboard-handlers.ts +20 -8
  397. package/src/dashboard/slash-runtime/help-from-registry.ts +2 -2
  398. package/src/dashboard/term-slash-runtime.ts +16 -18
  399. package/src/dashboard/turn-preamble.ts +14 -1
  400. package/src/disk-steward/judge.ts +73 -0
  401. package/src/disk-steward/ledger.ts +122 -0
  402. package/src/disk-steward/steward.ts +373 -0
  403. package/src/domains/guardian-tick.ts +191 -2
  404. package/src/domains/knowledge.ts +1 -1
  405. package/src/esc-abort-gate.ts +33 -1
  406. package/src/execution-loop/launch-gate.ts +206 -1
  407. package/src/graph-runner/graph-cli.ts +27 -4
  408. package/src/graph-runner/in-process-registry.ts +37 -0
  409. package/src/graph-runner/runner.ts +63 -11
  410. package/src/graph-wizard/generate.ts +16 -7
  411. package/src/graph-wizard/mission-compose.ts +201 -0
  412. package/src/grok/agent-search.ts +8 -2
  413. package/src/grok/credential.ts +5 -0
  414. package/src/grounding/ref-index.ts +30 -0
  415. package/src/grounding/ref-vector.ts +61 -0
  416. package/src/grounding/sources-cli.ts +11 -3
  417. package/src/grounding/sources.ts +15 -1
  418. package/src/harness/harness-cli-command.ts +305 -23
  419. package/src/harness/harness-incidents.ts +312 -7
  420. package/src/harness/harness-pod-dispatch.ts +7 -1
  421. package/src/harness/harness-space.ts +15 -1
  422. package/src/harness/progress-worker-entry.ts +59 -0
  423. package/src/harness/progress-worker-runtime.ts +11 -0
  424. package/src/index.ts +35 -5
  425. package/src/input/external-input-queue.ts +10 -0
  426. package/src/instance/dev-project.ts +25 -0
  427. package/src/intake-plane/collect-telegram-saved.ts +36 -1
  428. package/src/intake-plane/intake-to-tasks.ts +246 -3
  429. package/src/intelligence-map/model-alias.ts +6 -5
  430. package/src/intelligence-map/model-catalog.ts +59 -2
  431. package/src/lessons/friction-ledger.ts +154 -0
  432. package/src/live-supply/collector.ts +149 -0
  433. package/src/live-supply/probes.ts +52 -0
  434. package/src/live-supply/snapshot.ts +40 -0
  435. package/src/llm/model-defaults.ts +4 -4
  436. package/src/llm.ts +473 -87
  437. package/src/loops/orchestrator/tick.ts +56 -0
  438. package/src/mcp/mcp-oauth.ts +3 -1
  439. package/src/model-tier/llm-tier-map.ts +9 -9
  440. package/src/model-tier/turn-tier.ts +1 -1
  441. package/src/msg/msg-mirror-github.ts +80 -0
  442. package/src/msg/msg-mirror-policy.ts +61 -0
  443. package/src/msg/msg-mirror-runner.ts +219 -0
  444. package/src/msg/msg-mirror-state.ts +33 -0
  445. package/src/msg/msg-store.ts +11 -0
  446. package/src/nexus/api/harness-api.ts +2 -1
  447. package/src/output-truncation.ts +41 -12
  448. package/src/project/project-store.ts +48 -1
  449. package/src/pty/snapshot.py +132 -0
  450. package/src/pty-shell/pty-control-ipc.ts +29 -2
  451. package/src/pty-shell/pty-manifest.ts +59 -3
  452. package/src/pty-shell/registry.ts +2 -0
  453. package/src/pty-shell/tui-run-state.ts +80 -3
  454. package/src/release-loop/gate-host-reservation.ts +157 -4
  455. package/src/release-loop/gate-shard-ledger.ts +68 -0
  456. package/src/release-loop/merged-pr-checklist.ts +25 -2
  457. package/src/release-loop/rehearsal-shard-plan.ts +6 -1
  458. package/src/release-loop/rehearsal.ts +27 -0
  459. package/src/release-loop/release-schedule.ts +90 -1
  460. package/src/research/bloom-exemplars.ts +135 -0
  461. package/src/research/edge-decision.ts +124 -15
  462. package/src/research/gap-followup.ts +249 -0
  463. package/src/research/lenses/counter-evidence.ts +100 -0
  464. package/src/research/lenses/working-backwards.ts +89 -0
  465. package/src/research/plugin-discovery.ts +242 -0
  466. package/src/research-bridge/invoke.ts +4 -2
  467. package/src/research-bridge/types.ts +2 -0
  468. package/src/self-dev/ask-launch-flow.ts +73 -131
  469. package/src/self-dev/dev-cli.ts +19 -17
  470. package/src/self-dev/dev-pipeline.ts +8 -4
  471. package/src/self-dev/graph-front-nodes.ts +23 -0
  472. package/src/self-dev/graph-journey-route.ts +10 -2
  473. package/src/self-dev/launch-preflight-text.ts +2 -2
  474. package/src/self-dev/launch-preflight.ts +47 -11
  475. package/src/self-dev/orchestrate-cli.ts +1 -0
  476. package/src/self-dev/orchestrate.ts +15 -0
  477. package/src/self-dev/run-supervisor.ts +204 -3
  478. package/src/self-dev/run-types.ts +3 -0
  479. package/src/self-implement/device-first.ts +8 -2
  480. package/src/self-implement/doctor-visit.ts +76 -58
  481. package/src/self-implement/gate-artifacts.ts +16 -0
  482. package/src/self-implement/gate-baseline.ts +75 -4
  483. package/src/self-implement/gate-cli.ts +368 -30
  484. package/src/self-implement/gate-receipt-registry.ts +180 -0
  485. package/src/self-implement/gate-remote.ts +165 -24
  486. package/src/self-implement/goal-author-clarification.ts +205 -32
  487. package/src/self-implement/goal-author-decompose.ts +24 -15
  488. package/src/self-implement/goal-author.ts +86 -10
  489. package/src/self-implement/graph-stage-units.ts +172 -0
  490. package/src/self-implement/graph-templates.ts +162 -1
  491. package/src/self-implement/graph-variant.ts +37 -4
  492. package/src/self-implement/host-regate.ts +124 -49
  493. package/src/self-implement/impl-findings-feedback.ts +188 -0
  494. package/src/self-implement/knowhow-pack.ts +227 -10
  495. package/src/self-implement/off-diff-evidence.ts +124 -0
  496. package/src/self-implement/orchestrator.ts +320 -28
  497. package/src/self-implement/run-ledger.ts +110 -14
  498. package/src/self-implement/run-stop.ts +33 -2
  499. package/src/self-implement/running-runs.ts +35 -12
  500. package/src/self-implement/seams.ts +6 -3
  501. package/src/self-implement/self-implement-cli.ts +40 -6
  502. package/src/self-implement/stop-autoheal-operational.ts +43 -0
  503. package/src/self-implement/stop-autoheal.ts +15 -6
  504. package/src/session/chat.ts +66 -15
  505. package/src/session/request-size-guard.ts +123 -0
  506. package/src/session-runtime/provider-circuit.ts +140 -0
  507. package/src/shell-runner/file-engine.ts +1 -0
  508. package/src/shell-runner/types.ts +4 -0
  509. package/src/sidetab-core/model.ts +312 -0
  510. package/src/skills/tools/schedule-wakeup.ts +23 -1
  511. package/src/skills/tools/shell.ts +51 -5
  512. package/src/steward/directive-audit.ts +354 -0
  513. package/src/surface/child-process.ts +31 -0
  514. package/src/surface/tui-stderr-owner.ts +48 -0
  515. package/src/task-agent/cover.ts +30 -12
  516. package/src/task-agent/judge.ts +56 -0
  517. package/src/task-agent/parent-host.ts +14 -1
  518. package/src/task-agent/postland-card.ts +35 -2
  519. package/src/task-agent/rejudge-on-head.ts +46 -2
  520. package/src/task-agent/repair-cycle.ts +1 -1
  521. package/src/task-agent/task-hand.ts +133 -25
  522. package/src/task-agent/tier-split.ts +105 -21
  523. package/src/task-orchestrator/surfaces/pod-command-job.ts +330 -2
  524. package/src/task-orchestrator/surfaces/pod-config-snapshot.ts +123 -0
  525. package/src/task-orchestrator/surfaces/pod-failure-reason.ts +70 -2
  526. package/src/task-orchestrator/surfaces/pod-ledger-events.ts +29 -4
  527. package/src/task-orchestrator/surfaces/pod-mirror-seed.ts +11 -8
  528. package/src/task-orchestrator/surfaces/pod-si-warm-protocol.ts +1 -1
  529. package/src/task-orchestrator/surfaces/pod-source-receive.ts +74 -6
  530. package/src/task-orchestrator/surfaces/pod-warm-worker-pod.ts +2 -1
  531. package/src/task-orchestrator/surfaces/pod-warm-worker-provider.ts +56 -15
  532. package/src/task-orchestrator/surfaces/self-implement-pod.ts +298 -45
  533. package/src/task-orchestrator/surfaces/self-implement.ts +18 -0
  534. package/src/tool-runtime/skill-exec-runtime.ts +95 -5
  535. package/src/tui/entry.ts +25 -5
  536. package/src/tui/inline-choice.ts +188 -0
  537. package/src/tui/sidetab/list.ts +36 -165
  538. package/src/tui/sidetab/nl-tool.ts +2 -136
  539. package/src/tui/sidetab/peek.ts +52 -0
  540. package/src/tui/slash/term.ts +12 -1
  541. package/src/tui-client/dashboard-session.ts +10 -1
  542. package/src/user-config.ts +45 -9
  543. package/src/ux-sim/classic-tui-seat-scenarios.ts +1 -7
  544. package/src/ux-sim/fake-land-queue.ts +88 -0
  545. package/src/ux-sim/fault-needs-human-reason-repair.ts +107 -0
  546. package/src/ux-sim/fault-pod-child-result.ts +42 -0
  547. package/src/ux-sim/gate-shard-host-reroute.ts +82 -0
  548. package/src/ux-sim/goal-interim-trace.ts +24 -0
  549. package/src/ux-sim/next-tui-seat-scenarios.ts +8 -13
  550. package/src/ux-sim/release-sim-rig.ts +262 -0
  551. package/src/ux-sim/seminar-rehearsal.ts +109 -0
  552. package/src/ux-sim/subagent-tools-device.ts +2 -2
  553. package/src/ux-sim/task-orchestrator-surfaces-self-implement-pod-device.ts +4 -1
  554. package/src/version/packed-revision.json +1 -1
  555. package/src/video-pipeline/recipes/explainer.ts +54 -2
  556. package/src/web-search/grok.ts +32 -6
  557. package/src/web-search/index.ts +8 -7
  558. package/src/workflow-runtime/node-catalog.ts +53 -4
  559. package/apps/pwa/out/_next/static/chunks/1118.a8a74ea29aac3e46.js +0 -27
  560. package/apps/pwa/out/_next/static/chunks/1204-2aa830479adf80f4.js +0 -1
  561. package/apps/pwa/out/_next/static/chunks/1341-43b7d2dc77d45c9d.js +0 -1
  562. package/apps/pwa/out/_next/static/chunks/1440-c3ea8882badfd9bf.js +0 -1
  563. package/apps/pwa/out/_next/static/chunks/1698-9c11cbf97f13717e.js +0 -1
  564. package/apps/pwa/out/_next/static/chunks/1770-3b1fc92253ef9f2f.js +0 -1
  565. package/apps/pwa/out/_next/static/chunks/1923-5c1695332240246a.js +0 -1
  566. package/apps/pwa/out/_next/static/chunks/1938.0e6c60ee91c4d7f5.js +0 -148
  567. package/apps/pwa/out/_next/static/chunks/2104.70e086d5174a4736.js +0 -1
  568. package/apps/pwa/out/_next/static/chunks/213-20675f20673ba22a.js +0 -1
  569. package/apps/pwa/out/_next/static/chunks/214.186a430da28338f1.js +0 -1
  570. package/apps/pwa/out/_next/static/chunks/2277.3bd4c0ac7f1b5996.js +0 -93
  571. package/apps/pwa/out/_next/static/chunks/240.e09f433f71c78ff4.js +0 -104
  572. package/apps/pwa/out/_next/static/chunks/2417.02151393605a7cd0.js +0 -1
  573. package/apps/pwa/out/_next/static/chunks/2463.cd2641a76daaa9ff.js +0 -1
  574. package/apps/pwa/out/_next/static/chunks/2576.b9e9c629c4b84c52.js +0 -1
  575. package/apps/pwa/out/_next/static/chunks/265-c021de53f0865bd9.js +0 -1
  576. package/apps/pwa/out/_next/static/chunks/2998-b1cc13956cd6a6e7.js +0 -1
  577. package/apps/pwa/out/_next/static/chunks/2e4782d3.ba2f0ab2b63a53e7.js +0 -1
  578. package/apps/pwa/out/_next/static/chunks/3130.626b54382b4dc379.js +0 -1
  579. package/apps/pwa/out/_next/static/chunks/3221-1bb3f99a55088613.js +0 -1
  580. package/apps/pwa/out/_next/static/chunks/3280.24edb1ffd03a7f3f.js +0 -24
  581. package/apps/pwa/out/_next/static/chunks/3288-eb3c22a1cbf2ae68.js +0 -1
  582. package/apps/pwa/out/_next/static/chunks/33.ef99e8374f96c6c4.js +0 -36
  583. package/apps/pwa/out/_next/static/chunks/3341-f09b9efbd7a82f70.js +0 -1
  584. package/apps/pwa/out/_next/static/chunks/3410-d7c0f14b329d6fda.js +0 -1
  585. package/apps/pwa/out/_next/static/chunks/3421.c87d6313a7d670f7.js +0 -287
  586. package/apps/pwa/out/_next/static/chunks/3422-83a3953f9bd67e26.js +0 -1
  587. package/apps/pwa/out/_next/static/chunks/3587-002e24e368c515a9.js +0 -1
  588. package/apps/pwa/out/_next/static/chunks/3644.f12a7d821ab940af.js +0 -1
  589. package/apps/pwa/out/_next/static/chunks/3660.d7516588e2d875c3.js +0 -1
  590. package/apps/pwa/out/_next/static/chunks/3695.b82e2610f4cd4ea9.js +0 -1
  591. package/apps/pwa/out/_next/static/chunks/3858.ca1f5bc0f577eac9.js +0 -94
  592. package/apps/pwa/out/_next/static/chunks/3959-e6ac4a139d9d4bcc.js +0 -1
  593. package/apps/pwa/out/_next/static/chunks/3f0de3de-2340c532c00395db.js +0 -1
  594. package/apps/pwa/out/_next/static/chunks/4032.53f62176514ec0ea.js +0 -1
  595. package/apps/pwa/out/_next/static/chunks/4199-f7c6eb40cd0322f8.js +0 -1
  596. package/apps/pwa/out/_next/static/chunks/4204-ef8484cbecd5d62f.js +0 -1
  597. package/apps/pwa/out/_next/static/chunks/4259-163129ca79913c4b.js +0 -1
  598. package/apps/pwa/out/_next/static/chunks/428-eaa77df3d0c85969.js +0 -1
  599. package/apps/pwa/out/_next/static/chunks/4432-97e400ffa1e161f5.js +0 -1
  600. package/apps/pwa/out/_next/static/chunks/449-aa427cf2cbb75f50.js +0 -1
  601. package/apps/pwa/out/_next/static/chunks/4491-39a0fd32bbaf3840.js +0 -1
  602. package/apps/pwa/out/_next/static/chunks/4588.b7cf06d382953979.js +0 -1
  603. package/apps/pwa/out/_next/static/chunks/4690.70ec8060825366ab.js +0 -32
  604. package/apps/pwa/out/_next/static/chunks/4804.6012b5cd33c22792.js +0 -90
  605. package/apps/pwa/out/_next/static/chunks/4881.e4d22d730e3b9df5.js +0 -1
  606. package/apps/pwa/out/_next/static/chunks/4937.ce2e340dc29cad3e.js +0 -79
  607. package/apps/pwa/out/_next/static/chunks/5-bb1c08d84bd71df3.js +0 -1
  608. package/apps/pwa/out/_next/static/chunks/5005.de98df23b37cdf3c.js +0 -1
  609. package/apps/pwa/out/_next/static/chunks/5035.dc64a89cad5573cc.js +0 -74
  610. package/apps/pwa/out/_next/static/chunks/5041-5aada92ca215ffdd.js +0 -1
  611. package/apps/pwa/out/_next/static/chunks/5207.1a224035455790fd.js +0 -1
  612. package/apps/pwa/out/_next/static/chunks/5255-1b60d50eabe9f057.js +0 -1
  613. package/apps/pwa/out/_next/static/chunks/5269.d0436ee6d773382a.js +0 -286
  614. package/apps/pwa/out/_next/static/chunks/5309.3367c4d50f52b489.js +0 -1
  615. package/apps/pwa/out/_next/static/chunks/552-689827d49780fa00.js +0 -1
  616. package/apps/pwa/out/_next/static/chunks/5539.34cc9d60622cb69b.js +0 -8
  617. package/apps/pwa/out/_next/static/chunks/5568.218dea0c00ca2ec7.js +0 -1
  618. package/apps/pwa/out/_next/static/chunks/5645.b7e3b055455a04ea.js +0 -1
  619. package/apps/pwa/out/_next/static/chunks/5662.18cc0f30353cbd96.js +0 -1
  620. package/apps/pwa/out/_next/static/chunks/5671.da24fc9dc5e98325.js +0 -1
  621. package/apps/pwa/out/_next/static/chunks/5b141171.324c40fd49cb6821.js +0 -1
  622. package/apps/pwa/out/_next/static/chunks/6175-d4621f6a10b0cfab.js +0 -1
  623. package/apps/pwa/out/_next/static/chunks/6290.3eb53a20746b72ce.js +0 -1
  624. package/apps/pwa/out/_next/static/chunks/6415-9307f3eafa90837f.js +0 -1
  625. package/apps/pwa/out/_next/static/chunks/6579-3de35d00aacd71b5.js +0 -1
  626. package/apps/pwa/out/_next/static/chunks/680-2f324c4e039a5b67.js +0 -1
  627. package/apps/pwa/out/_next/static/chunks/6845-331b3c7481da3ba3.js +0 -1
  628. package/apps/pwa/out/_next/static/chunks/7000.28157393caaf5343.js +0 -62
  629. package/apps/pwa/out/_next/static/chunks/7311-60a7ea80d23c7521.js +0 -1
  630. package/apps/pwa/out/_next/static/chunks/7401.525d0a12f7d02c06.js +0 -1
  631. package/apps/pwa/out/_next/static/chunks/7438.c2cf72b66dca6aa4.js +0 -1
  632. package/apps/pwa/out/_next/static/chunks/7488.966b116789f3d41a.js +0 -1
  633. package/apps/pwa/out/_next/static/chunks/7524.ce973525d30b3d52.js +0 -1
  634. package/apps/pwa/out/_next/static/chunks/7577.ea6e9ac72e035520.js +0 -1
  635. package/apps/pwa/out/_next/static/chunks/7628.6b16863ac3972333.js +0 -34
  636. package/apps/pwa/out/_next/static/chunks/7657.8d1fb3d2f7ebe273.js +0 -1
  637. package/apps/pwa/out/_next/static/chunks/7903-1435d5d2f0dd7807.js +0 -1
  638. package/apps/pwa/out/_next/static/chunks/7954.4f7a8832663ee979.js +0 -115
  639. package/apps/pwa/out/_next/static/chunks/7978-30a91192c5dbe3c2.js +0 -1
  640. package/apps/pwa/out/_next/static/chunks/8025-8795821525cf1a07.js +0 -1
  641. package/apps/pwa/out/_next/static/chunks/8191.3674a00f0b565c23.js +0 -1
  642. package/apps/pwa/out/_next/static/chunks/8217-604955d8885c5ef2.js +0 -1
  643. package/apps/pwa/out/_next/static/chunks/8298-eed6f5f2585a63f4.js +0 -1
  644. package/apps/pwa/out/_next/static/chunks/8509.3a54d4e61893d7cb.js +0 -1
  645. package/apps/pwa/out/_next/static/chunks/8758.ac421f726a189125.js +0 -1
  646. package/apps/pwa/out/_next/static/chunks/891.d6c723a51a067b36.js +0 -149
  647. package/apps/pwa/out/_next/static/chunks/9223.cbcc88e0e9950426.js +0 -41
  648. package/apps/pwa/out/_next/static/chunks/9299.24e2a7d9b6d1f91b.js +0 -226
  649. package/apps/pwa/out/_next/static/chunks/9317.6a9869039c231bb3.js +0 -24
  650. package/apps/pwa/out/_next/static/chunks/9383.e4755f275b3c11ff.js +0 -1
  651. package/apps/pwa/out/_next/static/chunks/9581.da63ddf41acfad46.js +0 -1
  652. package/apps/pwa/out/_next/static/chunks/9715.8c5529a0a5c41a36.js +0 -1
  653. package/apps/pwa/out/_next/static/chunks/9817.3009d65f0889ef1f.js +0 -2
  654. package/apps/pwa/out/_next/static/chunks/app/_not-found/page-76873dd80da4f715.js +0 -1
  655. package/apps/pwa/out/_next/static/chunks/app/approvals/page-ed32b6ec5dea8f23.js +0 -1
  656. package/apps/pwa/out/_next/static/chunks/app/autopilot/page-fdd40e15babf3d25.js +0 -1
  657. package/apps/pwa/out/_next/static/chunks/app/board/page-384efc78e85e400b.js +0 -1
  658. package/apps/pwa/out/_next/static/chunks/app/bots/page-d91809c5aeed319a.js +0 -1
  659. package/apps/pwa/out/_next/static/chunks/app/ceo/page-128f3522f89a81ab.js +0 -1
  660. package/apps/pwa/out/_next/static/chunks/app/chat/page-595961abf3b43ad1.js +0 -1
  661. package/apps/pwa/out/_next/static/chunks/app/consult/page-f41dccb76d8c0263.js +0 -1
  662. package/apps/pwa/out/_next/static/chunks/app/control/page-a3205c2e28b7d0d9.js +0 -1
  663. package/apps/pwa/out/_next/static/chunks/app/decisions/page-c39a80277814a3f4.js +0 -1
  664. package/apps/pwa/out/_next/static/chunks/app/design-check/page-1ab3f98194513195.js +0 -1
  665. package/apps/pwa/out/_next/static/chunks/app/editor/page-a5246f7e254d77d0.js +0 -1
  666. package/apps/pwa/out/_next/static/chunks/app/exec/page-0f92287bdb81217d.js +0 -1
  667. package/apps/pwa/out/_next/static/chunks/app/field/page-5a37131ff63793ef.js +0 -1
  668. package/apps/pwa/out/_next/static/chunks/app/healthz/route-76873dd80da4f715.js +0 -1
  669. package/apps/pwa/out/_next/static/chunks/app/inside/page-ac4bd14bb2348bfd.js +0 -1
  670. package/apps/pwa/out/_next/static/chunks/app/intake/page-c348a3959c5b5fc6.js +0 -1
  671. package/apps/pwa/out/_next/static/chunks/app/layout-2addd81c0d3e2906.js +0 -1
  672. package/apps/pwa/out/_next/static/chunks/app/live/page-da6b765f58a3eefb.js +0 -1
  673. package/apps/pwa/out/_next/static/chunks/app/live-run/page-0661e40f8780c32c.js +0 -1
  674. package/apps/pwa/out/_next/static/chunks/app/loops/page-b89af1b1c8e4875b.js +0 -1
  675. package/apps/pwa/out/_next/static/chunks/app/market/page-da8aeb82ba751cdb.js +0 -1
  676. package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-cc71317b239439db.js +0 -1
  677. package/apps/pwa/out/_next/static/chunks/app/morning/page-bde7fc1d64ffe369.js +0 -1
  678. package/apps/pwa/out/_next/static/chunks/app/not-found-e2797214f713fa58.js +0 -1
  679. package/apps/pwa/out/_next/static/chunks/app/observatory/page-2a35bcda70defaf6.js +0 -1
  680. package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-3af03deedde45032.js +0 -1
  681. package/apps/pwa/out/_next/static/chunks/app/ops/release/page-d1d1210f99f620ae.js +0 -1
  682. package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-46d1b5500885861d.js +0 -1
  683. package/apps/pwa/out/_next/static/chunks/app/outputs/page-291ab19fe2acb173.js +0 -1
  684. package/apps/pwa/out/_next/static/chunks/app/page-7f569e533ddeecba.js +0 -1
  685. package/apps/pwa/out/_next/static/chunks/app/reflection/page-990129c9fee46d8f.js +0 -1
  686. package/apps/pwa/out/_next/static/chunks/app/scheduler/page-7737f785ebb1cdaf.js +0 -1
  687. package/apps/pwa/out/_next/static/chunks/app/sessions/page-9f3c73a4f7ffd2f8.js +0 -1
  688. package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-03be7fb347f01058.js +0 -1
  689. package/apps/pwa/out/_next/static/chunks/app/settings/page-96b0280625e4df2b.js +0 -1
  690. package/apps/pwa/out/_next/static/chunks/app/setup/done/page-56855545049eb56d.js +0 -1
  691. package/apps/pwa/out/_next/static/chunks/app/setup/layout-76873dd80da4f715.js +0 -1
  692. package/apps/pwa/out/_next/static/chunks/app/setup/page-79a909c9981f0338.js +0 -1
  693. package/apps/pwa/out/_next/static/chunks/app/share/page-a9d9a3e66459c1e0.js +0 -1
  694. package/apps/pwa/out/_next/static/chunks/app/showroom/page-c383cbf2013f7069.js +0 -1
  695. package/apps/pwa/out/_next/static/chunks/app/tasks/page-f57c6a2e54dbdca4.js +0 -1
  696. package/apps/pwa/out/_next/static/chunks/app/term/page-6b140f77593576eb.js +0 -1
  697. package/apps/pwa/out/_next/static/chunks/app/today/page-6b767ae2d9d0adfc.js +0 -1
  698. package/apps/pwa/out/_next/static/chunks/app/trace/page-116d6198d5da0e3d.js +0 -1
  699. package/apps/pwa/out/_next/static/chunks/app/vault/page-b9c9b778c7501370.js +0 -1
  700. package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-a6c78392ab8f6335.js +0 -1
  701. package/apps/pwa/out/_next/static/chunks/app/workflows/page-455183deb4ed0cfe.js +0 -1
  702. package/apps/pwa/out/_next/static/chunks/app/workspace/page-6a63e99526bd63d0.js +0 -1
  703. package/apps/pwa/out/_next/static/chunks/app/worktrees/page-31c22caafe788c08.js +0 -1
  704. package/apps/pwa/out/_next/static/chunks/bb6987f9.3647e1a23b0e3217.js +0 -122
  705. package/apps/pwa/out/_next/static/chunks/framework-4b12a946f352cee2.js +0 -1
  706. package/apps/pwa/out/_next/static/chunks/main-941155250ed2644b.js +0 -1
  707. package/apps/pwa/out/_next/static/chunks/main-app-f8b6765abed6d149.js +0 -1
  708. package/apps/pwa/out/_next/static/chunks/pages/_app-78432194c85388f9.js +0 -1
  709. package/apps/pwa/out/_next/static/chunks/pages/_error-cdf7390829512b1b.js +0 -1
  710. package/apps/pwa/out/_next/static/chunks/webpack-d5f0964a9c2e92d2.js +0 -1
  711. package/scripts/ratchets/next-tui-entry-budget.ts +0 -124
  712. /package/apps/pwa/out/_next/static/{RrjXTwz-urRAbChP1bX02 → GiOLWmt4MqDZePubBjA4Q}/_ssgManifest.js +0 -0
@@ -1,10 +1,9 @@
1
- import { existsSync, lstatSync, mkdirSync, mkdtempSync, readFileSync, realpathSync, renameSync, rmSync, writeFileSync } from 'node:fs';
2
- import { randomUUID } from 'node:crypto';
1
+ import { existsSync, lstatSync, mkdirSync, mkdtempSync, readFileSync, readdirSync, realpathSync, renameSync, rmSync, writeFileSync } from 'node:fs';
2
+ import { createHash, randomUUID } from 'node:crypto';
3
3
  import { tmpdir } from 'node:os';
4
4
  import { spawnSync } from 'node:child_process';
5
- import { join } from 'node:path/posix';
5
+ import { basename, join, resolve } from 'node:path/posix';
6
6
  import { prepareDeterministicChildEnvironment } from '../../scripts/lib/deterministic-env.js';
7
- import { audit as auditEntryBudget, entryBudgetAffected } from '../../scripts/ratchets/next-tui-entry-budget.js';
8
7
  import { withGateTestEnv } from '../../scripts/lib/gate-test-env.js';
9
8
  import { runIsolationHardcodeGate } from '../../scripts/ci-isolation-hardcode-gate.js';
10
9
  import { runModelHardcodeGate } from '../../scripts/ci-model-hardcode-gate.js';
@@ -14,11 +13,12 @@ import { runIosUnitTestGate } from '../../scripts/ci-ios-unit-tests.js';
14
13
  import { runPwaBuildGate } from '../../scripts/ci-pwa-build-gate.js';
15
14
  import { runMockModuleRestoreGate } from '../../scripts/ci-mock-module-restore-gate.js';
16
15
  import { parseReviewDepthFromFilesJson } from '../agent-mission/review-depth.js';
17
- import { buildGateBaselineReport, calculateGateTestCountChange, formatGateBaselineNote, formatGateTestCountNote, isGateTestFile, recheckTimeoutOnlyIntroducedFailures, runGateBaseline, type BaselineProcessResult, type BaselineProcessStatus, type GateTestFailure, type TimeoutRecheckRecord, type TimeoutRerunObservation } from './gate-baseline.js';
16
+ import { buildGateBaselineReport, calculateGateTestCountChange, formatGateBaselineNote, formatGateTestCountNote, isGateTestFile, recheckOutsideScopeFailures, recheckTimeoutOnlyIntroducedFailures, runGateBaseline, type BaselineProcessResult, type BaselineProcessStatus, type GateBaselineReport, type GateTestFailure, type InterferenceRecheckRecord, type TimeoutRecheckRecord, type TimeoutRerunObservation } from './gate-baseline.js';
18
17
  import { resolveGateScope } from './gate-scope.js';
19
18
  import { publicExposureFiles, runExposeGate } from './expose-gate.js';
20
19
  import { getUserConfig } from '../user-config.js';
21
20
  import { debug, redactSecretText } from '../debug/log.js';
21
+ import { getElanousConfigDir } from '../elanous-config-dir.js';
22
22
  import { buildDocumentGuardianIndex, formatDocumentGuardians } from './document-guardian-index.js';
23
23
  import { buildImporterTestIndex, importerTestsNotInRunSet, isTestPath, type ImporterTestIndex } from './importer-test-index.js';
24
24
  import { isCommentOnlySourceChange } from './comment-only-source.js';
@@ -38,6 +38,8 @@ import { defaultGateEnvKey, defaultRevResolver, resolveArtifactDir, writeGateArt
38
38
  export interface SelfGateCliOptions {
39
39
  base?: string;
40
40
  pr?: string;
41
+ /** Bypass reuse of the last passing test radius; still write this run's receipt for the next invocation. */
42
+ noInherit?: boolean;
41
43
  shards?: number;
42
44
  /** Live shard bundle concurrency; default three, bounded to one through four. */
43
45
  shardConcurrency?: number;
@@ -55,6 +57,49 @@ export interface SelfGateCliOptions {
55
57
  scenarioFile?: string;
56
58
  /** SIDE-VERIFY — 조각별 지금/기준 JUnit ⊕ summary.json 을 이 디렉토리에 «쓰기만» 한다(판정·exit·기존 줄 불변). */
57
59
  artifactDir?: string;
60
+ /** Marker captured by the process entry point; keeps receipts stable if the environment changes during dispatch. */
61
+ trainGate?: boolean;
62
+ }
63
+
64
+ const SELF_GATE_SEAT_TRACKS = new Set(['OP', 'OPC', 'OPT', 'TC', 'UX', 'MK']);
65
+
66
+ interface SelfGateTrainMarker {
67
+ track: string | null;
68
+ received: boolean;
69
+ }
70
+
71
+ /** Capture and log the marker exactly as the self-gate process received it. */
72
+ export function observeSelfGateTrainMarker(): SelfGateTrainMarker {
73
+ const track = process.env.ELANOUS_TRACK?.trim() || null;
74
+ const received = process.env.ELANOUS_TRAIN_GATE === '1';
75
+ try { debug.log('self-gate', 'train-gate-marker', { track, received }); } catch { /* evidence logging must not change gate behavior */ }
76
+ return { track, received };
77
+ }
78
+
79
+ /** Seat invocations may only measure the pinned tree after the landing train has admitted the gate. */
80
+ export function refuseSeatSelfGateWithoutTrainMarker(marker = observeSelfGateTrainMarker()): { track: string; message: string } | undefined {
81
+ const { track, received } = marker;
82
+ if (!track || !SELF_GATE_SEAT_TRACKS.has(track) || received) return undefined;
83
+ try { debug.log('self-gate', 'seat-refused', { track, requiredMarker: 'ELANOUS_TRAIN_GATE=1' }); } catch { /* refusal must survive an unavailable observer */ }
84
+ return { track, message: 'gate 는 열차가 착지 때 1회 — land-enqueue.sh 로 줄에 올려라' };
85
+ }
86
+
87
+ /** A refused admission still writes the observed marker when an artifact directory was requested. */
88
+ export function writeSeatSelfGateRefusalArtifact(cwd: string, artifactDir: string, marker: SelfGateTrainMarker): string | undefined {
89
+ if (!artifactDir.trim()) return undefined;
90
+ const dir = resolveArtifactDir(artifactDir, cwd);
91
+ const written = writeGateArtifacts({
92
+ dir,
93
+ head40: defaultRevResolver(cwd)('HEAD'),
94
+ base40: null,
95
+ envKey: defaultGateEnvKey(),
96
+ trainGate: marker.received,
97
+ testFiles: [],
98
+ verdict: 'seat-refused',
99
+ verdictLine: `seat gate refused before dispatch (track=${marker.track ?? 'none'}; trainGate=${marker.received})`,
100
+ exitCode: 2,
101
+ });
102
+ return written.summaryPath;
58
103
  }
59
104
 
60
105
  interface ProcessResult {
@@ -106,11 +151,11 @@ interface SelfGateCliDeps {
106
151
  runTests?: (cwd: string, files: readonly string[]) => ProcessResult;
107
152
  runBaseline?: (cwd: string, files: readonly string[], baseRef: string) => BaselineProcessResult;
108
153
  runTimeoutRecheck?: (cwd: string, file: string, name: string, timeoutMs: number) => { observation?: TimeoutRerunObservation; elapsedMs: number; output: string };
154
+ runInterferenceRecheck?: (cwd: string, report: GateBaselineReport, baseRef: string, relatedTestFiles: readonly string[]) => GateBaselineReport;
109
155
  runShards?: typeof runShardedGateTests;
110
156
  runShardsAsync?: typeof runShardedGateTestsAsync;
111
157
  /** Test seam for the live progress line. */
112
158
  writeProgressStderr?: (line: string) => void;
113
- now?: () => number;
114
159
  runIsolationGate?: (out: GateOutput) => number;
115
160
  runMockModuleRestoreGate?: (out: GateOutput) => number;
116
161
  /** 모델 이름 하드코딩 래칫(🅕 #20521) — `pr land` 만 물고 하니스 무인 병합은 안 물면 위반이 main 에 들어가 남의 착지를 막는다(🅣 2026-09-25). */
@@ -122,18 +167,24 @@ interface SelfGateCliDeps {
122
167
  /** iOS 순수-로직 시험 게이트 심(시험 주입용). */
123
168
  runIosGate?: (out: GateOutput) => number;
124
169
  runPwaGate?: (out: GateOutput) => number;
125
- runEntryBudgetGate?: (cwd: string, changedFiles: readonly string[]) => { affected: boolean; errors: string[] };
126
170
  listPrWorktrees?: (cwd: string) => PrWorktreeListEntry[] | { lookupFailed: string };
127
171
  inspectWorktreeDirtiness?: (path: string) => { dirty: boolean } | { lookupFailed: string };
128
172
  /** `--artifact-dir` 전용 심 — 커밋 sha 해석(실패 = null) · 환경 키. */
129
173
  resolveRev?: RevResolver;
130
174
  envKey?: () => string;
175
+ /** Receipt-store seam for tests; production stores under ~/.elanous/gate-receipts. */
176
+ gateReceiptDir?: () => string;
177
+ now?: () => number;
131
178
  }
132
179
 
133
180
  /** `--artifact-dir` 가 쓸 재료 — 판정 경로가 «채우기만» 하고 읽지 않는다. */
134
181
  interface GateArtifactCapture {
135
182
  baseRef?: string;
136
183
  testFiles?: readonly string[];
184
+ fullTestFiles?: readonly string[];
185
+ failedTestFiles?: readonly string[];
186
+ testReceiptMeasured?: boolean;
187
+ receiptDecision?: GateReceiptDecision;
137
188
  sharded?: ReturnType<typeof runShardedGateTests>;
138
189
  verdict?: string;
139
190
  verdictLine?: string;
@@ -144,6 +195,7 @@ interface GateArtifactCapture {
144
195
  unrunImporters?: number | null;
145
196
  importerLookupFailed?: string;
146
197
  timeoutRechecks?: readonly TimeoutRecheckRecord[];
198
+ interferenceRechecks?: readonly InterferenceRecheckRecord[];
147
199
  }
148
200
 
149
201
  /** SIDE-VERIFY ③ — summary 정수 칸: 게이트가 이미 낸 `result.baseline` ⊕ `unrunImporterTotal` 을 «옮기기만» 한다.
@@ -798,21 +850,25 @@ export function selectGateTestFiles(cwd: string, options: GateSelectionOptions =
798
850
 
799
851
  export function runSelfGateCli(cwd: string, options: SelfGateCliOptions = {}, deps: SelfGateCliDeps = {}): SelfGateCliResult {
800
852
  const capture: GateArtifactCapture = {};
853
+ const trainGate = options.trainGate ?? process.env.ELANOUS_TRAIN_GATE === '1';
801
854
  const result = runSelfGateCliCore(cwd, options, deps, capture, false) as SelfGateCliResult;
802
- if (options.artifactDir !== undefined) emitGateArtifacts(cwd, options.artifactDir, result, capture, deps);
855
+ persistGateReceipt(cwd, capture, deps);
856
+ if (options.artifactDir !== undefined) emitGateArtifacts(cwd, options.artifactDir, result, capture, deps, trainGate);
803
857
  return result;
804
858
  }
805
859
 
806
860
  /** Production path: shard bundles use async Bun children; all non-shard policy and timeout logic is shared. */
807
861
  export async function runSelfGateCliAsync(cwd: string, options: SelfGateCliOptions = {}, deps: SelfGateCliDeps = {}): Promise<SelfGateCliResult> {
808
862
  const capture: GateArtifactCapture = {};
863
+ const trainGate = options.trainGate ?? process.env.ELANOUS_TRAIN_GATE === '1';
809
864
  const result = await runSelfGateCliCore(cwd, options, deps, capture, true);
810
- if (options.artifactDir !== undefined) emitGateArtifacts(cwd, options.artifactDir, result, capture, deps);
865
+ persistGateReceipt(cwd, capture, deps);
866
+ if (options.artifactDir !== undefined) emitGateArtifacts(cwd, options.artifactDir, result, capture, deps, trainGate);
811
867
  return result;
812
868
  }
813
869
 
814
870
  /** 쓰기 실패는 «경고 한 줄»로만 접는다 — 판정·exit 코드는 그대로다. */
815
- function emitGateArtifacts(cwd: string, artifactDir: string, result: SelfGateCliResult, capture: GateArtifactCapture, deps: SelfGateCliDeps): void {
871
+ function emitGateArtifacts(cwd: string, artifactDir: string, result: SelfGateCliResult, capture: GateArtifactCapture, deps: SelfGateCliDeps, trainGate: boolean): void {
816
872
  if (!artifactDir.trim()) {
817
873
  result.lines.push('⚠ artifacts: --artifact-dir 가 빈 경로라 안 썼다 (판정은 그대로다)');
818
874
  return;
@@ -826,10 +882,12 @@ function emitGateArtifacts(cwd: string, artifactDir: string, result: SelfGateCli
826
882
  head40: resolveRev('HEAD'),
827
883
  base40: capture.baseRef ? resolveRev(capture.baseRef) : null,
828
884
  envKey: (deps.envKey ?? defaultGateEnvKey)(),
885
+ trainGate,
829
886
  testFiles: capture.testFiles ?? result.testFiles,
830
887
  verdict: capture.verdict ?? null,
831
888
  ...(capture.verdictLine !== undefined ? { verdictLine: capture.verdictLine } : {}),
832
889
  ...(capture.timeoutRechecks ? { timeoutRechecks: capture.timeoutRechecks } : {}),
890
+ ...(capture.interferenceRechecks ? { interferenceRechecks: capture.interferenceRechecks } : {}),
833
891
  exitCode: result.exitCode,
834
892
  counts: counts.counts,
835
893
  ...(counts.reason !== undefined ? { countsUnavailableReason: counts.reason } : {}),
@@ -844,6 +902,246 @@ function emitGateArtifacts(cwd: string, artifactDir: string, result: SelfGateCli
844
902
  }
845
903
  }
846
904
 
905
+ const GATE_RECEIPT_TTL_MS = 7 * 24 * 60 * 60 * 1000;
906
+ const GATE_RECEIPT_SCHEMA = 1;
907
+
908
+ interface GateReceipt {
909
+ schema: 1;
910
+ createdAt: number;
911
+ repositoryHash: string;
912
+ branch: string;
913
+ baseSha: string;
914
+ headSha: string;
915
+ runtime: string;
916
+ environmentKey: string;
917
+ lockfileHash: string;
918
+ fullTestFiles: string[];
919
+ failedTestFiles: string[];
920
+ measured: boolean;
921
+ }
922
+
923
+ interface GateReceiptIdentity extends Omit<GateReceipt, 'createdAt' | 'fullTestFiles' | 'failedTestFiles' | 'measured'> {
924
+ receiptPath: string;
925
+ receiptDir: string;
926
+ }
927
+
928
+ interface GateReceiptDecision {
929
+ mode: 'full' | 'inherit';
930
+ reason: string;
931
+ identity?: GateReceiptIdentity;
932
+ sourceHead?: string;
933
+ runTestFiles?: readonly string[];
934
+ inheritedTestFiles?: readonly string[];
935
+ }
936
+
937
+ function sha256(value: string | Buffer): string {
938
+ return createHash('sha256').update(value).digest('hex');
939
+ }
940
+
941
+ function normalizedRepositoryUrl(value: string): string | undefined {
942
+ const raw = value.trim();
943
+ if (!raw) return undefined;
944
+ if (!raw.includes('://')) {
945
+ const scp = /^(?:[^@]+@)?([^:]+):(.+)$/.exec(raw);
946
+ if (scp) return `${scp[1].toLowerCase()}/${scp[2]}`.replace(/\.git$/i, '');
947
+ }
948
+ try {
949
+ const url = new URL(raw);
950
+ url.username = '';
951
+ url.password = '';
952
+ url.search = '';
953
+ url.hash = '';
954
+ return `${url.protocol.toLowerCase()}//${url.host.toLowerCase()}${url.pathname}`.replace(/\.git$/i, '').replace(/\/$/, '');
955
+ } catch { return undefined; }
956
+ }
957
+
958
+ function gateReceiptIdentity(
959
+ cwd: string,
960
+ selection: ChangedFileSelection,
961
+ deps: SelfGateCliDeps,
962
+ ): { identity?: GateReceiptIdentity; reason?: string } {
963
+ const run = deps.runCommand ?? defaultRunCommand;
964
+ const command = (args: string[]) => {
965
+ try { return run('git', args, cwd); }
966
+ catch (error) { return { status: null, stderr: error instanceof Error ? error.message : String(error) }; }
967
+ };
968
+ const worktree = command(['status', '--porcelain=v1', '-z', '--untracked-files=all']);
969
+ if (worktree.status !== 0 || worktree.error || worktree.stdout === undefined) {
970
+ return { reason: 'worktree-status-unavailable' };
971
+ }
972
+ if (worktree.stdout.length > 0) return { reason: 'worktree-dirty' };
973
+ const remote = command(['config', '--get', 'remote.origin.url']);
974
+ const repositoryUrl = remote.status === 0 ? normalizedRepositoryUrl(remote.stdout ?? '') : undefined;
975
+ if (!repositoryUrl) return { reason: 'repository-origin-unavailable' };
976
+ const branch = selection.prHeadRefName?.trim() || (() => {
977
+ const result = command(['branch', '--show-current']);
978
+ return result.status === 0 ? (result.stdout ?? '').trim() : '';
979
+ })();
980
+ if (!branch) return { reason: 'branch-unavailable' };
981
+ if (selection.baseRef === 'HEAD') return { reason: 'uncommitted-or-no-stable-base' };
982
+ const resolveRev = deps.resolveRev ?? defaultRevResolver(cwd);
983
+ const baseSha = resolveRev(selection.baseRef);
984
+ const headSha = resolveRev('HEAD');
985
+ if (!baseSha || !headSha || !/^[0-9a-f]{40}$/.test(baseSha) || !/^[0-9a-f]{40}$/.test(headSha)) {
986
+ return { reason: 'base-or-head-sha-unavailable' };
987
+ }
988
+ const lockfile = ['bun.lock', 'bun.lockb'].map((name) => join(cwd, name)).find((path) => existsSync(path));
989
+ if (!lockfile) return { reason: 'lockfile-unavailable' };
990
+ let lockfileHash: string;
991
+ try { lockfileHash = sha256(readFileSync(lockfile)); }
992
+ catch { return { reason: 'lockfile-unreadable' }; }
993
+ const runtime = process.versions.bun ?? (globalThis as { Bun?: { version?: string } }).Bun?.version;
994
+ if (!runtime) return { reason: 'bun-runtime-unavailable' };
995
+ let environmentKey: string;
996
+ try { environmentKey = (deps.envKey ?? defaultGateEnvKey)(); }
997
+ catch { return { reason: 'environment-key-unavailable' }; }
998
+ const repositoryHash = sha256(repositoryUrl);
999
+ const receiptDir = deps.gateReceiptDir?.() ?? join(getElanousConfigDir(), 'gate-receipts');
1000
+ const key = sha256(`${repositoryUrl}\0${branch}\0${baseSha}`);
1001
+ return {
1002
+ identity: {
1003
+ schema: GATE_RECEIPT_SCHEMA, repositoryHash, branch, baseSha, headSha, runtime,
1004
+ environmentKey, lockfileHash, receiptDir, receiptPath: join(receiptDir, `${key}.json`),
1005
+ },
1006
+ };
1007
+ }
1008
+
1009
+ function pruneExpiredGateReceipts(receiptDir: string, now: number): void {
1010
+ try {
1011
+ for (const name of readdirSync(receiptDir)) {
1012
+ if (!/^[a-f0-9]{64}\.json$/.test(name)) continue;
1013
+ const path = join(receiptDir, name);
1014
+ try {
1015
+ const stat = lstatSync(path);
1016
+ if (stat.isFile() && !stat.isSymbolicLink() && now - stat.mtimeMs > GATE_RECEIPT_TTL_MS) rmSync(path, { force: true });
1017
+ } catch { /* a stale receipt disappearing concurrently is harmless */ }
1018
+ }
1019
+ } catch { /* the first receipt has no directory to prune */ }
1020
+ }
1021
+
1022
+ function isGateReceipt(value: unknown): value is GateReceipt {
1023
+ if (!value || typeof value !== 'object') return false;
1024
+ const item = value as Partial<GateReceipt>;
1025
+ return item.schema === GATE_RECEIPT_SCHEMA && typeof item.createdAt === 'number'
1026
+ && typeof item.repositoryHash === 'string' && typeof item.branch === 'string'
1027
+ && typeof item.baseSha === 'string' && /^[0-9a-f]{40}$/.test(item.baseSha)
1028
+ && typeof item.headSha === 'string' && /^[0-9a-f]{40}$/.test(item.headSha)
1029
+ && typeof item.runtime === 'string' && typeof item.environmentKey === 'string'
1030
+ && typeof item.lockfileHash === 'string' && /^[0-9a-f]{64}$/.test(item.lockfileHash)
1031
+ && Array.isArray(item.fullTestFiles) && item.fullTestFiles.every((path) => typeof path === 'string' && isGateTestFile(path))
1032
+ && Array.isArray(item.failedTestFiles) && item.failedTestFiles.every((path) => typeof path === 'string' && isGateTestFile(path))
1033
+ && typeof item.measured === 'boolean';
1034
+ }
1035
+
1036
+ function rejectGateReceipt(cwd: string, reason: string, details: Record<string, unknown> = {}): GateReceiptDecision {
1037
+ try { debug.log('self-implement', 'gate.receipt-inheritance-rejected', { reason, ...details }); } catch { /* telemetry must not alter the gate */ }
1038
+ return { mode: 'full', reason };
1039
+ }
1040
+
1041
+ function decideGateReceiptInheritance(
1042
+ cwd: string,
1043
+ options: SelfGateCliOptions,
1044
+ selection: ChangedFileSelection,
1045
+ fullTestFiles: readonly string[],
1046
+ deps: SelfGateCliDeps,
1047
+ ): GateReceiptDecision {
1048
+ // Existing injected-command fixtures stay isolated unless a test explicitly supplies a receipt directory.
1049
+ if (deps.runCommand && !deps.gateReceiptDir) return { mode: 'full', reason: 'injected-command-no-receipt-store' };
1050
+ const resolved = gateReceiptIdentity(cwd, selection, deps);
1051
+ if (!resolved.identity) return rejectGateReceipt(cwd, resolved.reason ?? 'receipt-identity-unavailable');
1052
+ const identity = resolved.identity;
1053
+ if (options.noInherit) {
1054
+ try { debug.log('self-implement', 'gate.receipt-inheritance-rejected', { reason: 'forced-full', baseSha: identity.baseSha, headSha: identity.headSha }); } catch { /* observation only */ }
1055
+ return { mode: 'full', reason: 'forced-full', identity };
1056
+ }
1057
+ const now = deps.now?.() ?? Date.now();
1058
+ pruneExpiredGateReceipts(identity.receiptDir, now);
1059
+ let prior: unknown;
1060
+ try {
1061
+ const stat = lstatSync(identity.receiptPath);
1062
+ if (!stat.isFile() || stat.isSymbolicLink()) return rejectGateReceipt(cwd, 'receipt-not-regular-file', { baseSha: identity.baseSha });
1063
+ prior = JSON.parse(readFileSync(identity.receiptPath, 'utf8'));
1064
+ } catch (error) {
1065
+ const code = (error as NodeJS.ErrnoException)?.code;
1066
+ return rejectGateReceipt(cwd, code === 'ENOENT' ? 'no-prior-receipt' : 'receipt-read-failed', { baseSha: identity.baseSha });
1067
+ }
1068
+ if (!isGateReceipt(prior)) return rejectGateReceipt(cwd, 'receipt-schema-invalid', { baseSha: identity.baseSha });
1069
+ if (now - prior.createdAt > GATE_RECEIPT_TTL_MS) {
1070
+ try { rmSync(identity.receiptPath, { force: true }); } catch { /* stale file can remain without affecting the full gate */ }
1071
+ return rejectGateReceipt(cwd, 'receipt-expired', { previousHead: prior.headSha });
1072
+ }
1073
+ if (prior.repositoryHash !== identity.repositoryHash || prior.branch !== identity.branch) return rejectGateReceipt(cwd, 'repository-or-branch-mismatch');
1074
+ if (prior.baseSha !== identity.baseSha) return rejectGateReceipt(cwd, 'base-sha-mismatch', { previousBase: prior.baseSha, currentBase: identity.baseSha });
1075
+ if (prior.runtime !== identity.runtime || prior.environmentKey !== identity.environmentKey) return rejectGateReceipt(cwd, 'runtime-mismatch', { previousRuntime: prior.runtime, currentRuntime: identity.runtime });
1076
+ if (prior.lockfileHash !== identity.lockfileHash) return rejectGateReceipt(cwd, 'lockfile-hash-mismatch');
1077
+ if (!prior.measured) return rejectGateReceipt(cwd, 'previous-test-run-unmeasured', { previousHead: prior.headSha });
1078
+ const ancestor = (deps.runCommand ?? defaultRunCommand)('git', ['merge-base', '--is-ancestor', prior.headSha, identity.headSha], cwd);
1079
+ if (ancestor.status !== 0 || ancestor.error) return rejectGateReceipt(cwd, 'previous-head-not-ancestor', { previousHead: prior.headSha, currentHead: identity.headSha });
1080
+
1081
+ const diff = (deps.runCommand ?? defaultRunCommand)('git', ['diff', '--name-only', `${prior.headSha}..${identity.headSha}`], cwd);
1082
+ if (diff.status !== 0 || diff.error || diff.stdout === undefined) return rejectGateReceipt(cwd, 'head-delta-unavailable', { previousHead: prior.headSha });
1083
+ const changedFiles = [...new Set(diff.stdout.split('\n').map((path) => normalizeGatePath(path.trim())).filter(Boolean))].sort();
1084
+ try {
1085
+ const deltaSelection = { files: changedFiles, baseRef: prior.headSha };
1086
+ const deltaOptions: GateSelectionOptions = { ...options, base: prior.headSha, pr: undefined };
1087
+ const deltaDeps: GateSelectionDeps = { ...deps, changedFiles: () => deltaSelection };
1088
+ const deltaPrepared = prepareGateTestSelection(cwd, deltaOptions, deltaDeps);
1089
+ if (deltaPrepared.lookupFailed || deltaPrepared.routeIndex?.lookupFailures.length) {
1090
+ return rejectGateReceipt(cwd, 'head-delta-test-radius-unmeasured', { previousHead: prior.headSha });
1091
+ }
1092
+ const deltaTests = finishGateTestSelection(deltaPrepared, deltaOptions, cwd, deltaDeps).testFiles;
1093
+ const current = new Set(fullTestFiles);
1094
+ const previous = new Set(prior.fullTestFiles);
1095
+ const previousFailures = new Set(prior.failedTestFiles);
1096
+ const changed = new Set(deltaTests);
1097
+ const runTestFiles = fullTestFiles.filter((path) => changed.has(path) || previousFailures.has(path) || !previous.has(path));
1098
+ const run = new Set(runTestFiles);
1099
+ const inheritedTestFiles = fullTestFiles.filter((path) => previous.has(path) && !previousFailures.has(path) && !run.has(path));
1100
+ // A current scope path not accounted for by the receipt is run, never silently inherited.
1101
+ for (const path of fullTestFiles) if (!previous.has(path) && !run.has(path)) return rejectGateReceipt(cwd, 'new-test-not-selected', { path });
1102
+ if (current.size !== fullTestFiles.length) return rejectGateReceipt(cwd, 'current-test-scope-duplicate');
1103
+ try {
1104
+ debug.log('self-implement', 'gate.receipt-inheritance-accepted', {
1105
+ previousHead: prior.headSha, currentHead: identity.headSha, baseSha: identity.baseSha,
1106
+ changedFiles, rerunTestFiles: runTestFiles, inheritedTestFiles,
1107
+ });
1108
+ } catch { /* observation only */ }
1109
+ return { mode: 'inherit', reason: 'matching-prior-receipt', identity, sourceHead: prior.headSha,
1110
+ runTestFiles, inheritedTestFiles };
1111
+ } catch (error) {
1112
+ return rejectGateReceipt(cwd, 'head-delta-test-radius-failed', { message: error instanceof Error ? error.message : String(error) });
1113
+ }
1114
+ }
1115
+
1116
+ function persistGateReceipt(cwd: string, capture: GateArtifactCapture, deps: SelfGateCliDeps): void {
1117
+ const decision = capture.receiptDecision;
1118
+ const identity = decision?.identity;
1119
+ if (!identity) return;
1120
+ if (deps.runCommand && !deps.gateReceiptDir) return;
1121
+ if (capture.testReceiptMeasured !== true || !capture.fullTestFiles || !capture.failedTestFiles) {
1122
+ try { debug.log('self-implement', 'gate.receipt-write-rejected', { reason: 'test-outcome-unmeasured', headSha: identity.headSha }); } catch { /* observation only */ }
1123
+ return;
1124
+ }
1125
+ const failed = [...new Set(capture.failedTestFiles)].filter((path) => capture.fullTestFiles!.includes(path)).sort();
1126
+ const receipt: GateReceipt = {
1127
+ schema: GATE_RECEIPT_SCHEMA, createdAt: deps.now?.() ?? Date.now(), repositoryHash: identity.repositoryHash,
1128
+ branch: identity.branch, baseSha: identity.baseSha, headSha: identity.headSha, runtime: identity.runtime,
1129
+ environmentKey: identity.environmentKey, lockfileHash: identity.lockfileHash,
1130
+ fullTestFiles: [...new Set(capture.fullTestFiles)].sort(), failedTestFiles: failed, measured: true,
1131
+ };
1132
+ const temporary = join(identity.receiptDir, `.${basename(identity.receiptPath)}.${process.pid}.${randomUUID()}.tmp`);
1133
+ try {
1134
+ mkdirSync(identity.receiptDir, { recursive: true, mode: 0o700 });
1135
+ pruneExpiredGateReceipts(identity.receiptDir, receipt.createdAt);
1136
+ writeFileSync(temporary, `${JSON.stringify(receipt, null, 2)}\n`, { flag: 'wx', mode: 0o600 });
1137
+ renameSync(temporary, identity.receiptPath);
1138
+ try { debug.log('self-implement', 'gate.receipt-written', { headSha: identity.headSha, baseSha: identity.baseSha, testFiles: receipt.fullTestFiles.length, failedTestFiles: failed.length }); } catch { /* observation only */ }
1139
+ } catch (error) {
1140
+ try { rmSync(temporary, { force: true }); } catch { /* best effort */ }
1141
+ try { debug.log('self-implement', 'gate.receipt-write-rejected', { reason: 'receipt-write-failed', message: error instanceof Error ? error.message : String(error) }); } catch { /* observation only */ }
1142
+ }
1143
+ }
1144
+
847
1145
  /** A completed bundle is observed immediately, before the synchronous runner returns. Each sink is best effort. */
848
1146
  function shardProgressObserver(cwd: string, options: SelfGateCliOptions, deps: SelfGateCliDeps): (progress: ShardRunProgress) => void {
849
1147
  const now = deps.now ?? Date.now;
@@ -879,8 +1177,17 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
879
1177
  const expose = publicExposureFiles(selection.files).length > 0
880
1178
  ? runExposeGate(cwd, selection.files, getUserConfig().harness?.exposeGate === 'strict' ? 'strict' : 'warn', deps.runCommand)
881
1179
  : { passed: true, log: '' };
882
- const { alwaysInclude, alwaysIncludeMissing, alwaysIncludeExtra, importerTestsAdded, commentOnlySources, scenarioTests, testFiles,
1180
+ const { alwaysInclude, alwaysIncludeMissing, alwaysIncludeExtra, importerTestsAdded, commentOnlySources, scenarioTests, testFiles: fullTestFiles,
883
1181
  skipTestStep, importerTestsNotRun, unrunImporterTotal, callerTestsOverflow, importerLookupFailed } = finishGateTestSelection(prepared, options, cwd, deps);
1182
+ const receiptDecision = options.base || options.pr || options.noInherit
1183
+ ? decideGateReceiptInheritance(cwd, options, selection, fullTestFiles, deps) : undefined;
1184
+ if (receiptDecision && !receiptDecision.identity && (!deps.runCommand || deps.gateReceiptDir)) {
1185
+ receiptDecision.identity = gateReceiptIdentity(cwd, selection, deps).identity;
1186
+ }
1187
+ const testFiles = receiptDecision?.mode === 'inherit' ? [...(receiptDecision.runTestFiles ?? fullTestFiles)] : [...fullTestFiles];
1188
+ capture.fullTestFiles = [...fullTestFiles];
1189
+ capture.receiptDecision = receiptDecision;
1190
+ const relatedTestFiles = [...new Set([...selection.files.filter(isTestPath), ...(scope.testArgs ?? []), ...importerTestsAdded])];
884
1191
  const lines = [
885
1192
  // ⛔⭐ 「changed=0」을 «초록»으로 읽는 사고가 났다(2026-09-02 · 🅕 보고 · 🅣 재현).
886
1193
  // 커밋 «전»에 돌리면 작업 트리 변경은 «안 세므로» changed=0 이 나오는데,
@@ -889,7 +1196,10 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
889
1196
  + (selection.files.length === 0 && (selection.ignoredDirtyPaths?.length ?? 0) > 0
890
1197
  ? ` ⚠️ 센 것이 0인데 «커밋 안 된» 변경 ${selection.ignoredDirtyPaths!.length}개가 있다 — 「통과」가 아니라 「안 쟀다」다(커밋 뒤 다시 돌려라)`
891
1198
  : ''),
892
- `scope: ${scope.testArgs?.join(', ') ?? '(test step skipped)'}`,
1199
+ `scope: ${receiptDecision?.mode === 'inherit' ? testFiles.join(', ') || '(all tests inherited)' : scope.testArgs?.join(', ') ?? '(test step skipped)'}`,
1200
+ ...(receiptDecision ? [receiptDecision.mode === 'inherit'
1201
+ ? `gate receipt: inherited ${receiptDecision.inheritedTestFiles?.length ?? 0} · rerun ${testFiles.length} · source head ${receiptDecision.sourceHead?.slice(0, 12) ?? '(unknown)'}`
1202
+ : `gate receipt: full radius (${receiptDecision.reason})`] : []),
893
1203
  `ignored unrelated worktree changes: ${selection.ignoredDirtyPaths === undefined ? '(not checked)' : selection.ignoredDirtyPaths.join(', ') || '(none)'}`,
894
1204
  `unverified: ${scope.unverified.length} (${scope.unverified.join(', ') || '(none)'})`,
895
1205
  `elanous runtime artifacts: ${scope.elanousRuntimeArtifacts.length} (${scope.elanousRuntimeArtifacts.join(', ') || '(none)'})`,
@@ -944,25 +1254,32 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
944
1254
  // 🍎 iOS 축 — 안드로이드와 «같은 자리»에 둔다(skipTestStep 앞). Swift 만 바뀐 PR 도 여기서 조기 리턴한다.
945
1255
  const iosPassed = runAdditionalGate('ios-gate', deps.runIosGate ?? runIosUnitTestGate, selection.files, cwd, lines);
946
1256
  const pwaPassed = runAdditionalGate('pwa-gate', deps.runPwaGate ?? runPwaBuildGate, selection.files, cwd, lines);
947
- let entryBudgetPassed = false;
948
- try {
949
- const budget = (deps.runEntryBudgetGate ?? ((dir, files) => {
950
- const affected = entryBudgetAffected(files);
951
- return { affected, errors: affected ? auditEntryBudget(dir).errors : [] };
952
- }))(cwd, selection.files);
953
- entryBudgetPassed = budget.errors.length === 0;
954
- lines.push(budget.affected
955
- ? `next-tui-entry-budget: ${entryBudgetPassed ? 'pass' : `FAIL ${budget.errors.join('; ')}`}`
956
- : 'next-tui-entry-budget: skip (unrelated changes)');
957
- } catch (error) {
958
- lines.push(`next-tui-entry-budget: UNMEASURED ${error instanceof Error ? error.message : String(error)}`);
1257
+ if (receiptDecision?.mode === 'inherit' && testFiles.length === 0 && fullTestFiles.length > 0) {
1258
+ capture.testReceiptMeasured = true;
1259
+ capture.failedTestFiles = [];
1260
+ capture.verdict = 'passed';
1261
+ const testLine = formatPartialObservationNote(unrunImporterTotal ?? 0,
1262
+ `tests: pass (${receiptDecision.inheritedTestFiles?.length ?? 0} files inherited from ${receiptDecision.sourceHead?.slice(0, 12) ?? 'prior receipt'})`);
1263
+ lines.push(testLine);
1264
+ capture.verdictLine = testLine;
1265
+ const policyPassed = runPolicyGates(selection.files, cwd, lines, deps);
1266
+ logGateCliBaseline(cwd, { ...ZERO_GATE_BASELINE, unrunImporterTotal, lookupFailed: importerLookupFailed });
1267
+ return {
1268
+ exitCode: policyPassed && androidPassed && iosPassed && pwaPassed && expose.passed ? 0 : 1,
1269
+ lines, changedFiles: selection.files, testFiles, unverified: scope.unverified,
1270
+ documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests,
1271
+ alwaysIncludeMissing, importerTestsAdded,
1272
+ baseline: { introduced: 0, preexisting: 0, unknown: 0, preconditionUnmet: 0 },
1273
+ };
959
1274
  }
960
1275
 
961
1276
  if (skipTestStep) {
962
1277
  const policyPassed = runPolicyGates(selection.files, cwd, lines, deps);
1278
+ capture.testReceiptMeasured = false;
1279
+ capture.failedTestFiles = [];
963
1280
  logGateCliBaseline(cwd, { ...ZERO_GATE_BASELINE, unrunImporterTotal, lookupFailed: importerLookupFailed });
964
1281
  Object.assign(capture, { verdict: 'skipped', artifactsUnavailable: 'no-tests' } satisfies GateArtifactCapture);
965
- return { exitCode: androidPassed && iosPassed && pwaPassed && entryBudgetPassed && policyPassed && expose.passed ? 0 : 1, lines, changedFiles: selection.files, testFiles: [], unverified: scope.unverified, documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests, alwaysIncludeMissing, importerTestsAdded, baseline: { introduced: 0, preexisting: 0, unknown: 0, preconditionUnmet: 0 } };
1282
+ return { exitCode: androidPassed && iosPassed && pwaPassed && policyPassed && expose.passed ? 0 : 1, lines, changedFiles: selection.files, testFiles: [], unverified: scope.unverified, documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests, alwaysIncludeMissing, importerTestsAdded, baseline: { introduced: 0, preexisting: 0, unknown: 0, preconditionUnmet: 0 } };
966
1283
  }
967
1284
 
968
1285
  // The default direct Bun path has one process and one 300s limit. Route real child/PTY tests through
@@ -1006,6 +1323,8 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1006
1323
  let shardBaseline: SelfGateCliResult['baseline'];
1007
1324
  let unmeasuredReason: string | undefined;
1008
1325
  if (aggregate.status === 'unmeasured') {
1326
+ capture.testReceiptMeasured = false;
1327
+ capture.failedTestFiles = [];
1009
1328
  unmeasuredReason = sharded.reason
1010
1329
  ? redactSecretText(sharded.reason).replace(/[\r\n\t\x00-\x1f\x7f]+/g, ' ').slice(0, 500)
1011
1330
  : aggregate.retryShardIds.join(', ') || 'no complete JUnit';
@@ -1017,8 +1336,12 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1017
1336
  capture.unmeasuredReason = unmeasuredReason;
1018
1337
  }
1019
1338
  else if (aggregate.report) {
1020
- const report = recheckTimeoutOnlyIntroducedFailures(cwd, aggregate.report, deps.runTimeoutRecheck);
1339
+ const timeoutReport = recheckTimeoutOnlyIntroducedFailures(cwd, aggregate.report, deps.runTimeoutRecheck);
1340
+ const report = deps.runShards || deps.runShardsAsync
1341
+ ? deps.runInterferenceRecheck?.(cwd, timeoutReport, selection.baseRef, relatedTestFiles) ?? timeoutReport
1342
+ : (deps.runInterferenceRecheck ?? recheckOutsideScopeFailures)(cwd, timeoutReport, selection.baseRef, relatedTestFiles);
1021
1343
  capture.timeoutRechecks = report.timeoutRechecks;
1344
+ capture.interferenceRechecks = report.interferenceRechecks;
1022
1345
  const timeoutRecheckResolvedFailure = aggregate.status === 'failed'
1023
1346
  && (report.loadTimeout ?? 0) > 0
1024
1347
  && report.introduced === 0 && report.unknown === 0 && report.preconditionUnmet === 0
@@ -1026,6 +1349,8 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1026
1349
  && report.baselineStatus !== 'unknown';
1027
1350
  const effectiveStatus = timeoutRecheckResolvedFailure ? 'passed' : aggregate.status;
1028
1351
  capture.verdict = effectiveStatus;
1352
+ capture.testReceiptMeasured = report.unknown === 0 && report.preconditionUnmet === 0 && report.worktreeFailuresParsed;
1353
+ capture.failedTestFiles = [...new Set(report.failures.map((failure) => failure.file).filter((file): file is string => typeof file === 'string'))];
1029
1354
  logGateCliBaseline(cwd, {
1030
1355
  introduced: report.introduced, preexisting: report.preexisting, unknown: report.unknown,
1031
1356
  preconditionUnmet: report.preconditionUnmet, timedOut: report.timedOut,
@@ -1035,6 +1360,8 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1035
1360
  lines.push(formatPartialObservationNote(unrunImporterTotal ?? 0, formatGateBaselineNote(report, unrunImporterTotal ?? 0)));
1036
1361
  shardBaseline = { introduced: report.introduced, preexisting: report.preexisting, unknown: report.unknown, preconditionUnmet: report.preconditionUnmet };
1037
1362
  } else {
1363
+ capture.testReceiptMeasured = true;
1364
+ capture.failedTestFiles = [];
1038
1365
  lines.push(formatPartialObservationNote(unrunImporterTotal ?? 0, `tests: pass (${testFiles.length} files)`));
1039
1366
  logGateCliBaseline(cwd, { ...ZERO_GATE_BASELINE, unrunImporterTotal, lookupFailed: importerLookupFailed });
1040
1367
  shardBaseline = { introduced: 0, preexisting: 0, unknown: 0, preconditionUnmet: 0 };
@@ -1042,7 +1369,7 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1042
1369
  capture.verdictLine = lines[lines.length - 1];
1043
1370
  const policyPassed = runPolicyGates(selection.files, cwd, lines, deps);
1044
1371
  return {
1045
- exitCode: capture.verdict !== 'passed' || !policyPassed || !androidPassed || !iosPassed || !pwaPassed || !entryBudgetPassed || !expose.passed ? 1 : 0,
1372
+ exitCode: capture.verdict !== 'passed' || !policyPassed || !androidPassed || !iosPassed || !pwaPassed || !expose.passed ? 1 : 0,
1046
1373
  lines, changedFiles: selection.files, testFiles, unverified: scope.unverified,
1047
1374
  documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests,
1048
1375
  alwaysIncludeMissing, importerTestsAdded, ...(shardBaseline ? { baseline: shardBaseline } : {}),
@@ -1056,17 +1383,28 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1056
1383
  const worktreeLog = formatProcessOutput(test);
1057
1384
  Object.assign(capture, { unshardedRc: test.status, artifactsUnavailable: 'unsharded' } satisfies GateArtifactCapture);
1058
1385
  if (test.status === 0 && !test.error) {
1386
+ capture.testReceiptMeasured = true;
1387
+ capture.failedTestFiles = [];
1059
1388
  lines.push(formatPartialObservationNote(unrunImporterTotal ?? 0, `tests: pass (${testFiles.length} files)`));
1060
1389
  Object.assign(capture, { verdict: 'passed', verdictLine: lines[lines.length - 1] } satisfies GateArtifactCapture);
1061
1390
  const policyPassed = runPolicyGates(selection.files, cwd, lines, deps);
1062
1391
  logGateCliBaseline(cwd, { ...ZERO_GATE_BASELINE, unrunImporterTotal, lookupFailed: importerLookupFailed });
1063
- return { exitCode: policyPassed && androidPassed && iosPassed && pwaPassed && entryBudgetPassed && expose.passed ? 0 : 1, lines, changedFiles: selection.files, testFiles, unverified: scope.unverified, documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests, alwaysIncludeMissing, importerTestsAdded, baseline: { introduced: 0, preexisting: 0, unknown: 0, preconditionUnmet: 0 } };
1392
+ return { exitCode: policyPassed && androidPassed && iosPassed && pwaPassed && expose.passed ? 0 : 1, lines, changedFiles: selection.files, testFiles, unverified: scope.unverified, documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests, alwaysIncludeMissing, importerTestsAdded, baseline: { introduced: 0, preexisting: 0, unknown: 0, preconditionUnmet: 0 } };
1064
1393
  }
1065
1394
 
1066
1395
  if (worktreeLog.includes('deterministic environment setup failed')) lines.push(worktreeLog);
1067
1396
  const baseline = (deps.runBaseline ?? runGateBaseline)(cwd, testFiles, selection.baseRef);
1068
- const report = recheckTimeoutOnlyIntroducedFailures(cwd, buildGateBaselineReport(worktreeLog, baseline), deps.runTimeoutRecheck);
1397
+ // An injected runner can represent a virtual checkout; only the real runner may use this host's file tree.
1398
+ const currentFileExists = deps.runTests ? undefined : (file: string) => existsSync(resolve(cwd, file));
1399
+ const timeoutReport = recheckTimeoutOnlyIntroducedFailures(cwd,
1400
+ buildGateBaselineReport(worktreeLog, baseline, undefined, 0, currentFileExists), deps.runTimeoutRecheck);
1401
+ const report = deps.runTests
1402
+ ? deps.runInterferenceRecheck?.(cwd, timeoutReport, selection.baseRef, relatedTestFiles) ?? timeoutReport
1403
+ : (deps.runInterferenceRecheck ?? recheckOutsideScopeFailures)(cwd, timeoutReport, selection.baseRef, relatedTestFiles);
1069
1404
  capture.timeoutRechecks = report.timeoutRechecks;
1405
+ capture.interferenceRechecks = report.interferenceRechecks;
1406
+ capture.testReceiptMeasured = report.unknown === 0 && report.preconditionUnmet === 0 && report.worktreeFailuresParsed;
1407
+ capture.failedTestFiles = [...new Set(report.failures.map((failure) => failure.file).filter((file): file is string => typeof file === 'string'))];
1070
1408
  logGateCliBaseline(cwd, {
1071
1409
  introduced: report.introduced,
1072
1410
  preexisting: report.preexisting,
@@ -1086,7 +1424,7 @@ function runSelfGateCliCore(cwd: string, options: SelfGateCliOptions, deps: Self
1086
1424
  verdictLine: lines[lines.length - 1],
1087
1425
  } satisfies GateArtifactCapture);
1088
1426
  const policyPassed = runPolicyGates(selection.files, cwd, lines, deps);
1089
- const exitCode = !androidPassed || !iosPassed || !pwaPassed || !entryBudgetPassed || !policyPassed || !expose.passed || report.introduced > 0 || report.unknown > 0 || report.preconditionUnmet > 0 ? 1 : 0;
1427
+ const exitCode = !androidPassed || !iosPassed || !pwaPassed || !policyPassed || !expose.passed || report.introduced > 0 || report.unknown > 0 || report.preconditionUnmet > 0 ? 1 : 0;
1090
1428
  return { exitCode, lines, changedFiles: selection.files, testFiles, unverified: scope.unverified, documentPaths: scope.documentPaths, documentsWithoutDerivedTests: scope.documentsWithoutDerivedTests, alwaysIncludeMissing, importerTestsAdded, baseline: { introduced: report.introduced, preexisting: report.preexisting, unknown: report.unknown, preconditionUnmet: report.preconditionUnmet } };
1091
1429
  }
1092
1430