elanous 0.2.42 → 0.2.44

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 (764) hide show
  1. package/apps/pwa/out/404/index.html +1 -1
  2. package/apps/pwa/out/404.html +1 -1
  3. package/apps/pwa/out/_next/static/{X1ucLw10Cds_h614NoEnh → HMXsxdy5MIIcHPMHv1wD4}/_buildManifest.js +1 -1
  4. package/apps/pwa/out/_next/static/chunks/08334415.f0e80896acbef722.js +1 -0
  5. package/apps/pwa/out/_next/static/chunks/1032-78ba4f6391258cab.js +1 -0
  6. package/apps/pwa/out/_next/static/chunks/1082-53f86a26e03d309d.js +1 -0
  7. package/apps/pwa/out/_next/static/chunks/1109-7d0e264f6f2edbc7.js +1 -0
  8. package/apps/pwa/out/_next/static/chunks/1124-7c26330402481143.js +1 -0
  9. package/apps/pwa/out/_next/static/chunks/{2160.a097e7b138ae1c55.js → 118.2a89982fe4276880.js} +1 -1
  10. package/apps/pwa/out/_next/static/chunks/1244.6c435dbf1bf21d8a.js +1 -0
  11. package/apps/pwa/out/_next/static/chunks/1252.9e665904d3aa3b1a.js +32 -0
  12. package/apps/pwa/out/_next/static/chunks/1266.a46cc33cb6a72d75.js +104 -0
  13. package/apps/pwa/out/_next/static/chunks/1306.967240ede9a0f757.js +24 -0
  14. package/apps/pwa/out/_next/static/chunks/1344.3b95f3bd1b77a3fe.js +94 -0
  15. package/apps/pwa/out/_next/static/chunks/{4043.6b91203436c9c86b.js → 1401.22dfe92640a2b1ac.js} +4 -4
  16. package/apps/pwa/out/_next/static/chunks/1431-f7c78bd5be21e011.js +1 -0
  17. package/apps/pwa/out/_next/static/chunks/1451-cdd35a8a0b31834b.js +1 -0
  18. package/apps/pwa/out/_next/static/chunks/{6632.0eac1c554f8f2ef3.js → 1694.18debfd77562e56d.js} +2 -2
  19. package/apps/pwa/out/_next/static/chunks/1708-f03d587b7a7545c8.js +1 -0
  20. package/apps/pwa/out/_next/static/chunks/1775-fa7152bdeff6c95f.js +1 -0
  21. package/apps/pwa/out/_next/static/chunks/178-4da509cd7266672a.js +1 -0
  22. package/apps/pwa/out/_next/static/chunks/1850-522de4ee34957210.js +1 -0
  23. package/apps/pwa/out/_next/static/chunks/1876-c6f6e0ddcc76c6a1.js +1 -0
  24. package/apps/pwa/out/_next/static/chunks/1976.097066b072432242.js +1 -0
  25. package/apps/pwa/out/_next/static/chunks/{3507.97e1977bc4d5fb0a.js → 1978.eeb60a606dc5deac.js} +2 -2
  26. package/apps/pwa/out/_next/static/chunks/2043.e233e3b5a3e790f5.js +1 -0
  27. package/apps/pwa/out/_next/static/chunks/2150.71b94e3348107c83.js +1 -0
  28. package/apps/pwa/out/_next/static/chunks/2158.ebc6fc5a10280ab7.js +1 -0
  29. package/apps/pwa/out/_next/static/chunks/2216.802962c04f40a26e.js +64 -0
  30. package/apps/pwa/out/_next/static/chunks/2294.7890edcfa046c97d.js +1 -0
  31. package/apps/pwa/out/_next/static/chunks/235.c89aaae4bcd6233a.js +74 -0
  32. package/apps/pwa/out/_next/static/chunks/{5885.0a3e52c8faccec98.js → 239.de075467b5523469.js} +2 -2
  33. package/apps/pwa/out/_next/static/chunks/249.ba7051590d603c8f.js +226 -0
  34. package/apps/pwa/out/_next/static/chunks/2571.a6ac4e26c8618403.js +1 -0
  35. package/apps/pwa/out/_next/static/chunks/2610.e149cd564a08913e.js +1 -0
  36. package/apps/pwa/out/_next/static/chunks/2705.9816f3c244f8b85f.js +1 -0
  37. package/apps/pwa/out/_next/static/chunks/2801.afeb8a4dae22f85f.js +1 -0
  38. package/apps/pwa/out/_next/static/chunks/2954.bbefc95d6b20e0d8.js +1 -0
  39. package/apps/pwa/out/_next/static/chunks/2e0f720a.a0697c08e3806a60.js +1 -0
  40. package/apps/pwa/out/_next/static/chunks/3042.96ec235fe41c8d4e.js +1 -0
  41. package/apps/pwa/out/_next/static/chunks/3097-8e358f158acef46b.js +1 -0
  42. package/apps/pwa/out/_next/static/chunks/3205-93b1abe28b4fb16a.js +1 -0
  43. package/apps/pwa/out/_next/static/chunks/3273.b4434f0dcae7eb29.js +1 -0
  44. package/apps/pwa/out/_next/static/chunks/3311.9cbc43ea0c90d60c.js +1 -0
  45. package/apps/pwa/out/_next/static/chunks/{1487.2f67b79444062da6.js → 3349.b5f09ee474d9533e.js} +1 -1
  46. package/apps/pwa/out/_next/static/chunks/3503.a47a9755fb4d97b0.js +1 -0
  47. package/apps/pwa/out/_next/static/chunks/3506-5f429b3b7e1392b0.js +1 -0
  48. package/apps/pwa/out/_next/static/chunks/3843.bad404d008893291.js +77 -0
  49. package/apps/pwa/out/_next/static/chunks/3877-4b40e530b47e3bf9.js +1 -0
  50. package/apps/pwa/out/_next/static/chunks/435-ce2958253cf7de61.js +1 -0
  51. package/apps/pwa/out/_next/static/chunks/4393.28fa5228d0eec217.js +149 -0
  52. package/apps/pwa/out/_next/static/chunks/4404.7281c847c6e10dfc.js +1 -0
  53. package/apps/pwa/out/_next/static/chunks/{8673-bab689a55f7e13b9.js → 4415-b9d6a90960920a4a.js} +3 -3
  54. package/apps/pwa/out/_next/static/chunks/447-5b304de1fe098f43.js +1 -0
  55. package/apps/pwa/out/_next/static/chunks/4484-8ebea83d431e6fae.js +1 -0
  56. package/apps/pwa/out/_next/static/chunks/{8262.ddc03e06b733f184.js → 4502.bdcc877abd437a05.js} +1 -1
  57. package/apps/pwa/out/_next/static/chunks/4599-f95790fc5c65b8df.js +1 -0
  58. package/apps/pwa/out/_next/static/chunks/{1262.e804feb8fd1acb8c.js → 46.57c783fa4884714f.js} +2 -2
  59. package/apps/pwa/out/_next/static/chunks/463-b9114e411f33728e.js +1 -0
  60. package/apps/pwa/out/_next/static/chunks/4659.a57d1f0c5d754cd2.js +36 -0
  61. package/apps/pwa/out/_next/static/chunks/4722-a847e7a28115035f.js +1 -0
  62. package/apps/pwa/out/_next/static/chunks/{1063.2fb8a9dc55c731f2.js → 4757.67c6d7473a038e78.js} +1 -1
  63. package/apps/pwa/out/_next/static/chunks/4874-c86f878ec4502ad3.js +1 -0
  64. package/apps/pwa/out/_next/static/chunks/{6377.bc7df239edbff244.js → 4891.3f80ba517a3b2373.js} +1 -1
  65. package/apps/pwa/out/_next/static/chunks/4998.810ca8833084caa9.js +62 -0
  66. package/apps/pwa/out/_next/static/chunks/4f98febc.ea5841d4d616bfb2.js +1 -0
  67. package/apps/pwa/out/_next/static/chunks/{3482.a9ae9d2ad6a5bd97.js → 5052.7dbb12a55d4f18f5.js} +1 -1
  68. package/apps/pwa/out/_next/static/chunks/5166-ca73b3e361085a6d.js +1 -0
  69. package/apps/pwa/out/_next/static/chunks/5180-039f4a18b07ad387.js +1 -0
  70. package/apps/pwa/out/_next/static/chunks/5232.5a2ce4daf7a9e11d.js +115 -0
  71. package/apps/pwa/out/_next/static/chunks/5439.3fec6dbce29ecb36.js +1 -0
  72. package/apps/pwa/out/_next/static/chunks/5612-074d9a5e00dfac6a.js +1 -0
  73. package/apps/pwa/out/_next/static/chunks/5675-01989d524a84c505.js +1 -0
  74. package/apps/pwa/out/_next/static/chunks/5751.af641a1adf5ec697.js +1 -0
  75. package/apps/pwa/out/_next/static/chunks/5758-c6cb98714d18ab0c.js +1 -0
  76. package/apps/pwa/out/_next/static/chunks/578eded8.b582637306e16964.js +122 -0
  77. package/apps/pwa/out/_next/static/chunks/5790.5eb06a653ebd8571.js +34 -0
  78. package/apps/pwa/out/_next/static/chunks/5853-4033e5bd5afbe06b.js +1 -0
  79. package/apps/pwa/out/_next/static/chunks/5904.97d70bb7f46b2db7.js +1 -0
  80. package/apps/pwa/out/_next/static/chunks/{3347.f846266b5e5f3ede.js → 5989.7ecd362c5c44b747.js} +3 -3
  81. package/apps/pwa/out/_next/static/chunks/{73d2eb0e.4966ad55293c801a.js → 5a34fb2f.52f1b4e1baebb48a.js} +3 -3
  82. package/apps/pwa/out/_next/static/chunks/{7a98bc80.fa935989e829f9c2.js → 5a5078f8.2099200e5ea95e16.js} +1 -1
  83. package/apps/pwa/out/_next/static/chunks/6036-c302c34ff0b3d410.js +1 -0
  84. package/apps/pwa/out/_next/static/chunks/606.ef81c313381f4264.js +1 -0
  85. package/apps/pwa/out/_next/static/chunks/616.1af54a928b1ba704.js +1 -0
  86. package/apps/pwa/out/_next/static/chunks/6201.bc936f71f613a8e9.js +41 -0
  87. package/apps/pwa/out/_next/static/chunks/6204-fdc86e0e64c4f92d.js +1 -0
  88. package/apps/pwa/out/_next/static/chunks/{7411.9b4b8b747dc7b802.js → 6245.1182e007e9d230d9.js} +1 -1
  89. package/apps/pwa/out/_next/static/chunks/{b450776b.3db34d8d965f82d3.js → 63699a35.17262e162bc514b2.js} +1 -1
  90. package/apps/pwa/out/_next/static/chunks/6420.494801a80030160c.js +27 -0
  91. package/apps/pwa/out/_next/static/chunks/{e8543907.5b040a5f22a0b0e5.js → 6549dad0.2740b25e51bf8f05.js} +1 -1
  92. package/apps/pwa/out/_next/static/chunks/{9427.96aa912ddb5801e0.js → 6881.9e7955847640c7fe.js} +17 -17
  93. package/apps/pwa/out/_next/static/chunks/6931.fcdfb94141e67b3d.js +1 -0
  94. package/apps/pwa/out/_next/static/chunks/6991-8e081c6ce38c0ba1.js +1 -0
  95. package/apps/pwa/out/_next/static/chunks/7010.1bbd17a7f2b3e376.js +1 -0
  96. package/apps/pwa/out/_next/static/chunks/7029.d1466acf55fae2ed.js +1 -0
  97. package/apps/pwa/out/_next/static/chunks/7152-a123aa8e129c131f.js +1 -0
  98. package/apps/pwa/out/_next/static/chunks/7455.196168fffac3b9c4.js +24 -0
  99. package/apps/pwa/out/_next/static/chunks/7638.6ca4770dd1129138.js +1 -0
  100. package/apps/pwa/out/_next/static/chunks/7649-f37d76260e5e2a5a.js +1 -0
  101. package/apps/pwa/out/_next/static/chunks/7679.32c40cdd14f20b4a.js +1 -0
  102. package/apps/pwa/out/_next/static/chunks/7751.04bfbd16b4c6cd0a.js +1 -0
  103. package/apps/pwa/out/_next/static/chunks/7864.b1ff31d4030b8994.js +148 -0
  104. package/apps/pwa/out/_next/static/chunks/7869-c47bd2c075c1fefa.js +1 -0
  105. package/apps/pwa/out/_next/static/chunks/{8138.6c10b2a356d52fca.js → 8442.2f09ca969d631615.js} +1 -1
  106. package/apps/pwa/out/_next/static/chunks/8445.2738dbd59a78c78c.js +1 -0
  107. package/apps/pwa/out/_next/static/chunks/8447.5510c439f9938c6d.js +286 -0
  108. package/apps/pwa/out/_next/static/chunks/{9415.69e4a21c60c7d2db.js → 8551.f762945c2cda2e95.js} +1 -1
  109. package/apps/pwa/out/_next/static/chunks/8635-57a9d8d9db70f4f1.js +1 -0
  110. package/apps/pwa/out/_next/static/chunks/86961958-4b0689a5048f756b.js +1 -0
  111. package/apps/pwa/out/_next/static/chunks/8709.3c6019bb18f8554f.js +8 -0
  112. package/apps/pwa/out/_next/static/chunks/8759.c999528a0a907bf6.js +1 -0
  113. package/apps/pwa/out/_next/static/chunks/{9a852a62-6192a6ea9346ced3.js → 87f498e5-0881de09f2e44707.js} +1 -1
  114. package/apps/pwa/out/_next/static/chunks/8843.c3197f904c952b81.js +1 -0
  115. package/apps/pwa/out/_next/static/chunks/{3d0154af.5331fec737ffe8c3.js → 892fd990.456232f326cc39c2.js} +1 -1
  116. package/apps/pwa/out/_next/static/chunks/8965-135a2c9eaa2464cb.js +1 -0
  117. package/apps/pwa/out/_next/static/chunks/8971-8d3b9c96f8a6c958.js +1 -0
  118. package/apps/pwa/out/_next/static/chunks/9059.c8598d96f8e5e9cd.js +1 -0
  119. package/apps/pwa/out/_next/static/chunks/9115.90447ae198b84eae.js +1 -0
  120. package/apps/pwa/out/_next/static/chunks/9147.d9b0a02e0babc9b4.js +93 -0
  121. package/apps/pwa/out/_next/static/chunks/9204-83075f4b70c61cdc.js +1 -0
  122. package/apps/pwa/out/_next/static/chunks/9244-c32ef14b5dc72bdf.js +1 -0
  123. package/apps/pwa/out/_next/static/chunks/930.2a9a30f964350c66.js +90 -0
  124. package/apps/pwa/out/_next/static/chunks/9398.1f56e3f17795f43f.js +1 -0
  125. package/apps/pwa/out/_next/static/chunks/9527.3e5ad31c891c5fcb.js +79 -0
  126. package/apps/pwa/out/_next/static/chunks/9571-4ac933e774d1225c.js +1 -0
  127. package/apps/pwa/out/_next/static/chunks/app/_not-found/page-9fc644de2d8edae3.js +1 -0
  128. package/apps/pwa/out/_next/static/chunks/app/approvals/page-0c9dace2db62bee8.js +1 -0
  129. package/apps/pwa/out/_next/static/chunks/app/autopilot/page-f5e65c3dc9d89f2a.js +1 -0
  130. package/apps/pwa/out/_next/static/chunks/app/board/page-2a9c19b9a140b7b1.js +1 -0
  131. package/apps/pwa/out/_next/static/chunks/app/botlab/page-61533ad92141adfb.js +1 -0
  132. package/apps/pwa/out/_next/static/chunks/app/bots/page-112004ced6fd0329.js +1 -0
  133. package/apps/pwa/out/_next/static/chunks/app/ceo/page-f733318c237a49d8.js +1 -0
  134. package/apps/pwa/out/_next/static/chunks/app/chat/page-51ea677d2d33bbc0.js +1 -0
  135. package/apps/pwa/out/_next/static/chunks/app/consult/page-428b41f2f9566e3c.js +1 -0
  136. package/apps/pwa/out/_next/static/chunks/app/control/page-1b29396ea90a61e5.js +1 -0
  137. package/apps/pwa/out/_next/static/chunks/app/decisions/page-cf83ec613ac904bf.js +1 -0
  138. package/apps/pwa/out/_next/static/chunks/app/design-check/page-3f4c0ecbc284bb5f.js +1 -0
  139. package/apps/pwa/out/_next/static/chunks/app/editor/page-b63c322f54f70cc6.js +1 -0
  140. package/apps/pwa/out/_next/static/chunks/app/exec/page-fe328c4ee9aac6b4.js +1 -0
  141. package/apps/pwa/out/_next/static/chunks/app/field/page-bfb855c584f0fb98.js +1 -0
  142. package/apps/pwa/out/_next/static/chunks/app/healthz/route-9fc644de2d8edae3.js +1 -0
  143. package/apps/pwa/out/_next/static/chunks/app/inside/page-47b1710c110eabd7.js +1 -0
  144. package/apps/pwa/out/_next/static/chunks/app/intake/page-42895214458bc6d2.js +1 -0
  145. package/apps/pwa/out/_next/static/chunks/app/layout-d03de0ebd8366e23.js +1 -0
  146. package/apps/pwa/out/_next/static/chunks/app/live/page-3ed6c47e4b1c61c2.js +1 -0
  147. package/apps/pwa/out/_next/static/chunks/app/live-run/page-ae653e9bf261c738.js +1 -0
  148. package/apps/pwa/out/_next/static/chunks/app/loops/page-23f3f0a0209c0ac4.js +1 -0
  149. package/apps/pwa/out/_next/static/chunks/app/market/page-88c691273aae66f9.js +1 -0
  150. package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-e187ac52a95538b3.js +1 -0
  151. package/apps/pwa/out/_next/static/chunks/app/morning/page-6e45828daed1295e.js +1 -0
  152. package/apps/pwa/out/_next/static/chunks/app/not-found-edb5d7287bb46186.js +1 -0
  153. package/apps/pwa/out/_next/static/chunks/app/observatory/page-4a7eaacd93c3f6a5.js +1 -0
  154. package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-3ca073d43d74cc84.js +1 -0
  155. package/apps/pwa/out/_next/static/chunks/app/ops/release/page-1e9fee67b1199436.js +1 -0
  156. package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-df1283ea963c6816.js +1 -0
  157. package/apps/pwa/out/_next/static/chunks/app/outputs/page-19fcf8d8301ccd18.js +1 -0
  158. package/apps/pwa/out/_next/static/chunks/app/page-5ab699e0303bbb40.js +1 -0
  159. package/apps/pwa/out/_next/static/chunks/app/reflection/page-7cde0d29756984c5.js +1 -0
  160. package/apps/pwa/out/_next/static/chunks/app/scheduler/page-9d4c598e8ee22f7a.js +1 -0
  161. package/apps/pwa/out/_next/static/chunks/app/sessions/page-cc1609a71f44ec62.js +1 -0
  162. package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-7659a9a1345bfaa9.js +1 -0
  163. package/apps/pwa/out/_next/static/chunks/app/settings/page-0afef60ecc0c4af5.js +1 -0
  164. package/apps/pwa/out/_next/static/chunks/app/setup/done/page-a3553949f8f34f5f.js +1 -0
  165. package/apps/pwa/out/_next/static/chunks/app/setup/layout-9fc644de2d8edae3.js +1 -0
  166. package/apps/pwa/out/_next/static/chunks/app/setup/page-057a69702f3c67c7.js +1 -0
  167. package/apps/pwa/out/_next/static/chunks/app/share/page-c0f0e570f3f74c73.js +1 -0
  168. package/apps/pwa/out/_next/static/chunks/app/showroom/page-1825071ae34e3b89.js +1 -0
  169. package/apps/pwa/out/_next/static/chunks/app/tasks/page-6244e3e135d8ccfc.js +1 -0
  170. package/apps/pwa/out/_next/static/chunks/app/term/page-da787e8a10b8a82e.js +1 -0
  171. package/apps/pwa/out/_next/static/chunks/app/today/page-1316d32498e2be42.js +1 -0
  172. package/apps/pwa/out/_next/static/chunks/app/trace/page-4df94572e343de2e.js +1 -0
  173. package/apps/pwa/out/_next/static/chunks/app/vault/page-708969f7475e88c1.js +1 -0
  174. package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-c58add08c919a1dc.js +1 -0
  175. package/apps/pwa/out/_next/static/chunks/app/workflows/page-a24847f45e5d5bf9.js +1 -0
  176. package/apps/pwa/out/_next/static/chunks/app/workspace/page-acfec65a3a60e22e.js +1 -0
  177. package/apps/pwa/out/_next/static/chunks/app/worktrees/page-3dfc598e6fbde245.js +1 -0
  178. package/apps/pwa/out/_next/static/chunks/framework-c658a626118411b7.js +1 -0
  179. package/apps/pwa/out/_next/static/chunks/main-4c73685fd891445b.js +1 -0
  180. package/apps/pwa/out/_next/static/chunks/main-app-6310f7e5de7dd01d.js +1 -0
  181. package/apps/pwa/out/_next/static/chunks/pages/_app-51c326bf48610be1.js +1 -0
  182. package/apps/pwa/out/_next/static/chunks/pages/_error-d0beadf754da59b0.js +1 -0
  183. package/apps/pwa/out/_next/static/chunks/webpack-acd243bfbf3f6732.js +1 -0
  184. package/apps/pwa/out/_next/static/css/d1f8bb401740a549.css +1 -0
  185. package/apps/pwa/out/approvals/index.html +1 -1
  186. package/apps/pwa/out/approvals/index.txt +23 -23
  187. package/apps/pwa/out/autopilot/index.html +1 -1
  188. package/apps/pwa/out/autopilot/index.txt +23 -23
  189. package/apps/pwa/out/board/index.html +1 -1
  190. package/apps/pwa/out/board/index.txt +23 -23
  191. package/apps/pwa/out/botlab/index.html +1 -1
  192. package/apps/pwa/out/botlab/index.txt +22 -22
  193. package/apps/pwa/out/bots/index.html +1 -1
  194. package/apps/pwa/out/bots/index.txt +22 -22
  195. package/apps/pwa/out/ceo/index.html +1 -1
  196. package/apps/pwa/out/ceo/index.txt +23 -23
  197. package/apps/pwa/out/chat/index.html +1 -1
  198. package/apps/pwa/out/chat/index.txt +22 -22
  199. package/apps/pwa/out/consult/index.html +1 -1
  200. package/apps/pwa/out/consult/index.txt +23 -23
  201. package/apps/pwa/out/control/index.html +1 -1
  202. package/apps/pwa/out/control/index.txt +23 -23
  203. package/apps/pwa/out/decisions/index.html +1 -1
  204. package/apps/pwa/out/decisions/index.txt +22 -22
  205. package/apps/pwa/out/design-check/index.html +1 -1
  206. package/apps/pwa/out/design-check/index.txt +23 -23
  207. package/apps/pwa/out/editor/index.html +1 -1
  208. package/apps/pwa/out/editor/index.txt +23 -23
  209. package/apps/pwa/out/exec/index.html +1 -1
  210. package/apps/pwa/out/exec/index.txt +23 -23
  211. package/apps/pwa/out/field/index.html +1 -1
  212. package/apps/pwa/out/field/index.txt +23 -23
  213. package/apps/pwa/out/healthz +1 -1
  214. package/apps/pwa/out/index.html +1 -1
  215. package/apps/pwa/out/index.txt +22 -22
  216. package/apps/pwa/out/inside/index.html +1 -1
  217. package/apps/pwa/out/inside/index.txt +22 -22
  218. package/apps/pwa/out/intake/index.html +1 -1
  219. package/apps/pwa/out/intake/index.txt +23 -23
  220. package/apps/pwa/out/live/index.html +1 -1
  221. package/apps/pwa/out/live/index.txt +23 -23
  222. package/apps/pwa/out/live-run/index.html +1 -1
  223. package/apps/pwa/out/live-run/index.txt +23 -23
  224. package/apps/pwa/out/loops/index.html +1 -1
  225. package/apps/pwa/out/loops/index.txt +22 -22
  226. package/apps/pwa/out/market/index.html +1 -1
  227. package/apps/pwa/out/market/index.txt +22 -22
  228. package/apps/pwa/out/missions/placeholder/index.html +1 -1
  229. package/apps/pwa/out/missions/placeholder/index.txt +22 -22
  230. package/apps/pwa/out/morning/index.html +1 -1
  231. package/apps/pwa/out/morning/index.txt +23 -23
  232. package/apps/pwa/out/observatory/index.html +1 -1
  233. package/apps/pwa/out/observatory/index.txt +23 -23
  234. package/apps/pwa/out/ops/checklist/index.html +1 -1
  235. package/apps/pwa/out/ops/checklist/index.txt +22 -22
  236. package/apps/pwa/out/ops/release/index.html +1 -1
  237. package/apps/pwa/out/ops/release/index.txt +22 -22
  238. package/apps/pwa/out/ops/seats/index.html +1 -1
  239. package/apps/pwa/out/ops/seats/index.txt +22 -22
  240. package/apps/pwa/out/outputs/index.html +1 -1
  241. package/apps/pwa/out/outputs/index.txt +22 -22
  242. package/apps/pwa/out/reflection/index.html +1 -1
  243. package/apps/pwa/out/reflection/index.txt +23 -23
  244. package/apps/pwa/out/scheduler/index.html +1 -1
  245. package/apps/pwa/out/scheduler/index.txt +23 -23
  246. package/apps/pwa/out/sessions/index.html +1 -1
  247. package/apps/pwa/out/sessions/index.txt +22 -22
  248. package/apps/pwa/out/settings/devices/index.html +1 -1
  249. package/apps/pwa/out/settings/devices/index.txt +23 -23
  250. package/apps/pwa/out/settings/index.html +1 -1
  251. package/apps/pwa/out/settings/index.txt +23 -23
  252. package/apps/pwa/out/setup/done/index.html +1 -1
  253. package/apps/pwa/out/setup/done/index.txt +23 -23
  254. package/apps/pwa/out/setup/index.html +1 -1
  255. package/apps/pwa/out/setup/index.txt +23 -23
  256. package/apps/pwa/out/share/index.html +1 -1
  257. package/apps/pwa/out/share/index.txt +23 -23
  258. package/apps/pwa/out/showroom/index.html +1 -1
  259. package/apps/pwa/out/showroom/index.txt +22 -22
  260. package/apps/pwa/out/tasks/index.html +1 -1
  261. package/apps/pwa/out/tasks/index.txt +23 -23
  262. package/apps/pwa/out/term/index.html +1 -1
  263. package/apps/pwa/out/term/index.txt +23 -23
  264. package/apps/pwa/out/today/index.html +1 -1
  265. package/apps/pwa/out/today/index.txt +23 -23
  266. package/apps/pwa/out/trace/index.html +1 -1
  267. package/apps/pwa/out/trace/index.txt +23 -23
  268. package/apps/pwa/out/vault/index.html +1 -1
  269. package/apps/pwa/out/vault/index.txt +23 -23
  270. package/apps/pwa/out/workflows/chat-ui/index.html +1 -1
  271. package/apps/pwa/out/workflows/chat-ui/index.txt +23 -23
  272. package/apps/pwa/out/workflows/index.html +1 -1
  273. package/apps/pwa/out/workflows/index.txt +23 -23
  274. package/apps/pwa/out/workspace/index.html +1 -1
  275. package/apps/pwa/out/workspace/index.txt +23 -23
  276. package/apps/pwa/out/worktrees/index.html +1 -1
  277. package/apps/pwa/out/worktrees/index.txt +23 -23
  278. package/catalog/external-commands.yaml +5 -3
  279. package/catalog/meta/catalogVersion.yaml +2 -1
  280. package/catalog/signing/catalog-signing-public.pem +3 -0
  281. package/graphs/intake/intake-daily.yaml +16 -0
  282. package/graphs/intake/news-sources.yaml +1 -0
  283. package/graphs/intake/recipes.yaml +7 -0
  284. package/graphs/overlays/README.md +6 -0
  285. package/graphs/overlays/examples/research-runtime-empty-terminal.yaml +28 -0
  286. package/graphs/profiles/local.yaml +5 -0
  287. package/graphs/profiles/pod.yaml +4 -0
  288. package/graphs/release/release-loop.yaml +33 -17
  289. package/graphs/units/verbs/make-doc.yaml +1 -0
  290. package/package.json +6 -2
  291. package/plugins/demo-absorption-briefing/plugin.json +18 -0
  292. package/plugins/demo-absorption-briefing/skills/demo-absorption-briefing/SKILL.md +8 -0
  293. package/plugins/demo-browser-hand/plugin.json +13 -0
  294. package/plugins/demo-browser-hand/skills/demo-browser-hand/SKILL.md +8 -0
  295. package/plugins/demo-linear-secretary/plugin.json +15 -0
  296. package/plugins/demo-linear-secretary/skills/demo-linear-secretary/SKILL.md +8 -0
  297. package/plugins/demo-plugin-wizard/plugin.json +11 -0
  298. package/plugins/demo-plugin-wizard/skills/demo-plugin-wizard/SKILL.md +8 -0
  299. package/plugins/demo-research/plugin.json +16 -0
  300. package/plugins/demo-research/skills/demo-research/SKILL.md +8 -0
  301. package/plugins/demo-video-briefing/plugin.json +15 -0
  302. package/plugins/demo-video-briefing/skills/demo-video-briefing/SKILL.md +8 -0
  303. package/scripts/bench-metering-plan.ts +229 -0
  304. package/scripts/build-signed-catalog.ts +48 -0
  305. package/scripts/ci-typecheck-main-delta.sh +88 -0
  306. package/scripts/codex-fallback-live-probe.ts +1 -1
  307. package/scripts/demo/demo1104-parallel-host.ts +56 -0
  308. package/scripts/demo/demo1104-parallel-scenes.ts +301 -0
  309. package/scripts/demo/demo1104-parallel.ts +72 -0
  310. package/scripts/demo/demo1104-stage.config.ts +21 -0
  311. package/scripts/demo/demo1104-stage.ts +316 -0
  312. package/scripts/goal-method-audit.ts +17 -1
  313. package/scripts/graph-units/land-enqueue.ts +90 -0
  314. package/scripts/hooks/codex-notify.sh +32 -0
  315. package/scripts/install.sh +10 -38
  316. package/scripts/landing-heal/land-plan.ts +57 -0
  317. package/scripts/public-leak-baseline.txt +0 -1
  318. package/scripts/release-loop/auto-approve-node.ts +1 -1
  319. package/scripts/release-loop/docs-node.ts +4 -2
  320. package/scripts/release-loop/gate-autoheal-sim-evidence.ts +60 -0
  321. package/scripts/release-loop/gate-image-pin.ts +116 -2
  322. package/scripts/release-loop/gate-method.ts +139 -0
  323. package/scripts/release-loop/gate-node.ts +395 -43
  324. package/scripts/release-loop/gate-progress-sim.ts +73 -0
  325. package/scripts/release-loop/gate-traffic-mode.ts +151 -3
  326. package/scripts/release-loop/node-verdict.ts +38 -25
  327. package/scripts/release-loop/notes-repair.ts +18 -1
  328. package/scripts/release-loop/preflight.ts +544 -10
  329. package/scripts/release-loop/render-warm-control-manifest.ts +22 -0
  330. package/scripts/release-loop/resume-release.ts +9 -7
  331. package/scripts/release-loop/resume.ts +13 -4
  332. package/scripts/release-loop/unattended-release.ts +20 -9
  333. package/scripts/release-loop/warm-control-forward.ts +178 -0
  334. package/scripts/retro-cycle.ts +30 -8
  335. package/scripts/rhythm/daily.ts +39 -4
  336. package/scripts/rhythm/linear-progress-sync.ts +311 -0
  337. package/scripts/ux-sim.ts +7 -1
  338. package/scripts/video-pipeline.ts +9 -1
  339. package/scripts/warm-pool-provider-config.ts +35 -7
  340. package/src/acp/agent-manager.ts +1 -0
  341. package/src/acp/codex-app-server-agent.ts +33 -0
  342. package/src/acp/codex-app-server-client.ts +153 -16
  343. package/src/acp/core-turn-bridge.ts +17 -12
  344. package/src/acp/event-router.ts +20 -1
  345. package/src/acp/server.ts +6 -0
  346. package/src/agent-mission/browser-roundtrip-coordinator.ts +85 -0
  347. package/src/agent-mission/claude-headless.ts +4 -1
  348. package/src/agent-mission/codex-exec.ts +105 -0
  349. package/src/agent-mission/driver.ts +192 -11
  350. package/src/agent-mission/grok-auth-status.ts +107 -0
  351. package/src/agent-mission/hand-hooks.ts +101 -0
  352. package/src/agent-mission/mission-cli.ts +56 -21
  353. package/src/agent-mission/mission-hand-reply.ts +118 -0
  354. package/src/agent-mission/mission-line.ts +180 -0
  355. package/src/agent-mission/mission-out.ts +256 -18
  356. package/src/agent-mission/tool-install.ts +122 -11
  357. package/src/agent-substrate/pr-reviewer.ts +147 -11
  358. package/src/agent-substrate/self-review-cli.ts +10 -2
  359. package/src/agents/general-purpose.md +1 -1
  360. package/src/auto-research/research-fanout.ts +221 -0
  361. package/src/auto-research/research-turn.ts +362 -31
  362. package/src/autopilot/mission-codebase-gate.ts +7 -3
  363. package/src/autopilot/pr-manager.ts +31 -3
  364. package/src/boot/daemon-tools/self-implement.ts +3 -1
  365. package/src/boot/daemon-tools/web-search.ts +1 -2
  366. package/src/briefing/brief-items.ts +55 -11
  367. package/src/cli/agent-cli.ts +2 -1
  368. package/src/cli/catalog-cli.ts +31 -0
  369. package/src/cli/connector-cli.ts +16 -0
  370. package/src/cli/control-cli.ts +15 -6
  371. package/src/cli/doctor-fix.ts +2 -2
  372. package/src/cli/intake-source-cli.ts +44 -8
  373. package/src/cli/log-event-names.ts +8 -0
  374. package/src/cli/msg-cli.ts +32 -3
  375. package/src/cli/pr-cli.ts +21 -1
  376. package/src/cli/pr-land-heavy-remote.ts +44 -6
  377. package/src/cli/pr-land-overlap-evidence.ts +13 -1
  378. package/src/cli/pr-land-pod-shadow-job.ts +143 -5
  379. package/src/cli/pr-land-pod-shadow.ts +9 -2
  380. package/src/cli/release-checklist-read-cli.ts +44 -16
  381. package/src/cli/release-cli.ts +23 -3
  382. package/src/cli/research-cli.ts +9 -0
  383. package/src/cli/setup-cli.ts +166 -6
  384. package/src/cli/setup-keys.ts +199 -0
  385. package/src/cli/task-plugin-wizard-host.ts +114 -0
  386. package/src/cli/tasks-cli.ts +54 -9
  387. package/src/cli/tui-test-cli.ts +190 -0
  388. package/src/config.ts +4 -2
  389. package/src/connectors/linear-daily-progress.ts +228 -0
  390. package/src/connectors/linear-projector.ts +34 -12
  391. package/src/connectors/linear.ts +151 -7
  392. package/src/control-plane/ledger.ts +42 -4
  393. package/src/control-plane/member-tokens.ts +25 -2
  394. package/src/control-plane/ports.ts +8 -3
  395. package/src/control-plane/server.ts +26 -5
  396. package/src/core-turn/deep-turn-bloom.ts +67 -0
  397. package/src/core-turn/research-policy.ts +43 -0
  398. package/src/core-turn/run-core-turn.ts +488 -51
  399. package/src/core-turn/types.ts +4 -0
  400. package/src/dashboard/chat/acp-chat.ts +10 -0
  401. package/src/dashboard/classic-sidetab-mission-job.ts +192 -0
  402. package/src/dashboard/classic-sidetab-mission-pair.ts +82 -0
  403. package/src/dashboard/classic-sidetab-mission-trio.ts +242 -0
  404. package/src/dashboard/classic-sidetab-mission.ts +169 -5
  405. package/src/dashboard/index.ts +387 -14
  406. package/src/dashboard/input/chat-main-acp-dispatch.ts +23 -0
  407. package/src/dashboard/input/chat-main-plain-turn-runtime.ts +8 -0
  408. package/src/dashboard/mission-cli-consumer.ts +20 -8
  409. package/src/dashboard/plugin-wizard-runtime.ts +50 -0
  410. package/src/dashboard/plugin-wizard-tool.ts +55 -0
  411. package/src/dashboard/sidetab-runtime.ts +3 -1
  412. package/src/dashboard/terminal-popup-runtime.ts +6 -3
  413. package/src/dashboard/visible-mission-diagnostics.ts +16 -0
  414. package/src/decisions/linear-progress-summary.ts +78 -0
  415. package/src/decisions/linear-progress-sync.ts +152 -0
  416. package/src/domains/outbound-alert.ts +49 -11
  417. package/src/domains/retro-cycle-observation.ts +43 -0
  418. package/src/domains/retro-cycle.ts +13 -2
  419. package/src/domains/retro-proposals.ts +92 -0
  420. package/src/domains/retro-report.ts +6 -1
  421. package/src/domains/telegram-kind-route.ts +16 -9
  422. package/src/graph-runner/arg-allowance.ts +13 -0
  423. package/src/graph-runner/graph-cli.ts +24 -1
  424. package/src/graph-runner/graph-grow-llm.ts +3 -1
  425. package/src/graph-runner/graph-run-api.ts +3 -1
  426. package/src/graph-runner/runner.ts +310 -46
  427. package/src/graph-wizard/mission-compose.ts +407 -12
  428. package/src/harness/dispatch-backpressure.ts +54 -1
  429. package/src/harness/dispatch-shadow-compare.ts +74 -0
  430. package/src/harness/harness-cli-command.ts +15 -3
  431. package/src/harness/harness-pod-dispatch.ts +3 -0
  432. package/src/harness/skill-exec.ts +21 -9
  433. package/src/harness/skill-select.ts +1 -1
  434. package/src/hooks/error-report-cloud.ts +101 -0
  435. package/src/hooks/receiver.ts +29 -2
  436. package/src/index.ts +129 -12
  437. package/src/intake-plane/actions.ts +354 -0
  438. package/src/intake-plane/adapters/telegram-ambient.ts +34 -18
  439. package/src/intake-plane/intake-sources.ts +78 -8
  440. package/src/intake-plane/items.ts +14 -4
  441. package/src/intake-plane/linear-mission-sync.ts +80 -0
  442. package/src/intake-plane/linear-secretary-runtime.ts +178 -0
  443. package/src/intake-plane/linear-wish.ts +227 -1
  444. package/src/life/life-cli.ts +168 -0
  445. package/src/life/life-kinds.ts +160 -0
  446. package/src/live-supply/budget-consumer.ts +78 -0
  447. package/src/live-supply/read.ts +3 -0
  448. package/src/live-supply/snapshot.ts +45 -0
  449. package/src/llm/child-first-llm-observation.ts +112 -0
  450. package/src/llm/provider-credentials.ts +68 -6
  451. package/src/llm/provider-failure-evidence.ts +44 -0
  452. package/src/llm.ts +172 -12
  453. package/src/maturity/feature-maturity.ts +3 -3
  454. package/src/mcp/client.ts +7 -0
  455. package/src/mcp/proxy-runtime.ts +6 -1
  456. package/src/mcp/server.ts +54 -0
  457. package/src/msg/msg-sse-server.ts +3 -3
  458. package/src/msg/msg-store.ts +177 -19
  459. package/src/native-tool-catalog.ts +36 -2
  460. package/src/nexus/api/consult-requests.ts +18 -6
  461. package/src/nexus/api/discord-trigger-bot.ts +6 -6
  462. package/src/nexus/api/graphs-api.ts +4 -2
  463. package/src/nexus/api/grokbot-trigger-bot.ts +206 -0
  464. package/src/nexus/api/http-server.ts +37 -1
  465. package/src/nexus/api/mcp-public-allowlist.ts +2 -0
  466. package/src/nexus/api/telegram-trigger-bot.ts +6 -6
  467. package/src/nexus/boot/register-mcp-clients.ts +114 -8
  468. package/src/nexus/index.ts +22 -2
  469. package/src/nexus/outbound/format.ts +9 -0
  470. package/src/nexus/outbound/grokbot-adapter.ts +71 -0
  471. package/src/nexus/outbound/router.ts +121 -16
  472. package/src/nexus/setup-status.ts +9 -0
  473. package/src/nexus/state/state.ts +3 -0
  474. package/src/oauth/codex-account-store.ts +20 -7
  475. package/src/oauth/codex-owner-mirror.ts +81 -0
  476. package/src/oauth/codex.ts +17 -2
  477. package/src/oauth/fallback-chain.ts +47 -17
  478. package/src/onboarding/first-run-doctor.ts +8 -1
  479. package/src/onboarding/first-run.ts +126 -29
  480. package/src/onboarding/key-setup.ts +103 -0
  481. package/src/onboarding/menu-answer.ts +13 -0
  482. package/src/onboarding/secret-prompt.ts +37 -0
  483. package/src/plugins/install/plugin-install.ts +59 -0
  484. package/src/pr-tool/census.ts +130 -0
  485. package/src/preview/terminal.ts +22 -7
  486. package/src/prompt-enhance/enhance.ts +10 -0
  487. package/src/pty-shell/pty-control-ipc.ts +4 -1
  488. package/src/pty-shell/pty-write-provenance.ts +21 -3
  489. package/src/pty-shell/registry.ts +9 -2
  490. package/src/registry/catalog-server.ts +232 -0
  491. package/src/registry/loader.ts +45 -1
  492. package/src/registry/types.ts +1 -2
  493. package/src/release-loop/proposal-auto-place.ts +83 -0
  494. package/src/research/axis-fanout.ts +79 -29
  495. package/src/research/lenses/second-order.ts +312 -0
  496. package/src/self-dev/ask-launch-flow.ts +72 -1
  497. package/src/self-dev/dev-cli.ts +7 -2
  498. package/src/self-dev/dev-pipeline.ts +5 -0
  499. package/src/self-dev/draft-residue.ts +64 -5
  500. package/src/self-dev/draft-sweep.ts +31 -10
  501. package/src/self-dev/draft-triage-rules.ts +60 -3
  502. package/src/self-dev/graph-front-nodes.ts +2 -1
  503. package/src/self-dev/graph-journey-route.ts +76 -21
  504. package/src/self-dev/launch-preflight.ts +58 -0
  505. package/src/self-dev/orchestrate.ts +1 -1
  506. package/src/self-dev/run-supervisor.ts +152 -2
  507. package/src/self-dev/shard-aggregate.ts +4 -0
  508. package/src/self-dev/shard-run.ts +36 -15
  509. package/src/self-implement/abandoned-classification.ts +12 -3
  510. package/src/self-implement/budget-gate.ts +7 -0
  511. package/src/self-implement/child-llm-preference.ts +10 -1
  512. package/src/self-implement/doctor-visit.ts +30 -8
  513. package/src/self-implement/elanous-tui-spawn.ts +3 -0
  514. package/src/self-implement/fixtures/tdd-green-missing-passing-child-transcript.txt +2 -0
  515. package/src/self-implement/gate-artifacts.ts +2 -1
  516. package/src/self-implement/goal-author-cli.ts +4 -2
  517. package/src/self-implement/goal-author.ts +549 -10
  518. package/src/self-implement/graph-overlay-yaml.ts +181 -4
  519. package/src/self-implement/graph-overlay.ts +3 -1
  520. package/src/self-implement/graph-profile-yaml.ts +107 -0
  521. package/src/self-implement/graph-yaml.ts +94 -5
  522. package/src/self-implement/off-diff-evidence.ts +249 -5
  523. package/src/self-implement/orchestrator.ts +298 -26
  524. package/src/self-implement/run-chart.ts +6 -3
  525. package/src/self-implement/run-ledger.ts +51 -1
  526. package/src/self-implement/runtime-overlay-run-steps.ts +95 -0
  527. package/src/self-implement/tdd-evidence-tags.ts +9 -0
  528. package/src/self-implement/test-scenario-request.ts +37 -6
  529. package/src/self-implement/train-gate-receipt.ts +166 -0
  530. package/src/self-implement/train-gate-remote.ts +62 -18
  531. package/src/session/chat.ts +6 -4
  532. package/src/session/session-fanout.ts +2 -0
  533. package/src/session/streaming/acp-stream-sink.ts +2 -1
  534. package/src/session/streaming/chunk-producer.ts +6 -0
  535. package/src/session/streaming/stream-compositor.ts +3 -2
  536. package/src/session-runtime/index.ts +74 -6
  537. package/src/session-runtime/retry-policy.ts +1 -1
  538. package/src/setup/llm-env-detect.ts +3 -0
  539. package/src/setup/service-key-catalog.ts +46 -0
  540. package/src/setup/service-keys.ts +241 -0
  541. package/src/sidetab-core/model.ts +205 -10
  542. package/src/sidetab-core/visible-agent-mission-pair.ts +51 -0
  543. package/src/sidetab-core/visible-agent-mission.ts +182 -48
  544. package/src/skills/tools/agent.ts +23 -4
  545. package/src/skills/tools/omni-search.ts +127 -27
  546. package/src/task-agent/parent-host.ts +29 -1
  547. package/src/task-agent/recall-inject.ts +98 -0
  548. package/src/task-agent/repair-outcomes.ts +65 -0
  549. package/src/task-agent/task-hand.ts +46 -14
  550. package/src/task-orchestrator/dispatcher.ts +14 -1
  551. package/src/task-orchestrator/linear-capture-events.ts +55 -0
  552. package/src/task-orchestrator/store.ts +16 -5
  553. package/src/task-orchestrator/surfaces/pod-artifact-return.ts +23 -1
  554. package/src/task-orchestrator/surfaces/pod-failure-reason.ts +107 -1
  555. package/src/task-orchestrator/surfaces/pod-ledger-events.ts +113 -14
  556. package/src/task-orchestrator/surfaces/pod-si-warm-host.ts +21 -9
  557. package/src/task-orchestrator/surfaces/pod-source-receive.ts +23 -11
  558. package/src/task-orchestrator/surfaces/pod-warm-switch.ts +2 -0
  559. package/src/task-orchestrator/surfaces/pod-warm-worker-pod.ts +1 -1
  560. package/src/task-orchestrator/surfaces/pod-warm-worker-provider.ts +467 -77
  561. package/src/task-orchestrator/surfaces/pod-warm-worker-runtime.ts +45 -3
  562. package/src/task-orchestrator/surfaces/self-implement-pod.ts +210 -14
  563. package/src/task-orchestrator/surfaces/self-implement.ts +27 -3
  564. package/src/task-orchestrator/surfaces/warm-reuse-evidence.ts +169 -0
  565. package/src/task-orchestrator/types.ts +14 -0
  566. package/src/telegram.ts +14 -16
  567. package/src/terminal/coding-agent.ts +14 -5
  568. package/src/terminal/session-registry.ts +1 -1
  569. package/src/tool-hints/gate.ts +46 -14
  570. package/src/tool-hints/signals.ts +1 -1
  571. package/src/tool-hints/types.ts +2 -0
  572. package/src/tool-runtime/agent-runtime.ts +1 -0
  573. package/src/tool-runtime/browser-hand-runtime.ts +391 -0
  574. package/src/tool-runtime/browser-runtime.ts +33 -19
  575. package/src/tool-runtime/elanous-linear-issue-runtime.ts +76 -0
  576. package/src/tool-runtime/elanous-linear-secretary-runtime.ts +173 -0
  577. package/src/tool-runtime/graph-mcp-runtimes.ts +240 -0
  578. package/src/tool-runtime/index.ts +6 -0
  579. package/src/tool-runtime/types.ts +5 -0
  580. package/src/tui/entry.ts +51 -8
  581. package/src/tui/sidetab/attach.ts +252 -11
  582. package/src/tui/sidetab/herdr-portal.ts +225 -0
  583. package/src/tui/sidetab/list.ts +3 -2
  584. package/src/tui-client/next-dashboard-runtime.ts +52 -0
  585. package/src/user-config.ts +34 -9
  586. package/src/user-intent/types.ts +4 -3
  587. package/src/ux-sim/browser-hand.ts +165 -0
  588. package/src/ux-sim/draft-inventory-builder.ts +199 -0
  589. package/src/ux-sim/fake-browser-page.ts +81 -0
  590. package/src/ux-sim/fake-linear-device.ts +31 -0
  591. package/src/ux-sim/graph-engine-sim.ts +47 -0
  592. package/src/ux-sim/linear-secretary.ts +208 -0
  593. package/src/ux-sim/mock-scenario-catalog.json +81 -26
  594. package/src/ux-sim/mock-scenario-catalog.ts +175 -5
  595. package/src/ux-sim/onboarding-first-run-device.ts +31 -21
  596. package/src/ux-sim/release-sim-rig.ts +62 -18
  597. package/src/ux-sim/scenario.ts +70 -26
  598. package/src/ux-sim/service-key-setup.ts +113 -0
  599. package/src/ux-sim/term-slash-device.ts +74 -0
  600. package/src/ux-sim/turn-throw-sim.ts +31 -0
  601. package/src/version/packed-revision.json +1 -1
  602. package/src/web-search/exa.ts +77 -0
  603. package/src/web-search/index.ts +30 -9
  604. package/src/web-search/provider.ts +4 -1
  605. package/src/web-search/x-intent.ts +5 -0
  606. package/apps/pwa/out/_next/static/chunks/0244e5b5.6fc7670f8223d82d.js +0 -1
  607. package/apps/pwa/out/_next/static/chunks/1121.13ba7a8aff19df81.js +0 -36
  608. package/apps/pwa/out/_next/static/chunks/1147-5196d19c222051b3.js +0 -1
  609. package/apps/pwa/out/_next/static/chunks/1319.b9b815ae0f181e06.js +0 -1
  610. package/apps/pwa/out/_next/static/chunks/1345-31427b833438f521.js +0 -1
  611. package/apps/pwa/out/_next/static/chunks/1455-530ca16c7e71baff.js +0 -1
  612. package/apps/pwa/out/_next/static/chunks/1574.878c18ecc97b1bd4.js +0 -1
  613. package/apps/pwa/out/_next/static/chunks/1586.fafc33a9a5835cb7.js +0 -32
  614. package/apps/pwa/out/_next/static/chunks/1744.855fd60ae4c4a8c8.js +0 -1
  615. package/apps/pwa/out/_next/static/chunks/193.21a47a3e07ef6860.js +0 -1
  616. package/apps/pwa/out/_next/static/chunks/1945.7b54990d578c119b.js +0 -1
  617. package/apps/pwa/out/_next/static/chunks/2004.e839fda7ea5a738a.js +0 -1
  618. package/apps/pwa/out/_next/static/chunks/2044-dd681a5c08779ff8.js +0 -1
  619. package/apps/pwa/out/_next/static/chunks/2101.2248decb38829b03.js +0 -286
  620. package/apps/pwa/out/_next/static/chunks/2300.41ea70ac1bef1446.js +0 -1
  621. package/apps/pwa/out/_next/static/chunks/2357-07b5eeb5fb12628d.js +0 -1
  622. package/apps/pwa/out/_next/static/chunks/2364.28652020695a6db3.js +0 -34
  623. package/apps/pwa/out/_next/static/chunks/2456.b6de0e1c05f28843.js +0 -1
  624. package/apps/pwa/out/_next/static/chunks/2526.c3e50ac1fec064bd.js +0 -1
  625. package/apps/pwa/out/_next/static/chunks/2549-cda50b716ff4250c.js +0 -1
  626. package/apps/pwa/out/_next/static/chunks/2550-5f1e88f615568045.js +0 -1
  627. package/apps/pwa/out/_next/static/chunks/261-319078c954e40d66.js +0 -1
  628. package/apps/pwa/out/_next/static/chunks/2690.0521c738b7749931.js +0 -115
  629. package/apps/pwa/out/_next/static/chunks/2974.595d1e29d040cb6a.js +0 -64
  630. package/apps/pwa/out/_next/static/chunks/3207.a756c95e9ec8c3c8.js +0 -1
  631. package/apps/pwa/out/_next/static/chunks/3285.89ee2f298682f5e5.js +0 -93
  632. package/apps/pwa/out/_next/static/chunks/3447.06edc7b092021417.js +0 -41
  633. package/apps/pwa/out/_next/static/chunks/3510-9ca392698bfe4391.js +0 -1
  634. package/apps/pwa/out/_next/static/chunks/3541.772e5ce425aaa611.js +0 -24
  635. package/apps/pwa/out/_next/static/chunks/3741.9cf76acaa2ee5298.js +0 -1
  636. package/apps/pwa/out/_next/static/chunks/3837.a210d7d0db8d8abd.js +0 -1
  637. package/apps/pwa/out/_next/static/chunks/3898-955c896f394217a6.js +0 -1
  638. package/apps/pwa/out/_next/static/chunks/3947-ef57acea76eaa8d2.js +0 -1
  639. package/apps/pwa/out/_next/static/chunks/4037-3b82ebc7d78afdc7.js +0 -1
  640. package/apps/pwa/out/_next/static/chunks/405.9022d4a478202b67.js +0 -77
  641. package/apps/pwa/out/_next/static/chunks/417-fb2cc9a9910e5968.js +0 -1
  642. package/apps/pwa/out/_next/static/chunks/4276.336d76d858fcdf1b.js +0 -1
  643. package/apps/pwa/out/_next/static/chunks/4302.6ced9aa4535de947.js +0 -1
  644. package/apps/pwa/out/_next/static/chunks/4320.583cbab64db6be02.js +0 -1
  645. package/apps/pwa/out/_next/static/chunks/4768-8eac183fd291ca53.js +0 -1
  646. package/apps/pwa/out/_next/static/chunks/4770.769c9cd9c7034eba.js +0 -148
  647. package/apps/pwa/out/_next/static/chunks/4895.65605ec3e6504e89.js +0 -74
  648. package/apps/pwa/out/_next/static/chunks/50061469.0326382241ef3b2d.js +0 -122
  649. package/apps/pwa/out/_next/static/chunks/5112.4b9f300124fab7b3.js +0 -149
  650. package/apps/pwa/out/_next/static/chunks/5335.375ee922bcd5bc83.js +0 -1
  651. package/apps/pwa/out/_next/static/chunks/5342.023a2e729689b320.js +0 -27
  652. package/apps/pwa/out/_next/static/chunks/53c73f84.373b6160adfa89a4.js +0 -1
  653. package/apps/pwa/out/_next/static/chunks/5431-72a1dbde59400691.js +0 -1
  654. package/apps/pwa/out/_next/static/chunks/5440-4236de26c5ea5856.js +0 -1
  655. package/apps/pwa/out/_next/static/chunks/5486-b318c165f645d8ba.js +0 -1
  656. package/apps/pwa/out/_next/static/chunks/5506-c7d2ec25c62a7c94.js +0 -1
  657. package/apps/pwa/out/_next/static/chunks/5570-c66ecbea26b4e3b1.js +0 -1
  658. package/apps/pwa/out/_next/static/chunks/5696.ffca5aa259d8451e.js +0 -1
  659. package/apps/pwa/out/_next/static/chunks/5793-8c584aea2aa87560.js +0 -1
  660. package/apps/pwa/out/_next/static/chunks/5848-6de6b8c173351a90.js +0 -1
  661. package/apps/pwa/out/_next/static/chunks/5999.94e3c83040200f31.js +0 -1
  662. package/apps/pwa/out/_next/static/chunks/5a7901d6-2d8d9b5587cf9042.js +0 -1
  663. package/apps/pwa/out/_next/static/chunks/6131.348b7d6bdcd267ce.js +0 -226
  664. package/apps/pwa/out/_next/static/chunks/6164.86133a0172611184.js +0 -90
  665. package/apps/pwa/out/_next/static/chunks/6515.e07e8b2b8a707a87.js +0 -1
  666. package/apps/pwa/out/_next/static/chunks/6522-c005514f87d18982.js +0 -1
  667. package/apps/pwa/out/_next/static/chunks/6642.648adb1767f39ecf.js +0 -1
  668. package/apps/pwa/out/_next/static/chunks/6848.138805a09d001d09.js +0 -1
  669. package/apps/pwa/out/_next/static/chunks/7049-c09e2b7a253a24f3.js +0 -1
  670. package/apps/pwa/out/_next/static/chunks/7072.1e00447d9fa39972.js +0 -104
  671. package/apps/pwa/out/_next/static/chunks/7106.64201c539c5e220c.js +0 -94
  672. package/apps/pwa/out/_next/static/chunks/7151-1f742b455986530e.js +0 -1
  673. package/apps/pwa/out/_next/static/chunks/7199.18d6b25e001154ce.js +0 -1
  674. package/apps/pwa/out/_next/static/chunks/7279-c199ea83f34338fa.js +0 -1
  675. package/apps/pwa/out/_next/static/chunks/728b938d.ffaa7ad583d60e58.js +0 -1
  676. package/apps/pwa/out/_next/static/chunks/7309.171c3de54e0322f1.js +0 -1
  677. package/apps/pwa/out/_next/static/chunks/733.7a1ab3342e03306f.js +0 -1
  678. package/apps/pwa/out/_next/static/chunks/7504.d5cf1e7cd89b1b08.js +0 -24
  679. package/apps/pwa/out/_next/static/chunks/7573-0fd4af62d65d4598.js +0 -1
  680. package/apps/pwa/out/_next/static/chunks/759.6f8267df4689c401.js +0 -1
  681. package/apps/pwa/out/_next/static/chunks/7825-668b046f72f14483.js +0 -1
  682. package/apps/pwa/out/_next/static/chunks/7852-1538768b6eb19388.js +0 -1
  683. package/apps/pwa/out/_next/static/chunks/7868.cff810430bb63c91.js +0 -1
  684. package/apps/pwa/out/_next/static/chunks/8084-dfcc796874ab4e07.js +0 -1
  685. package/apps/pwa/out/_next/static/chunks/8266.6bf9b131b2584678.js +0 -1
  686. package/apps/pwa/out/_next/static/chunks/8403.7b81d5e64074a725.js +0 -8
  687. package/apps/pwa/out/_next/static/chunks/8470.1998cbd0866a7eac.js +0 -1
  688. package/apps/pwa/out/_next/static/chunks/8505.fd803c6c33b54cc3.js +0 -79
  689. package/apps/pwa/out/_next/static/chunks/8546-6f03f8ea34dd61d9.js +0 -1
  690. package/apps/pwa/out/_next/static/chunks/8687-246fda8433d3477c.js +0 -1
  691. package/apps/pwa/out/_next/static/chunks/898-280022fb082936bc.js +0 -1
  692. package/apps/pwa/out/_next/static/chunks/9098-50eefc1844212e3d.js +0 -1
  693. package/apps/pwa/out/_next/static/chunks/9211-330b6736a63d4cb3.js +0 -1
  694. package/apps/pwa/out/_next/static/chunks/9249.976f1e69a9d80754.js +0 -1
  695. package/apps/pwa/out/_next/static/chunks/9255-cf88fceda5666645.js +0 -1
  696. package/apps/pwa/out/_next/static/chunks/9306-e523ba58bb8adc42.js +0 -1
  697. package/apps/pwa/out/_next/static/chunks/9324.a9866d717ba62cb6.js +0 -1
  698. package/apps/pwa/out/_next/static/chunks/9325.a8510e8aa87c8143.js +0 -1
  699. package/apps/pwa/out/_next/static/chunks/9353-12bfff0c130104cf.js +0 -1
  700. package/apps/pwa/out/_next/static/chunks/9479-154a697d4b6e4e98.js +0 -1
  701. package/apps/pwa/out/_next/static/chunks/9540-65aa6ccc31b3fd78.js +0 -1
  702. package/apps/pwa/out/_next/static/chunks/9633.ce5bddc56784da72.js +0 -1
  703. package/apps/pwa/out/_next/static/chunks/9656-374232558fd528d0.js +0 -1
  704. package/apps/pwa/out/_next/static/chunks/9832.f4a98c878ecf2c0a.js +0 -62
  705. package/apps/pwa/out/_next/static/chunks/9865.f094440645f02d98.js +0 -1
  706. package/apps/pwa/out/_next/static/chunks/app/_not-found/page-e772b4710df5d936.js +0 -1
  707. package/apps/pwa/out/_next/static/chunks/app/approvals/page-4361368e6a76b967.js +0 -1
  708. package/apps/pwa/out/_next/static/chunks/app/autopilot/page-802f349fdd65248d.js +0 -1
  709. package/apps/pwa/out/_next/static/chunks/app/board/page-7f35513988a2a495.js +0 -1
  710. package/apps/pwa/out/_next/static/chunks/app/botlab/page-798121656540e33e.js +0 -1
  711. package/apps/pwa/out/_next/static/chunks/app/bots/page-20a089490affe98c.js +0 -1
  712. package/apps/pwa/out/_next/static/chunks/app/ceo/page-e5e4ec786d70e604.js +0 -1
  713. package/apps/pwa/out/_next/static/chunks/app/chat/page-d12fe5d0801430e4.js +0 -1
  714. package/apps/pwa/out/_next/static/chunks/app/consult/page-d8cf21022fecc026.js +0 -1
  715. package/apps/pwa/out/_next/static/chunks/app/control/page-21ce565c9c57ee97.js +0 -1
  716. package/apps/pwa/out/_next/static/chunks/app/decisions/page-b56563025f619c9b.js +0 -1
  717. package/apps/pwa/out/_next/static/chunks/app/design-check/page-52f14dd133da8348.js +0 -1
  718. package/apps/pwa/out/_next/static/chunks/app/editor/page-c0ed7fdcdba76633.js +0 -1
  719. package/apps/pwa/out/_next/static/chunks/app/exec/page-af8c3020cb520f15.js +0 -1
  720. package/apps/pwa/out/_next/static/chunks/app/field/page-72eda67af9f5e35c.js +0 -1
  721. package/apps/pwa/out/_next/static/chunks/app/healthz/route-e772b4710df5d936.js +0 -1
  722. package/apps/pwa/out/_next/static/chunks/app/inside/page-67a6620d31f0a46f.js +0 -1
  723. package/apps/pwa/out/_next/static/chunks/app/intake/page-f059363aa0880ec2.js +0 -1
  724. package/apps/pwa/out/_next/static/chunks/app/layout-f9f917d6a57f69fb.js +0 -1
  725. package/apps/pwa/out/_next/static/chunks/app/live/page-d3ae55eee2f0826c.js +0 -1
  726. package/apps/pwa/out/_next/static/chunks/app/live-run/page-0e3d7b9421b79dac.js +0 -1
  727. package/apps/pwa/out/_next/static/chunks/app/loops/page-ba738f7e233eb211.js +0 -1
  728. package/apps/pwa/out/_next/static/chunks/app/market/page-33438b98c74fd599.js +0 -1
  729. package/apps/pwa/out/_next/static/chunks/app/missions/[id]/page-0b34d5fd990d793a.js +0 -1
  730. package/apps/pwa/out/_next/static/chunks/app/morning/page-0f291d3c8fd55a3a.js +0 -1
  731. package/apps/pwa/out/_next/static/chunks/app/not-found-3fced192be5279c1.js +0 -1
  732. package/apps/pwa/out/_next/static/chunks/app/observatory/page-04cb3cf182a7c1ea.js +0 -1
  733. package/apps/pwa/out/_next/static/chunks/app/ops/checklist/page-6ccbd2ab23a21542.js +0 -1
  734. package/apps/pwa/out/_next/static/chunks/app/ops/release/page-aa0518c48a5f4e56.js +0 -1
  735. package/apps/pwa/out/_next/static/chunks/app/ops/seats/page-4b32226d341ad7d7.js +0 -1
  736. package/apps/pwa/out/_next/static/chunks/app/outputs/page-3224fd8f6383b61f.js +0 -1
  737. package/apps/pwa/out/_next/static/chunks/app/page-efbc97459f2914e2.js +0 -1
  738. package/apps/pwa/out/_next/static/chunks/app/reflection/page-2fe487d88cd5d97c.js +0 -1
  739. package/apps/pwa/out/_next/static/chunks/app/scheduler/page-48861dd1a858bab7.js +0 -1
  740. package/apps/pwa/out/_next/static/chunks/app/sessions/page-197d5d4d21d228ea.js +0 -1
  741. package/apps/pwa/out/_next/static/chunks/app/settings/devices/page-a763ba89fbdd9c27.js +0 -1
  742. package/apps/pwa/out/_next/static/chunks/app/settings/page-7edb253510b1c136.js +0 -1
  743. package/apps/pwa/out/_next/static/chunks/app/setup/done/page-0c875702c61965ea.js +0 -1
  744. package/apps/pwa/out/_next/static/chunks/app/setup/layout-e772b4710df5d936.js +0 -1
  745. package/apps/pwa/out/_next/static/chunks/app/setup/page-e425c951151095f7.js +0 -1
  746. package/apps/pwa/out/_next/static/chunks/app/share/page-9c90e0aec4e27f77.js +0 -1
  747. package/apps/pwa/out/_next/static/chunks/app/showroom/page-733e09a02e727d42.js +0 -1
  748. package/apps/pwa/out/_next/static/chunks/app/tasks/page-4f899e14c34d77a1.js +0 -1
  749. package/apps/pwa/out/_next/static/chunks/app/term/page-bf067887b3307423.js +0 -1
  750. package/apps/pwa/out/_next/static/chunks/app/today/page-7af10868ff87d04e.js +0 -1
  751. package/apps/pwa/out/_next/static/chunks/app/trace/page-efe5304057aa11c7.js +0 -1
  752. package/apps/pwa/out/_next/static/chunks/app/vault/page-76bcd29aaa8a26c3.js +0 -1
  753. package/apps/pwa/out/_next/static/chunks/app/workflows/chat-ui/page-4cfd88e2273ce50f.js +0 -1
  754. package/apps/pwa/out/_next/static/chunks/app/workflows/page-0a1ddb47efba0a32.js +0 -1
  755. package/apps/pwa/out/_next/static/chunks/app/workspace/page-2a176c707152c892.js +0 -1
  756. package/apps/pwa/out/_next/static/chunks/app/worktrees/page-efe03031b8797fbf.js +0 -1
  757. package/apps/pwa/out/_next/static/chunks/framework-d0d2d673bfd8a8a9.js +0 -1
  758. package/apps/pwa/out/_next/static/chunks/main-4c9fceb2baa09cb7.js +0 -1
  759. package/apps/pwa/out/_next/static/chunks/main-app-b0ab8d8fc9a97556.js +0 -1
  760. package/apps/pwa/out/_next/static/chunks/pages/_app-7e2cc62a2e5cec96.js +0 -1
  761. package/apps/pwa/out/_next/static/chunks/pages/_error-22324935f753ec5e.js +0 -1
  762. package/apps/pwa/out/_next/static/chunks/webpack-9dc1bfa25334998a.js +0 -1
  763. package/apps/pwa/out/_next/static/css/be9019f696217521.css +0 -1
  764. /package/apps/pwa/out/_next/static/{X1ucLw10Cds_h614NoEnh → HMXsxdy5MIIcHPMHv1wD4}/_ssgManifest.js +0 -0
@@ -1,12 +1,14 @@
1
1
  // Research-only native fanout. The caller supplies Bloom's question ladder;
2
2
  // each axis gets its own direct tool call and evidence stays attributed to it.
3
3
  import type { BloomResearchQuestion, ResearchEvidenceEnvelope } from '../auto-research/question-ladder-contract.js';
4
- import { getAvailableWebSearchProviders } from '../web-search/index.js';
4
+ import { getAvailableResearchWebSearchProviders } from '../web-search/index.js';
5
5
  import type { WebSearchHit, WebSearchProvider } from '../web-search/provider.js';
6
6
  import { debug } from '../debug/log.js';
7
+ import { dispatchWebFetch } from '../skills/tools/webfetch.js';
7
8
 
8
- const RESEARCH_SEARCH_ENGINES = ['grok', 'grok-api', 'firecrawl'] as const;
9
- const RESEARCH_GROK_TIMEOUT_MS = 8_000;
9
+ const RESEARCH_SEARCH_ENGINES = ['exa', 'firecrawl'] as const;
10
+ const RESEARCH_WEB_FALLBACK_IDS = ['exa', 'firecrawl'] as const;
11
+ const RESEARCH_EXA_TIMEOUT_MS = 4_500;
10
12
  // Leave scheduler/logging headroom under the user-visible 15s aggregate cap.
11
13
  export const RESEARCH_SEARCH_BUDGET_MS = 14_500;
12
14
  const ENGINE_BREAKER_FAILURE_LIMIT = 2;
@@ -33,11 +35,17 @@ export interface AxisSearchResult {
33
35
  hits: AxisSearchHit[];
34
36
  errors: string[];
35
37
  }
36
- export type AxisSearch = (query: string, signal?: AbortSignal) => Promise<AxisSearchHit[] | AxisSearchResult>;
38
+ export interface AxisSearchContext {
39
+ questionPrompt?: string;
40
+ requestedWindow?: string;
41
+ }
42
+ export type AxisSearch = (query: string, signal?: AbortSignal, context?: AxisSearchContext) => Promise<AxisSearchHit[] | AxisSearchResult>;
37
43
 
38
44
  export interface AxisFanoutDeps {
39
45
  search?: AxisSearch;
46
+ fetchPage?: (url: string, question: BloomResearchQuestion, signal?: AbortSignal) => Promise<{ url: string; output: string }>;
40
47
  signal?: AbortSignal;
48
+ admitToolCall?: (toolName: 'OmniSearch' | 'WebFetch') => boolean;
41
49
  }
42
50
 
43
51
  interface ProviderHealth {
@@ -45,20 +53,16 @@ interface ProviderHealth {
45
53
  open: boolean;
46
54
  }
47
55
 
48
- /** Build one bounded searcher per research prepass. Free/DDG is deliberately
49
- * excluded: it is not a safe fallback for stock research and can consume a
50
- * full 15s timeout for every query. Per-engine serialization lets the first
51
- * timeout open that engine's breaker before queued Bloom axes start. */
56
+ /** Build one bounded searcher per research prepass. Research uses only the
57
+ * sequential Exa → Firecrawl fallback; Grok is reserved for explicit X intent.
58
+ * Per-engine serialization lets a timeout open that engine's
59
+ * breaker before queued Bloom axes start. */
52
60
  export function createResearchAxisSearcher(
53
- availableProviders: readonly WebSearchProvider[] = getAvailableWebSearchProviders(),
61
+ availableProviders: readonly WebSearchProvider[] = getAvailableResearchWebSearchProviders(),
54
62
  now: () => number = Date.now,
55
63
  ): AxisSearch {
56
- const grok = availableProviders.find(provider => provider.id === 'grok')
57
- ?? availableProviders.find(provider => provider.id === 'grok-api');
58
- const allowed = [
59
- ...(grok ? [grok] : []),
60
- ...availableProviders.filter(provider => provider.id === 'firecrawl'),
61
- ];
64
+ const webFallback = RESEARCH_WEB_FALLBACK_IDS.flatMap(id => availableProviders.filter(provider => provider.id === id));
65
+ const allowed = [...webFallback];
62
66
  const health = new Map(allowed.map(provider => [provider.id, { failures: 0, open: false }]));
63
67
  const deadline = now() + RESEARCH_SEARCH_BUDGET_MS;
64
68
  const tails = new Map<string, Promise<void>>();
@@ -81,23 +85,18 @@ export function createResearchAxisSearcher(
81
85
  return async (query, signal) => {
82
86
  const hits: AxisSearchHit[] = [];
83
87
  const errors: string[] = [];
84
- const selected = allowed.filter(provider => !health.get(provider.id)?.open);
85
- if (selected.length === 0) return { hits, errors: ['no healthy Grok/Firecrawl research provider'] };
86
-
87
- await Promise.all(selected.map(provider => enqueue(provider.id, async () => {
88
+ const execute = async (provider: WebSearchProvider): Promise<boolean> => enqueue(provider.id, async () => {
88
89
  const state = health.get(provider.id)!;
89
- if (state.open) return;
90
+ if (state.open) return false;
90
91
  const remainingMs = deadline - now();
91
92
  if (remainingMs <= 0) {
92
93
  state.open = true;
93
94
  errors.push(`${provider.id}: research search budget exhausted`);
94
- return;
95
+ return false;
95
96
  }
96
- const activeCount = Math.max(1, allowed.filter(candidate => !health.get(candidate.id)?.open).length);
97
- const isGrok = provider.id === 'grok' || provider.id === 'grok-api';
98
- const timeoutMs = isGrok
99
- ? Math.min(RESEARCH_GROK_TIMEOUT_MS, remainingMs)
100
- : Math.max(1, Math.floor(remainingMs / activeCount));
97
+ const timeoutMs = provider.id === 'exa'
98
+ ? Math.min(RESEARCH_EXA_TIMEOUT_MS, remainingMs)
99
+ : remainingMs;
101
100
  const startedAt = now();
102
101
  try {
103
102
  const controller = new AbortController();
@@ -131,6 +130,7 @@ export function createResearchAxisSearcher(
131
130
  provider: provider.id, queryLength: query.length, hits: result.hits.length,
132
131
  durationMs: now() - startedAt, breakerOpen: state.open,
133
132
  });
133
+ return result.hits.length > 0;
134
134
  } catch (error) {
135
135
  const message = error instanceof Error ? error.message : String(error);
136
136
  const timeout = error instanceof Error && /timeout|timed out|abort/i.test(`${error.name} ${error.message}`);
@@ -142,8 +142,16 @@ export function createResearchAxisSearcher(
142
142
  provider: provider.id, queryLength: query.length, durationMs: now() - startedAt,
143
143
  timeout, quota, failures: state.failures, breakerOpen: state.open,
144
144
  }, { level: 'warn' });
145
+ return false;
145
146
  }
146
- })));
147
+ });
148
+ const runWebFallback = async (): Promise<void> => {
149
+ for (const provider of webFallback) {
150
+ if (!health.get(provider.id)?.open && await execute(provider)) return;
151
+ }
152
+ };
153
+ await runWebFallback();
154
+ if (hits.length === 0 && errors.length === 0) errors.push('no healthy Exa/Firecrawl research provider');
147
155
  return { hits, errors };
148
156
  };
149
157
  }
@@ -195,7 +203,35 @@ export async function fanOutAxisEvidence(
195
203
  throw new Error('research axis question IDs must be unique');
196
204
  }
197
205
  const search = deps.search ?? createResearchAxisSearcher();
198
- const settled = await Promise.allSettled(plan.map(call => search(call.query, deps.signal)));
206
+ const fetchPage = deps.fetchPage ?? (!deps.search
207
+ ? async (url: string, question: BloomResearchQuestion, signal?: AbortSignal) =>
208
+ dispatchWebFetch({ url, prompt: question.prompt }, { signal })
209
+ : undefined);
210
+ const fetchedQuestions = new Set<string>();
211
+ const settled = await Promise.allSettled(plan.map(async call => {
212
+ if (deps.admitToolCall && !deps.admitToolCall('OmniSearch')) {
213
+ return { hits: [], errors: ['research tool budget reached'] } satisfies AxisSearchResult;
214
+ }
215
+ const question = questions.find(candidate => candidate.id === call.questionId)!;
216
+ const raw = await search(call.query, deps.signal, {
217
+ questionPrompt: question.prompt,
218
+ requestedWindow: question.requestedWindow,
219
+ });
220
+ const response = Array.isArray(raw) ? { hits: raw, errors: [] } : raw;
221
+ if (!fetchPage || response.hits.length === 0 || fetchedQuestions.has(question.id)) return response;
222
+ fetchedQuestions.add(question.id);
223
+ if (deps.admitToolCall && !deps.admitToolCall('WebFetch')) return response;
224
+ try {
225
+ const page = await fetchPage(response.hits[0]!.url, question, deps.signal);
226
+ return { ...response, fetchedPage: page };
227
+ } catch (error) {
228
+ const message = error instanceof Error ? error.message : String(error);
229
+ debug.log('research.search', 'native-fetch-failed', {
230
+ questionId: question.id, reason: message.slice(0, 200),
231
+ }, { level: 'warn' });
232
+ return response;
233
+ }
234
+ }));
199
235
  const axes: AxisEvidenceGroup[] = questions.map(question => ({ questionId: question.id, evidence: [] }));
200
236
  const groups = new Map(axes.map(axis => [axis.questionId, axis]));
201
237
  const byQuestion = new Map(questions.map(question => [question.id, question]));
@@ -211,10 +247,24 @@ export async function fanOutAxisEvidence(
211
247
  const group = groups.get(call.questionId)!;
212
248
  const question = byQuestion.get(call.questionId)!;
213
249
  if (outcome.status === 'fulfilled') {
214
- const response = Array.isArray(outcome.value) ? { hits: outcome.value, errors: [] } : outcome.value;
250
+ const response = outcome.value;
215
251
  if (response.hits.length === 0 && response.errors.length === 0) {
216
252
  group.evidence.push({ ...failedEvidence(question, call.query, 'no hits returned'), outcome: 'partial' });
217
253
  }
254
+ const fetchedPage = 'fetchedPage' in response ? response.fetchedPage : undefined;
255
+ if (fetchedPage) {
256
+ const content = fetchedPage.output;
257
+ const excerpt = Array.from(content).slice(0, 8_000).join('');
258
+ group.evidence.push({
259
+ questionId: question.id,
260
+ sourceKind: 'web-fetch',
261
+ source: fetchedPage.url,
262
+ ...(question.requestedWindow ? { requestedWindow: question.requestedWindow } : {}),
263
+ content: excerpt,
264
+ outcome: excerpt ? 'complete' : 'partial',
265
+ truncated: Array.from(content).length > 8_000,
266
+ });
267
+ }
218
268
  for (const hit of response.hits) {
219
269
  try {
220
270
  group.evidence.push(evidenceFromHit(question, hit));
@@ -0,0 +1,312 @@
1
+ /** Chain order a synthesis step lands in: what happens first, what that causes, what that settles. */
2
+ export type SecondOrderOrder = 'primary' | 'secondary' | 'tertiary';
3
+
4
+ export interface SecondOrderLensStage {
5
+ order: SecondOrderOrder;
6
+ label: string;
7
+ horizonDays: number;
8
+ purpose: string;
9
+ }
10
+
11
+ /** Public lens definition: what the T2 second-order lens is and which orders it fans a synthesis into. */
12
+ export interface SecondOrderLensDefinition {
13
+ id: string;
14
+ cell: string;
15
+ tier: string;
16
+ rfc: string;
17
+ description: string;
18
+ stages: readonly SecondOrderLensStage[];
19
+ }
20
+
21
+ /** Public verification format attached to every secondary effect. */
22
+ export interface SecondOrderVerificationNode {
23
+ claim: string;
24
+ scenarioCondition: string | null;
25
+ metric: string | null;
26
+ expectedValue: number | null;
27
+ threshold: number | null;
28
+ unit: string | null;
29
+ windowDays: number;
30
+ falsifiable: boolean | null;
31
+ measurementStatus: 'unmeasured' | 'needs-operationalization';
32
+ evidenceSource: string | null;
33
+ }
34
+
35
+ export interface SecondOrderEvidenceFact {
36
+ questionId: string;
37
+ question: string;
38
+ content: string;
39
+ source: string;
40
+ outcome: 'complete' | 'partial' | 'failed';
41
+ observedWindow?: string;
42
+ units?: string;
43
+ }
44
+
45
+ export interface SecondOrderChainNode {
46
+ id: string;
47
+ order: SecondOrderOrder;
48
+ orderIndex: 1 | 2 | 3;
49
+ statement: string;
50
+ horizonDays: number;
51
+ derivedFrom: readonly string[];
52
+ verification: SecondOrderVerificationNode | null;
53
+ }
54
+
55
+ /** Public result-chain format: primary → secondary → tertiary, with secondary effects verified. */
56
+ export interface SecondOrderResultChain {
57
+ lensId: string;
58
+ question: string;
59
+ orderStages: readonly SecondOrderLensStage[];
60
+ nodes: readonly SecondOrderChainNode[];
61
+ }
62
+
63
+ export type SecondOrderTriggerKind = 'decision' | 'forecast' | 'none';
64
+
65
+ export interface SecondOrderTriggerDecision {
66
+ triggered: boolean;
67
+ kind: SecondOrderTriggerKind;
68
+ score: number;
69
+ matchedSignals: readonly string[];
70
+ reason: string;
71
+ }
72
+
73
+ export interface SecondOrderLensInput {
74
+ question: string;
75
+ synthesis: readonly string[];
76
+ /** IDs must align with synthesis; evidence is joined by questionId, never by flat-array position. */
77
+ synthesisQuestionIds?: readonly string[];
78
+ evidenceFacts?: readonly SecondOrderEvidenceFact[];
79
+ }
80
+
81
+ export interface SecondOrderLensResult {
82
+ lens: SecondOrderLensDefinition;
83
+ trigger: SecondOrderTriggerDecision;
84
+ chain: SecondOrderResultChain | null;
85
+ }
86
+
87
+ /** Injection seam lets a host supply private trigger calibration without shipping it here. */
88
+ export type SecondOrderTriggerClassifier = (question: string) => SecondOrderTriggerDecision;
89
+
90
+ export const SECOND_ORDER_LENS: SecondOrderLensDefinition = {
91
+ id: 'second-order',
92
+ cell: 'THINK-LENS-T2-SECOND-ORDER',
93
+ tier: 'T2',
94
+ rfc: 'RFC-PRO §2',
95
+ description: '결정·예측 질문에서 6단 종합을 1차 → 2차 → 3차 결과 사슬로 펼치고, 2차 효과마다 검증 노드를 붙인다.',
96
+ stages: [
97
+ {
98
+ order: 'primary',
99
+ label: '1차 결과',
100
+ horizonDays: 30,
101
+ purpose: '결정이나 예측이 직접 만드는 즉시 효과',
102
+ },
103
+ {
104
+ order: 'secondary',
105
+ label: '2차 결과',
106
+ horizonDays: 180,
107
+ purpose: '1차 효과가 다른 주체로 전이되며 생기는 효과 — 검증 노드가 붙는 자리',
108
+ },
109
+ {
110
+ order: 'tertiary',
111
+ label: '3차 결과',
112
+ horizonDays: 540,
113
+ purpose: '2차 효과가 구조·규범·시장에 정착하며 생기는 효과',
114
+ },
115
+ ],
116
+ };
117
+
118
+ const DECISION_QUESTION_FORM = /(?:해야\s*(?:할까|하나|할지)|(?:고르|선택|결정|전환|도입|투자|진입|매수|매도)(?:해야\s*(?:할까|하나|할지)|할까|할지\s*(?:말지|여부)))|\b(?:should\s+(?:i|we)|whether\s+to|choose\s+between|decide\s+whether)\b/i;
119
+ const FORECAST_QUESTION_FORM = /(?:얼마나\s+[^?\n]{0,80}(?:될|오를|내릴|늘어날|줄어들|바뀔|변할)|(?:언제|몇)\s+[^?\n]{0,80}(?:될|오를|내릴|늘어날|줄어들|바뀔)|어떻게\s+(?:될까|변할까))|\b(?:how\s+much|how\s+many)\s+(?:will|might|could|is\s+expected\s+to|is\s+projected\s+to)\b.{0,120}\b(?:rise|fall|grow|shrink|change|cost|be)\b|\b(?:when\s+will|what\s+will)\b.{0,120}\b(?:rise|fall|grow|shrink|change|cost|be)\b|\bwill\s+[^?\n]{1,120}\b(?:increase|decrease|rise|fall|grow|shrink|change|cost|remain|reach|exceed|decline)\b/i;
120
+
121
+ /** Decide whether a question is a decision or a forecast, i.e. whether the second-order lens applies. */
122
+ export function detectSecondOrderTrigger(question: string): SecondOrderTriggerDecision {
123
+ const text = requireText(question, 'question').toLowerCase();
124
+ if (!/[??]\s*$/u.test(text)) return noTrigger();
125
+ const decision = DECISION_QUESTION_FORM.exec(text);
126
+ const forecast = FORECAST_QUESTION_FORM.exec(text);
127
+ const kind: SecondOrderTriggerKind = decision ? 'decision' : forecast ? 'forecast' : 'none';
128
+ const score = kind === 'none' ? 0 : 1;
129
+ const matchedSignals = Object.freeze(kind === 'decision' ? ['decision-form'] : kind === 'forecast' ? ['forecast-form'] : []);
130
+ if (kind === 'none') {
131
+ return {
132
+ triggered: false,
133
+ kind: 'none',
134
+ score,
135
+ matchedSignals,
136
+ reason: '질문이 결정이나 예측이 아니라 결과 사슬을 펼치지 않는다',
137
+ };
138
+ }
139
+ return {
140
+ triggered: true,
141
+ kind,
142
+ score,
143
+ matchedSignals,
144
+ reason: kind === 'decision'
145
+ ? '결정 질문이므로 1차 → 2차 → 3차 결과 사슬을 펼친다'
146
+ : '예측 질문이므로 1차 → 2차 → 3차 결과 사슬을 펼친다',
147
+ };
148
+ }
149
+
150
+ function noTrigger(): SecondOrderTriggerDecision {
151
+ return {
152
+ triggered: false,
153
+ kind: 'none',
154
+ score: 0,
155
+ matchedSignals: Object.freeze([]),
156
+ reason: '결정·예측 질문형이 아니므로 결과 사슬을 펼치지 않는다',
157
+ };
158
+ }
159
+
160
+ /** Expand synthesis steps into a primary → secondary → tertiary chain with a verification node on each secondary effect. */
161
+ export function buildSecondOrderResultChain(input: SecondOrderLensInput): SecondOrderResultChain {
162
+ const question = requireText(input.question, 'question');
163
+ const steps = input.synthesis.map((step, index) => requireText(step, `synthesis[${index}]`));
164
+ if (input.evidenceFacts?.length && input.synthesisQuestionIds?.length !== steps.length) {
165
+ throw new Error('synthesisQuestionIds must align with synthesis when evidenceFacts are supplied');
166
+ }
167
+ if (steps.length < SECOND_ORDER_LENS.stages.length) {
168
+ throw new Error('synthesis requires at least three steps to expand into a result chain');
169
+ }
170
+
171
+ const buckets = splitIntoOrders(steps, SECOND_ORDER_LENS.stages.length);
172
+ const nodes: SecondOrderChainNode[] = [];
173
+ let previousIds: string[] = [];
174
+ for (const [stageIndex, stage] of SECOND_ORDER_LENS.stages.entries()) {
175
+ const stageIds: string[] = [];
176
+ for (const [stepIndex, statement] of buckets[stageIndex]!.entries()) {
177
+ const inputIndex = buckets.slice(0, stageIndex).reduce((count, bucket) => count + bucket.length, 0) + stepIndex;
178
+ const questionId = input.synthesisQuestionIds?.[inputIndex];
179
+ const fact = questionId ? combineQuestionEvidence(questionId, input.evidenceFacts ?? []) : undefined;
180
+ const id = `${stage.order}-${stepIndex + 1}`;
181
+ stageIds.push(id);
182
+ const parentIndex = stageIndex === 0 ? -1 : Math.min(stepIndex, previousIds.length - 1);
183
+ const parentId = parentIndex >= 0 ? previousIds[parentIndex] : undefined;
184
+ const parent = parentId ? nodes.find((node) => node.id === parentId) : undefined;
185
+ const outputStatement = fact
186
+ ? makeOutcomeHypothesis(stage.order, question, fact, parent?.statement)
187
+ : stage.order === 'primary'
188
+ ? `1차 가설: ${statement}`
189
+ : `${stage.order === 'secondary' ? '2차' : '3차'} 가설: ${parent?.statement ?? '앞 단계 결과'}가 이어지면 ${statement}라는 후속 결과가 생길 수 있다.`;
190
+ nodes.push({
191
+ id,
192
+ order: stage.order,
193
+ orderIndex: (stageIndex + 1) as 1 | 2 | 3,
194
+ statement: outputStatement,
195
+ horizonDays: stage.horizonDays,
196
+ derivedFrom: Object.freeze(parentId ? [parentId] : []),
197
+ verification: stage.order === 'secondary'
198
+ ? buildVerificationNode(outputStatement, fact, stepIndex)
199
+ : null,
200
+ });
201
+ }
202
+ previousIds = stageIds;
203
+ }
204
+
205
+ return {
206
+ lensId: SECOND_ORDER_LENS.id,
207
+ question,
208
+ orderStages: SECOND_ORDER_LENS.stages,
209
+ nodes: Object.freeze(nodes),
210
+ };
211
+ }
212
+
213
+ /** Run the lens: the trigger decides whether a chain is produced at all. */
214
+ export function applySecondOrderLens(
215
+ input: SecondOrderLensInput,
216
+ classifyTrigger: SecondOrderTriggerClassifier = detectSecondOrderTrigger,
217
+ ): SecondOrderLensResult {
218
+ const trigger = classifyTrigger(input.question);
219
+ if (!trigger.triggered) return { lens: SECOND_ORDER_LENS, trigger, chain: null };
220
+ return { lens: SECOND_ORDER_LENS, trigger, chain: buildSecondOrderResultChain(input) };
221
+ }
222
+
223
+ function buildVerificationNode(statement: string, fact: SecondOrderEvidenceFact | undefined, index: number): SecondOrderVerificationNode {
224
+ const metric = fact?.outcome === 'complete' ? extractObservableMetric(fact.content) : null;
225
+ const windowDays = 90 * (index + 1);
226
+ const scenarioCondition = metric && fact
227
+ ? `${fact.observedWindow ? `${fact.observedWindow} 기준선` : '확인 가능한 기준선'}과 ${windowDays}일 뒤 ${metric}을 비교한다. 판정 임계값은 아직 정하지 않았다.`
228
+ : null;
229
+ return {
230
+ claim: statement,
231
+ scenarioCondition,
232
+ metric,
233
+ expectedValue: null,
234
+ threshold: null,
235
+ unit: fact?.units ?? null,
236
+ windowDays,
237
+ falsifiable: null,
238
+ measurementStatus: metric ? 'needs-operationalization' : 'unmeasured',
239
+ evidenceSource: fact?.source ?? null,
240
+ };
241
+ }
242
+
243
+ function splitIntoOrders(steps: readonly string[], orderCount: number): string[][] {
244
+ const base = Math.floor(steps.length / orderCount);
245
+ const remainder = steps.length % orderCount;
246
+ const buckets: string[][] = [];
247
+ let cursor = 0;
248
+ for (let index = 0; index < orderCount; index += 1) {
249
+ const size = base + (index < remainder ? 1 : 0);
250
+ buckets.push(steps.slice(cursor, cursor + size));
251
+ cursor += size;
252
+ }
253
+ return buckets;
254
+ }
255
+
256
+ function makeOutcomeHypothesis(
257
+ order: SecondOrderOrder,
258
+ question: string,
259
+ fact: SecondOrderEvidenceFact,
260
+ parentStatement?: string,
261
+ ): string {
262
+ const detail = compactEvidence(fact.content);
263
+ const citation = `[${fact.questionId}; ${fact.source}; ${fact.outcome}]`;
264
+ if (fact.outcome !== 'complete') {
265
+ return `${order === 'primary' ? '1차' : order === 'secondary' ? '2차' : '3차'} 가설 미작성: ${fact.question}에 대한 완전한 근거를 확보하지 못했다 (${fact.outcome}; ${citation}).`;
266
+ }
267
+ if (order === 'primary') return `1차 가설: 「${question}」의 직접 효과 후보는 「${detail}」이다. 근거 ${citation}`;
268
+ if (order === 'secondary') return `2차 가설: 「${parentStatement ?? '직접 결과'}」가 이어질 경우 「${detail}」라는 후속 효과가 생길 수 있다. 근거 ${citation}`;
269
+ return `3차 가설: 「${parentStatement ?? '2차 효과'}」가 지속될 경우 「${detail}」라는 장기 결과로 이어질 수 있다. 근거 ${citation}`;
270
+ }
271
+
272
+ function compactEvidence(value: string): string {
273
+ const normalized = value.replace(/\s+/g, ' ').trim();
274
+ return normalized.length > 180 ? `${normalized.slice(0, 177)}…` : normalized;
275
+ }
276
+
277
+ function combineQuestionEvidence(questionId: string, evidenceFacts: readonly SecondOrderEvidenceFact[]): SecondOrderEvidenceFact | undefined {
278
+ const matching = evidenceFacts.filter((fact) => fact.questionId === questionId);
279
+ if (!matching.length) return undefined;
280
+ const complete = matching.filter((fact) => fact.outcome === 'complete');
281
+ const selected = complete.length ? complete : matching;
282
+ const units = [...new Set(selected.map((fact) => fact.units).filter((unit): unit is string => Boolean(unit)))].join(', ');
283
+ const observedWindow = [...new Set(selected.map((fact) => fact.observedWindow).filter((window): window is string => Boolean(window)))].join(', ');
284
+ return {
285
+ questionId,
286
+ question: selected[0]!.question,
287
+ content: selected.map((fact) => fact.content).join(' · '),
288
+ source: [...new Set(selected.map((fact) => fact.source))].join(', '),
289
+ outcome: complete.length ? 'complete' : selected.some((fact) => fact.outcome === 'partial') ? 'partial' : 'failed',
290
+ ...(observedWindow ? { observedWindow } : {}),
291
+ ...(units ? { units } : {}),
292
+ };
293
+ }
294
+
295
+ function extractObservableMetric(value: string): string | null {
296
+ const patterns = [
297
+ /(?:응답\s*시간|처리\s*시간|처리량|대기\s*시간|전환율|이탈률|잔존율|오류율|정확도|매출|수익|비용|수출액|수출량|문의\s*건수|사용자\s*수|판매량|생산성|파이프라인)/iu,
298
+ /\b(?:response time|processing time|wait time|conversion rate|churn rate|retention rate|error rate|accuracy|revenue|cost|export volume|inquiry count|user count|sales volume|productivity|pipeline|adoption rate|demand)\b/iu,
299
+ ];
300
+ for (const pattern of patterns) {
301
+ const match = value.match(pattern);
302
+ if (match?.[0]) return match[0].replace(/\s+/g, ' ').trim();
303
+ }
304
+ return null;
305
+ }
306
+
307
+ function requireText(value: unknown, field: string): string {
308
+ if (typeof value !== 'string' || value.trim().length === 0) {
309
+ throw new Error(`${field} must not be empty`);
310
+ }
311
+ return value.trim();
312
+ }
@@ -29,8 +29,10 @@ import {
29
29
  renderConcurrentAuthoringNotice,
30
30
  renderLaunchPreflight,
31
31
  renderRepeatedBlockNotice,
32
+ renderSiblingContextLines,
32
33
  siblingTestPath,
33
34
  type AskPreflightDeps,
35
+ type SiblingContextCard,
34
36
  type LaunchPreflightResult,
35
37
  type PriorBlockSample,
36
38
  type RecentAuthoringSample,
@@ -245,6 +247,8 @@ export interface AskLaunchFlowInput {
245
247
  readonly goalType?: import('../self-implement/goal-author.js').GoalType;
246
248
  /** 런 식별자가 이미 있으면 앞단 관측을 그 키로 잇는다. 없으면 관측은 runId 없이 남는다. */
247
249
  readonly runId?: string;
250
+ /** CARD-TARGET-PATHS가 제공한 같은-경로 카드 관측. 발사 판정에는 쓰지 않는다. */
251
+ readonly cardsTouchingPaths?: readonly SiblingContextCard[];
248
252
  /** Explicit harness choice; false is distinct from omission. */
249
253
  readonly selfResolveClarifications?: boolean;
250
254
  }
@@ -258,6 +262,18 @@ export type AskLaunchFlowResult =
258
262
  /** ⑴ 저작에서 접지 예산(AUTHOR-TIMEBOX)을 넘겨 NOT-GROUNDED 로 끝났다 — 발사하지 «않는다». */
259
263
  | { readonly kind: 'stopped-by-timebox'; readonly goalFile: string };
260
264
 
265
+ /**
266
+ * A harness entry can be named inside a request whose operative instruction is
267
+ * explicitly read-only. Require both a read-only marker and a no-write marker;
268
+ * either alone is too broad (for example, implementing a read-only feature).
269
+ */
270
+ function isExplicitReadOnlyNoWriteRequest(text: string): boolean {
271
+ const normalized = text.normalize('NFKC').toLowerCase();
272
+ const readOnly = /(?:read[\s-]*only|readonly|읽기\s*전용|읽기만|파일\s*존재\s*여부만|상태만\s*확인)/u.test(normalized);
273
+ const noWrite = /(?:수정하지\s*마|변경하지\s*마|변경\s*금지|파일을?\s*만들지\s*마|쓰지\s*마|편집하지\s*마|no\s+(?:file\s+)?changes?|do\s+not\s+(?:edit|modify|write|create)|don't\s+(?:edit|modify|write|create)|without\s+(?:editing|modifying|writing)|\bcommit\b.{0,24}(?:하지\s*마|금지)|\bpush\b.{0,24}(?:하지\s*마|금지)|\bpr\b.{0,24}(?:하지\s*마|금지))/u.test(normalized);
274
+ return readOnly && noWrite;
275
+ }
276
+
261
277
  /** ⑴ AUTHOR-TIMEBOX NOT-GROUNDED — 결과 줄을 쓰고 흐름을 끊는 값. */
262
278
  export type AskLaunchFlowTimeboxStop = Extract<AskLaunchFlowResult, { kind: 'stopped-by-timebox' }>;
263
279
 
@@ -858,9 +874,23 @@ export async function runAskLaunchFlow(
858
874
  // ⛔ 이 목록은 «광고»다 — 실제 단계와 어긋나면 조회하는 사람이 없는 단계를 찾거나 있는 단계를 안 찾는다.
859
875
  // ⛔ 분해 단계는 «두 이름 중 하나»로 난다 — 켜졌으면 `…-decomposition`, 꺼졌으면 `…-decomposition-skipped`.
860
876
  // ⭐ 뒤엣것을 빼 두면 조회하는 사람이 「분해 관측이 0건이다」를 보고 «없어졌다»로 읽는다(실은 꺼진 것이다).
861
- steps: ['ask-start', 'ask-pre-preflight', 'ask-authored', 'ask-launching-tree', 'ask-preflight', 'ask-launch-decomposition', 'ask-launch-decomposition-skipped', 'ask-launch'],
877
+ steps: ['ask-start', 'ask-readonly-no-launch', 'ask-pre-preflight', 'ask-authored', 'ask-launching-tree', 'ask-preflight', 'ask-launch-decomposition', 'ask-launch-decomposition-skipped', 'ask-launch'],
862
878
  }, 'info');
863
879
 
880
+ if (isExplicitReadOnlyNoWriteRequest(input.askText)) {
881
+ deps.log('ask-readonly-no-launch', {
882
+ entrance: entrance.id,
883
+ surface: entrance.surface,
884
+ inputSource: input.inputSource,
885
+ runId: input.runId ?? process.env.ELANOUS_RUN_ID ?? null,
886
+ authoringSkipped: true,
887
+ launchSkipped: true,
888
+ completionModeSelected: false,
889
+ }, 'info');
890
+ deps.print('[ask] 읽기 전용·변경 금지 요청으로 판정해 구현·자동 병합을 시작하지 않았습니다. TUI 읽기 도구로 결과만 확인하세요.');
891
+ return { kind: 'stopped-before-authoring' };
892
+ }
893
+
864
894
  const launchPreflight = await runPrePreflight(input, deps);
865
895
  if (launchPreflight === false) return { kind: 'stopped-before-authoring' };
866
896
 
@@ -1036,6 +1066,47 @@ export async function runAskLaunchFlow(
1036
1066
  const preflight = decision.result;
1037
1067
  deps.print(renderLaunchPreflight(preflight, input.forceRequested && decision.shouldLaunch && preflight.blockers.length > 0, 'before-launch'));
1038
1068
  observeLaunchPreflight(deps, 'before-launch', decision);
1069
+ let siblingCards = input.cardsTouchingPaths;
1070
+ let siblingCardsUnmeasured = false;
1071
+ if (siblingCards === undefined && preflight.paths.length > 0) {
1072
+ try {
1073
+ // CARD-TARGET-PATHS is a read-only signal: production entrances use the shared task-card store when
1074
+ // no caller supplied a precomputed snapshot. The launch decision never depends on these matches.
1075
+ const taskHand = await import('../task-agent/task-hand.js');
1076
+ const state = taskHand.readTaskAgentState<{ tasks?: Record<string, import('../task-agent/task-hand.js').TaskCard> }>(taskHand.taskAgentStatePath());
1077
+ siblingCards = taskHand.cardsTouchingPaths(Object.values(state.tasks ?? {}), preflight.paths)
1078
+ .map(({ card, runId, paths }) => ({ cardId: card.id, ...(runId ? { runId } : {}), overlapPaths: paths }));
1079
+ } catch (error) {
1080
+ siblingCardsUnmeasured = true;
1081
+ try { debug.log('self-dev.ask', 'sibling-context-cards-unmeasured', { reason: error instanceof Error ? error.message : String(error) }); }
1082
+ catch { /* supplemental card context remains fail-soft */ }
1083
+ siblingCards = [];
1084
+ }
1085
+ }
1086
+ const siblingContextLines = renderSiblingContextLines(preflight, siblingCards);
1087
+ const recentLanded = preflight.warnings.filter((warning) => warning.kind === 'recent-change' && preflight.paths.includes(warning.name)).length;
1088
+ const siblingContextObservation = {
1089
+ liveRuns: preflight.warnings.filter((warning) => warning.kind === 'live-run').length,
1090
+ openPrs: preflight.warnings.filter((warning) => warning.kind === 'open-pr' || warning.kind === 'sibling-pr').length,
1091
+ recentLanded,
1092
+ unmeasured: siblingCardsUnmeasured || preflight.liveRuns.state === 'unknown' || preflight.openPrs.state === 'unknown' || preflight.recentChanges.state === 'unknown' || preflight.unreadableRuns > 0,
1093
+ };
1094
+ try { debug.log('self-dev.ask', 'sibling-context', siblingContextObservation); }
1095
+ catch { /* sibling context observation must not change launch */ }
1096
+ if (!sanitizeFailed && existsSync(goalFile)) {
1097
+ try {
1098
+ const document = deps.readFile(goalFile);
1099
+ const firstSection = document.search(/^## /mu);
1100
+ const header = siblingContextLines.join('\n');
1101
+ const beforeFirstSection = firstSection < 0 ? document : document.slice(0, firstSection).trimEnd();
1102
+ const contextualized = firstSection < 0
1103
+ ? `${header}\n\n${document}`
1104
+ : `${beforeFirstSection ? `${beforeFirstSection}\n` : ''}${header}\n형제가 같은 파일을 고친다 — 국소 변경만 · 무관 포맷 금지 · 자기 의도를 시험으로 고정\n\n${document.slice(firstSection)}`;
1105
+ (deps.writeGoalDocument ?? deps.writeFile)(goalFile, contextualized);
1106
+ } catch (error) {
1107
+ deps.print(`[ask] 형제 맥락 기록 못 남김 (${error instanceof Error ? error.message : String(error)})`);
1108
+ }
1109
+ }
1039
1110
  // ⛔ 자식 격리 worktree를 만들기 전, 이 흐름을 호출한 작업 트리에서만 센다.
1040
1111
  // 이 관측은 발사 판정의 입력이 아니다 — 의도적으로 옛 판에서 쏘는 경우도 있다.
1041
1112
  const invokerBehindDefaultBranch = deps.measureInvokerBehindDefaultBranch?.()
@@ -67,6 +67,7 @@ import { BEDROCK_DEFAULT_MODEL, BEDROCK_MODELS, findBedrockModel, resolveBedrock
67
67
  import { ZAI_CODING_DEFAULT_MODEL, ZAI_CODING_MODELS } from '../llm/zai-coding-plan.js';
68
68
  import { isVerifiedOpenGatewayModel, OPENGATEWAY_DEFAULT_MODEL, OPENGATEWAY_VERIFIED_MODELS } from '../llm/opengateway-models.js';
69
69
  import { DEV_PLAN_REPLACEMENT } from './cli-help-text.js';
70
+ import { DEFAULT_TUI_TEST_READY_TIMEOUT_MS } from '../self-implement/elanous-tui-spawn.js';
70
71
  export { DEV_PLAN_REPLACEMENT, formatDevPlanOptionHelp } from './cli-help-text.js';
71
72
 
72
73
  /** dev CLI 옵션(commander) — `--no-*` 는 false 로 도착. input/executor 는 액션이 빌드해 별도 전달. */
@@ -929,7 +930,9 @@ export function startDraftTriage(
929
930
  const inventory = inventories.find((entry) => entry.repository === repository)?.snapshot;
930
931
  const enriched = { ...draft, branch: draft.branch ?? '', ...inventoryByUrl.get(draft.url!) };
931
932
  if ((!inventory || !inventoryByUrl.has(draft.url!)) && !IN_TEST_PROCESS()) { unobservedDrafts.push(draft.number); continue; }
932
- const decision = decideDraft({ draft: enriched, runStatus: resolvedStatus, mergedTwins: inventory?.merged ?? [], ageHours: (nowMs() - draft.openedAtMs) / 3_600_000, liveBranches });
933
+ const triageNow = nowMs();
934
+ const decision = decideDraft({ draft: enriched, now: new Date(triageNow), runStatus: resolvedStatus,
935
+ mergedTwins: inventory?.merged ?? [], ageHours: (triageNow - draft.openedAtMs) / 3_600_000, liveBranches });
933
936
  if (decision.reason.startsWith('superseded-by')) decisions.superseded += 1;
934
937
  else if (decision.reason === 'stale-ended-run') decisions.staleEndedRun += 1;
935
938
  else if (decision.reason.startsWith('label:')) decisions.humanApproval += 1; // approval-waiting or human «keep»
@@ -2187,7 +2190,9 @@ export function buildDevCliSpec(
2187
2190
  ...spec,
2188
2191
  elanous: {
2189
2192
  ...(opts.hold ? { hold: true } : {}),
2190
- ...(opts.readyTimeoutMs !== undefined ? { readyTimeoutMs: parsePositiveInt(opts.readyTimeoutMs, '--ready-timeout-ms') } : {}),
2193
+ ...(opts.readyTimeoutMs !== undefined
2194
+ ? { readyTimeoutMs: parsePositiveInt(opts.readyTimeoutMs, '--ready-timeout-ms') }
2195
+ : opts.hold ? { readyTimeoutMs: DEFAULT_TUI_TEST_READY_TIMEOUT_MS } : {}),
2191
2196
  ...(opts.json ? { json: true } : {}),
2192
2197
  ...(opts.goal !== undefined ? { goal: opts.goal } : {}),
2193
2198
  ...(opts.maxSteps !== undefined ? { maxSteps: parsePositiveInt(opts.maxSteps, '--max-steps') } : {}),
@@ -68,6 +68,8 @@ export interface DevMissionOpts {
68
68
  resources?: 'on' | 'off';
69
69
  backendExplicit?: string;
70
70
  headless?: boolean;
71
+ /** Optional second user turn resumed in the same Claude/Codex CLI session. */
72
+ followUp?: string;
71
73
  evidence?: EvidenceMode;
72
74
  maxRounds?: number;
73
75
  commit?: boolean;
@@ -643,6 +645,7 @@ export function toAgentMissionSpec(
643
645
  evidence: m.evidence ?? { kind: 'tsc' }, // 기본 tsc(mission 옵션 미지정 시)
644
646
  agent: resolveBackend(plan.executor.backend),
645
647
  ...(m.headless === true ? { headless: true } : {}),
648
+ ...(m.followUp !== undefined ? { followUp: m.followUp } : {}),
646
649
  ...(m.chain ? { chain: m.chain } : {}),
647
650
  ...(m.plugin ? { plugin: m.plugin } : {}),
648
651
  ...(m.resources !== undefined ? { resources: m.resources } : {}),
@@ -670,6 +673,7 @@ export function buildAgentMissionDevSpec(o: {
670
673
  branch: string;
671
674
  base?: string;
672
675
  headless?: boolean;
676
+ followUp?: string;
673
677
  chain?: readonly ('codex' | 'claude' | 'elanous')[];
674
678
  plugin?: { plugin: string; marketplace: string };
675
679
  resources?: 'on' | 'off';
@@ -691,6 +695,7 @@ export function buildAgentMissionDevSpec(o: {
691
695
  mission: {
692
696
  evidence: o.evidence,
693
697
  ...(o.headless === true ? { headless: true } : {}),
698
+ ...(o.followUp !== undefined ? { followUp: o.followUp } : {}),
694
699
  ...(o.chain ? { chain: o.chain } : {}),
695
700
  ...(o.plugin ? { plugin: o.plugin } : {}),
696
701
  ...(o.resources !== undefined ? { resources: o.resources } : {}),