@made-by-moonlight/athene-web 0.9.2 → 0.10.0

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 (319) hide show
  1. package/.next/BUILD_ID +1 -1
  2. package/.next/app-build-manifest.json +241 -219
  3. package/.next/app-path-routes-manifest.json +10 -7
  4. package/.next/build-manifest.json +6 -6
  5. package/.next/prerender-manifest.json +23 -23
  6. package/.next/react-loadable-manifest.json +5 -5
  7. package/.next/required-server-files.json +4 -4
  8. package/.next/routes-manifest.json +16 -0
  9. package/.next/server/app/_not-found/page.js +2 -2
  10. package/.next/server/app/_not-found/page.js.nft.json +1 -1
  11. package/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  12. package/.next/server/app/_not-found.html +1 -1
  13. package/.next/server/app/_not-found.rsc +9 -9
  14. package/.next/server/app/api/backlog/route.js +1 -1
  15. package/.next/server/app/api/backlog/route.js.nft.json +1 -1
  16. package/.next/server/app/api/backlog/route_client-reference-manifest.js +1 -1
  17. package/.next/server/app/api/browse-directory/route.js +1 -1
  18. package/.next/server/app/api/browse-directory/route_client-reference-manifest.js +1 -1
  19. package/.next/server/app/api/filesystem/browse/route.js +1 -1
  20. package/.next/server/app/api/filesystem/browse/route.js.nft.json +1 -1
  21. package/.next/server/app/api/filesystem/browse/route_client-reference-manifest.js +1 -1
  22. package/.next/server/app/api/issues/route.js +1 -1
  23. package/.next/server/app/api/issues/route.js.nft.json +1 -1
  24. package/.next/server/app/api/issues/route_client-reference-manifest.js +1 -1
  25. package/.next/server/app/api/meta/[name]/start/route.js +1 -0
  26. package/.next/server/app/api/meta/[name]/start/route.js.nft.json +1 -0
  27. package/.next/server/app/api/meta/[name]/start/route_client-reference-manifest.js +1 -0
  28. package/.next/server/app/api/meta/route.js +1 -0
  29. package/.next/server/app/api/meta/route.js.nft.json +1 -0
  30. package/.next/server/app/api/meta/route_client-reference-manifest.js +1 -0
  31. package/.next/server/app/api/observability/route.js +1 -1
  32. package/.next/server/app/api/observability/route.js.nft.json +1 -1
  33. package/.next/server/app/api/observability/route_client-reference-manifest.js +1 -1
  34. package/.next/server/app/api/orchestrators/route.js +1 -1
  35. package/.next/server/app/api/orchestrators/route.js.nft.json +1 -1
  36. package/.next/server/app/api/orchestrators/route_client-reference-manifest.js +1 -1
  37. package/.next/server/app/api/projects/[id]/route.js +2 -2
  38. package/.next/server/app/api/projects/[id]/route.js.nft.json +1 -1
  39. package/.next/server/app/api/projects/[id]/route_client-reference-manifest.js +1 -1
  40. package/.next/server/app/api/projects/reload/route.js +1 -1
  41. package/.next/server/app/api/projects/reload/route.js.nft.json +1 -1
  42. package/.next/server/app/api/projects/reload/route_client-reference-manifest.js +1 -1
  43. package/.next/server/app/api/projects/route.js +1 -1
  44. package/.next/server/app/api/projects/route.js.nft.json +1 -1
  45. package/.next/server/app/api/projects/route_client-reference-manifest.js +1 -1
  46. package/.next/server/app/api/prs/[id]/merge/route.js +1 -1
  47. package/.next/server/app/api/prs/[id]/merge/route.js.nft.json +1 -1
  48. package/.next/server/app/api/prs/[id]/merge/route_client-reference-manifest.js +1 -1
  49. package/.next/server/app/api/reviews/execute/route.js +1 -1
  50. package/.next/server/app/api/reviews/execute/route.js.nft.json +1 -1
  51. package/.next/server/app/api/reviews/execute/route_client-reference-manifest.js +1 -1
  52. package/.next/server/app/api/reviews/findings/route.js +1 -1
  53. package/.next/server/app/api/reviews/findings/route.js.nft.json +1 -1
  54. package/.next/server/app/api/reviews/findings/route_client-reference-manifest.js +1 -1
  55. package/.next/server/app/api/reviews/route.js +1 -1
  56. package/.next/server/app/api/reviews/route.js.nft.json +1 -1
  57. package/.next/server/app/api/reviews/route_client-reference-manifest.js +1 -1
  58. package/.next/server/app/api/reviews/send/route.js +1 -1
  59. package/.next/server/app/api/reviews/send/route.js.nft.json +1 -1
  60. package/.next/server/app/api/reviews/send/route_client-reference-manifest.js +1 -1
  61. package/.next/server/app/api/runtime/terminal/route.js +1 -1
  62. package/.next/server/app/api/runtime/terminal/route_client-reference-manifest.js +1 -1
  63. package/.next/server/app/api/sessions/[id]/kill/route.js +1 -1
  64. package/.next/server/app/api/sessions/[id]/kill/route.js.nft.json +1 -1
  65. package/.next/server/app/api/sessions/[id]/kill/route_client-reference-manifest.js +1 -1
  66. package/.next/server/app/api/sessions/[id]/message/route.js +1 -1
  67. package/.next/server/app/api/sessions/[id]/message/route.js.nft.json +1 -1
  68. package/.next/server/app/api/sessions/[id]/message/route_client-reference-manifest.js +1 -1
  69. package/.next/server/app/api/sessions/[id]/remap/route.js +1 -1
  70. package/.next/server/app/api/sessions/[id]/remap/route.js.nft.json +1 -1
  71. package/.next/server/app/api/sessions/[id]/remap/route_client-reference-manifest.js +1 -1
  72. package/.next/server/app/api/sessions/[id]/restore/route.js +1 -1
  73. package/.next/server/app/api/sessions/[id]/restore/route.js.nft.json +1 -1
  74. package/.next/server/app/api/sessions/[id]/restore/route_client-reference-manifest.js +1 -1
  75. package/.next/server/app/api/sessions/[id]/route.js +1 -1
  76. package/.next/server/app/api/sessions/[id]/route.js.nft.json +1 -1
  77. package/.next/server/app/api/sessions/[id]/route_client-reference-manifest.js +1 -1
  78. package/.next/server/app/api/sessions/[id]/send/route.js +1 -1
  79. package/.next/server/app/api/sessions/[id]/send/route.js.nft.json +1 -1
  80. package/.next/server/app/api/sessions/[id]/send/route_client-reference-manifest.js +1 -1
  81. package/.next/server/app/api/sessions/patches/route.js +1 -1
  82. package/.next/server/app/api/sessions/patches/route.js.nft.json +1 -1
  83. package/.next/server/app/api/sessions/patches/route_client-reference-manifest.js +1 -1
  84. package/.next/server/app/api/sessions/route.js +1 -1
  85. package/.next/server/app/api/sessions/route.js.nft.json +1 -1
  86. package/.next/server/app/api/sessions/route_client-reference-manifest.js +1 -1
  87. package/.next/server/app/api/setup-labels/route.js +1 -1
  88. package/.next/server/app/api/setup-labels/route.js.nft.json +1 -1
  89. package/.next/server/app/api/setup-labels/route_client-reference-manifest.js +1 -1
  90. package/.next/server/app/api/spawn/route.js +1 -1
  91. package/.next/server/app/api/spawn/route.js.nft.json +1 -1
  92. package/.next/server/app/api/spawn/route_client-reference-manifest.js +1 -1
  93. package/.next/server/app/api/update/route.js +1 -1
  94. package/.next/server/app/api/update/route.js.nft.json +1 -1
  95. package/.next/server/app/api/update/route_client-reference-manifest.js +1 -1
  96. package/.next/server/app/api/verify/route.js +1 -1
  97. package/.next/server/app/api/verify/route.js.nft.json +1 -1
  98. package/.next/server/app/api/verify/route_client-reference-manifest.js +1 -1
  99. package/.next/server/app/api/version/route.js +1 -1
  100. package/.next/server/app/api/version/route.js.nft.json +1 -1
  101. package/.next/server/app/api/version/route_client-reference-manifest.js +1 -1
  102. package/.next/server/app/api/webhooks/[...slug]/route.js +1 -1
  103. package/.next/server/app/api/webhooks/[...slug]/route.js.nft.json +1 -1
  104. package/.next/server/app/api/webhooks/[...slug]/route_client-reference-manifest.js +1 -1
  105. package/.next/server/app/apple-icon/route.js +1 -1
  106. package/.next/server/app/apple-icon/route.js.nft.json +1 -1
  107. package/.next/server/app/apple-icon/route_client-reference-manifest.js +1 -1
  108. package/.next/server/app/apple-icon.body +0 -0
  109. package/.next/server/app/dev/terminal-test/page.js +2 -2
  110. package/.next/server/app/dev/terminal-test/page.js.nft.json +1 -1
  111. package/.next/server/app/dev/terminal-test/page_client-reference-manifest.js +1 -1
  112. package/.next/server/app/dev/terminal-test.html +1 -1
  113. package/.next/server/app/dev/terminal-test.rsc +10 -10
  114. package/.next/server/app/icon/route.js +1 -1
  115. package/.next/server/app/icon/route.js.nft.json +1 -1
  116. package/.next/server/app/icon/route_client-reference-manifest.js +1 -1
  117. package/.next/server/app/icon-192/route.js +1 -1
  118. package/.next/server/app/icon-192/route.js.nft.json +1 -1
  119. package/.next/server/app/icon-192/route_client-reference-manifest.js +1 -1
  120. package/.next/server/app/icon-512/route.js +1 -1
  121. package/.next/server/app/icon-512/route.js.nft.json +1 -1
  122. package/.next/server/app/icon-512/route_client-reference-manifest.js +1 -1
  123. package/.next/server/app/icon.body +0 -0
  124. package/.next/server/app/manifest.webmanifest/route.js +1 -1
  125. package/.next/server/app/manifest.webmanifest/route.js.nft.json +1 -1
  126. package/.next/server/app/manifest.webmanifest/route_client-reference-manifest.js +1 -1
  127. package/.next/server/app/manifest.webmanifest.body +1 -1
  128. package/.next/server/app/meta/[name]/page.js +2 -0
  129. package/.next/server/app/meta/[name]/page.js.nft.json +1 -0
  130. package/.next/server/app/meta/[name]/page_client-reference-manifest.js +1 -0
  131. package/.next/server/app/page.js +2 -2
  132. package/.next/server/app/page.js.nft.json +1 -1
  133. package/.next/server/app/page_client-reference-manifest.js +1 -1
  134. package/.next/server/app/projects/[projectId]/page.js +2 -2
  135. package/.next/server/app/projects/[projectId]/page.js.nft.json +1 -1
  136. package/.next/server/app/projects/[projectId]/page_client-reference-manifest.js +1 -1
  137. package/.next/server/app/projects/[projectId]/sessions/[id]/page.js +2 -2
  138. package/.next/server/app/projects/[projectId]/sessions/[id]/page.js.nft.json +1 -1
  139. package/.next/server/app/projects/[projectId]/sessions/[id]/page_client-reference-manifest.js +1 -1
  140. package/.next/server/app/projects/[projectId]/settings/page.js +2 -2
  141. package/.next/server/app/projects/[projectId]/settings/page.js.nft.json +1 -1
  142. package/.next/server/app/projects/[projectId]/settings/page_client-reference-manifest.js +1 -1
  143. package/.next/server/app/prs/page.js +2 -2
  144. package/.next/server/app/prs/page.js.nft.json +1 -1
  145. package/.next/server/app/prs/page_client-reference-manifest.js +1 -1
  146. package/.next/server/app/review/page.js +2 -2
  147. package/.next/server/app/review/page.js.nft.json +1 -1
  148. package/.next/server/app/review/page_client-reference-manifest.js +1 -1
  149. package/.next/server/app/reviews/page.js +2 -2
  150. package/.next/server/app/reviews/page.js.nft.json +1 -1
  151. package/.next/server/app/reviews/page_client-reference-manifest.js +1 -1
  152. package/.next/server/app/sessions/[id]/page.js +2 -2
  153. package/.next/server/app/sessions/[id]/page.js.nft.json +1 -1
  154. package/.next/server/app/sessions/[id]/page_client-reference-manifest.js +1 -1
  155. package/.next/server/app/test-direct/page.js +2 -2
  156. package/.next/server/app/test-direct/page.js.nft.json +1 -1
  157. package/.next/server/app/test-direct/page_client-reference-manifest.js +1 -1
  158. package/.next/server/app/test-direct.html +1 -1
  159. package/.next/server/app/test-direct.rsc +10 -10
  160. package/.next/server/app-paths-manifest.json +10 -7
  161. package/.next/server/chunks/1215.js +1 -1
  162. package/.next/server/chunks/1271.js +1 -1
  163. package/.next/server/chunks/1351.js +3 -0
  164. package/.next/server/chunks/1612.js +1 -0
  165. package/.next/server/chunks/2899.js +1 -1
  166. package/.next/server/chunks/5053.js +1 -1
  167. package/.next/server/chunks/5684.js +942 -0
  168. package/.next/server/chunks/6148.js +2 -2
  169. package/.next/server/chunks/{4033.js → 6319.js} +1 -1
  170. package/.next/server/chunks/7486.js +3 -3
  171. package/.next/server/chunks/9472.js +102 -40
  172. package/.next/server/middleware-build-manifest.js +1 -1
  173. package/.next/server/middleware-react-loadable-manifest.js +1 -1
  174. package/.next/server/next-font-manifest.js +1 -1
  175. package/.next/server/next-font-manifest.json +1 -1
  176. package/.next/server/pages/404.html +1 -1
  177. package/.next/server/pages/500.html +1 -1
  178. package/.next/server/server-reference-manifest.json +1 -1
  179. package/.next/static/TSIgyOuEpSp86lKtHn-Y4/_buildManifest.js +1 -0
  180. package/.next/static/chunks/1089-89713836690dc384.js +1 -0
  181. package/.next/static/chunks/{9876-de0c5a1a319b4e8e.js → 1145-b66ea7e0df4f6842.js} +1 -1
  182. package/.next/static/chunks/1160-0ae37be89137bb48.js +1 -0
  183. package/.next/static/chunks/{2073-4192de0bb00cc993.js → 2554-dbb4cd7dd7f11245.js} +1 -1
  184. package/.next/static/chunks/3764.9c44a4ac0ede4088.js +1 -0
  185. package/.next/static/chunks/5204.0d460c9e7de8b015.js +1 -0
  186. package/.next/static/chunks/8759-2ef1cec1061e251a.js +1 -0
  187. package/.next/static/chunks/9531-6d130ea1232ee102.js +1 -0
  188. package/.next/static/chunks/app/_not-found/page-5634011a1475aa0d.js +1 -0
  189. package/.next/static/chunks/app/api/backlog/route-5634011a1475aa0d.js +1 -0
  190. package/.next/static/chunks/app/api/browse-directory/route-5634011a1475aa0d.js +1 -0
  191. package/.next/static/chunks/app/api/filesystem/browse/route-5634011a1475aa0d.js +1 -0
  192. package/.next/static/chunks/app/api/issues/route-5634011a1475aa0d.js +1 -0
  193. package/.next/static/chunks/app/api/meta/[name]/start/route-5634011a1475aa0d.js +1 -0
  194. package/.next/static/chunks/app/api/meta/route-5634011a1475aa0d.js +1 -0
  195. package/.next/static/chunks/app/api/observability/route-5634011a1475aa0d.js +1 -0
  196. package/.next/static/chunks/app/api/orchestrators/route-5634011a1475aa0d.js +1 -0
  197. package/.next/static/chunks/app/api/projects/[id]/route-5634011a1475aa0d.js +1 -0
  198. package/.next/static/chunks/app/api/projects/reload/route-5634011a1475aa0d.js +1 -0
  199. package/.next/static/chunks/app/api/projects/route-5634011a1475aa0d.js +1 -0
  200. package/.next/static/chunks/app/api/prs/[id]/merge/route-5634011a1475aa0d.js +1 -0
  201. package/.next/static/chunks/app/api/reviews/execute/route-5634011a1475aa0d.js +1 -0
  202. package/.next/static/chunks/app/api/reviews/findings/route-5634011a1475aa0d.js +1 -0
  203. package/.next/static/chunks/app/api/reviews/route-5634011a1475aa0d.js +1 -0
  204. package/.next/static/chunks/app/api/reviews/send/route-5634011a1475aa0d.js +1 -0
  205. package/.next/static/chunks/app/api/runtime/terminal/route-5634011a1475aa0d.js +1 -0
  206. package/.next/static/chunks/app/api/sessions/[id]/kill/route-5634011a1475aa0d.js +1 -0
  207. package/.next/static/chunks/app/api/sessions/[id]/message/route-5634011a1475aa0d.js +1 -0
  208. package/.next/static/chunks/app/api/sessions/[id]/remap/route-5634011a1475aa0d.js +1 -0
  209. package/.next/static/chunks/app/api/sessions/[id]/restore/route-5634011a1475aa0d.js +1 -0
  210. package/.next/static/chunks/app/api/sessions/[id]/route-5634011a1475aa0d.js +1 -0
  211. package/.next/static/chunks/app/api/sessions/[id]/send/route-5634011a1475aa0d.js +1 -0
  212. package/.next/static/chunks/app/api/sessions/patches/route-5634011a1475aa0d.js +1 -0
  213. package/.next/static/chunks/app/api/sessions/route-5634011a1475aa0d.js +1 -0
  214. package/.next/static/chunks/app/api/setup-labels/route-5634011a1475aa0d.js +1 -0
  215. package/.next/static/chunks/app/api/spawn/route-5634011a1475aa0d.js +1 -0
  216. package/.next/static/chunks/app/api/update/route-5634011a1475aa0d.js +1 -0
  217. package/.next/static/chunks/app/api/verify/route-5634011a1475aa0d.js +1 -0
  218. package/.next/static/chunks/app/api/version/route-5634011a1475aa0d.js +1 -0
  219. package/.next/static/chunks/app/api/webhooks/[...slug]/route-5634011a1475aa0d.js +1 -0
  220. package/.next/static/chunks/app/apple-icon/route-5634011a1475aa0d.js +1 -0
  221. package/.next/static/chunks/app/dev/terminal-test/page-2a26b5fc208a0a35.js +1 -0
  222. package/.next/static/chunks/app/error-362a1ff5db756e6f.js +1 -0
  223. package/.next/static/chunks/app/{global-error-f6bef179169bcdae.js → global-error-ca208f2a552a271f.js} +1 -1
  224. package/.next/static/chunks/app/icon/route-5634011a1475aa0d.js +1 -0
  225. package/.next/static/chunks/app/icon-192/route-5634011a1475aa0d.js +1 -0
  226. package/.next/static/chunks/app/icon-512/route-5634011a1475aa0d.js +1 -0
  227. package/.next/static/chunks/app/layout-3937228484f6c652.js +1 -0
  228. package/.next/static/chunks/app/loading-5634011a1475aa0d.js +1 -0
  229. package/.next/static/chunks/app/manifest.webmanifest/route-5634011a1475aa0d.js +1 -0
  230. package/.next/static/chunks/app/meta/[name]/page-305f42c2c391f520.js +1 -0
  231. package/.next/static/chunks/app/{not-found-cba3f587e1f98dcb.js → not-found-3d7a362f3eaf10aa.js} +1 -1
  232. package/.next/static/chunks/app/page-305f42c2c391f520.js +1 -0
  233. package/.next/static/chunks/app/projects/[projectId]/layout-5634011a1475aa0d.js +1 -0
  234. package/.next/static/chunks/app/projects/[projectId]/loading-5634011a1475aa0d.js +1 -0
  235. package/.next/static/chunks/app/projects/[projectId]/page-daf2aefa15d58404.js +1 -0
  236. package/.next/static/chunks/app/projects/[projectId]/sessions/[id]/page-e3e30f31bc5a683f.js +1 -0
  237. package/.next/static/chunks/app/projects/[projectId]/settings/{page-63572555892d7a61.js → page-804b824af9b9d550.js} +1 -1
  238. package/.next/static/chunks/app/projects/layout-f7f6bc8388761510.js +1 -0
  239. package/.next/static/chunks/app/prs/page-220d66ff3931dad7.js +1 -0
  240. package/.next/static/chunks/app/review/{page-022b2d2c326ff413.js → page-13ec034d995001ab.js} +1 -1
  241. package/.next/static/chunks/app/reviews/page-5634011a1475aa0d.js +1 -0
  242. package/.next/static/chunks/app/sessions/[id]/{error-67c0d27f977a1cc1.js → error-419d086d9f9cee0d.js} +1 -1
  243. package/.next/static/chunks/app/sessions/[id]/loading-5634011a1475aa0d.js +1 -0
  244. package/.next/static/chunks/app/sessions/[id]/{not-found-cba3f587e1f98dcb.js → not-found-3d7a362f3eaf10aa.js} +1 -1
  245. package/.next/static/chunks/app/sessions/[id]/page-9879b78853fe3a80.js +1 -0
  246. package/.next/static/chunks/app/test-direct/{page-8b80ed180c0f2f42.js → page-ca223477414cb95d.js} +1 -1
  247. package/.next/static/chunks/{main-app-162601c3f1c01b19.js → main-app-bd2a1b10332da5d9.js} +1 -1
  248. package/.next/static/chunks/{webpack-f9566aaa604a1b07.js → webpack-cc5626a562806e84.js} +1 -1
  249. package/.next/static/css/0863eb7d19a9924a.css +1 -0
  250. package/.next/static/css/3effacfd2e5df88c.css +1 -0
  251. package/dist-server/mux-websocket.js +46 -25
  252. package/dist-server/single-port-server.js +2 -2
  253. package/dist-server/start-all.js +3 -3
  254. package/package.json +33 -33
  255. package/.next/server/chunks/2347.js +0 -3
  256. package/.next/server/chunks/4148.js +0 -942
  257. package/.next/server/chunks/5689.js +0 -1
  258. package/.next/server/chunks/9493.js +0 -1
  259. package/.next/static/chunks/1089-c6d7995c7c19039a.js +0 -1
  260. package/.next/static/chunks/3764.4c736d9a181489a4.js +0 -1
  261. package/.next/static/chunks/4115-1a4fa80ec67a29d3.js +0 -1
  262. package/.next/static/chunks/5204.7de7e266895bced7.js +0 -1
  263. package/.next/static/chunks/8204-7c7837ed694da99c.js +0 -1
  264. package/.next/static/chunks/8759-490573536f93f85c.js +0 -1
  265. package/.next/static/chunks/9531-a5175e55fa0db48d.js +0 -1
  266. package/.next/static/chunks/app/_not-found/page-6add9dacf1870b4b.js +0 -1
  267. package/.next/static/chunks/app/api/backlog/route-6add9dacf1870b4b.js +0 -1
  268. package/.next/static/chunks/app/api/browse-directory/route-6add9dacf1870b4b.js +0 -1
  269. package/.next/static/chunks/app/api/filesystem/browse/route-6add9dacf1870b4b.js +0 -1
  270. package/.next/static/chunks/app/api/issues/route-6add9dacf1870b4b.js +0 -1
  271. package/.next/static/chunks/app/api/observability/route-6add9dacf1870b4b.js +0 -1
  272. package/.next/static/chunks/app/api/orchestrators/route-6add9dacf1870b4b.js +0 -1
  273. package/.next/static/chunks/app/api/projects/[id]/route-6add9dacf1870b4b.js +0 -1
  274. package/.next/static/chunks/app/api/projects/reload/route-6add9dacf1870b4b.js +0 -1
  275. package/.next/static/chunks/app/api/projects/route-6add9dacf1870b4b.js +0 -1
  276. package/.next/static/chunks/app/api/prs/[id]/merge/route-6add9dacf1870b4b.js +0 -1
  277. package/.next/static/chunks/app/api/reviews/execute/route-6add9dacf1870b4b.js +0 -1
  278. package/.next/static/chunks/app/api/reviews/findings/route-6add9dacf1870b4b.js +0 -1
  279. package/.next/static/chunks/app/api/reviews/route-6add9dacf1870b4b.js +0 -1
  280. package/.next/static/chunks/app/api/reviews/send/route-6add9dacf1870b4b.js +0 -1
  281. package/.next/static/chunks/app/api/runtime/terminal/route-6add9dacf1870b4b.js +0 -1
  282. package/.next/static/chunks/app/api/sessions/[id]/kill/route-6add9dacf1870b4b.js +0 -1
  283. package/.next/static/chunks/app/api/sessions/[id]/message/route-6add9dacf1870b4b.js +0 -1
  284. package/.next/static/chunks/app/api/sessions/[id]/remap/route-6add9dacf1870b4b.js +0 -1
  285. package/.next/static/chunks/app/api/sessions/[id]/restore/route-6add9dacf1870b4b.js +0 -1
  286. package/.next/static/chunks/app/api/sessions/[id]/route-6add9dacf1870b4b.js +0 -1
  287. package/.next/static/chunks/app/api/sessions/[id]/send/route-6add9dacf1870b4b.js +0 -1
  288. package/.next/static/chunks/app/api/sessions/patches/route-6add9dacf1870b4b.js +0 -1
  289. package/.next/static/chunks/app/api/sessions/route-6add9dacf1870b4b.js +0 -1
  290. package/.next/static/chunks/app/api/setup-labels/route-6add9dacf1870b4b.js +0 -1
  291. package/.next/static/chunks/app/api/spawn/route-6add9dacf1870b4b.js +0 -1
  292. package/.next/static/chunks/app/api/update/route-6add9dacf1870b4b.js +0 -1
  293. package/.next/static/chunks/app/api/verify/route-6add9dacf1870b4b.js +0 -1
  294. package/.next/static/chunks/app/api/version/route-6add9dacf1870b4b.js +0 -1
  295. package/.next/static/chunks/app/api/webhooks/[...slug]/route-6add9dacf1870b4b.js +0 -1
  296. package/.next/static/chunks/app/apple-icon/route-6add9dacf1870b4b.js +0 -1
  297. package/.next/static/chunks/app/dev/terminal-test/page-d0132109f9d8524e.js +0 -1
  298. package/.next/static/chunks/app/error-d632d0714b987864.js +0 -1
  299. package/.next/static/chunks/app/icon/route-6add9dacf1870b4b.js +0 -1
  300. package/.next/static/chunks/app/icon-192/route-6add9dacf1870b4b.js +0 -1
  301. package/.next/static/chunks/app/icon-512/route-6add9dacf1870b4b.js +0 -1
  302. package/.next/static/chunks/app/layout-5cac6fe817194d7a.js +0 -1
  303. package/.next/static/chunks/app/loading-6add9dacf1870b4b.js +0 -1
  304. package/.next/static/chunks/app/manifest.webmanifest/route-6add9dacf1870b4b.js +0 -1
  305. package/.next/static/chunks/app/page-cf7bccb75990950d.js +0 -1
  306. package/.next/static/chunks/app/projects/[projectId]/layout-6add9dacf1870b4b.js +0 -1
  307. package/.next/static/chunks/app/projects/[projectId]/loading-6add9dacf1870b4b.js +0 -1
  308. package/.next/static/chunks/app/projects/[projectId]/page-039a93b16089ed57.js +0 -1
  309. package/.next/static/chunks/app/projects/[projectId]/sessions/[id]/page-043b525bedb8f0f7.js +0 -1
  310. package/.next/static/chunks/app/projects/layout-d43b2e38d46221bd.js +0 -1
  311. package/.next/static/chunks/app/prs/page-e447852fbe0c6ee4.js +0 -1
  312. package/.next/static/chunks/app/reviews/page-6add9dacf1870b4b.js +0 -1
  313. package/.next/static/chunks/app/sessions/[id]/loading-6add9dacf1870b4b.js +0 -1
  314. package/.next/static/chunks/app/sessions/[id]/page-863cf8dd2c76d06d.js +0 -1
  315. package/.next/static/css/0c9b7451c2ce7c02.css +0 -1
  316. package/.next/static/css/b4a15f23f468892a.css +0 -1
  317. package/.next/static/pROr0laPuZIdA4NYNygMD/_buildManifest.js +0 -1
  318. package/LICENSE +0 -22
  319. /package/.next/static/{pROr0laPuZIdA4NYNygMD → TSIgyOuEpSp86lKtHn-Y4}/_ssgManifest.js +0 -0
@@ -0,0 +1,942 @@
1
+ exports.id=5684,exports.ids=[5684],exports.modules={8868:(a,b,c)=>{"use strict";c.d(b,{U10:()=>d.U1,xU:()=>ci,hae:()=>cj,Oo1:()=>ch,o3u:()=>cg,kw3:()=>d.kw,V1$:()=>d.V1,PES:()=>d.PE,Kmu:()=>m,mUH:()=>al,HkR:()=>d.Hk,Agm:()=>d.Ag,D83:()=>d.D8,CMu:()=>d.CM,CK3:()=>d.CK,qUq:()=>er,HrC:()=>cT,_x4:()=>q,Bmx:()=>ev,nXN:()=>cb,Gfg:()=>dY,C1z:()=>eo,RaB:()=>ba,SkT:()=>dZ,Qum:()=>dF,WVn:()=>cA,My0:()=>P,sa4:()=>cW,vQK:()=>eK,ipO:()=>cE,g9C:()=>ab,LJf:()=>eq,yAg:()=>ep,Vo2:()=>ew,mKg:()=>cZ,Rv_:()=>o,NoB:()=>ac,zFo:()=>eR,k8N:()=>y,RxI:()=>cX,XqS:()=>u,IXO:()=>v,XGO:()=>d.XG,ry1:()=>K,getWindowsPtyHosts:()=>eY,Gfo:()=>ez,fgr:()=>d.fg,b8Q:()=>d.b8,tTz:()=>d.tT,qX9:()=>d.qX,zi:()=>d.zi,VoP:()=>eN,uFH:()=>G,g8K:()=>L,cI4:()=>n,Z9L:()=>a1,G_c:()=>am,rSb:()=>ao,_ZN:()=>cx,TF_:()=>dH,m5Y:()=>az,Etf:()=>r,DD3:()=>d.DD,DkI:()=>bX,Ahw:()=>eu,XIc:()=>c8,YOe:()=>bB,giR:()=>d$,wxm:()=>eQ,plx:()=>aa,JyZ:()=>ex,t9S:()=>ax,YEV:()=>eW,Vtt:()=>at,fzr:()=>c9,qhr:()=>cF,Eo9:()=>bZ,J06:()=>dl,kct:()=>c6,vgx:()=>cC,cv0:()=>eS,unregisterWindowsPtyHost:()=>eX,D58:()=>bE,$ry:()=>a2,Nv_:()=>p,inW:()=>aq});var d=c(15407),e=c(73024),f=c(77598),g=c(76760),h=c(48161),i=c(34446),j=c(20642),k=c(67157);let l="ATHENE_",m={CALLER_TYPE:`${l}CALLER_TYPE`,META_NAME:`${l}META_NAME`,SESSION_ID:`${l}SESSION_ID`,SESSION:`${l}SESSION`,SESSION_NAME:`${l}SESSION_NAME`,ISSUE_ID:`${l}ISSUE_ID`,PROJECT_ID:`${l}PROJECT_ID`,ORCHESTRATOR_SESSION_ID:`${l}ORCHESTRATOR_SESSION_ID`,TMUX_NAME:`${l}TMUX_NAME`,DATA_DIR:`${l}DATA_DIR`,CONFIG_PATH:`${l}CONFIG_PATH`,GLOBAL_CONFIG:`${l}GLOBAL_CONFIG`,PORT:`${l}PORT`,PUBLIC_URL:`${l}PUBLIC_URL`,LOG_LEVEL:`${l}LOG_LEVEL`,OBSERVABILITY_STDERR:`${l}OBSERVABILITY_STDERR`,AGENT_GH_TRACE:`${l}AGENT_GH_TRACE`,GH_TRACE_FILE:`${l}GH_TRACE_FILE`,DEBUG:`${l}DEBUG`,SHELL:`${l}SHELL`,BASH_PATH:`${l}BASH_PATH`,REPO_ROOT:`${l}REPO_ROOT`,SCRIPT_LAYOUT:`${l}SCRIPT_LAYOUT`,DEV:`${l}DEV`,TEST:`${l}TEST`,NODE_PTY_SPAWN_HELPER_PATH:`${l}NODE_PTY_SPAWN_HELPER_PATH`,PATH_BASED_MUX:`${l}PATH_BASED_MUX`,NO_UPDATE_NOTIFIER:`${l}NO_UPDATE_NOTIFIER`,NON_INTERACTIVE_INSTALL:`${l}NON_INTERACTIVE_INSTALL`,UPDATE_GIT_REMOTE:`${l}UPDATE_GIT_REMOTE`,UPDATE_GIT_BRANCH:`${l}UPDATE_GIT_BRANCH`,UPDATE_BRANCH:`${l}UPDATE_BRANCH`,PLUGIN_REGISTRY_URL:`${l}PLUGIN_REGISTRY_URL`,PLUGIN_REGISTRY_CACHE_PATH:`${l}PLUGIN_REGISTRY_CACHE_PATH`,DESKTOP_SETUP_PLATFORM:`${l}DESKTOP_SETUP_PLATFORM`,DESKTOP_APP_INSTALL_PATH:`${l}DESKTOP_APP_INSTALL_PATH`,NOTIFIER_MACOS_APP_PATH:`${l}NOTIFIER_MACOS_APP_PATH`,ENABLE_PORTFOLIO:`${l}ENABLE_PORTFOLIO`,CODE_REVIEW_COMMAND:`${l}CODE_REVIEW_COMMAND`,E2E_KEEP_ARTIFACTS:`${l}E2E_KEEP_ARTIFACTS`,DOCTOR_TMP_ROOT:`${l}DOCTOR_TMP_ROOT`};function n(a){return`AO_${a.slice(l.length)}`}function o(a){let b=process.env[a];if(void 0!==b&&""!==b)return b;let c=process.env[n(a)];return void 0!==c&&""!==c?c:b}function p(a){let b={...a};for(let[c,d]of Object.entries(a)){if(void 0===d||!c.startsWith(l))continue;let a=`AO_${c.slice(l.length)}`;a in b||(b[a]=d)}return b}function q(a){return`\${${a}:-\${${n(a)}:-}}`}function r(a){return`(process.env[${JSON.stringify(a)}] ?? process.env[${JSON.stringify(n(a))}])`}function s(a){if(a.length<=4)return a.toLowerCase();let b=a.match(/[A-Z]/g);if(b&&b.length>1)return b.join("").toLowerCase();if(a.includes("-")||a.includes("_")){let b=a.includes("-")?"-":"_";return a.split(b).map(a=>a[0]).join("").toLowerCase()}return a.slice(0,3).toLowerCase()}let t=/^[a-zA-Z0-9][a-zA-Z0-9._-]*$/;function u(a){if(!a||"."===a||".."===a||a.length>128||!t.test(a))throw Error(`Unsafe project ID: "${a}"`);return(0,g.join)(C(),"projects",a)}function v(a){return(0,g.join)(u(a),"sessions")}function w(a){return(0,g.join)(u(a),"worktrees")}function x(a){return(0,g.join)(u(a),"code-reviews")}function y(a){return z(a),(0,g.join)(C(),"projects","_meta",a,"sessions")}function z(a){if(!a||"."===a||".."===a||a.length>128||!/^[a-zA-Z0-9_-]+$/.test(a))throw Error(`Unsafe meta orchestrator name: "${a}"`)}function A(a){return z(a),(0,g.join)(C(),"projects","_meta",a,"workspace")}function B(a){return a.startsWith("~/")?(0,g.join)((0,h.homedir)(),a.slice(2)):a}function C(){return B("~/.agent-orchestrator")}var D=c(31421),E=c(57975);let F=(0,E.promisify)(D.execFile);function G(){return"win32"===process.platform}function H(){return G()?"process":"tmux"}let I=null;function J(a){let b=process.env.PATHEXT?.split(";").filter(Boolean)??[".COM",".EXE",".BAT",".CMD"];for(let c of(process.env.PATH??"").split(";").filter(Boolean)){let d=c.endsWith("\\")||c.endsWith("/")?c.slice(0,-1):c;for(let c of[...b,""]){let b=`${d}\\${a}${c}`;if((0,e.existsSync)(b))return b}}return null}function K(){return I||(I=G()?function(){let a=o(m.SHELL);if(a)return{cmd:a,args:function(a){let b=a.replace(/\\/g,"/").split("/").pop().toLowerCase().replace(/\.exe$/,"");return"cmd"===b?a=>["/c",a]:"bash"===b||"sh"===b||"zsh"===b||"dash"===b?a=>["-c",a]:a=>["-Command",a]}(a)};let b=J("pwsh");if(b)return{cmd:b,args:a=>["-Command",a]};let c=process.env.SystemRoot||"C:\\Windows",d=`${c}\\System32\\WindowsPowerShell\\v1.0\\powershell.exe`;if((0,e.existsSync)(d))return{cmd:d,args:a=>["-Command",a]};let f=J("powershell");return f?{cmd:f,args:a=>["-Command",a]}:{cmd:process.env.ComSpec||"cmd.exe",args:a=>["/c",a]}}():{cmd:"/bin/sh",args:a=>["-c",a]})}async function L(a,b="SIGTERM"){if(!(a<=0))if(G()){let b=["/T","/F","/PID",String(a)];try{await F("taskkill",b,{windowsHide:!0})}catch{}}else try{process.kill(-a,b)}catch{try{process.kill(a,b)}catch{}}}let M=10*!!G();function N(a,b){let c=`${a}.tmp.${process.pid}.${Date.now()}`;(0,e.writeFileSync)(c,b,"utf-8");try{!function(a,b){let c;for(let d=0;d<=M;d++)try{(0,e.renameSync)(a,b);return}catch(b){c=b;let a=b?.code;if("EPERM"!==a&&"EACCES"!==a&&"EBUSY"!==a)throw b;if(d===M)break}throw c}(c,a)}catch(a){try{(0,e.unlinkSync)(c)}catch{}throw a}}function O(a){let b=a.toLowerCase();return"github.com"===b||b.endsWith(".github.com")?"github":"gitlab.com"===b||b.endsWith(".gitlab.com")?"gitlab":"bitbucket.org"===b||b.endsWith(".bitbucket.org")||b.endsWith(".bitbucket.com")?"bitbucket":"unknown"}function P(a){let b=(0,g.join)(a,".git","HEAD");if((0,e.existsSync)(b)){let c=(0,e.readFileSync)(b,"utf-8").trim().match(/^ref: refs\/heads\/(.+)$/);if(c){for(let b of["main","master","next","develop"]){let c=(0,g.join)(a,".git","refs","remotes","origin",b),d=(0,g.join)(a,".git","packed-refs");if((0,e.existsSync)(c)||(0,e.existsSync)(d)&&(0,e.readFileSync)(d,"utf-8").includes(`refs/remotes/origin/${b}`))return b}return c[1]}}return"main"}function Q(a,b,c={}){let d=c.timeoutMs??1e4,f=c.staleMs??6e4;(0,e.mkdirSync)((0,g.dirname)(a),{recursive:!0});let h=Date.now()+d,i=null,j=10;for(;null===i;)try{i=(0,e.openSync)(a,"wx")}catch(b){var k;if("EEXIST"!==b.code)throw Error(`Failed to acquire file lock: ${a}`,{cause:b});try{let b=(0,e.statSync)(a);if(Date.now()-b.mtimeMs>f){(0,e.rmSync)(a,{force:!0});continue}}catch{continue}if(Date.now()>h)throw Error(`Timed out waiting for file lock: ${a}`,{cause:b});k=j,Atomics.wait(new Int32Array(new SharedArrayBuffer(4)),0,0,k),j=Math.min(2*j,250)}try{return b()}finally{try{(0,e.closeSync)(i)}catch{}try{(0,e.rmSync)(a,{force:!0})}catch{}}}function R(a){return a.replace(/\.git$/i,"")}function S(a){return"/"===a?"":a.replace(/\/+$/,"")}var T=c(98995);let U=(0,T.createRequire)("file:///home/runner/work/Athene/Athene/packages/core/dist/events-db.js"),V=null,W=!1,X=!1,Y=0,Z=0,$=/token|password|secret|authorization|cookie|api[-_]?key/i,_=[[/\bBearer\s+[A-Za-z0-9._~+/=-]{12,}\b/gi,"Bearer [redacted]"],[/\bgh[pousr]_[A-Za-z0-9_]{20,}\b/g,"[redacted]"],[/\bgithub_pat_[A-Za-z0-9_]{20,}\b/g,"[redacted]"],[/\bsk-(?:ant-)?(?:proj-|svcacct-)?[A-Za-z0-9_-]{16,}\b/g,"[redacted]"],[/\bxox[baprs]-[A-Za-z0-9-]{10,}\b/g,"[redacted]"],[/\bAKIA[0-9A-Z]{16}\b/g,"[redacted]"],[/\beyJ[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\b/g,"[redacted]"],[/\b([A-Z][A-Z0-9_]*(?:TOKEN|PASSWORD|SECRET|AUTHORIZATION|COOKIE|API_KEY|APIKEY)[A-Z0-9_]*)=([^\s"'`]{6,})/g,"$1=[redacted]"]];function aa(a){try{var b,c;let d=function(){if(W)return null;if(V)return V;try{return V=function(){let a=U("better-sqlite3");(0,e.mkdirSync)(C(),{recursive:!0});let b=new a((0,g.join)(C(),"activity-events.db"));b.pragma("journal_mode = WAL"),b.pragma("busy_timeout = 3000"),b.pragma("synchronous = NORMAL");let c=b.pragma("user_version",{simple:!0});b.exec(`
2
+ CREATE TABLE IF NOT EXISTS activity_events (
3
+ id INTEGER PRIMARY KEY AUTOINCREMENT,
4
+ ts_epoch INTEGER NOT NULL,
5
+ ts TEXT NOT NULL,
6
+ project_id TEXT,
7
+ session_id TEXT,
8
+ source TEXT NOT NULL,
9
+ type TEXT NOT NULL,
10
+ log_level TEXT NOT NULL DEFAULT 'info',
11
+ summary TEXT NOT NULL,
12
+ data TEXT
13
+ );
14
+
15
+ CREATE INDEX IF NOT EXISTS idx_ae_ts ON activity_events(ts_epoch);
16
+ CREATE INDEX IF NOT EXISTS idx_ae_session ON activity_events(session_id);
17
+ CREATE INDEX IF NOT EXISTS idx_ae_project ON activity_events(project_id);
18
+ CREATE INDEX IF NOT EXISTS idx_ae_type ON activity_events(type);
19
+ CREATE INDEX IF NOT EXISTS idx_ae_source ON activity_events(source);
20
+ `),c<1&&b.pragma("user_version = 1");try{b.exec(`
21
+ CREATE VIRTUAL TABLE IF NOT EXISTS activity_events_fts USING fts5(
22
+ summary, data,
23
+ content='activity_events',
24
+ content_rowid='id'
25
+ );
26
+
27
+ CREATE TRIGGER IF NOT EXISTS activity_events_ai
28
+ AFTER INSERT ON activity_events
29
+ BEGIN
30
+ INSERT INTO activity_events_fts(rowid, summary, data)
31
+ VALUES (new.id, new.summary, new.data);
32
+ END;
33
+
34
+ CREATE TRIGGER IF NOT EXISTS activity_events_ad
35
+ AFTER DELETE ON activity_events
36
+ BEGIN
37
+ INSERT INTO activity_events_fts(activity_events_fts, rowid, summary, data)
38
+ VALUES ('delete', old.id, old.summary, old.data);
39
+ END;
40
+
41
+ CREATE TRIGGER IF NOT EXISTS activity_events_au
42
+ AFTER UPDATE ON activity_events
43
+ BEGIN
44
+ INSERT INTO activity_events_fts(activity_events_fts, rowid, summary, data)
45
+ VALUES ('delete', old.id, old.summary, old.data);
46
+ INSERT INTO activity_events_fts(rowid, summary, data)
47
+ VALUES (new.id, new.summary, new.data);
48
+ END;
49
+ `),b.exec("INSERT INTO activity_events_fts(activity_events_fts) VALUES('rebuild')")}catch(a){console.warn("[ao] activity-events FTS unavailable — writes will continue and search will use a bounded LIKE fallback:",a instanceof Error?a.message:String(a))}let d=Date.now()-6048e5;return b.prepare(`DELETE FROM activity_events
50
+ WHERE rowid IN (
51
+ SELECT rowid FROM activity_events WHERE ts_epoch < ? LIMIT ?
52
+ )`).run(d,1e3),b}()}catch(b){var a;return W=!0,a=b,!X&&("1"===o(m.DEBUG)||function(a=process.argv){return a.slice(2).includes("events")}())&&(X=!0,console.warn(function(a){return function(a){let b=a instanceof Error?a.message:String(a);return b.includes("Could not locate the bindings file")||b.includes("better_sqlite3.node")||b.includes("Cannot find module 'better-sqlite3'")}(a)?`[ao] activity-events disabled: better-sqlite3 not compiled for Node ${process.version} (ABI v${process.versions.modules}). Run \`pnpm rebuild better-sqlite3\` or use a supported Node version.`:`[ao] activity-events disabled: better-sqlite3 failed to load: ${(a instanceof Error?a.message:String(a)).split(/\r?\n/,1)[0]??"unknown error"}`}(a))),null}}();if(!d)return void Y++;let f=Date.now(),h=new Date(f).toISOString(),i=(b=a.summary).length<=500?b:`${b.slice(0,497)}...`,j=a.data?function(a){let b,c=function a(b,c){if("bigint"==typeof b)return b.toString();if("string"==typeof b){let a=function(a){let b=a,c=0;for(;c<b.length;){let a=b.indexOf("://",c);if(-1===a)break;if(a<4){c=a+3;continue}let d=b.slice(Math.max(0,a-5),a).toLowerCase();if(!d.endsWith("http")&&!d.endsWith("https")){c=a+3;continue}let e=a+3;for(;e<b.length;){let d=b.charCodeAt(e);if(d<=32||47===d)break;if(64===d){b=b.slice(0,a+3).toLowerCase()+"[redacted]"+b.slice(e),c=a+3+10+1;break}e++}(e>=b.length||32>=b.charCodeAt(e)||47===b.charCodeAt(e))&&(c=a+3)}return b}(b);for(let[b,c]of _)a=a.replace(b,c);return a.length>500&&(a=`${a.slice(0,497)}...`),a}if(null===b||"object"!=typeof b)return b;if(c.has(b))return"[circular]";if(c.add(b),Array.isArray(b))return b.map(b=>a(b,c));let d={};for(let[e,f]of Object.entries(b))d[e]=$.test(e)?"[redacted]":a(f,c);return d}(a,new WeakSet);try{b=JSON.stringify(c)}catch{return}if(!(b.length>16384))return b}(a.data):void 0;d.prepare(`INSERT INTO activity_events
53
+ (ts_epoch, ts, project_id, session_id, source, type, log_level, summary, data)
54
+ VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?)`).run(f,h,a.projectId??null,a.sessionId??null,a.source,a.kind,a.level??"info",i,j??null),f-Z>=36e5&&(Z=f,c=f-6048e5,d?.prepare(`DELETE FROM activity_events
55
+ WHERE rowid IN (
56
+ SELECT rowid FROM activity_events WHERE ts_epoch < ? LIMIT ?
57
+ )`).run(c,1e3))}catch{Y++}}function ab(a,b){let c=(0,g.resolve)(a),d=(0,g.basename)(c).toLowerCase().replace(/[^a-z0-9_-]/g,"-").replace(/^[^a-z0-9]/,"x").replace(/-+/g,"-").slice(0,30),e=`${c}:${b??""}`,h=(0,f.createHash)("sha256").update(e).digest("hex").slice(0,10);return`${d}_${h}`}function ac(){let a=o(m.GLOBAL_CONFIG);if(a)return(0,g.resolve)(a);let b=process.env.XDG_CONFIG_HOME;return b?(0,g.join)(b,"agent-orchestrator","config.yaml"):(0,g.join)((0,h.homedir)(),".agent-orchestrator","config.yaml")}let ad=k.Ik({owner:k.Yj(),name:k.Yj(),platform:k.k5(["github","gitlab","bitbucket"]),originUrl:k.Yj()}),ae=new Set(["projectId","path","repo","defaultBranch","source","registeredAt","displayName","sessionPrefix","storageKey"]),af=["agent-orchestrator.yaml","agent-orchestrator.yml"],ag=new Set(["repo","defaultBranch","originUrl","projectId","path","storageKey"]),ah=k.Ik({projectId:k.Yj().optional(),path:k.Yj(),repo:ad.optional(),defaultBranch:k.Yj().optional(),source:k.Yj().optional(),registeredAt:k.ai().optional(),displayName:k.Yj().optional(),sessionPrefix:k.Yj().optional(),storageKey:k.Yj().optional()}),ai=k.k5(["stable","nightly","manual"]),aj=k.k5(["git","npm-global","pnpm-global","bun-global","homebrew","unknown"]),ak=k.Ik({port:k.ai().default(3e3),terminalPort:k.ai().optional(),directTerminalPort:k.ai().optional(),readyThresholdMs:k.ai().nonnegative().default(3e5),updateChannel:ai.optional().catch(void 0),installMethod:aj.optional().catch(void 0),observability:k.Ik({logLevel:k.k5(["debug","info","warn","error"]).default("warn"),stderr:k.zM().default(!1)}).optional(),defaults:k.Ik({runtime:k.Yj().default(()=>H()),agent:k.Yj().default("claude-code"),workspace:k.Yj().default("worktree"),notifiers:k.YO(k.Yj()).default(["composio","desktop"]),orchestrator:k.Ik({agent:k.Yj().optional()}).optional(),worker:k.Ik({agent:k.Yj().optional()}).optional()}).default({}),projects:k.g1(ah).default({}),projectOrder:k.YO(k.Yj()).optional(),notifiers:k.g1(k.Ik({plugin:k.Yj()}).passthrough()).default({}),notificationRouting:k.g1(k.YO(k.Yj())).default({urgent:["desktop","composio"],action:["desktop","composio"],warning:["composio"],info:["composio"]}),reactions:k.g1(k.Ik({}).passthrough()).default({}),metaOrchestrators:k.g1(k.Ik({}).passthrough()).optional()}).passthrough(),al=k.Ik({repo:k.Yj().optional(),defaultBranch:k.Yj().optional(),runtime:k.Yj().optional(),agent:k.Yj().optional(),workspace:k.Yj().optional(),tracker:k.Ik({plugin:k.Yj()}).passthrough().optional(),scm:k.Ik({plugin:k.Yj(),webhook:k.Ik({enabled:k.zM().optional(),path:k.Yj().optional(),secretEnvVar:k.Yj().optional(),signatureHeader:k.Yj().optional(),eventHeader:k.Yj().optional(),deliveryHeader:k.Yj().optional(),maxBodyBytes:k.ai().optional()}).optional()}).passthrough().optional(),symlinks:k.YO(k.Yj()).optional(),postCreate:k.YO(k.Yj()).optional(),agentConfig:k.Ik({permissions:k.k5(["permissionless","default","auto-edit","suggest","skip"]).optional(),model:k.Yj().optional(),orchestratorModel:k.Yj().optional()}).passthrough().optional(),orchestrator:k.Ik({agent:k.Yj().optional(),agentConfig:k.Ik({}).passthrough().optional()}).optional(),worker:k.Ik({agent:k.Yj().optional(),agentConfig:k.Ik({}).passthrough().optional()}).optional(),reactions:k.g1(k.Ik({}).passthrough()).optional(),agentRules:k.Yj().optional(),agentRulesFile:k.Yj().optional(),orchestratorRules:k.Yj().optional(),orchestratorSessionStrategy:k.k5(["reuse","delete","ignore","delete-new","ignore-new","kill-previous"]).optional(),opencodeIssueSessionStrategy:k.k5(["reuse","delete","ignore"]).optional(),decomposer:k.Ik({}).passthrough().optional()}).passthrough();function am(a,b={}){let c=a??ac();if(!(0,e.existsSync)(c))return null;let{parsed:f,migrationSummary:i}=function(a,b){let c=aC(a);if(!c)return{parsed:null,migrationSummary:null};if(!aB(c).changed)return{parsed:c,migrationSummary:null};let d=null,e=()=>{let b=aC(a);if(!b){c=null;return}let e=aB(b);c=b,e.changed&&(d=function(a){if(0===a.strippedProjects.length)return"[ao] migrated legacy project registry fields in global config";let b=a.strippedProjects.reduce((a,b)=>a+b.strippedFieldCount,0),c=a.strippedProjects.map(a=>`${a.projectId} (${a.strippedFieldCount})`).join(", ");return`[ao] stripped ${b} legacy project registry fields from ${a.strippedProjects.length} project${1===a.strippedProjects.length?"":"s"}: ${c}`}(e),an(ak.parse(b),a))};if(b.alreadyLocked)e();else Q(`${a}.lock`,e);return{parsed:c,migrationSummary:d}}(c,b);if(!f)return null;i&&(console.info(i),aa({source:"config",kind:"config.migrated",summary:"global config migrated",data:{migrationSummary:i}}));let j=ak.parse(f);for(let[a,b]of Object.entries(j.projects))b.path=function(a,b){if("~"===b)return(0,h.homedir)();if(b.startsWith("~/")){let c=(0,h.homedir)(),e=(0,g.resolve)(c,b.slice(2));if(!function(a,b){let c=(0,g.relative)(a,b);return""===c||!c.startsWith("..")&&!c.startsWith(`..${g.sep}`)}(c,e))throw new d.c5(a,`Project path "${b}" escapes the home directory and cannot be loaded from the global registry.`);return e}return(0,g.resolve)(b)}(a,b.path);return j}function an(a,b){let c=b??ac(),d=(0,g.dirname)(c);(0,e.mkdirSync)(d,{recursive:!0}),N(c,(0,i.As)(a,{indent:2}))}function ao(a){for(let b of af.map(b=>(0,g.join)(a,b))){let a;if((0,e.existsSync)(b)){try{let c=(0,e.readFileSync)(b,"utf-8");a=(0,i.qg)(c)}catch(a){return{kind:"malformed",path:b,error:`Failed to parse local config at ${b}: ${a instanceof Error?a.message:String(a)}`}}if(!a||"object"!=typeof a)return{kind:"invalid",path:b,error:`Local config at ${b} must parse to an object`};if("projects"in a)return{kind:"old-format",path:b,error:`Local config at ${b} still uses a wrapped projects: format`};try{return{kind:"loaded",path:b,config:al.parse(a)}}catch(a){return{kind:"invalid",path:b,error:`Local config at ${b} failed validation: ${a instanceof Error?a.message:String(a)}`}}}}return{kind:"missing"}}function ap(a){let b={...a};for(let a of ag)Reflect.deleteProperty(b,a);return b}function aq(a,b,c=function(a){for(let b of af){let c=(0,g.join)(a,b);if((0,e.existsSync)(c))return c}return(0,g.join)(a,af[0])}(a)){(0,e.mkdirSync)((0,g.dirname)(c),{recursive:!0});let d=al.parse(ap(b));return N(c,(0,i.As)(d,{indent:2})),c}function ar(a){return null!=a&&"object"==typeof a&&!Array.isArray(a)}function as(a,b,c){let d=ar(a[c])?a[c]:void 0,e=ar(b[c])?b[c]:void 0,f={...d??{},...e??{}};return Object.keys(f).length>0?f:void 0}function at(a,b){let c=ao(b);if("old-format"!==c.kind||!c.path)throw Error(`No wrapped local config found for project "${a}" at ${b}`);let d=c.path,f=(0,e.readFileSync)(d,"utf-8"),g=(0,i.qg)(f);if(!g||"object"!=typeof g||!ay(g))throw Error(`Local config at ${d} is not a wrapped old-format config.`);let h=g.projects??{},j=h[a];if(!j||"object"!=typeof j){let a=Object.values(h).filter(a=>null!=a&&"object"==typeof a);j=1===a.length?a[0]:void 0}if(!j||"object"!=typeof j)throw Error(`Wrapped local config at ${d} does not contain project "${a}".`);aq(b,function(a,b){let c=ar(a.defaults)?a.defaults:{},d={};for(let a of["runtime","agent","workspace"])null!==c[a]&&void 0!==c[a]&&(d[a]=c[a]);let{name:e,path:f,sessionPrefix:g,projectId:h,source:i,registeredAt:j,displayName:k,orchestrator:l,worker:m,...n}=b,o={...d,...n},p=as(c,b,"orchestrator"),q=as(c,b,"worker");return p&&(o.orchestrator=p),q&&(o.worker=q),o}(g,j),d)}function au(a){if(!a)return;let b=function(a){let b,c=a.trim(),d=c.match(/^git@([^:]+):(.+)$/);if(d){let a=d[1].toLowerCase(),b=R(S(d[2]));return`https://${a}/${b}`}let e=c.replace(/^[A-Za-z][A-Za-z0-9+.-]*:\/\//,a=>a.toLowerCase());try{b=new URL(e)}catch{throw Error(`Invalid origin URL: ${a}`)}let f=b.hostname.toLowerCase(),g=R(S(b.pathname));return`https://${f}${g}`}(a);if(b.startsWith("https://"))try{let a=new URL(b),c=a.pathname.split("/").filter(Boolean);if(c.length<2)return;let d=c[c.length-1],e=c.slice(0,-1).join("/"),f=O(a.host);if("unknown"===f)return;return{owner:e,name:d,platform:f,originUrl:b}}catch{return}}function av(a){if("string"!=typeof a)return;let b=a.trim();if(!b)return;if(b.startsWith("http://")||b.startsWith("https://")||b.startsWith("git@"))return au(b);let c=b.split("/").filter(Boolean);if(2===c.length)return au(`https://github.com/${c[0]}/${c[1]}`);if(c.length>=3&&c[0].includes(".")){let a=c[0];if("unknown"===O(a))return;let b=c.slice(1,-1).join("/"),d=c[c.length-1];return au(`https://${a}/${b}/${d}`)}}function aw(a,b,c){for(let[d,e]of Object.entries(a.projects))if(d!==c&&(e.sessionPrefix??s((0,g.basename)(e.path??d)))===b)return d;return null}function ax(a,b,c,d,f,h){let i="string"==typeof f?f:h??ac(),j=(0,g.resolve)(c),k=(0,e.realpathSync)((0,g.resolve)(c)),l=function(a){let b=function(a){let b=(0,g.join)(a,".git");if(!(0,e.existsSync)(b))return null;if((0,e.statSync)(b).isDirectory()){let a=(0,g.join)(b,"config");return(0,e.existsSync)(a)?a:null}let c=(0,e.readFileSync)(b,"utf-8").trim().match(/^gitdir:\s*(.+)$/i);if(!c)return null;let d=(0,g.resolve)(a,c[1]),f=(0,g.join)(d,"config");if((0,e.existsSync)(f))return f;let h=(0,g.join)(d,"commondir");if(!(0,e.existsSync)(h))return null;let i=(0,g.resolve)(d,(0,e.readFileSync)(h,"utf-8").trim()),j=(0,g.join)(i,"config");return(0,e.existsSync)(j)?j:null}(function(a){let b=(0,g.resolve)(a);for(;;){if((0,e.existsSync)((0,g.join)(b,".git")))return b;let c=(0,g.dirname)(b);if(c===b)return(0,g.resolve)(a);b=c}}(a));if(!b)return null;let c=(0,e.readFileSync)(b,"utf-8").split(/\r?\n/),d=!1;for(let a of c){let b=a.match(/^\s*\[(.+)\]\s*$/);if(b){d='remote "origin"'===b[1];continue}if(!d)continue;let c=a.match(/^\s*url\s*=\s*(.+)\s*$/);if(c?.[1])return c[1].trim()}return null}(k);return Q(`${i}.lock`,()=>{let c=am(i,{alreadyLocked:!0})??aA(),e=a,f=c.projects[a];if(!f){let a=ab(k,l),b=c.projects[a];if(b?.path&&(0,g.resolve)(b.path)===k)e=a,f=b;else if(b)throw Error(`Project ID collision: "${a}" already registered at a different path (${b.path}). This is extremely unlikely — please file a bug.`);else e=a}if(f?.path&&(0,g.resolve)(f.path)!==k)throw Error(`Project id "${e}" is already registered for "${f.path}". Choose a different configProjectKey to add "${k}" as a separate project.`);for(let[a,b]of Object.entries(c.projects))if(a!==e&&(0,g.resolve)(b.path)===k)throw Error(`Project "${a}" is already registered at "${k}". Choose a different project ID or path.`);let h=f?.repo??au(l)??(d?.repo?av(d.repo):void 0),m=f?.defaultBranch??d?.defaultBranch??"main",n=f?.sessionPrefix??d?.sessionPrefix??s((0,g.basename)(j)),o=f?.source??(h?"ao-project-add":"local"),p=f?.registeredAt??Math.floor(Date.now()/1e3),q=!f?.sessionPrefix&&!!d?.sessionPrefix,r=aw(c,n,e);if(r&&q)throw Error(`Duplicate session prefix detected: "${n}"
58
+ Projects "${r}" and "${e}" would generate the same prefix.
59
+
60
+ Choose a different configProjectKey or add an explicit sessionPrefix before registering the project.`);let t=r?function(a,b,c){if(!aw(b,a,c))return a;for(let d=1;d<1e4;d+=1){let e=`${a}-${d}`;if(!aw(b,e,c))return e}throw Error(`Could not allocate a session prefix for "${a}" after 9999 attempts.`)}(n,c,e):n;return c.projects[e]={projectId:e,path:k,...h?{repo:h}:{},defaultBranch:m,source:o,registeredAt:p,displayName:b,sessionPrefix:t},an(c,i),e})}function ay(a){return!!a&&"object"==typeof a&&"projects"in a&&"object"==typeof a.projects&&Object.values(a.projects).some(a=>null!=a&&"object"==typeof a&&"path"in a)}function az(a,b){let c=b??ac(),d=(0,e.readFileSync)(a,"utf-8"),f=(0,i.qg)(d);if(!ay(f))throw Error(`File at ${a} is not an old-format config.`);let j=f.projects??{},k=aA();for(let[a,b]of("number"==typeof f.port&&(k.port=f.port),null!==f.terminalPort&&void 0!==f.terminalPort&&(k.terminalPort=f.terminalPort),null!==f.directTerminalPort&&void 0!==f.directTerminalPort&&(k.directTerminalPort=f.directTerminalPort),null!==f.readyThresholdMs&&void 0!==f.readyThresholdMs&&(k.readyThresholdMs=f.readyThresholdMs),null!==f.observability&&void 0!==f.observability&&(k.observability=f.observability),null!==f.defaults&&void 0!==f.defaults&&(k.defaults=f.defaults),null!==f.notifiers&&void 0!==f.notifiers&&(k.notifiers=f.notifiers),null!==f.notificationRouting&&void 0!==f.notificationRouting&&(k.notificationRouting=f.notificationRouting),null!==f.reactions&&void 0!==f.reactions&&(k.reactions=f.reactions),Object.entries(j))){if(!b.path)continue;let c="string"==typeof b.path&&b.path.startsWith("~/")?(0,g.join)((0,h.homedir)(),b.path.slice(2)):b.path,d="string"==typeof b.originUrl?au(b.originUrl):void 0;k.projects[a]={projectId:a,path:c,...d?{repo:d}:{},..."string"==typeof b.defaultBranch?{defaultBranch:b.defaultBranch}:{},source:"migrated",registeredAt:Math.floor(Date.now()/1e3),displayName:b.name??a,..."string"==typeof b.sessionPrefix?{sessionPrefix:b.sessionPrefix}:{}}}for(let[b,d]of(an(k,c),Object.entries(j))){if(!d.path)continue;let b="string"==typeof d.path&&d.path.startsWith("~/")?(0,g.join)((0,h.homedir)(),d.path.slice(2)):d.path,{name:c,path:e,sessionPrefix:f,...j}=d;N((0,g.join)(b,(0,g.basename)(a)),(0,i.As)(j,{indent:2}))}return c}function aA(){return{port:3e3,readyThresholdMs:3e5,observability:{logLevel:"warn",stderr:!1},defaults:{runtime:H(),agent:"claude-code",workspace:"worktree",notifiers:["composio","desktop"]},projects:{},notifiers:{},notificationRouting:{urgent:["desktop","composio"],action:["desktop","composio"],warning:["composio"],info:["composio"]},reactions:{}}}function aB(a){let b=a.projects;if(!b||"object"!=typeof b)return{changed:!1,strippedProjects:[]};let c=!1,d=[];for(let[a,e]of Object.entries(b)){if(!e||"object"!=typeof e)continue;let b=e.projectId!==a||"string"==typeof e.name&&"string"!=typeof e.displayName||"string"==typeof e.repo||"string"==typeof e.originUrl&&void 0===e.repo,f=function(a,b){let c=0;if(b.projectId=a,"string"==typeof b.name&&"string"!=typeof b.displayName&&(b.displayName=b.name),"string"==typeof b.originUrl&&void 0===b.repo){let a=au(b.originUrl);a&&(b.repo=a)}if("string"==typeof b.repo){let a=av(b.repo);a?b.repo=a:delete b.repo}for(let a of(delete b.name,delete b.originUrl,Object.keys(b)))ae.has(a)||(Reflect.deleteProperty(b,a),c+=1);return{strippedFieldCount:c}}(a,e);f.strippedFieldCount>0&&d.push({projectId:a,strippedFieldCount:f.strippedFieldCount}),(f.strippedFieldCount>0||b)&&(c=!0)}return{changed:c,strippedProjects:d}}function aC(a){let b=(0,e.readFileSync)(a,"utf-8"),c=(0,i.qg)(b);return c&&"object"==typeof c?c:null}function aD(a,b,c){let e=function(a,b,c){let e=b.projects[a];if(!e||!e.path)return null;let f=e.path,h=e.displayName??a,i="string"==typeof e.sessionPrefix&&e.sessionPrefix.length>0?e.sessionPrefix:s((0,g.basename)(f)),j="string"==typeof e.defaultBranch&&e.defaultBranch.length>0?e.defaultBranch:"main",k=e.repo&&"string"==typeof e.repo.owner&&"string"==typeof e.repo.name?`${e.repo.owner}/${e.repo.name}`:void 0,l={name:h,path:f,...k?{repo:k}:{},sessionPrefix:i,defaultBranch:j},m=c=>{let e={...c},f=b.defaults??{};void 0===e.runtime&&(e.runtime=f.runtime),void 0===e.agent&&(e.agent=f.agent),void 0===e.workspace&&(e.workspace=f.workspace);let g={...f.orchestrator??{},...e.orchestrator??{}};Object.keys(g).length>0&&(e.orchestrator=g);let h={...f.worker??{},...e.worker??{}};Object.keys(h).length>0&&(e.worker=h);let i=["runtime","agent","workspace"].filter(a=>{let b=e[a];return"string"!=typeof b||0===b.length});if(i.length>0)throw new d.c5(a,`Project "${a}" is missing required behavior fields with no defaults: ${i.join(", ")}`);return e},n=ao(f);if("loaded"===n.kind&&n.config)return{...m(ap(n.config)),...l};"malformed"===n.kind?aa({projectId:a,source:"config",kind:"config.project_malformed",level:"error",summary:`local config for ${a} could not be parsed`,data:{path:n.path,error:n.error}}):"invalid"===n.kind&&aa({projectId:a,source:"config",kind:"config.project_invalid",level:"error",summary:`local config for ${a} failed validation`,data:{path:n.path,error:n.error}});let o="missing"!==n.kind?n.error??"Failed to load local config":void 0,p="malformed"===n.kind||"invalid"===n.kind||"old-format"===n.kind?n.kind:void 0;return{...o?{}:m({}),...l,...o?{resolveError:o}:{},...p?{resolveErrorKind:p}:{}}}(a,b);if(!e)throw new d.c5(a,`Unknown project: ${a}`);if("string"==typeof e.resolveError&&e.resolveError.length>0)throw new d.c5(a,e.resolveError,e.resolveErrorKind);return e}function aE(a,b,c){a.plugin||a.package||a.path||b.addIssue({code:j.eq.custom,message:`${c} config requires either 'plugin' (for built-ins) or 'package'/'path' (for external plugins)`}),a.package&&a.path&&b.addIssue({code:j.eq.custom,message:`${c} config cannot have both 'package' and 'path' - use one or the other`})}let aF=k.Ik({auto:k.zM().default(!0),action:k.k5(["send-to-agent","notify","auto-merge"]).default("notify"),message:k.Yj().optional(),priority:k.k5(["urgent","action","warning","info"]).optional(),retries:k.ai().optional(),escalateAfter:k.KC([k.ai(),k.Yj()]).optional(),threshold:k.Yj().optional(),includeSummary:k.zM().optional()}),aG=k.Ik({plugin:k.Yj().optional(),package:k.Yj().optional(),path:k.Yj().optional()}).passthrough().superRefine((a,b)=>aE(a,b,"Tracker")),aH=k.Ik({plugin:k.Yj().optional(),package:k.Yj().optional(),path:k.Yj().optional(),webhook:k.Ik({enabled:k.zM().default(!0),path:k.Yj().optional(),secretEnvVar:k.Yj().optional(),signatureHeader:k.Yj().optional(),eventHeader:k.Yj().optional(),deliveryHeader:k.Yj().optional(),maxBodyBytes:k.ai().int().positive().optional()}).optional()}).passthrough().superRefine((a,b)=>aE(a,b,"SCM")),aI=k.Ik({plugin:k.Yj().optional(),package:k.Yj().optional(),path:k.Yj().optional()}).passthrough().superRefine((a,b)=>aE(a,b,"Notifier")),aJ=k.Ik({logLevel:k.k5(["debug","info","warn","error"]).default("warn"),stderr:k.zM().default(!1)}).default({}),aK=k.k5(["permissionless","default","auto-edit","suggest","skip"]).default("permissionless").transform(a=>"skip"===a?"permissionless":a),aL=k.Ik({permissions:aK,model:k.Yj().optional(),orchestratorModel:k.Yj().optional(),opencodeSessionId:k.Yj().optional()}).passthrough(),aM=k.Ik({permissions:k.KC([k.k5(["permissionless","default","auto-edit","suggest"]),k.eu("skip")]).optional(),model:k.Yj().optional(),orchestratorModel:k.Yj().optional(),opencodeSessionId:k.Yj().optional()}).passthrough(),aN=k.Ik({agent:k.Yj().optional()}).optional(),aO=k.Ik({agent:k.Yj().optional(),agentConfig:aM.optional()}).optional(),aP=k.Ik({name:k.Yj().optional(),repo:k.Yj().optional(),description:k.Yj().optional(),path:k.Yj(),defaultBranch:k.Yj().default("main"),sessionPrefix:k.Yj().regex(/^[a-zA-Z0-9_-]+$/,"sessionPrefix must match [a-zA-Z0-9_-]+").optional(),resolveError:k.Yj().optional(),runtime:k.Yj().optional(),agent:k.Yj().optional(),workspace:k.Yj().optional(),env:k.g1(k.Yj(),k.Yj()).optional(),tracker:aG.optional(),scm:aH.optional(),symlinks:k.YO(k.Yj()).optional(),postCreate:k.YO(k.Yj()).optional(),agentConfig:aL.default({}),orchestrator:aO,worker:aO,reactions:k.g1(aF.partial()).optional(),agentRules:k.Yj().optional(),agentRulesFile:k.Yj().optional(),orchestratorRules:k.Yj().optional(),orchestratorSessionStrategy:k.k5(["reuse","delete","ignore","delete-new","ignore-new","kill-previous"]).optional(),opencodeIssueSessionStrategy:k.k5(["reuse","delete","ignore"]).optional()}),aQ=k.Ik({runtime:k.Yj().default(()=>H()),agent:k.Yj().default("claude-code"),workspace:k.Yj().default("worktree"),notifiers:k.YO(k.Yj()).default([]),orchestrator:aN,worker:aN}),aR=k.Ik({name:k.Yj(),source:k.k5(["registry","npm","local"]),package:k.Yj().optional(),version:k.Yj().optional(),path:k.Yj().optional(),enabled:k.zM().default(!0)}).superRefine((a,b)=>{"local"!==a.source||a.path||b.addIssue({code:j.eq.custom,path:["path"],message:"Local plugins require a path"}),"registry"!==a.source&&"npm"!==a.source||a.package||b.addIssue({code:j.eq.custom,path:["package"],message:"Registry and npm plugins require a package name"})}),aS=k.Ik({preventIdleSleep:k.zM().default("darwin"===process.platform)}).default({}),aT=k.Ik({attentionZones:k.k5(["simple","detailed"]).default("simple")}),aU=k.Ik({autoCleanupOnMerge:k.zM().default(!0),mergeCleanupIdleGraceMs:k.ai().int().nonnegative().refine(a=>0===a||a>=1e4,{message:"mergeCleanupIdleGraceMs is in milliseconds; values between 1 and 9999 are likely a units mistake (use 0 to disable the gate, or e.g. 10000 for 10s, 300000 for 5min)"}).default(3e5)}).default({}),aV=k.KC([k.eu("all"),k.Ik({projects:k.YO(k.Yj()).min(1)})]),aW=k.Ik({scope:aV,discover:k.zM().default(!1),agent:k.Yj().optional(),rules:k.Yj().optional()}),aX=k.Ik({$schema:k.Yj().optional(),port:k.ai().int().default(3e3),terminalPort:k.ai().int().optional(),directTerminalPort:k.ai().int().optional(),readyThresholdMs:k.ai().int().nonnegative().default(3e5),power:aS,lifecycle:aU,observability:aJ,defaults:aQ.default({}),plugins:k.YO(aR).default([]),dashboard:aT.optional(),projects:k.g1(k.Yj().regex(/^[a-zA-Z0-9_-]+$/,"Project ID must match [a-zA-Z0-9_-]+ (no dots, slashes, or special characters)"),aP),notifiers:k.g1(aI).default({}),notificationRouting:k.g1(k.YO(k.Yj())).default({}),reactions:k.g1(aF).default({}),metaOrchestrators:k.g1(k.Yj().regex(/^[a-zA-Z0-9_-]+$/,"meta orchestrator name must match [a-zA-Z0-9_-]+"),aW).optional()}).superRefine((a,b)=>{let c=a.projects??{};Object.prototype.hasOwnProperty.call(c,"_meta")&&b.addIssue({code:j.eq.custom,path:["projects","_meta"],message:"'_meta' is a reserved project ID used for meta orchestrator storage; rename this project."})});function aY(a,b){if(!a)return;let c=new Set(b);for(let[d,e]of Object.entries(a)){let a=e?.scope;if(!a||"all"===a||"object"!=typeof a)continue;let f=a.projects;if(Array.isArray(f)){for(let a of f)if("string"==typeof a&&!c.has(a))throw Error(`Meta orchestrator '${d}' references unknown project '${a}'. Known projects: ${b.join(", ")||"(none)"}.`)}}}function aZ(a){return a.startsWith("~/")?(0,g.join)((0,h.homedir)(),a.slice(2)):a}function a$(a,b){if(a){let b=a.split("/"),c=b[b.length-1]??a,d=c.match(/^(?:ao-)?plugin-(?:runtime|agent|workspace|tracker|scm|notifier|terminal)-(.+)$/);return d?.[1]?d[1]:c}if(b){let a=b.split("/").filter(a=>a&&"."!==a&&".."!==a);return a[a.length-1]??b}return"unknown"}function a_(a,b,c,d){if(!a.package&&!a.path)return null;a.path&&(a.path=aZ(a.path));let e=a.plugin;return a.plugin||(a.plugin=a$(a.package,a.path)),{source:b,location:c,slot:d,package:a.package,path:a.path,expectedPluginName:e}}function a0(a){let b=a2(a);return aY(b.metaOrchestrators,Object.keys(b.projects)),b}function a1(a){let b=a??function(a){let b=o(m.CONFIG_PATH);if(b){let a=(0,g.resolve)(b);if((0,e.existsSync)(a))return a}let c=a=>{for(let b of["agent-orchestrator.yaml","agent-orchestrator.yml"]){let c=(0,g.resolve)(a,b);if((0,e.existsSync)(c))return c}let b=(0,g.resolve)(a,"..");return b===a?null:c(b)},d=c(process.cwd());if(d)return d;let f=ac();if((0,e.existsSync)(f))return f;for(let a of[(0,g.resolve)((0,h.homedir)(),".agent-orchestrator.yaml"),(0,g.resolve)((0,h.homedir)(),".agent-orchestrator.yml"),(0,g.resolve)((0,h.homedir)(),".config","agent-orchestrator","config.yaml")])if((0,e.existsSync)(a))return a;return null}();if(!b)throw new d.kw;let c=(0,e.readFileSync)(b,"utf-8"),j=(0,i.qg)(c),k=function(a){if(!(0,e.existsSync)(a))return"missing";let b=(0,e.readFileSync)(a,"utf-8"),c=(0,i.qg)(b);return c&&"object"==typeof c&&"projects"in c?"wrapped":"flat-or-nonobject"}(b),l=!!b&&(0,g.resolve)(b)===(0,g.resolve)(ac()),n=l||"wrapped"!==k?j:j&&"object"==typeof j&&"projects"in j&&j.projects&&"object"==typeof j.projects?{...j,projects:Object.fromEntries(Object.entries(j.projects).map(([a,c])=>c&&"object"==typeof c?"string"==typeof c.storageKey||"string"!=typeof c.path?[a,c]:[a,{...c,storageKey:function(a,b){let c=(0,e.realpathSync)(a),d=(0,g.dirname)(c),h=(0,f.createHash)("sha256").update(d).digest("hex").slice(0,12);return`${h}-${(0,g.basename)(b)}`}(b,c.path)}]:[a,c]))}:j,p=l?function(a){let b=am(a);if(!b)return null;aY(b.metaOrchestrators,Object.keys(b.projects));let c={},e={};for(let[f,g]of Object.entries(b.projects))try{c[f]=aD(f,b,a)}catch(a){if(!(a instanceof d.c5))throw a;if(e[f]={projectId:f,path:g.path,resolveError:a.message},"malformed"===a.reasonKind||"invalid"===a.reasonKind)continue;aa({projectId:f,source:"config",kind:"config.project_resolve_failed",level:"error",summary:`project ${f} failed to resolve`,data:{path:g.path,error:a.message}})}return{...a2({port:b.port,terminalPort:b.terminalPort,directTerminalPort:b.directTerminalPort,readyThresholdMs:b.readyThresholdMs,observability:b.observability,defaults:b.defaults,notifiers:b.notifiers,notificationRouting:b.notificationRouting,reactions:b.reactions,metaOrchestrators:b.metaOrchestrators,projects:c}),degradedProjects:e}}(b)??a0(n):"wrapped"===k?a0(n):function(a,b){let c=am(ac());if(!c)return null;aY(c.metaOrchestrators,Object.keys(c.projects));let d=(()=>{try{return(0,e.realpathSync)((0,g.resolve)((0,g.dirname)(a)))}catch{return(0,g.resolve)((0,g.dirname)(a))}})(),f=Object.entries(c.projects).find(([,a])=>{if("string"!=typeof a.path)return!1;try{return(0,e.realpathSync)((0,g.resolve)(a.path))===d}catch{return(0,g.resolve)(a.path)===d}});if(!f)return null;let[h]=f,i=aD(h,c);return{...a2({port:c.port,terminalPort:c.terminalPort,directTerminalPort:c.directTerminalPort,readyThresholdMs:c.readyThresholdMs,observability:c.observability,defaults:c.defaults,notifiers:c.notifiers,notificationRouting:c.notificationRouting,reactions:c.reactions,metaOrchestrators:c.metaOrchestrators,projects:{[h]:{...i}}}),degradedProjects:{}}}(b)??a2(n);return p.configPath=b,"degradedProjects"in p||(p.degradedProjects={}),p}function a2(a){var b;let c=aX.parse(a);(b=c=function(a){for(let[b,c]of Object.entries(a.projects)){c.name||(c.name=b),c.sessionPrefix||(c.sessionPrefix=s((0,g.basename)(c.path)));let a=function(a){if("gitlab"===a.scm?.plugin)return"gitlab";let b=a.scm?.host;if("string"==typeof b&&b.toLowerCase().includes("gitlab")||"gitlab"===a.tracker?.plugin)return"gitlab";let c=a.tracker?.host;return"string"==typeof c&&c.toLowerCase().includes("gitlab")?"gitlab":"github"}(c);!c.scm&&c.repo?.includes("/")&&(c.scm={plugin:a}),!c.tracker&&c.repo?.includes("/")&&(c.tracker={plugin:a})}return a}(c=function(a){for(let b of Object.values(a.projects))b.path=aZ(b.path);for(let b of a.plugins??[])b.path&&(b.path=aZ(b.path));return a}(c))).reactions={"pr-closed":{auto:!0,action:"notify",priority:"action",message:"A PR was closed without merging. Decide whether to learn from the closure, resume the work, or terminate the session."},"ci-failed":{auto:!0,action:"send-to-agent",retries:2,escalateAfter:2},"changes-requested":{auto:!0,action:"send-to-agent",message:"There are new review comments on your PR requesting changes.",escalateAfter:"30m"},"bugbot-comments":{auto:!0,action:"send-to-agent",message:"Automated review comments found on your PR. Details will follow shortly.",escalateAfter:"30m"},"merge-conflicts":{auto:!0,action:"send-to-agent",message:"Your branch has merge conflicts. Rebase on the default branch and resolve them.",escalateAfter:"15m"},"approved-and-green":{auto:!1,action:"notify",priority:"action",message:"PR is ready to merge"},"agent-idle":{auto:!0,action:"send-to-agent",message:"You appear to be idle. If your task is not complete, continue working — write the code, commit, push, and create a PR. If you are blocked, explain what is blocking you.",retries:2,escalateAfter:"15m"},"agent-stuck":{auto:!0,action:"notify",priority:"urgent",threshold:"10m"},"agent-needs-input":{auto:!0,action:"notify",priority:"urgent"},"agent-exited":{auto:!0,action:"notify",priority:"urgent"},"all-complete":{auto:!0,action:"notify",priority:"info",includeSummary:!0},...b.reactions};let d=function(a){let b=[];for(let[c,d]of Object.entries(a.projects)){if(d.tracker){let a=a_(d.tracker,`projects.${c}.tracker`,{kind:"project",projectId:c,configType:"tracker"},"tracker");a&&b.push(a)}if(d.scm){let a=a_(d.scm,`projects.${c}.scm`,{kind:"project",projectId:c,configType:"scm"},"scm");a&&b.push(a)}}for(let[c,d]of Object.entries(a.notifiers??{}))if(d){let a=a_(d,`notifiers.${c}`,{kind:"notifier",notifierId:c},"notifier");a&&b.push(a)}return b}(c=b);return d.length>0&&(c.plugins=function(a,b){let c=[...a??[]],d=new Set;for(let a of c)a.package&&d.add(`package:${a.package}`),a.path&&d.add(`path:${a.path}`);for(let a of b){let b=a.package?`package:${a.package}`:`path:${a.path}`;if(d.has(b)){let b=c.find(b=>a.package&&b.package===a.package||a.path&&b.path===a.path);b&&!1===b.enabled&&(b.enabled=!0);continue}d.add(b);let e=a.expectedPluginName??a$(a.package,a.path);c.push({name:e,source:a.package?"npm":"local",package:a.package,path:a.path,enabled:!0})}return c}(c.plugins,d),c._externalPluginEntries=d),!function(a){let b=new Set;for(let[c]of Object.entries(a.projects)){if(b.has(c))throw Error(`Duplicate project ID detected: "${c}"
61
+ Each project entry must use a unique registry key.`);b.add(c)}let c=new Set,d={};for(let[b,e]of Object.entries(a.projects)){let f=e.sessionPrefix||s(b);if(c.has(f)){let c=d[f];throw Error(`Duplicate session prefix detected: "${f}"
62
+ Projects "${c}" and "${b}" would generate the same prefix.
63
+
64
+ To fix this, add an explicit sessionPrefix to one of these projects:
65
+
66
+ projects:
67
+ ${c}:
68
+ path: ${a.projects[c]?.path}
69
+ sessionPrefix: ${f}1 # Add explicit prefix
70
+ ${b}:
71
+ path: ${e.path}
72
+ sessionPrefix: ${f}2 # Add explicit prefix
73
+ `)}c.add(f),d[f]=b}}(c),c}var a3=c(73136);let a4=["dist/index.js","index.js"],a5=[{slot:"runtime",name:"tmux",pkg:"@made-by-moonlight/athene-plugin-runtime-tmux"},{slot:"runtime",name:"process",pkg:"@made-by-moonlight/athene-plugin-runtime-process"},{slot:"agent",name:"claude-code",pkg:"@made-by-moonlight/athene-plugin-agent-claude-code"},{slot:"agent",name:"codex",pkg:"@made-by-moonlight/athene-plugin-agent-codex"},{slot:"agent",name:"aider",pkg:"@made-by-moonlight/athene-plugin-agent-aider"},{slot:"agent",name:"cursor",pkg:"@made-by-moonlight/athene-plugin-agent-cursor"},{slot:"agent",name:"kimicode",pkg:"@made-by-moonlight/athene-plugin-agent-kimicode"},{slot:"agent",name:"grok",pkg:"@made-by-moonlight/athene-plugin-agent-grok"},{slot:"agent",name:"opencode",pkg:"@made-by-moonlight/athene-plugin-agent-opencode"},{slot:"workspace",name:"worktree",pkg:"@made-by-moonlight/athene-plugin-workspace-worktree"},{slot:"workspace",name:"clone",pkg:"@made-by-moonlight/athene-plugin-workspace-clone"},{slot:"tracker",name:"github",pkg:"@made-by-moonlight/athene-plugin-tracker-github"},{slot:"tracker",name:"linear",pkg:"@made-by-moonlight/athene-plugin-tracker-linear"},{slot:"tracker",name:"gitlab",pkg:"@made-by-moonlight/athene-plugin-tracker-gitlab"},{slot:"scm",name:"github",pkg:"@made-by-moonlight/athene-plugin-scm-github"},{slot:"scm",name:"gitlab",pkg:"@made-by-moonlight/athene-plugin-scm-gitlab"},{slot:"notifier",name:"composio",pkg:"@made-by-moonlight/athene-plugin-notifier-composio"},{slot:"notifier",name:"dashboard",pkg:"@made-by-moonlight/athene-plugin-notifier-dashboard"},{slot:"notifier",name:"desktop",pkg:"@made-by-moonlight/athene-plugin-notifier-desktop"},{slot:"notifier",name:"discord",pkg:"@made-by-moonlight/athene-plugin-notifier-discord"},{slot:"notifier",name:"openclaw",pkg:"@made-by-moonlight/athene-plugin-notifier-openclaw"},{slot:"notifier",name:"slack",pkg:"@made-by-moonlight/athene-plugin-notifier-slack"},{slot:"notifier",name:"webhook",pkg:"@made-by-moonlight/athene-plugin-notifier-webhook"},{slot:"terminal",name:"iterm2",pkg:"@made-by-moonlight/athene-plugin-terminal-iterm2"},{slot:"terminal",name:"web",pkg:"@made-by-moonlight/athene-plugin-terminal-web"}];function a6(a,b,c){let d=c.plugin;return"string"==typeof d&&d.length>0?d===a:b===a}function a7(a,b){if(!Object.prototype.hasOwnProperty.call(b.notifiers??{},a))return!1;let c=b.notifiers?.[a];return!c||"object"!=typeof c||!a6(a,a,c)}function a8(a){return!!a&&"object"==typeof a&&!!(a.manifest&&"function"==typeof a.create)}function a9(a){if(a8(a))return a;if(a&&"object"==typeof a&&"default"in a){let b=a.default;if(a8(b))return b}return null}function ba(){let a=new Map;function b(b,c,d,e){a.set(`${b}:${c}`,{manifest:d,instance:e})}function c(a,d,e=!1){let{manifest:f}=a,g=function(a,b,c=!1){let d=new Map,e=Object.entries(b.notifiers??{}),f=Array.isArray(b.defaults?.notifiers)?b.defaults.notifiers:[],g=Object.values(b.notificationRouting??{}).flatMap(a=>Array.isArray(a)?a:[]),h=f.includes(a)||g.includes(a),i=b.notifiers?.[a];for(let[b,c]of(i&&"object"==typeof i&&a6(a,a,i)&&d.set(a,i),e))c&&"object"==typeof c&&a6(a,b,c)&&d.set(b,c);return 0===d.size&&h&&!a7(a,b)&&d.set(a,{}),[...d.entries()].map(([d,e])=>({registrationName:d,config:function(a,b,c,d,e,f=!1){if("package"in d&&"path"in d)throw Error(`In ${a} "${c}": both "package" and "path" are specified. Use "package" for npm plugins or "path" for local plugins, not both.`);let g=!f&&a5.some(c=>c.slot===a&&c.name===b);if((d.package||g)&&"path"in d){let e=d.package?`npm package "${d.package}"`:`built-in plugin "${b}"`;throw Error(`In ${a} "${c}": "path" field conflicts with reserved plugin loading field. You're loading via ${e}, but also have a "path" field which would be stripped. Rename your configuration field to something else (e.g., "apiPath", "webhookPath").`)}let{plugin:h,package:i,path:j,...k}=d;return e?{...k,configPath:e}:k}("notifier",a,d,e,b.configPath,c)}))}(f.name,d,e);if(0===g.length){if(a7(f.name,d))return;b(f.slot,f.name,f,a.create(void 0));return}for(let[c,d]of g.entries()){let e=a.create(d.config);b(f.slot,d.registrationName,f,e),0===c&&d.registrationName!==f.name&&b(f.slot,f.name,f,e)}}return{register(a,c){let{manifest:d}=a,e=a.create(c);b(d.slot,d.name,d,e)},get(b,c){let d=a.get(`${b}:${c}`);return d?d.instance:null},list(b){let c=new Map;for(let[d,e]of a)d.startsWith(`${b}:`)&&!c.has(e.manifest.name)&&c.set(e.manifest.name,e.manifest);return[...c.values()]},async loadBuiltins(a,b){let d=b??(a=>import(a));for(let b of a5){let e;try{e=a9(await d(b.pkg))}catch{continue}if(e)try{a&&"notifier"===e.manifest.slot?c(e,a):this.register(e)}catch(c){let a=c instanceof Error?c.message:String(c);process.stderr.write(`[plugin-registry] Failed to load built-in plugin "${b.name}": ${c}
74
+ `),aa({source:"plugin-registry",kind:"plugin-registry.load_failed",level:"error",summary:`built-in plugin ${b.name} failed to load`,data:{plugin:b.name,slot:b.slot,pkg:b.pkg,builtin:!0,error:a}})}}},async loadFromConfig(a,b){await this.loadBuiltins(a,b);let d=b??(a=>import(a)),f=function(a){let b=new Map;if(!a)return b;for(let c of a){let a=c.package?`package:${c.package}`:`path:${c.path}`,d=b.get(a);d?d.push(c):b.set(a,[c])}return b}(a._externalPluginEntries);for(let b of a.plugins??[]){if(!1===b.enabled)continue;let i=function(a,b){switch(a.source){case"local":{if(!a.path)return null;let c=function(a){let b;if(!(0,e.existsSync)(a))return null;try{b=(0,e.statSync)(a)}catch{return null}if(b.isFile())return a;if(!b.isDirectory())return null;let c=(0,g.join)(a,"package.json");if((0,e.existsSync)(c))try{let b=(0,e.readFileSync)(c,"utf-8"),d=JSON.parse(b),f=function(a){if("string"==typeof a)return a;if(!a||"object"!=typeof a)return null;let b=a["."];if("string"==typeof b)return b;if(b&&"object"==typeof b){let a=b.import;if("string"==typeof a)return a;let c=b.default;if("string"==typeof c)return c}let c=a.import;if("string"==typeof c)return c;let d=a.default;return"string"==typeof d?d:null}(d.exports);if(f){let b=(0,g.resolve)(a,f);if((0,e.existsSync)(b))return b}if("string"==typeof d.module){let b=(0,g.resolve)(a,d.module);if((0,e.existsSync)(b))return b}if("string"==typeof d.main){let b=(0,g.resolve)(a,d.main);if((0,e.existsSync)(b))return b}}catch{}for(let b of a4){let c=(0,g.join)(a,b);if((0,e.existsSync)(c))return c}return null}(function(a,b){if((0,g.isAbsolute)(a))return a;let c=b?(0,g.dirname)(b):process.cwd();return(0,g.resolve)(c,a)}(a.path,b.configPath));return c?(0,a3.pathToFileURL)(c).href:null}case"registry":case"npm":var c;return a.package??(!(c=a.name)||c.startsWith(".")||c.startsWith("/")?null:c.startsWith("@")||c.includes("/")?c:null);default:return null}}(b,a);if(!i){process.stderr.write(`[plugin-registry] Could not resolve specifier for plugin "${b.name}" (source: ${b.source})
75
+ `),aa({source:"plugin-registry",kind:"plugin-registry.specifier_failed",level:"error",summary:`could not resolve specifier for plugin ${b.name}`,data:{plugin:b.name,source:b.source??null}});continue}try{let e=a9(await d(i));if(!e)continue;for(let c of b.package?f.get(`package:${b.package}`)??[]:b.path?f.get(`path:${b.path}`)??[]:[])try{var h=e.manifest;if(c.expectedPluginName&&c.expectedPluginName!==h.name){let a=c.package?"package":"path";throw Error(`Plugin manifest.name mismatch at ${c.source}: expected "${c.expectedPluginName}" but ${a} "${i}" has manifest.name "${h.name}". Either update the 'plugin' field to match the actual manifest.name, or remove it to auto-infer.`)}!function(a,b,c){let{location:d,slot:e,source:f}=b;if("project"===d.kind){let{projectId:b,configType:e}=d,f=c.projects[b];f?.[e]&&(f[e].plugin=a.name)}else if("notifier"===d.kind){let{notifierId:b}=d,e=c.notifiers[b];e&&(e.plugin=a.name)}a.slot!==e&&process.stderr.write(`[plugin-registry] Plugin at ${f} has slot "${a.slot}" but was configured as "${e}". The plugin will be registered under its declared slot "${a.slot}".
76
+ `)}(e.manifest,c,a)}catch(d){let a=d instanceof Error?d.message:String(d);process.stderr.write(`[plugin-registry] Config validation failed for ${c.source}: ${d}
77
+ `),aa({source:"plugin-registry",kind:"plugin-registry.validation_failed",level:"error",summary:`plugin manifest validation failed for ${b.name}`,data:{plugin:b.name,externalSource:c.source,specifier:i,manifestName:e.manifest.name,manifestSlot:e.manifest.slot,error:a}})}"notifier"===e.manifest.slot?c(e,a,!0):this.register(e)}catch(c){let a=c instanceof Error?c.message:String(c);process.stderr.write(`[plugin-registry] Failed to load plugin "${i}": ${c}
78
+ `),aa({source:"plugin-registry",kind:"plugin-registry.load_failed",level:"error",summary:`external plugin ${b.name} failed to load`,data:{plugin:b.name,specifier:i,source:b.source??null,builtin:!1,error:a}})}}}}}let bb=/\/(\d+)$/;function bc(a){let b=function(a){try{return new URL(a)}catch{return null}}(a),c=b?.pathname.split("/").filter(Boolean)??[],d=c.findIndex(a=>"pull"===a);if(d>=2&&d+1<c.length){let b=c[d-2],e=c[d-1],f=c[d+1];if(b&&e&&f&&/^\d+$/.test(f))return{owner:b,repo:e,number:Number.parseInt(f,10),url:a}}let e=c.findIndex((a,b)=>"-"===a&&"merge_requests"===c[b+1]&&b>=2&&b+2<c.length);if(e>=2){let b=c[e-2],d=c[e-1],f=c[e+2];if(b&&d&&f&&/^\d+$/.test(f))return{owner:b,repo:d,number:Number.parseInt(f,10),url:a}}let f=a.match(bb);return f?{owner:"",repo:"",number:parseInt(f[1],10),url:a}:null}function bd(a){let b=new Set,c=[];for(let d of a){let a=function(a){let b=bc(a.url),c=a.owner||b?.owner||"",d=a.repo||b?.repo||"",e=a.number||b?.number||0;return c&&d&&e>0?`${c}/${d}#${e}`:`url:${a.url}`}(d);b.has(a)||(b.add(a),c.push(d))}return c}function be(a){let b=new Set,c=[];for(let d of a){let a=d.trim();if(!a)continue;let e=bc(a),f=e&&e.owner&&e.repo&&e.number>0?`${e.owner}/${e.repo}#${e.number}`:`url:${a}`;b.has(f)||(b.add(f),c.push(a))}return c}let bf=new Set(["spawning","working","detecting","pr_open","ci_failed","review_pending","changes_requested","approved","mergeable","merged","cleanup","needs_input","stuck","errored","killed","idle","done","terminated"]);function bg(a){try{return JSON.parse(a)}catch{return null}}function bh(a){return"starting"===a?"working":a&&bf.has(a)?a:"spawning"}let bi=k.Yj().nullable(),bj=k.Ik({id:k.Yj(),runtimeName:k.Yj(),data:k.vk(a=>null===a||"object"!=typeof a||Array.isArray(a)?{}:a,k.g1(k.L5()))}),bk=k.Ik({version:k.eu(2),session:k.Ik({kind:k.k5(["worker","orchestrator"]),state:k.k5(["not_started","working","idle","needs_input","stuck","detecting","done","terminated"]),reason:k.k5(["spawn_requested","agent_acknowledged","task_in_progress","pr_created","pr_closed_waiting_decision","fixing_ci","resolving_review_comments","awaiting_user_input","awaiting_external_review","research_complete","merged_waiting_decision","manually_killed","runtime_lost","agent_process_exited","probe_failure","error_in_process","auto_cleanup","pr_merged"]),startedAt:bi,completedAt:bi,terminatedAt:bi,lastTransitionAt:k.Yj()}).partial().optional(),pr:k.Ik({state:k.k5(["none","open","merged","closed"]),reason:k.k5(["not_created","in_progress","ci_failing","review_pending","changes_requested","approved","merge_ready","merged","closed_unmerged","cleared_on_restore"]),number:k.ai().int().nullable(),url:k.Yj().nullable(),lastObservedAt:bi}).partial().optional(),runtime:k.Ik({state:k.k5(["unknown","alive","exited","missing","probe_failed"]),reason:k.k5(["spawn_incomplete","process_running","process_missing","tmux_missing","manual_kill_requested","probe_error","pr_merged_cleanup","auto_cleanup"]),lastObservedAt:bi,handle:bj.nullable(),tmuxName:k.Yj().nullable()}).partial().optional()}),bl=new Set(["done","terminated"]);function bm(a){bl.has(a.session.state)||(a.session.completedAt=null,a.session.terminatedAt=null)}function bn(a,b=null){if("string"!=typeof a)return b;let c=Date.parse(a);return Number.isNaN(c)?b:new Date(c).toISOString()}function bo(a,b=new Date){return{version:2,session:{kind:a,state:"not_started",reason:"spawn_requested",startedAt:null,completedAt:null,terminatedAt:null,lastTransitionAt:b.toISOString()},pr:{state:"none",reason:"not_created",number:null,url:null,lastObservedAt:null},runtime:{state:"unknown",reason:"spawn_incomplete",lastObservedAt:null,handle:null,tmuxName:null}}}function bp(a,b={}){let c=b.status??bh(a.status),d=b.sessionKind??("orchestrator"===a.role||b.sessionId?.endsWith("-orchestrator")?"orchestrator":"worker"),e=b.createdAt?.toISOString()??bn(a.createdAt,new Date().toISOString())??new Date().toISOString(),f=function(a){switch(a){case"spawning":return{state:"not_started",reason:"spawn_requested"};case"needs_input":return{state:"needs_input",reason:"awaiting_user_input"};case"stuck":return{state:"stuck",reason:"probe_failure"};case"errored":return{state:"terminated",reason:"error_in_process"};case"killed":case"terminated":case"cleanup":return{state:"terminated",reason:"manually_killed"};case"done":return{state:"done",reason:"research_complete"};case"merged":return{state:"idle",reason:"merged_waiting_decision"};case"idle":return{state:"idle",reason:"awaiting_external_review"};default:return{state:"working",reason:"task_in_progress"}}}(c),g=function(a,b){let c=a.pr??null;if(!c)return"merged"===b?{state:"merged",reason:"merged",number:null,url:null}:{state:"none",reason:"not_created",number:null,url:null};let d=bc(c);return{state:"merged"===b?"merged":"open",reason:"merged"===b?"merged":"in_progress",number:d?.number??null,url:c}}(a,c),h=function(a,b){let c=a.tmuxName?.trim()||null,d=b??(a.runtimeHandle?bg(a.runtimeHandle):null);return d||c?{state:"unknown",reason:"spawn_incomplete",handle:d??null,tmuxName:c}:{state:"unknown",reason:"spawn_incomplete",handle:null,tmuxName:null}}(a,b.runtimeHandle??null);return{version:2,session:{kind:d,state:f.state,reason:f.reason,startedAt:"spawning"===c?null:e,completedAt:"done"===c?e:null,terminatedAt:"killed"===c||"terminated"===c||"cleanup"===c?e:null,lastTransitionAt:e},pr:{state:g.state,reason:g.reason,number:g.number,url:g.url,lastObservedAt:g.url?e:null},runtime:{state:h.state,reason:h.reason,lastObservedAt:h.handle||h.tmuxName?e:null,handle:h.handle,tmuxName:h.tmuxName}}}function bq(a,b={}){let c=a.lifecycle?bg(a.lifecycle):a.statePayload&&"2"===a.stateVersion?bg(a.statePayload):null,d=bk.safeParse(c);return d.success?function(a,b,c={}){let d=bp(b,c),e=a.session,f=a.pr,g=a.runtime,h=Object.hasOwn(e??{},"kind"),i=Object.hasOwn(e??{},"state"),j=Object.hasOwn(e??{},"reason"),k=Object.hasOwn(e??{},"startedAt"),l=Object.hasOwn(e??{},"completedAt"),m=Object.hasOwn(e??{},"terminatedAt"),n=Object.hasOwn(e??{},"lastTransitionAt"),o=Object.hasOwn(f??{},"state"),p=Object.hasOwn(f??{},"reason"),q=Object.hasOwn(f??{},"number"),r=Object.hasOwn(f??{},"url"),s=Object.hasOwn(f??{},"lastObservedAt"),t=Object.hasOwn(g??{},"state"),u=Object.hasOwn(g??{},"reason"),v=Object.hasOwn(g??{},"lastObservedAt"),w=Object.hasOwn(g??{},"handle"),x=Object.hasOwn(g??{},"tmuxName");return{version:2,session:{kind:h?e?.kind==="orchestrator"?"orchestrator":"worker":d.session.kind,state:i?e?.state??d.session.state:d.session.state,reason:j?e?.reason??d.session.reason:d.session.reason,startedAt:k?bn(e?.startedAt):d.session.startedAt,completedAt:l?bn(e?.completedAt):d.session.completedAt,terminatedAt:m?bn(e?.terminatedAt):d.session.terminatedAt,lastTransitionAt:n?bn(e?.lastTransitionAt,d.session.lastTransitionAt)??d.session.lastTransitionAt:d.session.lastTransitionAt},pr:{state:o?f?.state??d.pr.state:d.pr.state,reason:p?f?.reason??d.pr.reason:d.pr.reason,number:q?"number"==typeof f?.number?f.number:null:d.pr.number,url:r?"string"==typeof f?.url?f.url:null:d.pr.url,lastObservedAt:s?bn(f?.lastObservedAt):d.pr.lastObservedAt},runtime:{state:t?g?.state??d.runtime.state:d.runtime.state,reason:u?g?.reason??d.runtime.reason:d.runtime.reason,lastObservedAt:v?bn(g?.lastObservedAt):d.runtime.lastObservedAt,handle:w?function(a){if(!a||"object"!=typeof a||"string"!=typeof a.id||"string"!=typeof a.runtimeName)return null;let b=a.data;return{id:a.id,runtimeName:a.runtimeName,data:b&&"object"==typeof b?b:{}}}(g?.handle):d.runtime.handle,tmuxName:x?"string"==typeof g?.tmuxName?g.tmuxName:null:d.runtime.tmuxName}}}(d.data,a,b):bp(a,b)}function br(a){switch(a.session.state){case"not_started":return"spawning";case"needs_input":return"needs_input";case"stuck":return"stuck";case"done":return"done";case"terminated":switch(a.session.reason){case"manually_killed":case"runtime_lost":return"killed";case"auto_cleanup":case"pr_merged":return"cleanup";case"error_in_process":case"probe_failure":return"errored";default:return"terminated"}case"detecting":return"detecting"}return"merged"===a.pr.state?"merged":"open"===a.pr.state?"ci_failing"===a.pr.reason?"ci_failed":"changes_requested"===a.pr.reason?"changes_requested":"review_pending"===a.pr.reason?"review_pending":"approved"===a.pr.reason?"approved":"merge_ready"===a.pr.reason?"mergeable":"pr_open":"idle"===a.session.state?"idle":"working"}function bs(a){return{lifecycle:JSON.stringify(a),pr:a.pr.url??"",runtimeHandle:a.runtime.handle?JSON.stringify(a.runtime.handle):"",tmuxName:a.runtime.tmuxName??"",role:"orchestrator"===a.session.kind?"orchestrator":""}}function bt(a){return{version:2,session:{...a.session},pr:{...a.pr},runtime:{...a.runtime,handle:a.runtime.handle?{id:a.runtime.handle.id,runtimeName:a.runtime.handle.runtimeName,data:structuredClone(a.runtime.handle.data)}:null}}}let bu=/^[a-zA-Z0-9_-]+$/;function bv(a,b="session ID"){if(!bu.test(a))throw Error(`Invalid ${b}: ${a}`)}function bw(a){let b={};for(let[c,d]of Object.entries(a))null!=d&&("object"==typeof d?b[c]=JSON.stringify(d):b[c]=String(d));return b}let bx=".json";function by(a){return JSON.stringify(a,null,2)+"\n"}function bz(a){try{let b=JSON.parse(a);if("object"!=typeof b||null===b||Array.isArray(b))return null;return b}catch{return null}}function bA(a,b){return bv(b),(0,g.join)(a,`${b}${bx}`)}function bB(a,b){let c,d=bA(a,b);try{c=(0,e.readFileSync)(d,"utf-8").trim()}catch{return null}if(!c)return null;let f=bz(c);if(!f)return null;if(f.lifecycle||f.statePayload&&"2"===f.stateVersion){let a=function(a){if(a.lifecycle&&"object"==typeof a.lifecycle)return a.lifecycle;if(a.statePayload&&"2"===a.stateVersion){if("object"==typeof a.statePayload)return a.statePayload;if("string"==typeof a.statePayload)try{return JSON.parse(a.statePayload)}catch{}}}(f);a&&(f.status=br(a))}return bw(f)}let bC=new Set(["runtimeHandle","lifecycle","statePayload","dashboard","agentReport","reportWatcher"]);function bD(a,b,c){let d=bA(a,b);(0,e.mkdirSync)((0,g.dirname)(d),{recursive:!0});let f={worktree:c.worktree,branch:c.branch,...c.lifecycle?{}:{status:c.status}};c.tmuxName&&(f.tmuxName=c.tmuxName),c.issue&&(f.issue=c.issue),c.issueTitle&&(f.issueTitle=c.issueTitle),c.pr&&(f.pr=c.pr),void 0!==c.prAutoDetect&&(f.prAutoDetect=c.prAutoDetect),c.summary&&(f.summary=c.summary),c.project&&(f.project=c.project),c.agent&&(f.agent=c.agent),c.createdAt&&(f.createdAt=c.createdAt),c.runtimeHandle&&(f.runtimeHandle=c.runtimeHandle),c.lifecycle&&(f.lifecycle=c.lifecycle),c.restoredAt&&(f.restoredAt=c.restoredAt),c.role&&(f.role=c.role),c.dashboard&&(f.dashboard=c.dashboard),c.opencodeSessionId&&(f.opencodeSessionId=c.opencodeSessionId),c.pinnedSummary&&(f.pinnedSummary=c.pinnedSummary),c.userPrompt&&(f.userPrompt=c.userPrompt),c.displayName&&(f.displayName=c.displayName),void 0!==c.displayNameUserSet&&(f.displayNameUserSet=c.displayNameUserSet),N(d,by(f))}function bE(a,b,c){bG(a,b,a=>bF(a,c),{createIfMissing:!0})}function bF(a,b){let c={...a};for(let[a,d]of Object.entries(b))if(void 0!==d)if(""===d){let{[a]:b,...d}=c;c=d}else c[a]=d;return c}function bG(a,b,c,d={}){let f=bA(a,b);return Q(`${f}.lock`,()=>{let h,i={};try{h=(0,e.readFileSync)(f,"utf-8").trim()}catch{}if(void 0!==h){if(h){let c=bz(h);if(c)i=bw(c);else{let c=`${f}.corrupt-${Date.now()}`,i=!1;try{(0,e.renameSync)(f,c),i=!0,console.warn(`[metadata] corrupt JSON at ${f}; preserved as ${c} before rewriting`)}catch{}let j=h.length>200?h.slice(0,200):h,k=(0,g.basename)((0,g.dirname)(a)),l=i?`Corrupt metadata for session ${b} renamed to ${(0,g.basename)(c)}`:`Corrupt metadata detected for session ${b}; failed to rename forensic copy before rewrite`;aa({projectId:k||void 0,sessionId:b,source:d.activityEventSource??"session-manager",kind:"metadata.corrupt_detected",level:"error",summary:l,data:{path:f,renamedTo:i?c:null,renameSucceeded:i,contentSample:j,contentLength:h.length}})}}}else if(!d.createIfMissing)return null;let j=Object.fromEntries(Object.entries(c({...i})).filter(([,a])=>void 0!==a&&""!==a));return(0,e.mkdirSync)((0,g.dirname)(f),{recursive:!0}),N(f,by(function(a){let b={},c=new Set(["dashboardPort","terminalWsPort","directTerminalWsPort"]),d=new Set(["prAutoDetect","displayNameUserSet"]);for(let[e,f]of Object.entries(a))if(void 0!==f&&""!==f)if(d.has(e))b[e]="on"===f||"true"===f||"off"!==f&&"false"!==f&&f;else if(c.has(e)){let a=Number(f);b[e]=Number.isFinite(a)?a:f}else if(bC.has(e)&&(f.startsWith("{")||f.startsWith("[")))try{b[e]=JSON.parse(f)}catch{b[e]=f}else b[e]=f;return b}(j))),j},{timeoutMs:5e3,staleMs:3e4})}function bH(a,b){let c=bA(a,b);if((0,e.existsSync)(c))try{(0,e.unlinkSync)(c)}catch{}}function bI(a){return(0,e.existsSync)(a)?(0,e.readdirSync)(a).filter(b=>{if(!b.endsWith(bx))return!1;let c=b.slice(0,-bx.length);if(!c||c.startsWith(".")||!bu.test(c))return!1;try{return(0,e.statSync)((0,g.join)(a,b)).isFile()}catch{return!1}}).map(a=>a.slice(0,-bx.length)):[]}function bJ(a,b){let c=bA(a,b);(0,e.mkdirSync)((0,g.dirname)(c),{recursive:!0});try{let a=(0,e.openSync)(c,e.constants.O_WRONLY|e.constants.O_CREAT|e.constants.O_EXCL);return(0,e.closeSync)(a),!0}catch{return!1}}function bK(a,b,c,e){return(0,d.tT)({id:a,metadata:b},c,e)?"orchestrator":"worker"}function bL(a){let{role:b,project:c,defaults:e,persistedAgent:f,spawnAgentOverride:g}=a,h="orchestrator"===b?c.orchestrator:c.worker,i="orchestrator"===b?e.orchestrator:e.worker,j=c.agentConfig??{},k=h?.agentConfig??{},l=f||("worker"===b?g??h?.agent??c.agent??i?.agent??e.agent:h?.agent??c.agent??i?.agent??e.agent),m={...j};for(let[a,b]of Object.entries(k))void 0!==b&&(m[a]=b);let n="orchestrator"===b?k.orchestratorModel??k.model??j.orchestratorModel??j.model:k.model??j.model;void 0!==n&&(m.model=n);let o=(0,d.DD)("string"==typeof m.permissions?m.permissions:void 0);void 0!==o&&(m.permissions=o);let p="string"==typeof m.subagent?m.subagent:void 0;return{role:b,agentName:l,agentConfig:m,model:n,permissions:o,subagent:p}}let bM=new Set(["active","ready","idle","blocked"]),bN=new Set(["active","ready"]),bO=new Set(["idle","blocked"]);function bP(a,b=new Date){if(!a)return"none";let c=Math.max(0,b.getTime()-a.getTime());return c<=6e4?"strong":c<=3e5?"weak":"stale"}function bQ(a,b={}){return{state:a,activity:b.activity??null,timestamp:b.timestamp,source:b.source??"none",detail:b.detail}}function bR(a,b,c=new Date){return bM.has(a.state)?!a.timestamp&&bO.has(a.state)?bQ("stale",{activity:a.state,source:b,detail:"missing_timestamp"}):a.timestamp?bN.has(a.state)&&"stale"===bP(a.timestamp,c)?bQ("stale",{activity:a.state,timestamp:a.timestamp,source:b,detail:"stale_timestamp"}):bQ("valid",{activity:a.state,timestamp:a.timestamp,source:b}):bQ("valid",{activity:a.state,source:b}):bQ("valid",{activity:a.state,timestamp:a.timestamp,source:b})}function bS(a){return"valid"===a.state&&a.timestamp instanceof Date&&null!==a.activity&&bO.has(a.activity)}function bT(a){let b="none"===a.source?"":` via_${a.source}`,c=a.activity?` activity=${a.activity}`:"",d=a.timestamp?` at=${a.timestamp.toISOString()}`:"",e=a.detail?` detail=${a.detail}`:"";return`activity_signal=${a.state}${b}${c}${d}${e}`}var bU=c(51455);let bV=["started","working","waiting","needs_input","fixing_ci","addressing_reviews","pr_created","draft_pr_created","ready_for_review","completed"],bW={STATE:"agentReportedState",AT:"agentReportedAt",NOTE:"agentReportedNote",PR_NUMBER:"agentReportedPrNumber",PR_URL:"agentReportedPrUrl",PR_IS_DRAFT:"agentReportedPrIsDraft"};async function bX(a,b){let c=function(a,b){return bv(b),(0,g.join)((0,g.join)(a,".agent-report-audit"),`${b}.ndjson`)}(a,b);return(0,e.existsSync)(c)?(await (0,bU.readFile)(c,"utf8")).split("\n").map(a=>a.trim()).filter(a=>a.length>0).flatMap(a=>{try{let b=JSON.parse(a);if("string"!=typeof b.timestamp||"string"!=typeof b.actor||"acknowledge"!==b.source&&"report"!==b.source||!bV.includes(b.reportState)||"boolean"!=typeof b.accepted||!b.before||!b.after)return[];return[b]}catch{return[]}}).reverse():[]}function bY(a){if(!a)return null;let b=a[bW.STATE],c=a[bW.AT];if(!b||!c||!bV.includes(b))return null;let d=Date.parse(c);if(Number.isNaN(d))return null;let e=a[bW.NOTE],f=a[bW.PR_NUMBER],g=f&&/^\d+$/.test(f)?Number.parseInt(f,10):void 0,h=a[bW.PR_URL]||void 0,i=a[bW.PR_IS_DRAFT];return{state:b,timestamp:new Date(d).toISOString(),note:e&&e.length>0?e:void 0,prNumber:g,prUrl:h,prIsDraft:"true"===i||"false"!==i&&void 0}}function bZ(a,b,c={}){let d=void 0!==c.runtimeHandle?c.runtimeHandle:b.runtimeHandle?bg(b.runtimeHandle):null,e=bq(b,{sessionId:a,status:c.status??bh(b.status),runtimeHandle:d,createdAt:c.createdAt,sessionKind:c.sessionKind}),f=c.status??br(e),g=e.pr.url??b.pr,h="true"===b[bW.PR_IS_DRAFT],i=(a,c=!1,d)=>{let e=bc(a);return{number:e?.number||d||0,url:a,title:"",owner:e?.owner??"",repo:e?.repo??"",branch:b.branch??"",baseBranch:"",isDraft:c}},j=b.prs,k=e.pr.number??null,l=bd(j?j.split(",").map((a,b)=>i(a.trim(),0===b&&h,0===b?k:null)).filter(a=>!!a.url):g?[i(g,h,k)]:[]);return{id:a,projectId:b.project??c.projectId??"",status:f,activity:c.activity??null,activitySignal:c.activitySignal?c.activitySignal:void 0===c.activity||null===c.activity?bQ("unavailable"):bQ("valid",{activity:c.activity,timestamp:c.lastActivityAt,source:"exited"===c.activity?"runtime":"native"}),lifecycle:e,branch:b.branch||null,issueId:b.issue||null,pr:l[0]??null,prs:l,workspacePath:b.worktree||c.workspacePathFallback||null,runtimeHandle:e.runtime.handle??d,agentInfo:b.summary?{summary:b.summary,agentSessionId:null}:null,createdAt:b.createdAt?new Date(b.createdAt):c.createdAt??new Date,lastActivityAt:c.lastActivityAt??new Date,restoredAt:c.restoredAt??(b.restoredAt?new Date(b.restoredAt):void 0),metadata:b}}let b$=/^[a-zA-Z0-9][a-zA-Z0-9._-]*$/;function b_(a,b){if(!a||"."===a||".."===a||!b$.test(a))throw Error(`Unsafe ${b}: "${a}"`)}function b0(a){if("string"!=typeof a)return;let b=Date.parse(a);return Number.isNaN(b)?void 0:new Date(b).toISOString()}function b1(a){return"object"==typeof a&&null!==a&&!Array.isArray(a)}function b2(a){return"number"==typeof a&&Number.isFinite(a)?a:void 0}function b3(a){return"string"==typeof a&&a.trim().length>0?a:void 0}function b4(a){try{return JSON.parse((0,e.readFileSync)(a,"utf-8"))}catch{return null}}function b5(a,b){N(a,`${JSON.stringify(b,null,2)}
79
+ `)}function b6(a){return Object.fromEntries(Object.entries(a).filter(([,a])=>void 0!==a))}function b7(a,b){return Date.parse(b.updatedAt)-Date.parse(a.updatedAt)||Date.parse(b.createdAt)-Date.parse(a.createdAt)||a.id.localeCompare(b.id)}function b8(a,b){if(!b1(b))return null;let c=b3(b.id),d=b3(b.linkedSessionId),e=b3(b.reviewerSessionId),f=b0(b.createdAt),g=b0(b.updatedAt)??f;return c&&d&&e&&f&&g?b6({id:c,projectId:b3(b.projectId)??a,linkedSessionId:d,reviewerSessionId:e,status:function(a){switch(a){case"queued":case"preparing":case"running":case"needs_triage":case"sent_to_agent":case"waiting_update":case"clean":case"outdated":case"failed":case"cancelled":return a;default:return"queued"}}(b.status),createdAt:f,updatedAt:g,startedAt:b0(b.startedAt),completedAt:b0(b.completedAt),targetSha:b3(b.targetSha),baseSha:b3(b.baseSha),prNumber:b2(b.prNumber),prUrl:b3(b.prUrl),reviewerWorkspacePath:b3(b.reviewerWorkspacePath),summary:b3(b.summary),terminationReason:b3(b.terminationReason)}):null}function b9(a,b){if(!b1(b))return null;let c=b3(b.id),d=b3(b.runId),e=b3(b.linkedSessionId),f=b3(b.title),g=b3(b.body),h=b0(b.createdAt),i=b0(b.updatedAt)??h;return c&&d&&e&&f&&g&&h&&i?b6({id:c,projectId:b3(b.projectId)??a,runId:d,linkedSessionId:e,status:function(a){switch(a){case"dismissed":case"sent_to_agent":case"resolved":return a;default:return"open"}}(b.status),severity:function(a){switch(a){case"error":case"warning":case"info":return a;default:return"warning"}}(b.severity),title:f,body:g,filePath:b3(b.filePath),startLine:b2(b.startLine),endLine:b2(b.endLine),category:b3(b.category),confidence:b2(b.confidence),fingerprint:b3(b.fingerprint),createdAt:h,updatedAt:i,dismissedAt:b0(b.dismissedAt),dismissedBy:b3(b.dismissedBy),sentToAgentAt:b0(b.sentToAgentAt)}):null}class ca{constructor(a,b={}){this.projectId=a,this.storeDir=b.storeDir??x(a)}get runsDir(){return(0,g.join)(this.storeDir,"runs")}get findingsDir(){return(0,g.join)(this.storeDir,"findings")}ensure(){(0,e.mkdirSync)(this.runsDir,{recursive:!0}),(0,e.mkdirSync)(this.findingsDir,{recursive:!0})}listRuns(a={}){return this.readAllRuns().filter(b=>!a.linkedSessionId||b.linkedSessionId===a.linkedSessionId).filter(b=>!a.status||b.status===a.status).sort(b7)}listRunSummaries(a={}){let b=this.listFindings(),c=new Map;for(let a of b){let b=c.get(a.runId)??{findingCount:0,openFindingCount:0,dismissedFindingCount:0,sentFindingCount:0,resolvedFindingCount:0};b.findingCount++,"open"===a.status&&b.openFindingCount++,"dismissed"===a.status&&b.dismissedFindingCount++,"sent_to_agent"===a.status&&b.sentFindingCount++,"resolved"===a.status&&b.resolvedFindingCount++,c.set(a.runId,b)}return this.listRuns(a).map(a=>({...a,...c.get(a.id)??{findingCount:0,openFindingCount:0,dismissedFindingCount:0,sentFindingCount:0,resolvedFindingCount:0}}))}getRun(a){return b_(a,"review run id"),b8(this.projectId,b4(this.runPath(a)))}createRun(a,b=new Date){let c=`review-run-${(0,f.randomUUID)()}`,d=b.toISOString(),e=b6({id:c,projectId:this.projectId,linkedSessionId:a.linkedSessionId,reviewerSessionId:a.reviewerSessionId,status:a.status??"queued",createdAt:d,updatedAt:d,startedAt:"running"===a.status?d:void 0,targetSha:a.targetSha,baseSha:a.baseSha,prNumber:a.prNumber,prUrl:a.prUrl,reviewerWorkspacePath:a.reviewerWorkspacePath,summary:a.summary});return this.writeRun(e),e}updateRun(a,b,c=new Date){let d=this.getRun(a);if(!d)throw Error(`Code review run not found: ${a}`);let e=b6({...d,...b,id:d.id,projectId:d.projectId,createdAt:d.createdAt,updatedAt:c.toISOString()});return this.writeRun(e),e}listFindings(a={}){return this.readAllFindings().filter(b=>!a.runId||b.runId===a.runId).filter(b=>!a.linkedSessionId||b.linkedSessionId===a.linkedSessionId).filter(b=>!a.status||b.status===a.status).sort(b7)}getFinding(a){return b_(a,"review finding id"),b9(this.projectId,b4(this.findingPath(a)))}createFinding(a,b=new Date){if(!this.getRun(a.runId))throw Error(`Code review run not found: ${a.runId}`);let c=`review-finding-${(0,f.randomUUID)()}`,d=b.toISOString(),e=b6({id:c,projectId:this.projectId,runId:a.runId,linkedSessionId:a.linkedSessionId,status:a.status??"open",severity:a.severity,title:a.title,body:a.body,filePath:a.filePath,startLine:a.startLine,endLine:a.endLine,category:a.category,confidence:a.confidence,fingerprint:a.fingerprint,createdAt:d,updatedAt:d});return this.writeFinding(e),e}updateFinding(a,b,c=new Date){let d=this.getFinding(a);if(!d)throw Error(`Code review finding not found: ${a}`);let e=b6({...d,...b,id:d.id,projectId:d.projectId,runId:d.runId,linkedSessionId:d.linkedSessionId,createdAt:d.createdAt,updatedAt:c.toISOString()});return this.writeFinding(e),e}deleteAll(){(0,e.rmSync)(this.storeDir,{recursive:!0,force:!0})}runPath(a){return b_(a,"review run id"),(0,g.join)(this.runsDir,`${a}.json`)}findingPath(a){return b_(a,"review finding id"),(0,g.join)(this.findingsDir,`${a}.json`)}writeRun(a){this.ensure(),b5(this.runPath(a.id),a)}writeFinding(a){this.ensure(),b5(this.findingPath(a.id),a)}readAllRuns(){return this.readAllJsonFiles(this.runsDir).map(a=>b8(this.projectId,a)).filter(a=>null!==a)}readAllFindings(){return this.readAllJsonFiles(this.findingsDir).map(a=>b9(this.projectId,a)).filter(a=>null!==a)}readAllJsonFiles(a){return(0,e.existsSync)(a)?(0,e.readdirSync)(a,{withFileTypes:!0}).filter(a=>a.isFile()&&a.name.endsWith(".json")).map(b=>b4((0,g.join)(a,b.name))).filter(a=>null!==a):[]}}function cb(a,b={}){return new ca(a,b)}var cc=c(58500);let cd=/^[a-zA-Z0-9][a-zA-Z0-9._-]*$/;async function ce(a,b,d={}){let{execFile:e}=await Promise.resolve().then(c.t.bind(c,31421,19));return(0,E.promisify)(e)(a,b,{windowsHide:!0,...d})}async function cf(a,b,d={}){let{spawn:e}=await Promise.resolve().then(c.t.bind(c,31421,19));return new Promise((c,f)=>{let g=e(a,b,{cwd:d.cwd,env:d.env,shell:d.shell,windowsHide:d.windowsHide??!0,detached:!G(),stdio:["ignore","pipe","pipe"]}),h=d.maxBuffer??8388608,i="",j="",k=!1,l=a=>{k||(k=!0,o&&clearTimeout(o),a())},m=()=>void 0!==g.pid?L(g.pid).catch(()=>void 0):(g.kill("SIGTERM"),Promise.resolve()),n=(a,b,c)=>{let d=Error(a);d.code=b,d.signal=c,d.stdout=i,d.stderr=j,f(d)},o=d.timeout&&d.timeout>0?setTimeout(()=>{m().finally(()=>{l(()=>n(`Command timed out after ${d.timeout}ms`,null,"SIGTERM"))})},d.timeout):null,p=(a,b)=>{let c=b.toString();"stdout"===a?i+=c:j+=c,Buffer.byteLength(i)+Buffer.byteLength(j)<=h||(m(),l(()=>n(`Command output exceeded maxBuffer ${h}`)))};g.stdout?.on("data",a=>p("stdout",a)),g.stderr?.on("data",a=>p("stderr",a)),g.once("error",a=>l(()=>f(a))),g.once("close",(a,b)=>{l(()=>{if(0===a)return void c({stdout:i,stderr:j});n(`Command failed with code ${a??b??"unknown"}`,a,b)})})})}class cg extends Error{constructor(a){super(`Code review run not found: ${a}`),this.name="CodeReviewRunNotFoundError"}}class ch extends Error{constructor(a){super(`Code review run ${a.reviewerSessionId} is ${a.status}, not queued`),this.name="CodeReviewRunNotExecutableError",this.runId=a.id,this.reviewerSessionId=a.reviewerSessionId,this.status=a.status}}class ci extends Error{constructor(a){super(a),this.name="CodeReviewInvalidSessionError"}}class cj extends Error{constructor(a){super(`No open review findings to send for ${a.reviewerSessionId}.`),this.name="CodeReviewNoOpenFindingsError",this.runId=a.id,this.reviewerSessionId=a.reviewerSessionId}}function ck(a,b){return a.length>b?`${a.slice(0,b-1)}…`:a}function cl(a){return"number"==typeof a&&Number.isFinite(a)?a:void 0}function cm(a){return"object"!=typeof a||null===a||Array.isArray(a)?null:a}function cn(a,b){return"object"==typeof a&&null!==a&&"code"in a&&a.code===b}async function co({store:a,lockFileName:b,label:c}){(0,e.mkdirSync)(a.storeDir,{recursive:!0});let d=(0,g.join)(a.storeDir,b),f=Date.now();for(;;)try{let a=(0,e.openSync)(d,"wx");(0,e.writeFileSync)(a,`${process.pid}
80
+ ${new Date().toISOString()}
81
+ `);let b=!1;return()=>{if(!b){b=!0;try{(0,e.closeSync)(a)}catch{}try{(0,e.unlinkSync)(d)}catch{}}}}catch(a){if(!cn(a,"EEXIST"))throw a;try{if(Date.now()-(0,e.statSync)(d).mtimeMs>3e4){(0,e.unlinkSync)(d);continue}}catch(a){if(cn(a,"ENOENT"))continue}if(Date.now()-f>5e3)throw Error(`Timed out waiting for ${c} lock`,{cause:a});await (0,cc.setTimeout)(25)}}async function cp(a,b){let c=await co({store:a,lockFileName:".create-run.lock",label:"code review run creation"});try{return await b()}finally{c()}}async function cq(a,b,c){if(!b||"."===b||".."===b||!cd.test(b))throw Error(`Unsafe review run id: "${b}"`);let d=await co({store:a,lockFileName:`.execute-run-${b}.lock`,label:`code review run ${b} execution`});try{return await c()}finally{d()}}let cr=new Set(["queued","needs_triage","sent_to_agent","waiting_update","clean"]);function cs({store:a,existingRuns:b,linkedSessionId:c,targetSha:d,now:e}){if(!d)return 0;let f=0;for(let g of b)g.linkedSessionId===c&&g.targetSha&&g.targetSha!==d&&cr.has(g.status)&&(a.updateRun(g.id,{status:"outdated"},e),f++);return f}async function ct(a){let b=a.workspacePath;if(b)try{let{stdout:a}=await ce("git",["rev-parse","HEAD"],{cwd:b,timeout:5e3}),c=a.trim();return c.length>0?c:void 0}catch{return}}async function cu(a,b,c=3e4){let{stdout:d}=await ce("git",b,{cwd:a,timeout:c});return d.trim()}async function cv(a){if(a)try{return await cu(a,["rev-parse","HEAD"],5e3)}catch{return}}async function cw(a,b){if(!(0,e.existsSync)(b)){try{await cu(a,["worktree","prune"])}catch{}return}try{await cu(a,["worktree","remove","--force",b]);return}catch{try{await cu(a,["worktree","prune"])}catch{}(0,e.rmSync)(b,{recursive:!0,force:!0})}}async function cx({store:a,session:b,resolveTargetSha:c=ct,now:d=new Date}){let e=await c(b);return cs({store:a,existingRuns:a.listRuns({linkedSessionId:b.id}),linkedSessionId:b.id,targetSha:e,now:d})}async function cy({projectId:a,project:b,session:c,run:d}){let f=(0,g.join)(x(a),"workspaces"),h=(0,g.join)(f,d.reviewerSessionId);(0,e.mkdirSync)(f,{recursive:!0}),await cw(b.path,h);let i=d.targetSha??await cv(c.workspacePath)??"HEAD";return await cu(b.path,["worktree","add","--detach",h,i],6e4),h}async function cz(a){if(!(0,e.existsSync)(a))return null;try{return(0,e.readFileSync)(a,"utf-8")}catch{return null}}function cA(a){return async b=>{let c=K(),{stdout:d,stderr:e}=await ce(c.cmd,c.args(a),{cwd:b.workspacePath,timeout:6e5,maxBuffer:8388608,env:process.env});return{rawOutput:d.trim()||e.trim()}}}async function cB(a){let b=(0,g.join)(a.workspacePath,".ao-code-review-output.json"),c=`You are an AO reviewer agent. Review this repository snapshot for concrete bugs only.
82
+ Do not modify files. Do not publish comments anywhere.
83
+ Review the changes against base ref "${a.baseRef}". Start with: git diff --merge-base ${a.baseRef} HEAD -- .
84
+ If that diff command fails, inspect git status/log and compare this detached reviewer workspace to the base ref using read-only commands.
85
+ Linked coding worker: ${a.session.id}
86
+ Reviewer run: ${a.run.reviewerSessionId}
87
+ Base ref: ${a.baseRef}
88
+ Return only JSON using this schema:
89
+ {"findings":[{"severity":"warning|error|info","title":"short title","body":"specific issue and fix","filePath":"optional/path","startLine":1,"endLine":1,"confidence":0.8}]}
90
+ If there are no concrete bugs, return {"findings":[]}.`;try{let{stdout:d,stderr:e}=await cf("codex",["exec","--sandbox","read-only","--output-last-message",b,c],{cwd:a.workspacePath,timeout:6e5,maxBuffer:8388608,env:process.env,shell:G()});return{rawOutput:await cz(b)??(d.trim()||e.trim())}}catch(b){let a=b instanceof Error&&"stderr"in b&&"string"==typeof b.stderr?b.stderr.trim():b instanceof Error?b.message:String(b);throw Error(`Codex review failed: ${a}`,{cause:b})}}async function cC({config:a,sessionManager:b,storeFactory:c=cb,resolveTargetSha:e=ct,now:f=new Date},g){let h=await b.get(g.sessionId);if(!h)throw new d.Ag(g.sessionId);let i=a.projects[h.projectId];if(!i)throw new ci(`Unknown project for session ${h.id}: ${h.projectId}`);let j=i.sessionPrefix??h.projectId,k=Object.entries(a.projects).map(([a,b])=>b.sessionPrefix??a);if((0,d.tT)(h,j,k))throw new ci(`Cannot request code review for orchestrator session: ${h.id}`);let l=c(h.projectId),m=h.pr?.url??h.metadata.pr,n=h.pr?.number??function(a){if(!a)return;let b=a.match(/\/pull\/(\d+)(?:\D*$|$)/);if(!b)return;let c=Number.parseInt(b[1],10);return Number.isNaN(c)?void 0:c}(m),o=await e(h),p=g.requestedBy??"system";return cp(l,()=>{let a=l.listRuns(),b=function(a,b){let c=0,d=RegExp(`^${b.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}-rev-(\\d+)$`);for(let b of a){let a=b.reviewerSessionId.match(d);if(!a)continue;let e=Number.parseInt(a[1],10);!Number.isNaN(e)&&e>c&&(c=e)}return`${b}-rev-${c+1}`}(a,j);return cs({store:l,existingRuns:a,linkedSessionId:h.id,targetSha:o,now:f}),{...l.createRun({linkedSessionId:h.id,reviewerSessionId:b,status:g.status??"queued",targetSha:o,prNumber:n,prUrl:m,summary:g.summary??`Review requested from ${"cli"===p?"CLI":"web"===p?"dashboard":"automation"} for ${h.id}.`},f),findingCount:0,openFindingCount:0,dismissedFindingCount:0,sentFindingCount:0,resolvedFindingCount:0}})}function cD(a,b){let c=a.listRunSummaries().find(a=>a.id===b);if(!c)throw new cg(b);return c}async function cE({config:a,sessionManager:b,storeFactory:c=cb,prepareWorkspace:e=cy,runReviewer:f=cB,now:g=()=>new Date,force:h=!1},{projectId:i,runId:j}){let k=a.projects[i];if(!k)throw Error(`Unknown project: ${i}`);let l=c(i),m=await cq(l,j,async()=>{let a=function(a,b,c){let d=a.getRun(b);if(!d)throw new cg(b);if("preparing"===d.status||"running"===d.status||!c&&!["queued","failed"].includes(d.status))throw new ch(d);return d}(l,j,h),c=await b.get(a.linkedSessionId);if(!c)throw new d.Ag(a.linkedSessionId);let e=g();return{run:l.updateRun(a.id,{status:"preparing",startedAt:a.startedAt??e.toISOString(),completedAt:void 0,terminationReason:void 0},e),session:c}}),n=m.run,o=m.session;try{let b=await e({projectId:i,project:k,session:o,run:n});n=l.updateRun(n.id,{status:"running",reviewerWorkspacePath:b},g());let c=o.pr?.baseBranch?.trim()||k.defaultBranch,d=await f({config:a,project:k,session:o,run:n,workspacePath:b,baseRef:c}),h=d.findings??function(a){let b=a.trim();if(!b)return[];let c=function(a){let b=[function(a){let b=a.trim(),c=b.match(/^```(?:json)?\s*([\s\S]*?)\s*```$/i);return c?.[1]?.trim()??b}(a)],c=a.match(/```(?:json)?\s*([\s\S]*?)\s*```/i);for(let d of(c?.[1]&&b.push(c[1].trim()),a.split(/\r?\n/).map(a=>a.trim()).filter(Boolean).reverse()))(d.startsWith("{")||d.startsWith("["))&&b.push(d);for(let a of b)try{return JSON.parse(a)}catch{}return null}(b),d=cm(c),e=Array.isArray(c)?c:Array.isArray(d?.findings)?d.findings:null;return e?e.map((a,b)=>(function(a,b){let c=cm(a);if(!c)return null;let d="string"==typeof c.body?c.body.trim():"string"==typeof c.message?c.message.trim():"";if(!d)return null;let e="string"==typeof c.title&&c.title.trim()?c.title.trim():`Review finding ${b}`,f="string"==typeof c.filePath?c.filePath:"string"==typeof c.path?c.path:void 0;return{severity:function(a){switch(a){case"error":case"warning":case"info":return a;default:return"warning"}}(c.severity),title:ck(e,160),body:ck(d,12e3),filePath:f,startLine:cl(c.startLine??c.line),endLine:cl(c.endLine),category:"string"==typeof c.category?c.category:void 0,confidence:cl(c.confidence),fingerprint:"string"==typeof c.fingerprint?c.fingerprint:void 0}})(a,b+1)).filter(a=>null!==a):/^no findings?\.?$/i.test(b)?[]:[{severity:"warning",title:"Reviewer output",body:ck(b,12e3)}]}(d.rawOutput??"");for(let a of h)l.createFinding({runId:n.id,linkedSessionId:n.linkedSessionId,severity:a.severity??"warning",title:a.title?.trim()||"Review finding",body:a.body?.trim()||"Reviewer reported an issue without details.",filePath:a.filePath,startLine:a.startLine,endLine:a.endLine,category:a.category,confidence:a.confidence,fingerprint:a.fingerprint},g());let j=g();l.updateRun(n.id,{status:h.length>0?"needs_triage":"clean",completedAt:j.toISOString(),summary:d.summary??n.summary,terminationReason:void 0},j)}catch(b){let a=g();l.updateRun(n.id,{status:"failed",completedAt:a.toISOString(),terminationReason:b instanceof Error?b.message:String(b)},a)}return cD(l,n.id)}async function cF({config:a,sessionManager:b,storeFactory:c=cb,now:e=()=>new Date},{projectId:f,runId:g}){if(!a.projects[f])throw Error(`Unknown project: ${f}`);let h=c(f),i=h.getRun(g);if(!i)throw new cg(g);let j=await b.get(i.linkedSessionId);if(!j)throw new d.Ag(i.linkedSessionId);let k=h.listFindings({runId:i.id,status:"open"});if(0===k.length)throw new cj(i);let l=function({run:a,findings:b,session:c}){let d=a.prNumber?`PR #${a.prNumber}${a.prUrl?` (${a.prUrl})`:""}`:a.prUrl?`PR ${a.prUrl}`:"the current PR",e=a.targetSha?`
91
+ Target SHA reviewed: ${a.targetSha}`:"";return[`AO reviewer ${a.reviewerSessionId} found ${b.length} open issue${1===b.length?"":"s"} for ${d}.`,`Linked coding worker: ${c.id}`,`Review run: ${a.id}${e}`,"\nPlease address each finding below. Verify each issue against the current source before editing, then update the PR branch and push your fixes.\nWhen you start working on these, report `athene report addressing-reviews`. When the fixes are ready for another review, report `athene report ready-for-review`.\n\nFindings:",b.map((a,b)=>(function(a,b){let c=[`${b}. [${a.severity}] ${a.title}`],d=a.filePath?void 0===a.startLine?a.filePath:void 0!==a.endLine&&a.endLine!==a.startLine?`${a.filePath}:${a.startLine}-${a.endLine}`:`${a.filePath}:${a.startLine}`:null;return d&&c.push(` Location: ${d}`),void 0!==a.confidence&&c.push(` Confidence: ${a.confidence}`),c.push(" Details:"),c.push(...a.body.split(/\r?\n/).map(a=>` ${a}`).filter((a,b,c)=>a.trim()||b<c.length-1)),c.join("\n")})(a,b+1)).join("\n\n")].join("\n")}({run:i,findings:k,session:j});await b.send(j.id,l);let m=e();for(let a of k)h.updateFinding(a.id,{status:"sent_to_agent",sentToAgentAt:m.toISOString()},m);return h.updateRun(i.id,{status:"waiting_update"},m),{run:cD(h,i.id),sentFindingCount:k.length,message:l}}function cG(a,b=new Date){if(!a)return!1;let c=Date.parse(a);return!Number.isNaN(c)&&b.getTime()-c>3e5}function cH(a){var b;let c="now"in a&&a.now?a.now:new Date,e=c.toISOString(),g=(b=a.evidence,(0,f.createHash)("sha256").update(b.replace(/\sactivity=[^\s]+/g,"").replace(/\sat=[^\s]+/g,"").trim()).digest("hex").slice(0,12)),h="previousEvidenceHash"in a?a.previousEvidenceHash:void 0,i="detectingStartedAt"in a?a.detectingStartedAt:void 0,j=void 0!==h&&h!==g,k=j?e:i??e,l=j?1:a.currentAttempts+1,m=cG(k,c);return l>3||m?{status:d.SB.STUCK,evidence:a.evidence,detecting:{attempts:l,startedAt:k,evidenceHash:g},sessionState:"stuck",sessionReason:a.idleWasBlocked?"error_in_process":"probe_failure"}:{status:d.SB.DETECTING,evidence:a.evidence,detecting:{attempts:l,startedAt:k,evidenceHash:g},sessionState:"detecting",sessionReason:a.reason??"probe_failure"}}function cI(a){return a===d.bz.MERGED?{status:d.SB.MERGED,evidence:"pr_merged",detecting:{attempts:0},prState:"merged",prReason:"merged",sessionState:"idle",sessionReason:"merged_waiting_decision"}:a===d.bz.CLOSED?{status:d.SB.IDLE,evidence:"pr_closed",detecting:{attempts:0},prState:"closed",prReason:"closed_unmerged",sessionState:"idle",sessionReason:"pr_closed_waiting_decision"}:null}function cJ(a){if(a.ciFailing)return{status:d.SB.CI_FAILED,evidence:"ci_failing",detecting:{attempts:0},prState:"open",prReason:"ci_failing",sessionState:"working",sessionReason:"fixing_ci"};if("changes_requested"===a.reviewDecision)return{status:d.SB.CHANGES_REQUESTED,evidence:"review_changes_requested",detecting:{attempts:0},prState:"open",prReason:"changes_requested",sessionState:"working",sessionReason:"resolving_review_comments"};if("approved"===a.reviewDecision||"none"===a.reviewDecision){if(a.mergeable)return{status:d.SB.MERGEABLE,evidence:"merge_ready",detecting:{attempts:0},prState:"open",prReason:"merge_ready",sessionState:"idle",sessionReason:"awaiting_external_review"};if("approved"===a.reviewDecision)return{status:d.SB.APPROVED,evidence:"review_approved",detecting:{attempts:0},prState:"open",prReason:"approved",sessionState:"idle",sessionReason:"awaiting_external_review"}}return"pending"===a.reviewDecision?{status:d.SB.REVIEW_PENDING,evidence:"review_pending",detecting:{attempts:0},prState:"open",prReason:"review_pending",sessionState:"idle",sessionReason:"awaiting_external_review"}:a.shouldEscalateIdleToStuck?{status:d.SB.STUCK,evidence:`idle_beyond_threshold ${a.activityEvidence}`,detecting:{attempts:0},prState:"open",prReason:"in_progress",sessionState:"stuck",sessionReason:a.idleWasBlocked?"error_in_process":"probe_failure"}:{status:d.SB.PR_OPEN,evidence:"pr_open",detecting:{attempts:0},prState:"open",prReason:"in_progress",sessionState:"idle",sessionReason:"pr_created"}}function cK(a){if(!a)return 0;let b=Number.parseInt(a,10);return Number.isFinite(b)&&b>0?b:0}function cL(a,b){let c=cI(a.state);return c||cJ({reviewDecision:a.reviewDecision,ciFailing:a.ciStatus===d.U1.FAILING,mergeable:a.mergeable,shouldEscalateIdleToStuck:b.shouldEscalateIdleToStuck,idleWasBlocked:b.idleWasBlocked,activityEvidence:b.activityEvidence})}function cM(a){let b=cI(a.prState);return b||cJ({reviewDecision:a.reviewDecision,ciFailing:a.ciStatus===d.U1.FAILING,mergeable:a.mergeable,shouldEscalateIdleToStuck:a.shouldEscalateIdleToStuck,idleWasBlocked:a.idleWasBlocked,activityEvidence:a.activityEvidence})}let cN={acknowledgeTimeoutMs:6e5,staleReportTimeoutMs:18e5,checkAcknowledge:!0,checkStale:!0,checkBlocked:!0},cO=new Set(["done","terminated","killed","cleanup","merged","errored"]),cP={LAST_AUDITED_AT:"reportWatcherLastAuditedAt",ACTIVE_TRIGGER:"reportWatcherActiveTrigger",TRIGGER_ACTIVATED_AT:"reportWatcherTriggerActivatedAt",TRIGGER_COUNT:"reportWatcherTriggerCount"},cQ=`You are an AI coding agent managed by the Athene (ao).
92
+
93
+ ## Session Lifecycle
94
+ - You are running inside a managed session. Focus on the assigned task.
95
+ - When you finish your work, create a PR and push it. The orchestrator will handle CI monitoring and review routing.
96
+ - If you're told to take over or continue work on an existing PR, run \`athene session claim-pr <pr-number-or-url>\` from inside this session before making changes.
97
+ - If CI fails, the orchestrator will send you the failures — fix them and push again.
98
+ - If reviewers request changes, the orchestrator will forward their comments — address each one, push fixes, and reply to the comments.
99
+
100
+ ## Reporting Progress to AO
101
+ The orchestrator infers your status from runtime signals, but explicit reports are always preferred — they are accurate and fresh. Run these commands from the session shell (ATHENE_SESSION_ID is pre-set for you):
102
+
103
+ - \`athene acknowledge\` — run once after reading the initial task so AO knows you picked it up.
104
+ - \`athene report working\` — declare you are actively making progress (useful after pauses or long thinking blocks).
105
+ - \`athene report waiting\` — you are blocked on something AO cannot unblock on its own (e.g. waiting for a human, external service).
106
+ - \`athene report needs-input\` — you need a decision or info from the human before proceeding.
107
+ - \`athene report fixing-ci\` — you are working specifically on making CI green again.
108
+ - \`athene report addressing-reviews\` — you are working on reviewer-requested changes.
109
+ - \`athene report pr-created --pr-url <url>\` / \`draft-pr-created\` / \`ready-for-review\` — declare PR workflow milestones as soon as you create or update the PR.
110
+ - \`athene report completed\` — you finished non-coding research or analysis work that doesn't produce a PR.
111
+
112
+ Rules:
113
+ - Do NOT self-report \`done\`, \`terminated\`, or terminal PR states like \`merged\`/\`closed\` — AO owns those transitions via SCM ground truth.
114
+ - A fresh report is trusted over weak inference but runtime death, activity-based waiting_input, and SCM events (merged/closed PR, CI failure, reviews) still take precedence.
115
+ - Use \`--note "<text>"\` to attach a short rationale when the state change is non-obvious.
116
+
117
+ ## Git Workflow
118
+ - Always create a feature branch from the default branch (never commit directly to it).
119
+ - Use conventional commit messages (feat:, fix:, chore:, etc.).
120
+ - Push your branch and create a PR when the implementation is ready.
121
+ - Keep PRs focused — one issue per PR.
122
+
123
+ ## PR Best Practices
124
+ - Write a clear PR title and description explaining what changed and why.
125
+ - Link the issue in the PR description so it auto-closes when merged.
126
+ - If the repo has CI checks, make sure they pass before requesting review.
127
+ - Respond to every review comment, even if just to acknowledge it.`,cR=`You are an AI coding agent managed by the Athene (ao).
128
+
129
+ ## Session Lifecycle
130
+ - You are running inside a managed session. Focus on the assigned task.
131
+ - No remote repository is configured — work locally. PR, CI, and review features are unavailable.
132
+
133
+ ## Reporting Progress to AO
134
+ Explicit reports help the orchestrator track your state accurately. Run these from the session shell (ATHENE_SESSION_ID is pre-set):
135
+ - \`athene acknowledge\` — run once after reading the initial task.
136
+ - \`athene report working\` / \`waiting\` / \`needs-input\` — declare your current phase.
137
+ - \`athene report pr-created --pr-url <url>\` or \`draft-pr-created\` / \`ready-for-review\` — declare non-terminal PR workflow events when relevant.
138
+ - \`athene report completed\` — finish non-coding research or analysis work.
139
+ Do NOT self-report \`done\` or \`terminated\` — AO owns those transitions.
140
+
141
+ ## Git Workflow
142
+ - Always create a feature branch from the default branch (never commit directly to it).
143
+ - Use conventional commit messages (feat:, fix:, chore:, etc.).`,cS=/^ses_[A-Za-z0-9_-]+$/;function cT(a){if("string"!=typeof a)return;let b=a.trim();if(0!==b.length)return cS.test(b)?b:void 0}let cU=(0,E.promisify)(D.execFile),cV=null;function cW(){let a=cV||(cV=(0,g.join)(C(),".bun-tmp"));try{(0,e.mkdirSync)(a,{recursive:!0})}catch{}return a}function cX(a){let b=cW();return{...process.env,TMPDIR:b,TMP:b,TEMP:b,...a}}let cY=null;async function cZ(a){let b=a?.timeoutMs??3e4,c=a?.forceRefresh??!1,d=Date.now();if(cY){if(cY.promise)return cY.promise;if(!c&&d-cY.timestamp<500)return cY.entries}let e=cU("opencode",["session","list","--format","json"],{timeout:b,env:cX(),..."win32"===process.platform?{shell:!0,windowsHide:!0}:{}}).then(({stdout:a})=>{let b=function(a){let b=bg(a);return Array.isArray(b)?b.flatMap(a=>{if(!a||"object"!=typeof a)return[];let b=cT(a.id);if(!b)return[];let c="string"==typeof a.title?a.title:"",d=a.updated,e="string"==typeof d||"number"==typeof d?d:void 0,f=function(a){if("number"==typeof a&&Number.isFinite(a))return a;if("string"!=typeof a)return;let b=a.trim();if(0===b.length)return;if(/^\d+$/.test(b)){let a=Number(b);return Number.isFinite(a)?a:void 0}let c=Date.parse(b);return Number.isNaN(c)?void 0:c}(d);return[{id:b,title:c,...void 0!==e?{updated:e}:{},...void 0!==f?{updatedAt:f}:{}}]}):[]}(a);return cY?.promise===e&&(cY={entries:b,timestamp:Date.now()}),b}).catch(()=>(cY?.promise===e&&(cY=null),[]));return cY={entries:[],timestamp:d,promise:e},e}function c$(){if(cY?.promise){cY={...cY,timestamp:0};return}cY=null}let c_="\x3c!-- AO_ORCHESTRATOR_PROMPT_START --\x3e",c0="\x3c!-- AO_ORCHESTRATOR_PROMPT_END --\x3e";function c1(a,b){let c=(0,g.join)(a,"AGENTS.md");(0,e.mkdirSync)(a,{recursive:!0});let d=(function(a){let b=a.indexOf(c_),c=a.indexOf(c0);if(-1===b||-1===c||c<b)return a;let d=a.slice(0,b).trimEnd(),e=a.slice(c+c0.length).trimStart();return d&&e?`${d}
144
+
145
+ ${e}`:d||e})((0,e.existsSync)(c)?(0,e.readFileSync)(c,"utf-8"):"").trimEnd(),f=[c_,"## Athene\n",(0,e.readFileSync)(b,"utf-8").trim(),c0].join("\n"),h=d?`${d}
146
+
147
+ ${f}
148
+ `:`${f}
149
+ `;return(0,e.writeFileSync)(c,h,"utf-8"),c}function c2(a,b,c){(0,e.mkdirSync)(a,{recursive:!0});let d=(0,g.join)(a,`opencode-config-${b}.json`);return(0,e.writeFileSync)(d,JSON.stringify({instructions:c},null,2),"utf-8"),d}class c3{push(a){this.dismissed||this.fns.push(a)}dismiss(){this.dismissed=!0}async runAll(a){if(!this.dismissed)for(this.dismissed=!0;this.fns.length>0;){let b=this.fns.pop();try{await b()}catch(b){a&&a(b)}}}constructor(){this.fns=[],this.dismissed=!1}}function c4(a){return`${a.sessionPrefix}-orchestrator`}function c5(a){return"kill-previous"===a||"delete-new"===a?"delete":"ignore-new"===a?"ignore":a??"reuse"}function c6(a){return G()?"'"+a.replace(/'/g,"''")+"'":"'"+a.replace(/'/g,"'\\''")+"'"}async function c7(a){let b=await (0,bU.open)(a,"r");try{let{size:a}=await b.stat();if(0===a)return null;let c=[],d=0,e=a;for(;e>0;){let a=Math.min(4096,e);e-=a;let f=Buffer.alloc(a);await b.read(f,0,a,e),c.unshift(f),d+=a;let g=Buffer.concat(c,d).toString("utf-8").split("\n");for(let a=g.length-1;a>=0;a--){let b=g[a].trim();if(b&&(a>0||0===e))return b}}return Buffer.concat(c,d).toString("utf-8").trim()||null}finally{await b.close()}}async function c8(a){try{let[b,c]=await Promise.all([c7(a),(0,bU.stat)(a)]);if(!b)return null;let d=JSON.parse(b);if("object"==typeof d&&null!==d&&!Array.isArray(d)){let a="string"==typeof d.type?d.type:null,b="string"==typeof d.subtype?d.subtype:null,e="string"==typeof d.level?d.level:null,f=null;if("object"==typeof d.payload&&null!==d.payload&&!Array.isArray(d.payload)){let a=d.payload;"string"==typeof a.type&&(f=a.type)}return{lastType:a,payloadType:f,lastSubtype:b,lastLevel:e,modifiedAt:c.mtime}}return{lastType:null,payloadType:null,lastSubtype:null,lastLevel:null,modifiedAt:c.mtime}}catch{return null}}function c9(a,b){for(let[c,d]of Object.entries(a.projects)){let a=d.sessionPrefix;if(b===a||b.startsWith(`${a}-`))return c}}let da="/usr/local/bin",db=`${da}/gh`;function dc(){return(0,g.join)((0,h.homedir)(),".ao","bin")}let dd="0.8.0";function de(a){let b=G()?";":":",c=(a??(G()?"":"/usr/bin:/bin")).split(b).filter(Boolean),d=[],e=new Set,f=a=>{!a||e.has(a)||(d.push(a),e.add(a))};for(let a of(f(dc()),G()||f(da),c))f(a);return d.join(b)}let df=`#!/usr/bin/env bash
150
+ # ao-metadata-helper — shared by gh/git wrappers
151
+ # Provides: update_ao_metadata, read_ao_metadata, ao_cache_*
152
+
153
+ # ── Shared validation ────────────────────────────────────────────────────────
154
+
155
+ _ao_validate_env() {
156
+ local ao_dir="${q(m.DATA_DIR)}"
157
+ local ao_session="${q(m.SESSION)}"
158
+ [[ -z "$ao_dir" || -z "$ao_session" ]] && return 1
159
+ case "$ao_session" in */* | *..*) return 1 ;; esac
160
+ case "$ao_dir" in
161
+ "$HOME"/.ao/* | "$HOME"/.agent-orchestrator/* | /tmp/*) ;;
162
+ *) return 1 ;;
163
+ esac
164
+ return 0
165
+ }
166
+
167
+ # ── Metadata write ───────────────────────────────────────────────────────────
168
+
169
+ update_ao_metadata() {
170
+ local key="$1" value="$2"
171
+ local ao_dir="${q(m.DATA_DIR)}"
172
+ local ao_session="${q(m.SESSION)}"
173
+
174
+ [[ -z "$ao_dir" || -z "$ao_session" ]] && return 0
175
+
176
+ # Validate: session name must not contain path separators or traversal
177
+ case "$ao_session" in
178
+ */* | *..*) return 0 ;;
179
+ esac
180
+
181
+ # Validate: ao_dir must be an absolute path under known ao directories or /tmp
182
+ case "$ao_dir" in
183
+ "$HOME"/.ao/* | "$HOME"/.agent-orchestrator/* | /tmp/*) ;;
184
+ *) return 0 ;;
185
+ esac
186
+
187
+ # V2 storage uses .json extension; fallback to bare filename for pre-migration layouts
188
+ local metadata_file="$ao_dir/\${ao_session}.json"
189
+ if [[ ! -f "$metadata_file" ]]; then
190
+ metadata_file="$ao_dir/$ao_session"
191
+ fi
192
+
193
+ # Resolve symlinks and verify canonicalized paths are still within trusted roots
194
+ local real_dir real_ao_dir
195
+ real_ao_dir="$(cd "$ao_dir" 2>/dev/null && pwd -P)" || return 0
196
+ real_dir="$(cd "$(dirname "$metadata_file")" 2>/dev/null && pwd -P)" || return 0
197
+
198
+ # Re-validate real_ao_dir against trusted roots after canonicalization
199
+ # (prevents /tmp/../../home/user from escaping the allowlist)
200
+ case "$real_ao_dir" in
201
+ "$HOME"/.ao/* | "$HOME"/.ao | "$HOME"/.agent-orchestrator/* | "$HOME"/.agent-orchestrator | /tmp/*) ;;
202
+ *) return 0 ;;
203
+ esac
204
+
205
+ [[ "$real_dir" == "$real_ao_dir"* ]] || return 0
206
+
207
+ [[ -f "$metadata_file" ]] || return 0
208
+
209
+ # Validate key — only allow alphanumeric, underscore, hyphen (prevents sed/jq injection)
210
+ [[ "$key" =~ ^[a-zA-Z0-9_-]+$ ]] || return 0
211
+
212
+ local temp_file="\${metadata_file}.tmp.$$"
213
+
214
+ # Strip newlines from value to prevent injection
215
+ local clean_value="$(printf '%s' "$value" | tr -d '\\n')"
216
+
217
+ # Detect JSON vs key=value format
218
+ local first_char
219
+ first_char="$(head -c1 "$metadata_file" 2>/dev/null)"
220
+
221
+ if [[ "$first_char" == "{" ]]; then
222
+ # JSON format
223
+ if command -v jq &>/dev/null; then
224
+ jq --arg k "$key" --arg v "$clean_value" '.[$k] = $v' "$metadata_file" > "$temp_file"
225
+ mv "$temp_file" "$metadata_file"
226
+ else
227
+ # jq unavailable — use node (hard dep) for safe nested JSON update
228
+ node -e "
229
+ const fs = require('fs');
230
+ const d = JSON.parse(fs.readFileSync(process.argv[1], 'utf8'));
231
+ d[process.argv[2]] = process.argv[3];
232
+ fs.writeFileSync(process.argv[4], JSON.stringify(d, null, 2));
233
+ " "$metadata_file" "$key" "$clean_value" "$temp_file"
234
+ mv "$temp_file" "$metadata_file"
235
+ fi
236
+ else
237
+ # Key=value format (legacy)
238
+ local escaped_value="$(printf '%s' "$clean_value" | sed 's/[&|\\\\]/\\\\&/g')"
239
+ if grep -q "^\${key}=" "$metadata_file" 2>/dev/null; then
240
+ sed "s|^\${key}=.*|\${key}=\${escaped_value}|" "$metadata_file" > "$temp_file"
241
+ else
242
+ cp "$metadata_file" "$temp_file"
243
+ printf '%s=%s\\n' "$key" "$clean_value" >> "$temp_file"
244
+ fi
245
+ mv "$temp_file" "$metadata_file"
246
+ fi
247
+ }
248
+
249
+ # ── Metadata read ────────────────────────────────────────────────────────────
250
+
251
+ read_ao_metadata() {
252
+ local key="$1"
253
+ _ao_validate_env || return 1
254
+ local metadata_file="${q(m.DATA_DIR)}/${q(m.SESSION)}"
255
+ [[ -f "$metadata_file" ]] || return 1
256
+ [[ "$key" =~ ^[a-zA-Z0-9_-]+$ ]] || return 1
257
+ local line
258
+ line=$(grep "^\${key}=" "$metadata_file" 2>/dev/null | head -1) || return 1
259
+ printf '%s' "\${line#*=}"
260
+ }
261
+
262
+ # ── Cache helpers ────────────────────────────────────────────────────────────
263
+
264
+ ao_cache_dir() {
265
+ _ao_validate_env || return 1
266
+ local d="${q(m.DATA_DIR)}/.ghcache/${q(m.SESSION)}"
267
+ mkdir -p "$d" 2>/dev/null || return 1
268
+ printf '%s' "$d"
269
+ }
270
+
271
+ ao_cache_fresh() {
272
+ local cache_key="$1" max_age="$2"
273
+ [[ "$cache_key" =~ ^[a-zA-Z0-9_.-]+$ ]] || return 1
274
+ local cache_dir
275
+ cache_dir="$(ao_cache_dir)" || return 1
276
+ local ts_file="$cache_dir/\${cache_key}.ts"
277
+ local stdout_file="$cache_dir/\${cache_key}.stdout"
278
+ [[ -f "$stdout_file" && -f "$ts_file" ]] || return 1
279
+ local cached_ts now
280
+ cached_ts=$(cat "$ts_file" 2>/dev/null) || return 1
281
+ # Sanity check: cached_ts must be a positive integer (epoch seconds)
282
+ [[ "$cached_ts" =~ ^[0-9]+$ && "$cached_ts" -gt 0 ]] || return 1
283
+ # max_age=0 means infinite TTL
284
+ [[ "$max_age" -eq 0 ]] 2>/dev/null && return 0
285
+ now=$(date +%s)
286
+ (( now - cached_ts < max_age ))
287
+ }
288
+
289
+ ao_cache_read() {
290
+ local cache_key="$1"
291
+ [[ "$cache_key" =~ ^[a-zA-Z0-9_.-]+$ ]] || return 1
292
+ local cache_dir
293
+ cache_dir="$(ao_cache_dir)" || return 1
294
+ cat "$cache_dir/\${cache_key}.stdout"
295
+ }
296
+
297
+ ao_cache_write() {
298
+ local cache_key="$1"
299
+ [[ "$cache_key" =~ ^[a-zA-Z0-9_.-]+$ ]] || return 1
300
+ local cache_dir
301
+ cache_dir="$(ao_cache_dir)" || return 1
302
+ local tmp="$cache_dir/\${cache_key}.stdout.tmp.$$"
303
+ cat > "$tmp" && mv "$tmp" "$cache_dir/\${cache_key}.stdout"
304
+ date +%s > "$cache_dir/\${cache_key}.ts"
305
+ }
306
+ `,dg=`#!/usr/bin/env bash
307
+ # ao gh wrapper — caches reads + auto-updates metadata on writes
308
+
309
+ # Find real gh by removing our wrapper directory from PATH
310
+ ao_bin_dir="$(cd "$(dirname "$0")" && pwd)"
311
+ clean_path="$(echo "$PATH" | tr ':' '\\n' | grep -Fxv "$ao_bin_dir" | grep . | tr '\\n' ':')"
312
+ clean_path="\${clean_path%:}"
313
+ real_gh=""
314
+
315
+ # Prefer explicit gh path when provided by AO environment.
316
+ # Guard against recursive self-reference to the wrapper in ~/.ao/bin.
317
+ if [[ -n "\${GH_PATH:-}" && -x "$GH_PATH" ]]; then
318
+ gh_dir="$(cd "$(dirname "$GH_PATH")" 2>/dev/null && pwd)"
319
+ if [[ "$gh_dir" != "$ao_bin_dir" ]]; then
320
+ real_gh="$GH_PATH"
321
+ fi
322
+ fi
323
+
324
+ if [[ -z "$real_gh" ]]; then
325
+ real_gh="$(PATH="$clean_path" command -v gh 2>/dev/null)"
326
+ fi
327
+
328
+ if [[ -z "$real_gh" ]]; then
329
+ echo "ao-wrapper: gh not found in PATH" >&2
330
+ exit 127
331
+ fi
332
+
333
+ # Source the metadata helper (provides update/read_ao_metadata, ao_cache_*)
334
+ source "$ao_bin_dir/ao-metadata-helper.sh" 2>/dev/null || true
335
+
336
+ # Redact sensitive values from args before tracing.
337
+ # Handles: -H "Authorization: ...", token=..., password=..., secret=...
338
+ _ao_redact_args() {
339
+ local prev=""
340
+ local out=()
341
+ for arg in "$@"; do
342
+ if [[ "$prev" == "-H" || "$prev" == "--header" ]] && [[ "$arg" =~ ^[Aa]uthorization: ]]; then
343
+ out+=("Authorization: [REDACTED]")
344
+ elif [[ "$arg" =~ ^-H[Aa]uthorization: ]]; then
345
+ out+=("-HAuthorization: [REDACTED]")
346
+ elif [[ "$arg" =~ ^[Tt]oken= ]]; then
347
+ out+=("token=[REDACTED]")
348
+ elif [[ "$arg" =~ ^[Pp]assword= ]]; then
349
+ out+=("password=[REDACTED]")
350
+ elif [[ "$arg" =~ ^[Ss]ecret= ]]; then
351
+ out+=("secret=[REDACTED]")
352
+ else
353
+ out+=("$arg")
354
+ fi
355
+ prev="$arg"
356
+ done
357
+ printf '%s
358
+ ' "\${out[@]}"
359
+ }
360
+
361
+ # Best-effort JSONL tracing for agent-side gh invocations.
362
+ log_gh_invocation() {
363
+ local trace_file="${q(m.AGENT_GH_TRACE)}"
364
+ [[ -z "$trace_file" ]] && return 0
365
+ command -v jq >/dev/null 2>&1 || return 0
366
+
367
+ mkdir -p "$(dirname "$trace_file")" 2>/dev/null || return 0
368
+
369
+ local args_json
370
+ args_json="$(_ao_redact_args "$@" | jq -Rsc 'split("
371
+ ")[:-1]')" || return 0
372
+
373
+ # Compute operation: gh.{arg1}.{arg2} (mirrors AO-side extractOperation)
374
+ local _ao_op="gh"
375
+ [[ $# -ge 1 ]] && _ao_op="gh.$1"
376
+ [[ $# -ge 2 && "$2" != -* ]] && _ao_op="gh.$1.$2"
377
+
378
+ jq -nc \
379
+ --arg timestamp "$(date -u +"%Y-%m-%dT%H:%M:%SZ")" \
380
+ --arg cwd "$PWD" \
381
+ --arg operation "$_ao_op" \
382
+ --arg aoSession "${q(m.SESSION)}" \
383
+ --arg aoSessionName "${q(m.SESSION_NAME)}" \
384
+ --arg aoProjectId "${q(m.PROJECT_ID)}" \
385
+ --arg aoIssueId "${q(m.ISSUE_ID)}" \
386
+ --arg aoCallerType "${q(m.CALLER_TYPE)}" \
387
+ --arg pid "$$" \
388
+ --arg wrapperVersion "${dd}" \
389
+ --argjson args "$args_json" \
390
+ '{
391
+ timestamp: $timestamp,
392
+ cwd: $cwd,
393
+ args: $args,
394
+ operation: $operation,
395
+ aoSession: (if $aoSession == "" then null else $aoSession end),
396
+ aoSessionName: (if $aoSessionName == "" then null else $aoSessionName end),
397
+ aoProjectId: (if $aoProjectId == "" then null else $aoProjectId end),
398
+ aoIssueId: (if $aoIssueId == "" then null else $aoIssueId end),
399
+ aoCallerType: (if $aoCallerType == "" then null else $aoCallerType end),
400
+ pid: ($pid | tonumber),
401
+ wrapperVersion: $wrapperVersion
402
+ }' >> "$trace_file" 2>/dev/null || true
403
+ }
404
+
405
+ log_gh_invocation "$@"
406
+
407
+ # Best-effort cache-outcome tracing (appends to same JSONL trace file).
408
+ # result: hit | miss-stored | miss-write-failed | miss-negative | miss-error | passthrough
409
+ log_ao_cache() {
410
+ local result="$1" cache_key="$2" duration_ms="\${3:-0}" exit_code="\${4:-0}" ok="\${5:-true}"
411
+ local trace_file="${q(m.AGENT_GH_TRACE)}"
412
+ [[ -z "$trace_file" ]] && return 0
413
+ printf '{"timestamp":"%s","cacheResult":"%s","cacheKey":"%s","pid":%s,"durationMs":%s,"exitCode":%s,"ok":%s}\\n' \
414
+ "$(date -u +"%Y-%m-%dT%H:%M:%SZ")" "$result" "$cache_key" "$$" \
415
+ "$duration_ms" "$exit_code" "$ok" \
416
+ >> "$trace_file" 2>/dev/null || true
417
+ }
418
+
419
+ # =============================================================================
420
+ # Cacheable reads
421
+ # =============================================================================
422
+
423
+ # ── 1. PR discovery: gh pr list --head <B> --limit 1 ────────────────────────
424
+ # 120s TTL for positive results (non-empty array). Never caches [].
425
+ if [[ "$1" == "pr" && "$2" == "list" ]]; then
426
+ _ao_head="" _ao_limit="" _ao_json="" _ao_repo="" _ao_cacheable=true
427
+ _ao_saved_args=("$@")
428
+ shift 2
429
+ while [[ $# -gt 0 ]]; do
430
+ case "$1" in
431
+ --head) _ao_head="$2"; shift 2 ;;
432
+ --head=*) _ao_head="\${1#--head=}"; shift ;;
433
+ --limit) _ao_limit="$2"; shift 2 ;;
434
+ --limit=*) _ao_limit="\${1#--limit=}"; shift ;;
435
+ --json) _ao_json="$2"; shift 2 ;;
436
+ --json=*) _ao_json="\${1#--json=}"; shift ;;
437
+ --repo) _ao_repo="$2"; shift 2 ;;
438
+ --repo=*) _ao_repo="\${1#--repo=}"; shift ;;
439
+ --search|--state|--assignee|--label|--jq|--template)
440
+ _ao_cacheable=false; break ;;
441
+ --search=*|--state=*|--assignee=*|--label=*|--jq=*|--template=*)
442
+ _ao_cacheable=false; break ;;
443
+ -*) shift ;; # skip unknown flags
444
+ *) shift ;; # skip positional
445
+ esac
446
+ done
447
+ set -- "\${_ao_saved_args[@]}"
448
+
449
+ if [[ "$_ao_cacheable" == true && "$_ao_limit" == "1" && -n "$_ao_head" ]]; then
450
+ # Use sha256 hash suffix to avoid collisions from tr-based sanitization
451
+ # (e.g. feat/foo, feat-foo, feat_foo would otherwise map to the same key)
452
+ _ao_raw_key="pr-discovery-\${_ao_repo}-\${_ao_head}"
453
+ if [[ -n "$_ao_json" ]]; then
454
+ _ao_raw_key="\${_ao_raw_key}-j-\${_ao_json}"
455
+ fi
456
+ _ao_cache_key=$(printf '%s' "$_ao_raw_key" | shasum -a 256 | cut -c1-16)
457
+ _ao_cache_key="pr-disc-\${_ao_cache_key}"
458
+
459
+ if ao_cache_fresh "$_ao_cache_key" 120 2>/dev/null; then
460
+ log_ao_cache "hit" "$_ao_cache_key" 0 0 true
461
+ ao_cache_read "$_ao_cache_key"
462
+ exit 0
463
+ fi
464
+
465
+ # Cache miss — call real gh, cache positive results (stderr passes through)
466
+ _ao_tmpout="$(mktemp)"
467
+ trap 'rm -f "$_ao_tmpout"' EXIT
468
+ _ao_start_s=$(date +%s)
469
+ "$real_gh" "$@" > "$_ao_tmpout"
470
+ _ao_exit=$?
471
+ _ao_duration_ms=$(( ($(date +%s) - _ao_start_s) * 1000 ))
472
+ _ao_ok=true; [[ $_ao_exit -ne 0 ]] && _ao_ok=false
473
+ cat "$_ao_tmpout"
474
+ if [[ $_ao_exit -eq 0 ]]; then
475
+ _ao_trimmed=$(tr -d '[:space:]' < "$_ao_tmpout")
476
+ # Only cache non-empty positive results
477
+ if [[ -n "$_ao_trimmed" && "$_ao_trimmed" != "[]" ]]; then
478
+ if ao_cache_write "$_ao_cache_key" < "$_ao_tmpout" 2>/dev/null; then
479
+ log_ao_cache "miss-stored" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
480
+ else
481
+ log_ao_cache "miss-write-failed" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
482
+ fi
483
+ else
484
+ log_ao_cache "miss-negative" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
485
+ fi
486
+ else
487
+ log_ao_cache "miss-error" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
488
+ fi
489
+ exit $_ao_exit
490
+ fi
491
+ fi
492
+
493
+ # ── 2. Issue context: gh issue view <N> ─────────────────────────────────────
494
+ # 300-second TTL. Caches any successful response.
495
+ if [[ "$1" == "issue" && "$2" == "view" ]]; then
496
+ _ao_issue_id="" _ao_json="" _ao_repo="" _ao_cacheable=true
497
+ _ao_saved_args=("$@")
498
+ shift 2
499
+ # First non-flag arg is the issue identifier
500
+ while [[ $# -gt 0 ]]; do
501
+ case "$1" in
502
+ --web|--comments|--jq|--template)
503
+ _ao_cacheable=false; break ;;
504
+ --jq=*|--template=*)
505
+ _ao_cacheable=false; break ;;
506
+ --json) _ao_json="$2"; shift 2 ;;
507
+ --json=*) _ao_json="\${1#--json=}"; shift ;;
508
+ --repo) _ao_repo="$2"; shift 2 ;;
509
+ --repo=*) _ao_repo="\${1#--repo=}"; shift ;;
510
+ -*) shift ;;
511
+ *)
512
+ if [[ -z "$_ao_issue_id" && "$1" =~ ^[0-9]+$ ]]; then
513
+ _ao_issue_id="$1"
514
+ fi
515
+ shift ;;
516
+ esac
517
+ done
518
+ set -- "\${_ao_saved_args[@]}"
519
+
520
+ if [[ "$_ao_cacheable" == true && -n "$_ao_issue_id" ]]; then
521
+ _ao_raw_key="issue-ctx-\${_ao_repo}-\${_ao_issue_id}"
522
+ if [[ -n "$_ao_json" ]]; then
523
+ _ao_raw_key="\${_ao_raw_key}-j-\${_ao_json}"
524
+ fi
525
+ _ao_cache_key=$(printf '%s' "$_ao_raw_key" | shasum -a 256 | cut -c1-16)
526
+ _ao_cache_key="issue-\${_ao_cache_key}"
527
+
528
+ if ao_cache_fresh "$_ao_cache_key" 300 2>/dev/null; then
529
+ log_ao_cache "hit" "$_ao_cache_key" 0 0 true
530
+ ao_cache_read "$_ao_cache_key"
531
+ exit 0
532
+ fi
533
+
534
+ _ao_tmpout="$(mktemp)"
535
+ trap 'rm -f "$_ao_tmpout"' EXIT
536
+ _ao_start_s=$(date +%s)
537
+ "$real_gh" "$@" > "$_ao_tmpout"
538
+ _ao_exit=$?
539
+ _ao_duration_ms=$(( ($(date +%s) - _ao_start_s) * 1000 ))
540
+ _ao_ok=true; [[ $_ao_exit -ne 0 ]] && _ao_ok=false
541
+ cat "$_ao_tmpout"
542
+ if [[ $_ao_exit -eq 0 ]]; then
543
+ if ao_cache_write "$_ao_cache_key" < "$_ao_tmpout" 2>/dev/null; then
544
+ log_ao_cache "miss-stored" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
545
+ else
546
+ log_ao_cache "miss-write-failed" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
547
+ fi
548
+ else
549
+ log_ao_cache "miss-error" "$_ao_cache_key" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
550
+ fi
551
+ exit $_ao_exit
552
+ fi
553
+ fi
554
+
555
+ # =============================================================================
556
+ # Write intercepts
557
+ # =============================================================================
558
+
559
+ case "$1/$2" in
560
+ pr/create)
561
+ tmpout="$(mktemp)"
562
+ trap 'rm -f "$tmpout"' EXIT
563
+
564
+ _ao_start_s=$(date +%s)
565
+ "$real_gh" "$@" 2>&1 | tee "$tmpout"
566
+ exit_code=\${PIPESTATUS[0]}
567
+ _ao_duration_ms=$(( ($(date +%s) - _ao_start_s) * 1000 ))
568
+ _ao_ok=true; [[ $exit_code -ne 0 ]] && _ao_ok=false
569
+
570
+ if [[ $exit_code -eq 0 ]]; then
571
+ output="$(cat "$tmpout")"
572
+ pr_url="$(echo "$output" | grep -Eo 'https?://[^/]+/[^/]+/[^/]+/pull/[0-9]+' | head -1)"
573
+ report_state="pr_created"
574
+ report_draft="false"
575
+ for arg in "$@"; do
576
+ if [[ "$arg" == "--draft" || "$arg" == "-d" ]]; then
577
+ report_state="draft_pr_created"
578
+ report_draft="true"
579
+ break
580
+ fi
581
+ done
582
+ if [[ -n "$pr_url" ]]; then
583
+ update_ao_metadata pr "$pr_url"
584
+ update_ao_metadata agentReportedPrUrl "$pr_url"
585
+ # Append to prs field (comma-separated list of all PR URLs for this session).
586
+ # Supports multiple PRs per session — same repo or different repos.
587
+ _ao_meta_f="${q(m.DATA_DIR)}/${q(m.SESSION)}.json"
588
+ [[ -f "$_ao_meta_f" ]] || _ao_meta_f="${q(m.DATA_DIR)}/${q(m.SESSION)}"
589
+ if head -c1 "$_ao_meta_f" 2>/dev/null | grep -q '{'; then
590
+ existing_prs="$(jq -r '.prs // empty' "$_ao_meta_f" 2>/dev/null || echo "")"
591
+ else
592
+ existing_prs="$(grep '^prs=' "$_ao_meta_f" 2>/dev/null | cut -d'=' -f2- || echo "")"
593
+ fi
594
+ if [[ -z "$existing_prs" ]]; then
595
+ new_prs="$pr_url"
596
+ else
597
+ if ! echo ",$existing_prs," | grep -qF ",$pr_url,"; then
598
+ new_prs="$existing_prs,$pr_url"
599
+ else
600
+ new_prs="$existing_prs"
601
+ fi
602
+ fi
603
+ update_ao_metadata prs "$new_prs"
604
+ fi
605
+ pr_number="$(printf '%s' "$pr_url" | grep -Eo '[0-9]+$' | head -1)"
606
+ if [[ -n "$pr_number" ]]; then
607
+ update_ao_metadata agentReportedPrNumber "$pr_number"
608
+ fi
609
+ update_ao_metadata agentReportedState "$report_state"
610
+ update_ao_metadata agentReportedAt "$(date -u +%Y-%m-%dT%H:%M:%SZ)"
611
+ update_ao_metadata agentReportedPrIsDraft "$report_draft"
612
+ fi
613
+
614
+ log_ao_cache "passthrough" "" "$_ao_duration_ms" "$exit_code" "$_ao_ok"
615
+ exit $exit_code
616
+ ;;
617
+ *)
618
+ _ao_start_s=$(date +%s)
619
+ "$real_gh" "$@"
620
+ _ao_exit=$?
621
+ _ao_duration_ms=$(( ($(date +%s) - _ao_start_s) * 1000 ))
622
+ _ao_ok=true; [[ $_ao_exit -ne 0 ]] && _ao_ok=false
623
+ log_ao_cache "passthrough" "" "$_ao_duration_ms" "$_ao_exit" "$_ao_ok"
624
+ exit $_ao_exit
625
+ ;;
626
+ esac
627
+ `,dh=`#!/usr/bin/env bash
628
+ # ao git wrapper — auto-updates session metadata on branch operations
629
+
630
+ # Find real git by removing our wrapper directory from PATH
631
+ ao_bin_dir="$(cd "$(dirname "$0")" && pwd)"
632
+ clean_path="$(echo "$PATH" | tr ':' '\\n' | grep -Fxv "$ao_bin_dir" | grep . | tr '\\n' ':')"
633
+ clean_path="\${clean_path%:}"
634
+ real_git="$(PATH="$clean_path" command -v git 2>/dev/null)"
635
+
636
+ if [[ -z "$real_git" ]]; then
637
+ echo "ao-wrapper: git not found in PATH" >&2
638
+ exit 127
639
+ fi
640
+
641
+ # Source the metadata helper
642
+ source "$ao_bin_dir/ao-metadata-helper.sh" 2>/dev/null || true
643
+
644
+ # Run real git
645
+ "$real_git" "$@"
646
+ exit_code=$?
647
+
648
+ # Only update metadata on success
649
+ if [[ $exit_code -eq 0 ]]; then
650
+ case "$1/$2" in
651
+ checkout/-b)
652
+ update_ao_metadata branch "$3"
653
+ ;;
654
+ switch/-c)
655
+ update_ao_metadata branch "$3"
656
+ ;;
657
+ checkout/*|switch/*)
658
+ # Existing branch switch — only track feature-looking branches (contain / or -)
659
+ # Skip flags (e.g. -B), HEAD, tags, commit hashes, and simple names like "main"
660
+ branch="$2"
661
+ # If $2 is a flag, the actual branch name is in $3
662
+ if [[ "$branch" == -* ]]; then branch="$3"; fi
663
+ if [[ -n "$branch" && "$branch" != "HEAD" && "$branch" != -* && "$branch" == *[/-]* ]]; then
664
+ update_ao_metadata branch "$branch"
665
+ fi
666
+ ;;
667
+ esac
668
+ fi
669
+
670
+ exit $exit_code
671
+ `,di=`\
672
+ // ---------------------------------------------------------------------------
673
+ // Metadata update (shared by gh/git wrappers)
674
+ // ---------------------------------------------------------------------------
675
+ function updateAoMetadata(key, value) {
676
+ const aoDir = ${r(m.DATA_DIR)} || "";
677
+ const aoSession = ${r(m.SESSION)} || "";
678
+ if (!aoDir || !aoSession) return;
679
+
680
+ // Validate session — no path separators or traversal
681
+ if (aoSession.includes("/") || aoSession.includes("\\\\") || aoSession.includes("..")) return;
682
+
683
+ // Validate key
684
+ if (!/^[a-zA-Z0-9_-]+$/.test(key)) return;
685
+
686
+ // Validate aoDir is under expected locations (mirrors bash ao-metadata-helper.sh)
687
+ const os = require("os");
688
+ const home = os.homedir();
689
+ const sep = path.sep;
690
+ let resolvedDir;
691
+ try { resolvedDir = fs.realpathSync(aoDir); } catch { resolvedDir = path.resolve(aoDir); }
692
+ const allowed = [path.join(home, ".ao"), path.join(home, ".agent-orchestrator"), os.tmpdir()];
693
+ if (!allowed.some(a => resolvedDir === a || resolvedDir.startsWith(a + sep))) return;
694
+
695
+ // Try V2 (.json) first, then fall back to V1 (bare) — mirrors bash ao-metadata-helper.sh
696
+ let metadataFile = path.join(resolvedDir, aoSession + ".json");
697
+ if (!fs.existsSync(metadataFile)) {
698
+ metadataFile = path.join(resolvedDir, aoSession);
699
+ }
700
+ if (!fs.existsSync(metadataFile)) return;
701
+
702
+ // Strip newlines from value
703
+ const cleanValue = String(value).replace(/[\\r\\n]/g, "");
704
+
705
+ let content;
706
+ try { content = fs.readFileSync(metadataFile, "utf8"); } catch { return; }
707
+
708
+ const tmpFile = metadataFile + ".tmp." + process.pid;
709
+ try {
710
+ if (metadataFile.endsWith(".json")) {
711
+ // V2 JSON format
712
+ let d;
713
+ try { d = JSON.parse(content); } catch { return; }
714
+ d[key] = cleanValue;
715
+ fs.writeFileSync(tmpFile, JSON.stringify(d, null, 2), "utf8");
716
+ } else {
717
+ // V1 key=value format
718
+ const lines = content.split("\\n");
719
+ const keyPrefix = key + "=";
720
+ const idx = lines.findIndex(l => l.startsWith(keyPrefix));
721
+ if (idx >= 0) {
722
+ lines[idx] = key + "=" + cleanValue;
723
+ } else {
724
+ lines.push(key + "=" + cleanValue);
725
+ }
726
+ fs.writeFileSync(tmpFile, lines.join("\\n"), "utf8");
727
+ }
728
+ fs.renameSync(tmpFile, metadataFile);
729
+ } catch {
730
+ try { fs.unlinkSync(tmpFile); } catch {}
731
+ }
732
+ }`,dj=`
733
+ ## Athene (ao) Session
734
+
735
+ You are running inside an Athene managed workspace.
736
+ Session metadata is updated automatically via shell wrappers.
737
+
738
+ If automatic updates fail, you can manually update metadata:
739
+ \`\`\`bash
740
+ ~/.ao/bin/ao-metadata-helper.sh # sourced automatically
741
+ # Then call: update_ao_metadata <key> <value>
742
+ \`\`\`
743
+ `;async function dk(a,b,c){let d=(0,f.randomBytes)(6).toString("hex"),e=`${a}.tmp.${d}`;await (0,bU.writeFile)(e,b,{encoding:"utf-8",mode:c}),await (0,bU.rename)(e,a)}async function dl(a){await (0,bU.mkdir)(dc(),{recursive:!0});let b=(0,g.join)(dc(),".ao-version"),c=!0;try{(await (0,bU.readFile)(b,"utf-8")).trim()===dd&&(c=!1)}catch{}if(c){if(G())for(let a of["gh","git"]){let b=(0,g.join)(dc(),a),c="gh"===a?`#!/usr/bin/env node
744
+ // ao gh wrapper (Windows Node.js) — auto-updates session metadata on PR operations
745
+ "use strict";
746
+ const { spawnSync } = require("child_process");
747
+ const fs = require("fs");
748
+ const path = require("path");
749
+
750
+ // ---------------------------------------------------------------------------
751
+ // Real binary resolution
752
+ // ---------------------------------------------------------------------------
753
+ const AO_BIN_DIR = path.dirname(__filename);
754
+
755
+ function findRealGh() {
756
+ const explicit = process.env["GH_PATH"] || "";
757
+ if (explicit) {
758
+ try {
759
+ const resolved = path.resolve(explicit);
760
+ const dir = path.dirname(resolved);
761
+ if (dir !== AO_BIN_DIR && fs.existsSync(resolved)) return resolved;
762
+ } catch {}
763
+ }
764
+
765
+ // Walk PATH, skip wrapper directory
766
+ const pathDirs = (process.env["PATH"] || "").split(path.delimiter);
767
+ for (const dir of pathDirs) {
768
+ if (!dir || path.resolve(dir) === AO_BIN_DIR) continue;
769
+ // Windows executables always have an extension (.exe/.cmd). Skip the bare
770
+ // no-extension case — on Windows X_OK is identical to F_OK (execute bit
771
+ // doesn't exist), so a bare text file named "gh" would otherwise be
772
+ // selected before gh.exe.
773
+ for (const ext of [".exe", ".cmd"]) {
774
+ const candidate = path.join(dir, "gh" + ext);
775
+ try {
776
+ fs.accessSync(candidate, fs.constants.F_OK);
777
+ return candidate;
778
+ } catch {}
779
+ }
780
+ }
781
+ return null;
782
+ }
783
+
784
+ ${di}
785
+
786
+ // ---------------------------------------------------------------------------
787
+ // Main
788
+ // ---------------------------------------------------------------------------
789
+ const realGh = findRealGh();
790
+ if (!realGh) {
791
+ process.stderr.write("ao-wrapper: gh not found in PATH\\n");
792
+ process.exit(127);
793
+ }
794
+
795
+ const args = process.argv.slice(2);
796
+ const sub1 = args[0] || "";
797
+ const sub2 = args[1] || "";
798
+ const key = sub1 + "/" + sub2;
799
+
800
+ if (key === "pr/create" || key === "pr/merge") {
801
+ const result = spawnSync(realGh, args, {
802
+ stdio: ["inherit", "pipe", "pipe"],
803
+ encoding: "utf8",
804
+ });
805
+
806
+ if (result.stdout) process.stdout.write(result.stdout);
807
+ if (result.stderr) process.stderr.write(result.stderr);
808
+
809
+ if (result.status === 0) {
810
+ const output = (result.stdout || "") + (result.stderr || "");
811
+ if (key === "pr/create") {
812
+ const match = output.match(/https:\\/\\/github\\.com\\/[^/]+\\/[^/]+\\/pull\\/[0-9]+/);
813
+ if (match) {
814
+ const prUrl = match[0];
815
+ updateAoMetadata("pr", prUrl);
816
+ updateAoMetadata("status", "pr_open");
817
+ // Append to prs field — supports multiple PRs per session
818
+ let existingPrs = "";
819
+ try {
820
+ const aoDir = ${r(m.DATA_DIR)} || "";
821
+ const aoSession = ${r(m.SESSION)} || "";
822
+ if (aoDir && aoSession && /^[a-zA-Z0-9_-]+$/.test(aoSession)) {
823
+ let metaFile = path.join(aoDir, aoSession + ".json");
824
+ if (!fs.existsSync(metaFile)) metaFile = path.join(aoDir, aoSession);
825
+ if (fs.existsSync(metaFile)) {
826
+ const raw = fs.readFileSync(metaFile, "utf8");
827
+ if (metaFile.endsWith(".json")) {
828
+ existingPrs = JSON.parse(raw).prs || "";
829
+ } else {
830
+ const line = raw.split("\\n").find(l => l.startsWith("prs="));
831
+ existingPrs = line ? line.slice(4) : "";
832
+ }
833
+ }
834
+ }
835
+ } catch {}
836
+ const newPrs = existingPrs
837
+ ? existingPrs.split(",").map((u) => u.trim()).includes(prUrl)
838
+ ? existingPrs
839
+ : existingPrs + "," + prUrl
840
+ : prUrl;
841
+ updateAoMetadata("prs", newPrs);
842
+ }
843
+ } else if (key === "pr/merge") {
844
+ updateAoMetadata("status", "merged");
845
+ }
846
+ }
847
+
848
+ process.exit(result.status ?? 1);
849
+ } else {
850
+ const result = spawnSync(realGh, args, { stdio: "inherit" });
851
+ process.exit(result.status ?? 1);
852
+ }
853
+ `:`#!/usr/bin/env node
854
+ // ao git wrapper (Windows Node.js) — auto-updates session metadata on branch operations
855
+ "use strict";
856
+ const { spawnSync } = require("child_process");
857
+ const fs = require("fs");
858
+ const path = require("path");
859
+
860
+ // ---------------------------------------------------------------------------
861
+ // Real binary resolution
862
+ // ---------------------------------------------------------------------------
863
+ const AO_BIN_DIR = path.dirname(__filename);
864
+
865
+ function findRealGit() {
866
+ const pathDirs = (process.env["PATH"] || "").split(path.delimiter);
867
+ for (const dir of pathDirs) {
868
+ if (!dir || path.resolve(dir) === AO_BIN_DIR) continue;
869
+ // Windows executables always have an extension (.exe/.cmd). Skip the bare
870
+ // no-extension case — on Windows X_OK is identical to F_OK (execute bit
871
+ // doesn't exist), so a bare text file named "git" would otherwise be
872
+ // selected before git.exe.
873
+ for (const ext of [".exe", ".cmd"]) {
874
+ const candidate = path.join(dir, "git" + ext);
875
+ try {
876
+ fs.accessSync(candidate, fs.constants.F_OK);
877
+ return candidate;
878
+ } catch {}
879
+ }
880
+ }
881
+ return null;
882
+ }
883
+
884
+ ${di}
885
+
886
+ // ---------------------------------------------------------------------------
887
+ // Main
888
+ // ---------------------------------------------------------------------------
889
+ const realGit = findRealGit();
890
+ if (!realGit) {
891
+ process.stderr.write("ao-wrapper: git not found in PATH\\n");
892
+ process.exit(127);
893
+ }
894
+
895
+ const args = process.argv.slice(2);
896
+ const result = spawnSync(realGit, args, { stdio: "inherit" });
897
+ const exitCode = result.status ?? 1;
898
+
899
+ if (exitCode === 0) {
900
+ const sub1 = args[0] || "";
901
+ const sub2 = args[1] || "";
902
+ const key = sub1 + "/" + sub2;
903
+
904
+ if (key === "checkout/-b" || key === "switch/-c") {
905
+ const branch = args[2];
906
+ if (branch) updateAoMetadata("branch", branch);
907
+ } else if (sub1 === "checkout" || sub1 === "switch") {
908
+ // Existing branch switch — only track feature-looking branches (contain / or -)
909
+ let branch = sub2;
910
+ // If sub2 is a flag, the actual branch name is in args[2]
911
+ if (branch && branch.startsWith("-")) branch = args[2] || "";
912
+ if (
913
+ branch &&
914
+ branch !== "HEAD" &&
915
+ !branch.startsWith("-") &&
916
+ (branch.includes("/") || branch.includes("-"))
917
+ ) {
918
+ updateAoMetadata("branch", branch);
919
+ }
920
+ }
921
+ }
922
+
923
+ process.exit(exitCode);
924
+ `;await dk(b+".cjs",c,420),await dk(b+".cmd",`@node "%~dp0${a}.cjs" %*\r
925
+ `,420)}else await dk((0,g.join)(dc(),"ao-metadata-helper.sh"),df,493),await dk((0,g.join)(dc(),"gh"),dg,493),await dk((0,g.join)(dc(),"git"),dh,493);await dk(b,dd,420)}let d=(0,g.join)(a,".ao","AGENTS.md");await (0,bU.mkdir)((0,g.join)(a,".ao"),{recursive:!0});let e=G()?`## Athene (ao) Session
926
+
927
+ You are running inside an Athene managed workspace.
928
+ Session metadata is updated automatically via shell wrappers.
929
+ `:dj.trimStart();await (0,bU.writeFile)(d,e,"utf-8")}let dm=(0,E.promisify)(D.execFile),dn=/^(prEnrichment|prReviewComments)_\d+$/,dp="win32"===process.platform?{shell:!0,windowsHide:!0}:{};async function dq(a){let b,c=cT(a);if(c){for(let a of[0,200,600]){a>0&&await new Promise(b=>setTimeout(b,a));try{await dm("opencode",["session","delete",c],{timeout:3e4,...dp,env:cX()}),c$();return}catch(a){if(function(a){if(!(a instanceof Error))return!1;let b=[a.message,a.stderr,a.stdout].filter(Boolean).join("\n");return/session not found/i.test(b)}(a))return void c$();b=a}}throw b instanceof Error?b:Error(String(b))}}async function dr(a=1e4){return cZ({timeoutMs:a})}async function ds(a,b=1e4,c){let d=await (c??dr(b)),e=`AO:${a}`;return d.filter(a=>a.title===e).sort((a,b)=>{let c=a.updatedAt??-1/0,d=b.updatedAt??-1/0;return c===d?0:d-c}).map(a=>a.id)}async function dt(a,b,c){return(await ds(a,b,c))[0]}function du(a){return a.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}let dv=new Set(["pr_open","ci_failed","review_pending","changes_requested","approved","mergeable"]),dw=new Set([...dv,"merged"]);function dx(a){let b=a=>{let b=a.replace(/\s+/g," ").trim(),c=Array.from(b);return c.length<=80?b:`${c.slice(0,79).join("").trimEnd()}…`};if(a.issueTitle&&a.issueTitle.trim())return b(a.issueTitle);if(a.prompt&&a.prompt.trim()){let c=(a.prompt.split(/\r?\n/).map(a=>a.trim()).find(a=>a.length>0)??"").replace(/^#{1,6}\s+/,"");if(c)return b(c)}}function dy(a){return new Promise(b=>setTimeout(b,a))}let dz=0;async function dA(a,b){try{return await a.isProcessRunning(b)!==!1}catch{return!0}}function dB(a,b){return a instanceof Error&&a.message.includes(`Orchestrator session "${b}" already exists`)}async function dC(a){try{let{stdout:b}=await dm("tmux",["display-message","-p","-t",a,"#{pane_current_command}"],{timeout:5e3,windowsHide:!0}),c=b.trim();return c.length>0?c:null}catch{return null}}function dD(a){let b=a.lifecycle??a.statePayload;if(b)try{return JSON.parse(b)}catch{return}}function dE(a,b,c){let d="orchestrator"===b.role||c.sessionPrefix&&RegExp(`^${du(c.sessionPrefix)}-orchestrator-\\d+$`).test(a)?"orchestrator":"worker";return bZ(a,b,{projectId:c.projectId,workspacePathFallback:c.workspacePathFallback,sessionKind:d,createdAt:c.createdAt,lastActivityAt:c.modifiedAt??new Date})}function dF(a){let{config:b,registry:c}=a;function f(a){return(0,g.resolve)(a).replace(/[/\\]$/,"")}function i(a,b,c){return!!a&&!!b&&f(c)!==f(a.path)&&(function(a,b){let c=[w(a)],d=new Set;for(let e of(d.add(a),d.add((0,g.basename)(b)),d))c.push((0,g.join)((0,h.homedir)(),".worktrees",e));return c})(b,a.path).some(a=>(function(a,b){let c=f(a),d=f(b),e="win32"===process.platform?"\\":"/";return c===d||c.startsWith(`${d}${e}`)})(c,a))}function j(a,b,c){return!!b&&("orchestrator"===b.role||!!c&&(a===`${c}-orchestrator`||RegExp(`^${du(c)}-orchestrator-\\d+$`).test(a)))}function k(a,b,c){return b===`${a.sessionPrefix}-orchestrator`||j(b,c??{},a.sessionPrefix)}function l(a,b){let c={...a};for(let[a,d]of Object.entries(b))if(void 0!==d){if(""===d){let{[a]:b,...d}=c;c=d;continue}c[a]=d}return c}function n(a,b,c){let d=bt(bq(b,{sessionId:a,status:bh(b.status)}));return c(d),bm(d),d}function q(a,b,c,d){let f=(0,g.join)(a,`${b}.json`),h=d;if(!h)try{h=(0,e.statSync)(f).mtime}catch{h=void 0}if(bE(a,b,c),h)try{(0,e.utimesSync)(f,h,h)}catch{}}let r=null,s=new Map,t=new Map,x=new Map;function z(){r=null}function B(a,b,c){if(b.raw.agent)return b;let d=J(c,b.sessionName,b.raw).agentName;return q(a,b.sessionName,{agent:d},b.modifiedAt),{...b,raw:l(b.raw,{agent:d})}}function C(a,b,c){let d={...b,raw:{...b.raw}};if(!j(d.sessionName,d.raw,c))return d;let e={};if("orchestrator"!==d.raw.role&&(e.role="orchestrator"),d.raw.pr&&(e.pr=""),"off"!==d.raw.prAutoDetect&&"false"!==d.raw.prAutoDetect&&(e.prAutoDetect="false"),dw.has(d.raw.status??"")&&(e.status="working"),Object.keys(e).length>0){let b=n(d.sessionName,d.raw,a=>{a.session.kind="orchestrator",a.pr.state="none",a.pr.reason="not_created",a.pr.number=null,a.pr.url=null,a.pr.lastObservedAt=null,"working"===e.status&&(a.session.state="working",a.session.reason="task_in_progress")});q(a,d.sessionName,{...e,...(d.raw,bs(b))},d.modifiedAt),d.raw=l(d.raw,{...e,...(d.raw,bs(b))})}return d}function D(a){let b=Date.parse(a.raw.restoredAt??a.raw.createdAt??"");return a.modifiedAt?a.modifiedAt.getTime():Number.isNaN(b)?0:b}function E(a,b){let c=v(a);if(!(0,e.existsSync)(c))return[];let d=bI(c).flatMap(a=>{let b,d=bB(c,a);if(!d)return[];try{b=(0,e.statSync)((0,g.join)(c,`${a}.json`)).mtime}catch{}return[{sessionName:a,raw:d,modifiedAt:b}]});return function(a,b,c){let d=b.map(a=>({...a,raw:{...a.raw}})),e=new Map;for(let b of d){if(!b.raw.lifecycle&&(!b.raw.statePayload||"2"!==b.raw.stateVersion)){let d=bt(bq(b.raw,{sessionId:b.sessionName,status:bh(b.raw.status),createdAt:b.raw.createdAt?new Date(b.raw.createdAt):void 0,sessionKind:j(b.sessionName,b.raw,c.sessionPrefix)?"orchestrator":"worker"})),e=(b.raw,bs(d));q(a,b.sessionName,e,b.modifiedAt),b.raw=l(b.raw,e)}if(j(b.sessionName,b.raw,c.sessionPrefix)){b.raw=C(a,b,c.sessionPrefix).raw,b.raw=B(a,b,c).raw;continue}b.raw=B(a,b,c).raw;let d=b.raw.pr;if(!d)continue;let f=e.get(d)??[];f.push(b),e.set(d,f)}for(let b of e.values()){if(b.length<2)continue;let[c,...d]=[...b].sort((a,b)=>{let c=Number(dv.has(b.raw.status??""))-Number(dv.has(a.raw.status??""));if(0!==c)return c;let d=D(b)-D(a);return 0!==d?d:b.sessionName.localeCompare(a.sessionName)});for(let b of d){let c={pr:"",prAutoDetect:"false",...dv.has(b.raw.status??"")?{status:"working"}:{}},d=n(b.sessionName,b.raw,a=>{a.pr.state="none",a.pr.reason="not_created",a.pr.number=null,a.pr.url=null,a.pr.lastObservedAt=null,"working"===c.status&&(a.session.state="working",a.session.reason="task_in_progress")}),e=(b.raw,bs(d));q(a,b.sessionName,{...c,...e},b.modifiedAt),b.raw=l(b.raw,{...c,...e})}}return d}(c,d,b)}async function F(a){let{sessionsDir:b,criteria:c,strategy:d,includeTitleDiscoveryForSessionId:e=!1}=a;if("ignore"===d)return;let f=function(a,b){let c=[],d=(a,d)=>{if(!d||"opencode"!==d.agent||void 0!==b.issueId&&d.issue!==b.issueId||void 0!==b.sessionId&&a!==b.sessionId)return;let e=cT(d?.opencodeSessionId);e&&c.push(e)};for(let b of function(a){let b=a=>{let b=a.match(/-(\d+)$/);if(!b)return;let c=Number.parseInt(b[1],10);return Number.isNaN(c)?void 0:c};return[...a].sort((a,c)=>{let d=b(a),e=b(c);return void 0!==d&&void 0!==e&&d!==e?e-d:void 0!==d&&void 0===e?-1:void 0===d&&void 0!==e?1:c.localeCompare(a)})}(bI(a)))d(b,bB(a,b));return[...new Set(c)]}(b,c);if("delete"===d){for(let a of(e&&c.sessionId&&(f=[...f,...await ds(c.sessionId)]),[...new Set(f)]))await dq(a);return}return 0===f.length&&c.sessionId&&(f=await ds(c.sessionId)),f[0]}async function G(a){try{let{stdout:b}=await dm("git",["ls-remote","--heads","origin",`session/${a.sessionPrefix}-*`],{cwd:a.path,timeout:5e3,...dp});return b.split("\n").flatMap(b=>{let c=b.trim();if(!c)return[];let d=(c.split(/\s+/)[1]??"").match(RegExp(`refs/heads/session/${du(a.sessionPrefix)}-(\\d+)$`));if(!d)return[];let e=Number.parseInt(d[1],10);return Number.isNaN(e)?[]:[e]}).filter((a,b,c)=>c.indexOf(a)===b)}catch{return[]}}async function H(a,b){let c=u(a);(0,e.mkdirSync)(c,{recursive:!0});let d=(0,g.join)(c,"spawn.lock"),f=Date.now()+3e4,h=null,i=10;for(;null===h;)try{h=(0,e.openSync)(d,"wx")}catch(b){if("EEXIST"!==b.code)throw Error(`Failed to acquire spawn lock: ${d}`,{cause:b});if(Date.now()>f)throw Error(`Timed out acquiring spawn lock for project '${a}'`,{cause:b});if(function(a,b=Date.now()){let c,d;try{c=(0,e.readFileSync)(a,"utf8").trim(),d=(0,e.statSync)(a).mtimeMs}catch{return!0}if(b-d>3e5)return!0;let f=function(a){let b=a.split(":",1)[0]??"",c=Number.parseInt(b,10);return Number.isInteger(c)&&c>0&&String(c)===b?c:null}(c);return null!==f&&!function(a){if(!Number.isInteger(a)||a<=0)return!1;try{return process.kill(a,0),!0}catch(a){return"EPERM"===a.code}}(f)}(d)){(0,e.rmSync)(d,{force:!0});continue}await dy(i),i=Math.min(2*i,250)}let j=`${process.pid}:${process.hrtime.bigint().toString(36)}-${(dz++).toString(36)}`;try{(0,e.writeFileSync)(d,j)}catch{}try{return await b()}finally{try{(0,e.closeSync)(h)}catch{}try{(0,e.readFileSync)(d,"utf8").trim()===j&&(0,e.rmSync)(d,{force:!0})}catch{}}}function I(a,d){let e=c.get("runtime",a.runtime??b.defaults.runtime),f=c.get("agent",d??a.agent??b.defaults.agent),g=c.get("workspace",a.workspace??b.defaults.workspace);return{runtime:e,agent:f,workspace:g,tracker:a.tracker?.plugin?c.get("tracker",a.tracker.plugin):null,scm:a.scm?.plugin?c.get("scm",a.scm.plugin):null}}function J(a,c,d){var e;return bL({role:bK((e={sessionId:c,metadata:d,project:a,defaults:b.defaults,allSessionPrefixes:Object.values(b.projects).map(a=>a.sessionPrefix)}).sessionId,e.metadata,e.project.sessionPrefix,e.allSessionPrefixes),project:e.project,defaults:e.defaults,persistedAgent:e.metadata?.agent})}async function K(a,b,c,d,e){if("opencode"!==d||cT(a.metadata.opencodeSessionId))return;let f=await dt(b,1e4,e);f&&(a.metadata.opencodeSessionId=f,bE(c,b,{opencodeSessionId:f}))}function L(a){for(let[c,d]of Object.entries(b.projects)){let b,f=v(c),h=bB(f,a);if(h){try{b=(0,e.statSync)((0,g.join)(f,`${a}.json`)).mtime}catch{b=void 0}return{raw:B(f,C(f,{sessionName:a,raw:h,modifiedAt:b},d.sessionPrefix),d).raw,sessionsDir:f,project:d,projectId:c}}}return null}function M(a){let b=L(a);if(!b)throw new d.Ag(a);return b}async function N(a,c,d,e,f,g,h){await K(a,c,d,f,h);let i=a.metadata.tmuxName?.trim(),j="string"==typeof i&&i.length>0,k=null!==a.runtimeHandle||j;k?!a.runtimeHandle&&j&&(a.runtimeHandle={id:i,runtimeName:e.runtime??b.defaults.runtime,data:{}}):a.runtimeHandle={id:c,runtimeName:e.runtime??b.defaults.runtime,data:{}},await P(a,g,k,d)}!function(){let a=!1;for(let[c]of Object.entries(b.projects)){let b=v(c);if((0,e.existsSync)(b))for(let d of bI(b)){let e=bB(b,d);if(!e)continue;let f=e.prs?e.prs.split(",").map(a=>a.trim()).filter(Boolean):[],g=be(f),h={};f.length!==g.length&&(h.prs=g.join(","));let i=0;for(let a of Object.keys(e))dn.test(a)&&(h[a]="",i+=1);0!==Object.keys(h).length&&(bE(b,d,h),a=!0,aa({projectId:c,sessionId:d,source:"session-manager",kind:"metadata.deduplicated",summary:`deduplicated PR metadata: ${d}`,data:{beforePrCount:f.length,afterPrCount:g.length,deletedIndexedKeyCount:i}}))}}a&&z()}();let O=new Set(["killed","done","merged","terminated","cleanup"]);async function P(a,c,d,e){async function f(b){let d;if(!c.agent||b?.skipIfNativeRestoreMetadataPresent&&function(a,b){let c=a.metadata??{};switch(b.name){case"claude-code":return"string"==typeof c.claudeSessionUuid&&c.claudeSessionUuid.trim().length>0;case"codex":return"string"==typeof c.codexThreadId&&c.codexThreadId.trim().length>0;case"opencode":return null!==cT(c.opencodeSessionId);default:return!1}}(a,c.agent))return;try{d=await c.agent.getSessionInfo(a)}catch{d=null}if(!d)return;a.agentInfo=d;let f=d.metadata??{};if(!Object.keys(f).every(b=>a.metadata?.[b]===f[b])&&Object.keys(f).length>0)try{bE(e,a.id,f),a.metadata=bF(a.metadata,f),z()}catch{}}if(d&&a.runtimeHandle&&c.runtime&&"spawning"!==a.status)try{if(!await c.runtime.isAlive(a.runtimeHandle)){var g;a.lifecycle.runtime.state="missing",a.lifecycle.runtime.reason="tmux"===a.runtimeHandle.runtimeName?"tmux_missing":"process_missing",a.lifecycle.runtime.lastObservedAt=new Date().toISOString(),"done"!==a.lifecycle.session.state&&"terminated"!==a.lifecycle.session.state&&(a.lifecycle.session.state="detecting",a.lifecycle.session.reason="runtime_lost",a.lifecycle.session.lastTransitionAt=new Date().toISOString()),O.has(a.status)||(a.status="killed"),a.activity="exited",a.activitySignal=bQ("valid",{activity:"exited",source:"runtime"}),c.agent&&(g=c.agent,"claude-code"===g.name||"codex"===g.name)&&await f({skipIfNativeRestoreMetadataPresent:!0});return}}catch{a.lifecycle.runtime.state="probe_failed",a.lifecycle.runtime.reason="probe_error",a.lifecycle.runtime.lastObservedAt=new Date().toISOString()}if(a.activitySignal=bQ("unavailable"),c.agent){try{let d=await c.agent.getActivityState(a,b.readyThresholdMs);null!==d?(a.activitySignal=bR(d,"native"),a.activity=d.state,a.lifecycle.runtime.state="alive",a.lifecycle.runtime.reason="process_running",a.lifecycle.runtime.lastObservedAt=new Date().toISOString(),d.timestamp&&d.timestamp>a.lastActivityAt&&(a.lastActivityAt=d.timestamp)):a.activitySignal=bQ("null",{source:"native"})}catch{a.activitySignal=bQ("probe_failure",{source:"native"})}await f()}}async function Q(a){let c,f,h,j=b.projects[a.projectId];if(!j)throw Error(`Unknown project: ${a.projectId}`);let k=bL({role:"worker",project:j,defaults:b.defaults,spawnAgentOverride:a.agent}),l=I(j,k.agentName);if(!l.runtime)throw Error(`Runtime plugin '${j.runtime??b.defaults.runtime}' not found`);if(!l.agent)throw Error(`Agent plugin '${k.agentName}' not found`);if(a.issueId&&l.tracker)try{c=await l.tracker.getIssue(a.issueId,j)}catch(b){if((0,d.Fx)(b));else throw aa({projectId:a.projectId,source:"session-manager",kind:"tracker.issue_fetch_failed",level:"error",summary:`tracker getIssue failed for ${a.issueId}`,data:{issueId:a.issueId,tracker:l.tracker.name,reason:b instanceof Error?b.message:String(b)}}),Error(`Failed to fetch issue ${a.issueId}: ${b}`,{cause:b})}let n=v(a.projectId),q=new c3,r=await G(j);if(await H(a.projectId,async()=>{let b=function(a,b){let c=a.filter(a=>a.projectId===b.projectId),d=b.issueId?.toLowerCase();return{hard:d?c.find(a=>a.issueId?.toLowerCase()===d)??null:null,advisory:c}}((function(a){let b=v(a),c=[];for(let d of bI(b)){let e=bB(b,d);e&&c.push(bZ(d,e,{projectId:a}))}return c})(a.projectId).filter(a=>!function(a){let b=a.lifecycle.session.state;return"done"===b||"terminated"===b||"merged"===a.lifecycle.pr.state}(a)),{projectId:a.projectId,issueId:a.issueId});if(b.hard)throw Error(function(a){let b=a.metadata?.ownerKind==="meta"?"meta":"project";return`SPAWN REFUSED: ${a.id} already owns ${a.issueId} (owner=${b}, status=${a.status})`}(b.hard));if({sessionId:f,tmuxName:h}=function(a,b,c){let d=new Set;for(let c of bI(b)){let b=function(a,b){let c=a.match(RegExp(`^${du(b)}-(\\d+)$`));if(!c)return;let d=Number.parseInt(c[1],10);return Number.isNaN(d)?void 0:d}(c,a.sessionPrefix);void 0!==b&&d.add(b)}for(let a of c)d.add(a);let e=function(a,b){let c=0,d=RegExp(`^${du(b)}-(\\d+)$`);for(let b of a){let a=b.match(d);if(a){let b=parseInt(a[1],10);b>c&&(c=b)}}return c+1}([...d].map(b=>`${a.sessionPrefix}-${b}`),a.sessionPrefix);for(let c=0;c<1e4;c++){var f,g;let c=`${a.sessionPrefix}-${e}`,h=a.path?(f=a.sessionPrefix,g=e,`${f}-${g}`):void 0;if(!d.has(e)&&bJ(b,c))return{num:e,sessionId:c,tmuxName:h};d.add(e),e+=1}throw Error(`Failed to reserve session ID after 10000 attempts (prefix: ${a.sessionPrefix})`)}(j,n,r),a.issueId)try{bE(n,f,{issue:a.issueId,project:a.projectId,status:"spawning"})}catch(a){try{bH(n,f)}catch{}throw a}}),!f)throw Error("Failed to reserve a session id");let s=f;q.push(()=>bH(n,s));try{let d,r,s;if(a.branch)d=a.branch;else if(a.issueId&&l.tracker&&c){let b=c.branchName;d=b&&function(a){if(!a||"@"===a||a.startsWith(".")||a.endsWith(".")||a.endsWith("/")||a.endsWith(".lock")||a.includes("..")||a.includes("//")||a.includes("/.")||a.includes("@{")||a.startsWith("/"))return!1;for(let b=0;b<a.length;b++){let c=a.charCodeAt(b);if(c<=31||127===c)return!1}return!/[\s~^:?*[\\]/.test(a)}(b)?b:l.tracker.branchName(a.issueId,j)}else if(a.issueId){let b=a.issueId,c=/^[A-Za-z0-9][A-Za-z0-9._-]*$/.test(b)&&!b.includes("..")?b:b.toLowerCase().replace(/[^a-z0-9]+/g,"-").slice(0,60).replace(/^-+|-+$/g,"");d=`feat/${c||f}`}else d=`session/${f}`;let t=j.path;if(l.workspace){let b=await l.workspace.create({projectId:a.projectId,project:j,sessionId:f,branch:d,worktreeDir:w(a.projectId)});if(t=b.path,i(j,a.projectId,t)){let a=l.workspace;q.push(()=>a.destroy(t))}l.workspace.postCreate&&await l.workspace.postCreate(b,j)}if(a.issueId&&l.tracker&&c)try{r=await l.tracker.generatePrompt(a.issueId,j)}catch(b){aa({projectId:a.projectId,sessionId:f,source:"session-manager",kind:"tracker.generate_prompt_failed",level:"warn",summary:`tracker generatePrompt failed for ${a.issueId}`,data:{issueId:a.issueId,tracker:l.tracker.name,reason:b instanceof Error?b.message:String(b)}})}let v=`${j.sessionPrefix}-orchestrator`,x=null!==bB(n,v),{systemPrompt:y,taskPrompt:A}=function(a){let b=function(a){let b=[];if(a.agentRules&&b.push(a.agentRules),a.agentRulesFile){let c=(0,g.resolve)(a.path,a.agentRulesFile);try{let a=(0,e.readFileSync)(c,"utf-8").trim();a&&b.push(a)}catch{}}return b.length>0?b.join("\n\n"):null}(a.project),c=[];return c.push(a.project.repo?cQ:cR),a.orchestratorSessionId&&c.push(`## Talking to the Orchestrator
930
+ You can message the orchestrator session that spawned you with:
931
+
932
+ \`athene send ${a.orchestratorSessionId} "<your message>"\`
933
+
934
+ Only do this when you genuinely cannot proceed alone — cross-session coordination, a decision only the human-facing orchestrator can make, or a blocker outside your repo's scope. Do NOT ping for things you can resolve yourself (research, retries, normal CI/review fixes go through \`athene report\` and the existing flow). \`athene send\` automatically tags the message with your session ID, so the orchestrator always knows who's writing.`),c.push(function(a){let{project:b,projectId:c,issueId:d,issueContext:e}=a,f=[];if(f.push("## Project Context"),f.push(`- Project: ${b.name??c}`),b.repo&&f.push(`- Repository: ${b.repo}`),f.push(`- Default branch: ${b.defaultBranch}`),b.tracker&&f.push(`- Tracker: ${b.tracker.plugin}`),d){let a=d.replace(/^#/,"");f.push(`
935
+ ## Task`),f.push(`Work on issue #${a}`),f.push(`Create a branch named so that it auto-links to the issue tracker (e.g. feat/${a}).`)}if(e&&(f.push(`
936
+ ## Issue Details`),f.push(e)),b.reactions){let a=[];for(let[c,d]of Object.entries(b.reactions))d.auto&&"send-to-agent"===d.action&&a.push(`- ${c}: auto-handled (you'll receive instructions)`);a.length>0&&(f.push(`
937
+ ## Automated Reactions`),f.push("The orchestrator will automatically handle these events:"),f.push(...a))}return f.join("\n")}(a)),b&&c.push(`## Project Rules
938
+ ${b}`),{systemPrompt:c.join("\n\n"),taskPrompt:a.userPrompt?a.userPrompt:a.issueId?a.issueContext?`Work on issue #${a.issueId.replace(/^#/,"")}. The issue title, description, and labels are already in your system prompt — start implementing without re-fetching the issue. Fetch comments or linked issues only if you need additional context.`:`Work on issue #${a.issueId.replace(/^#/,"")}. Issue details were not pre-fetched — start by reading the issue (e.g. \`gh issue view ${a.issueId.replace(/^#/,"")}\`), then implement.`:void 0}}({project:j,projectId:a.projectId,issueId:a.issueId,issueContext:r,userPrompt:a.prompt,...x&&{orchestratorSessionId:v}}),B=u(a.projectId);(0,e.mkdirSync)(B,{recursive:!0});let C=(0,g.join)(B,`worker-prompt-${f}.md`);if((0,e.writeFileSync)(C,y,"utf-8"),q.push(()=>(0,e.unlinkSync)(C)),"opencode"===l.agent.name){let a=s=c2(B,f,[C]);q.push(()=>(0,e.unlinkSync)(a))}let D=j.opencodeIssueSessionStrategy??"reuse",E="opencode"===l.agent.name&&a.issueId?await F({sessionsDir:n,criteria:{issueId:a.issueId},strategy:D}):void 0,G={sessionId:f,projectConfig:{...j,agentConfig:{...k.agentConfig,...E?{opencodeSessionId:E}:{}}},workspacePath:t,issueId:a.issueId,prompt:A,systemPromptFile:C,permissions:k.permissions,model:k.model,subagent:a.subagent??k.subagent},H=l.agent.getLaunchCommand(G),I=l.agent.getEnvironment(G);l.agent.preLaunchSetup&&await l.agent.preLaunchSetup(t),l.agent.setupWorkspaceHooks&&await l.agent.setupWorkspaceHooks(t,{dataDir:n}),"claude-code"!==l.agent.name&&await dl(t);let J=await l.runtime.create({sessionId:h??f,workspacePath:t,launchCommand:H,environment:p({...I,...s?{OPENCODE_CONFIG:s}:{},...j.env??{},PATH:de(I.PATH??process.env.PATH),GH_PATH:db,...o(m.AGENT_GH_TRACE)&&{[m.AGENT_GH_TRACE]:o(m.AGENT_GH_TRACE)},[m.SESSION]:f,[m.DATA_DIR]:n,[m.SESSION_NAME]:f,...h&&{[m.TMUX_NAME]:h},[m.CALLER_TYPE]:"agent",[m.PROJECT_ID]:a.projectId,[m.CONFIG_PATH]:b.configPath,...void 0!==b.port&&null!==b.port&&{[m.PORT]:String(b.port)}})}),K=l.runtime;q.push(()=>K.destroy(J));let L=dx({issueTitle:c?.title,prompt:a.prompt}),M=new Date,N=bo("worker",M);N.runtime.handle=J,N.runtime.tmuxName=h??null;let O={id:f,projectId:a.projectId,status:br(N),activity:"active",activitySignal:bQ("valid",{activity:"active",timestamp:M,source:"runtime"}),lifecycle:N,branch:d,issueId:a.issueId??null,pr:null,prs:[],workspacePath:t,runtimeHandle:J,agentInfo:null,createdAt:M,lastActivityAt:M,metadata:{...E?{opencodeSessionId:E}:{},...a.prompt?{userPrompt:a.prompt}:{},...L?{displayName:L}:{},..."meta"===a.ownerKind?{ownerKind:"meta",...a.metaOwner?{metaOwner:a.metaOwner}:{}}:{}}};if(bD(n,f,{worktree:t,branch:d,status:br(N),...bs(N),lifecycle:N,tmuxName:h,issue:a.issueId,issueTitle:c?.title,project:a.projectId,agent:k.agentName,createdAt:M.toISOString(),runtimeHandle:J,opencodeSessionId:E,userPrompt:a.prompt,displayName:L}),l.agent.postLaunchSetup&&await l.agent.postLaunchSetup(O),"post-launch"===l.agent.promptDelivery&&G.prompt&&await l.runtime.sendMessage(J,G.prompt),"opencode"===l.agent.name&&"reuse"===D&&!O.metadata.opencodeSessionId){let a=await dt(f,1e4);a&&(O.metadata.opencodeSessionId=a)}return Object.keys(O.metadata||{}).length>0&&bE(n,f,O.metadata),z(),q.dismiss(),aa({projectId:a.projectId,sessionId:f,source:"session-manager",kind:"session.spawned",summary:`spawned: ${f}`,data:{agent:l.agent.name,branch:O.branch??void 0}}),O}catch(b){throw aa({projectId:a.projectId,sessionId:f,source:"session-manager",kind:"session.rollback_started",level:"warn",summary:"spawn rollback started",data:{reason:b instanceof Error?b.message:String(b)}}),await q.runAll(b=>{console.error("[session-manager] spawn rollback step failed:",b),aa({projectId:a.projectId,sessionId:f,source:"session-manager",kind:"session.rollback_step_failed",level:"error",summary:"spawn rollback step failed",data:{reason:b instanceof Error?b.message:String(b)}})}),b}}function R(a,b,c){aa({projectId:a.projectId,...c?{sessionId:c}:{},source:"session-manager",kind:"session.spawn_failed",level:"error",summary:"orchestrator spawn failed",data:{role:"orchestrator",reason:b instanceof Error?b.message:String(b)}})}async function S(a,c){aa({projectId:a.projectId,source:"session-manager",kind:"session.spawn_started",summary:"orchestrator spawn started",data:{agent:a.agent??void 0,role:"orchestrator"}});try{return await T(a)}catch(f){let d=b.projects[a.projectId],e=d?c4(d):void 0;throw c?.suppressFixedReservationFailure===!0&&void 0!==e&&dB(f,e)||R(a,f,e),f}}async function T(a){let c,d,f,h,i=b.projects[a.projectId];if(!i)throw Error(`Unknown project: ${a.projectId}`);let j=bL({role:"orchestrator",project:i,defaults:b.defaults,spawnAgentOverride:a.agent}),k=I(i,j.agentName);if(!k.runtime)throw Error(`Runtime plugin '${i.runtime??b.defaults.runtime}' not found`);if(!k.agent)throw Error(`Agent plugin '${j.agentName}' not found`);let l=v(a.projectId),n=c5(i.orchestratorSessionStrategy),q=function(a,c){let d=c4(a);if(!bJ(c,d))throw Error(`Orchestrator session "${d}" already exists. Use ensureOrchestrator() to reuse or restore it.`);return{sessionId:d,tmuxName:b.configPath?d:void 0}}(i,l),r=q.sessionId,s=q.tmuxName,t=`orchestrator/${r}`;if(!k.workspace){try{bH(l,r)}catch{}throw Error(`spawnOrchestrator requires a workspace plugin but none is configured for project '${a.projectId}'`)}let x={projectId:a.projectId,project:i,sessionId:r,branch:t,worktreeDir:w(a.projectId)},y=!1;try{let a=await k.workspace.findManagedWorkspace?.(x);c=(a??await k.workspace.create(x)).path,y=null!=a}catch(b){aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawn_step_failed",level:"error",summary:"orchestrator workspace.create failed",data:{role:"orchestrator",stage:"workspace_create",reason:b instanceof Error?b.message:String(b)}});try{bH(l,r)}catch{}throw b}let A=async a=>{if(!y)try{await k.workspace.destroy(c)}catch{}try{bH(l,r)}catch{}if(a)try{(0,e.unlinkSync)(a)}catch{}};try{k.agent.setupWorkspaceHooks&&await k.agent.setupWorkspaceHooks(c,{dataDir:l}),"claude-code"!==k.agent.name&&await dl(c)}catch(b){throw aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.workspace_hooks_failed",level:"error",summary:"orchestrator workspace hooks installation failed",data:{agent:k.agent.name,reason:b instanceof Error?b.message:String(b)}}),await A(),b}if(a.systemPrompt)try{let b=u(a.projectId);(0,e.mkdirSync)(b,{recursive:!0}),d=(0,g.join)(b,`orchestrator-prompt-${r}.md`),(0,e.writeFileSync)(d,a.systemPrompt,"utf-8")}catch(b){throw aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawn_step_failed",level:"error",summary:"orchestrator systemPrompt write failed",data:{role:"orchestrator",stage:"system_prompt_write",reason:b instanceof Error?b.message:String(b)}}),await A(d),b}if("opencode"===k.agent.name&&d)try{c1(c,d)}catch(b){throw aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawn_step_failed",level:"error",summary:"orchestrator AGENTS.md write failed",data:{role:"orchestrator",stage:"agents_md_write",reason:b instanceof Error?b.message:String(b)}}),await A(d),b}try{f="opencode"===k.agent.name&&"reuse"===n?await F({sessionsDir:l,criteria:{sessionId:r},strategy:"reuse"}):void 0,"opencode"===k.agent.name&&"delete"===n&&await F({sessionsDir:l,criteria:{sessionId:r},strategy:"delete",includeTitleDiscoveryForSessionId:!0})}catch(b){throw aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawn_step_failed",level:"error",summary:"orchestrator opencode session resolution failed",data:{role:"orchestrator",stage:"opencode_session_reuse",reason:b instanceof Error?b.message:String(b)}}),await A(d),b}let B={sessionId:r,projectConfig:{...i,agentConfig:{...j.agentConfig,permissions:"permissionless",...f?{opencodeSessionId:f}:{}}},workspacePath:c,permissions:"permissionless",model:j.model,systemPromptFile:d,subagent:j.subagent},C=k.agent.getLaunchCommand(B),D=k.agent.getEnvironment(B);k.agent.preLaunchSetup&&await k.agent.preLaunchSetup(c);try{h=await k.runtime.create({sessionId:s??r,workspacePath:c,launchCommand:C,environment:p({...D,...i.env??{},PATH:de(D.PATH??process.env.PATH),GH_PATH:db,...o(m.AGENT_GH_TRACE)&&{[m.AGENT_GH_TRACE]:o(m.AGENT_GH_TRACE)},[m.SESSION]:r,[m.DATA_DIR]:l,[m.SESSION_NAME]:r,...s&&{[m.TMUX_NAME]:s},[m.CALLER_TYPE]:"orchestrator",[m.PROJECT_ID]:a.projectId,[m.CONFIG_PATH]:b.configPath,...void 0!==b.port&&null!==b.port&&{[m.PORT]:String(b.port)}})})}catch(b){throw aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawn_step_failed",level:"error",summary:"orchestrator runtime.create failed",data:{role:"orchestrator",stage:"runtime_create",reason:b instanceof Error?b.message:String(b)}}),await A(d),b}let E=dx({prompt:a.systemPrompt}),G=new Date,H=bo("orchestrator",G);H.session.state="working",H.session.reason="task_in_progress",H.session.startedAt=G.toISOString(),H.session.lastTransitionAt=G.toISOString(),H.runtime.handle=h,H.runtime.tmuxName=s??null;let J={id:r,projectId:a.projectId,status:br(H),activity:"active",activitySignal:bQ("valid",{activity:"active",timestamp:G,source:"runtime"}),lifecycle:H,branch:t,issueId:null,pr:null,prs:[],workspacePath:c,runtimeHandle:h,agentInfo:null,createdAt:G,lastActivityAt:G,metadata:{...f?{opencodeSessionId:f}:{},...E?{displayName:E}:{}}};try{if(bD(l,r,{worktree:c,branch:t,status:br(H),...bs(H),lifecycle:H,role:"orchestrator",tmuxName:s,project:a.projectId,agent:j.agentName,createdAt:G.toISOString(),runtimeHandle:h,opencodeSessionId:f,displayName:E}),k.agent.postLaunchSetup&&await k.agent.postLaunchSetup(J),"post-launch"===k.agent.promptDelivery&&a.systemPrompt&&await k.runtime.sendMessage(h,"Begin."),"opencode"===k.agent.name&&"reuse"===n&&!J.metadata.opencodeSessionId){let a=await dt(r,1e4);a&&(J.metadata.opencodeSessionId=a)}Object.keys(J.metadata||{}).length>0&&bE(l,r,J.metadata),z()}catch(b){aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawn_step_failed",level:"error",summary:"orchestrator post-launch metadata write failed",data:{role:"orchestrator",stage:"post_launch_metadata",reason:b instanceof Error?b.message:String(b)}});try{await k.runtime.destroy(h)}catch{}throw await A(d),b}return aa({projectId:a.projectId,sessionId:r,source:"session-manager",kind:"session.spawned",summary:`spawned: ${r}`,data:{agent:k.agent.name,branch:J.branch??void 0,role:"orchestrator"}}),J}async function U(a){let b=Date.now()+2e4;for(;Date.now()<b;){let b=await ac(a);if(b?.metadata.role==="orchestrator")return b;await dy(250)}return null}async function V(a){let c=b.projects[a.projectId];if(!c)throw Error(`Unknown project: ${a.projectId}`);let e=c4(c),f=t.get(e);f&&await f.catch(a=>{console.warn(`[ensureOrchestrator] in-flight relaunch for ${e} failed before ensure proceeded:`,a)});let g=await ac(e);if(g){let b=c5(c.orchestratorSessionStrategy);if("delete"===b||"ignore"===b)return await ad(e,{purgeOpenCode:"delete"===b}),bH(v(a.projectId),e),S(a);if("done"===g.lifecycle.session.state)throw new d.D8(e,`canonical orchestrator session is terminal with status "${g.status}". Remove or clean up this session before starting a new orchestrator.`);if((0,d.qX)(g))return ah(e);if(!(0,d.zi)(g))return g;throw new d.D8(e,`canonical orchestrator session is terminal with status "${g.status}". Remove or clean up this session before starting a new orchestrator.`)}try{return await S(a,{suppressFixedReservationFailure:!0})}catch(c){if(!dB(c,e))throw c;aa({projectId:a.projectId,sessionId:e,source:"session-manager",kind:"session.orchestrator_conflict",level:"warn",summary:"concurrent orchestrator reservation conflict",data:{reason:c instanceof Error?c.message:String(c)}});let b=await U(e);if(b)return b;throw R(a,c,e),c}}function W(a){let b=bB(y(a),a);return b?bZ(a,b,{projectId:"_meta",sessionKind:"meta-orchestrator"}):null}function X(a,c){let d={name:`${a} (meta)`,path:A(a),defaultBranch:"main",sessionPrefix:a},e=bL({role:"orchestrator",project:d,defaults:b.defaults,spawnAgentOverride:c}),f=I(d,e.agentName);return{metaProject:d,selection:e,plugins:f}}async function Y(a){let b=a.name,c=W(b);if(c&&!(0,d.zi)(c)){let{plugins:d}=X(b,a.agent);if(c.runtimeHandle&&d.agent&&await dA(d.agent,c.runtimeHandle))return c;bH(y(b),b)}return Z(a)}async function Z(a){let c,f,h=a.name,i=y(h),j=A(h);aa({projectId:"_meta",source:"session-manager",kind:"session.spawn_started",summary:"meta orchestrator spawn started",data:{agent:a.agent??void 0,role:"meta-orchestrator"}});let{metaProject:k,selection:l,plugins:n}=X(h,a.agent);if(!n.runtime)throw Error(`Runtime plugin '${b.defaults.runtime}' not found`);if(!n.agent)throw Error(`Agent plugin '${l.agentName}' not found`);if((0,e.mkdirSync)(j,{recursive:!0}),(0,e.mkdirSync)(i,{recursive:!0}),!bJ(i,h)){let a=W(h);if(a&&!(0,d.zi)(a)&&a.runtimeHandle&&n.agent&&await dA(n.agent,a.runtimeHandle))return a;if(bH(i,h),!bJ(i,h))throw Error(`Meta orchestrator '${h}' is already being created`)}let o=async a=>{if(a)try{await n.runtime.destroy(a)}catch{}try{bH(i,h)}catch{}};try{n.agent.setupWorkspaceHooks&&await n.agent.setupWorkspaceHooks(j,{dataDir:i}),"claude-code"!==n.agent.name&&await dl(j)}catch(a){throw await o(),a}a.systemPrompt&&(c=(0,g.join)(j,`meta-orchestrator-prompt-${h}.md`),(0,e.writeFileSync)(c,a.systemPrompt,"utf-8"),"opencode"===n.agent.name&&c1(j,c));let q={sessionId:h,projectConfig:{...k,agentConfig:{...l.agentConfig,permissions:"permissionless"}},workspacePath:j,permissions:"permissionless",model:l.model,systemPromptFile:c,subagent:l.subagent},r=n.agent.getLaunchCommand(q),s=n.agent.getEnvironment(q);n.agent.preLaunchSetup&&await n.agent.preLaunchSetup(j);try{f=await n.runtime.create({sessionId:h,workspacePath:j,launchCommand:r,environment:p({...s,PATH:de(s.PATH??process.env.PATH),GH_PATH:db,[m.SESSION]:h,[m.DATA_DIR]:i,[m.SESSION_NAME]:h,[m.CALLER_TYPE]:"meta-orchestrator",[m.PROJECT_ID]:"_meta",[m.META_NAME]:h,[m.CONFIG_PATH]:b.configPath,...void 0!==b.port&&null!==b.port&&{[m.PORT]:String(b.port)}})})}catch(a){throw await o(),a}let t=new Date,u=bo("meta-orchestrator",t);u.session.state="working",u.session.reason="task_in_progress",u.session.startedAt=t.toISOString(),u.session.lastTransitionAt=t.toISOString(),u.runtime.handle=f;let v=`${h} (meta)`,w={id:h,projectId:"_meta",status:br(u),activity:"active",activitySignal:bQ("valid",{activity:"active",timestamp:t,source:"runtime"}),lifecycle:u,branch:null,issueId:null,pr:null,prs:[],workspacePath:j,runtimeHandle:f,agentInfo:null,createdAt:t,lastActivityAt:t,metadata:{role:"meta-orchestrator",metaName:h,...v?{displayName:v}:{}}};try{bD(i,h,{worktree:j,branch:"",status:br(u),...bs(u),lifecycle:u,role:"meta-orchestrator",project:"_meta",agent:l.agentName,createdAt:t.toISOString(),runtimeHandle:f,displayName:v}),n.agent.postLaunchSetup&&await n.agent.postLaunchSetup(w),"post-launch"===n.agent.promptDelivery&&a.systemPrompt&&await n.runtime.sendMessage(f,"Begin."),Object.keys(w.metadata||{}).length>0&&bE(i,h,w.metadata),z()}catch(a){throw await o(f),a}return aa({projectId:"_meta",sessionId:h,source:"session-manager",kind:"session.spawned",summary:`spawned: ${h}`,data:{agent:n.agent.name,role:"meta-orchestrator"}}),w}async function $(a){let c=b.projects[a.projectId];if(!c)throw Error(`Unknown project: ${a.projectId}`);let d=c4(c),e=v(a.projectId),f=s.get(d);if(f&&await f.catch(a=>{console.warn(`[relaunchOrchestrator] in-flight ensure for ${d} failed before relaunch proceeded:`,a)}),await ac(d)){let a=J(c,d,bB(e,d)??{}).agentName;await ad(d,{purgeOpenCode:"opencode"===a}),bH(e,d)}return S(a)}async function _(a){let c,d=Object.entries(b.projects).flatMap(([b,c])=>a&&b!==a?[]:E(b,c).map(a=>({sessionName:a.sessionName,projectId:b,raw:a.raw}))).map(async({sessionName:a,projectId:d,raw:f})=>{let h,i,j=b.projects[d];if(!j)return null;let k=v(d);try{let b=(0,g.join)(k,`${a}.json`),c=(0,e.statSync)(b);h=c.birthtime,i=c.mtime}catch{}let l=dE(a,f,{projectId:d,sessionPrefix:j.sessionPrefix,createdAt:h,modifiedAt:i,workspacePathFallback:j.path}),m=J(j,a,f).agentName,o=I(j,m),p="opencode"===m?c??=dr():void 0,q=null,r=new Promise(a=>{q=setTimeout(a,12e3)}),s=N(l,a,k,j,m,o,p).catch(()=>{});try{await Promise.race([s,r])}finally{q&&clearTimeout(q)}let t=bq(f,{sessionId:a,status:bh(f.status)});if(l.lifecycle&&("missing"===l.lifecycle.runtime.state||"exited"===l.lifecycle.runtime.state)&&"terminated"!==t.session.state&&"done"!==t.session.state&&"detecting"!==t.session.state){let b=l.lifecycle.runtime.state,c=l.lifecycle.runtime.reason;try{let e=n(a,f,a=>{a.session.state="detecting",a.session.reason="runtime_lost",a.session.lastTransitionAt=new Date().toISOString(),a.runtime.state=b,a.runtime.reason=c,a.runtime.lastObservedAt=new Date().toISOString()});bE(k,a,bs(e)),l.lifecycle=e,l.status=br(e),aa({projectId:d,sessionId:a,source:"session-manager",kind:"runtime.lost_detected",level:"warn",summary:`runtime lost reconciled: ${a}`,data:{runtimeState:b,runtimeReason:c}})}catch(b){aa({projectId:d,sessionId:a,source:"session-manager",kind:"runtime.lost_persist_failed",level:"error",summary:`runtime_lost persist failed: ${a}`,data:{reason:b instanceof Error?b.message:String(b)}})}}return l});return(await Promise.all(d)).filter(a=>null!==a)}async function ab(a){if(r&&Date.now()<r.expiresAt)return a?r.sessions.filter(b=>b.projectId===a):r.sessions;let b=await _();return r={sessions:b,expiresAt:Date.now()+35e3},a?b.filter(b=>b.projectId===a):b}async function ac(a){for(let[c,d]of Object.entries(b.projects)){let b,f,h=v(c),i=bB(h,a);if(!i)continue;try{let c=(0,g.join)(h,`${a}.json`),d=(0,e.statSync)(c);b=d.birthtime,f=d.mtime}catch{}let j=B(h,C(h,{sessionName:a,raw:i,modifiedAt:f},d.sessionPrefix),d),k=dE(a,j.raw,{projectId:c,sessionPrefix:d.sessionPrefix,createdAt:b,modifiedAt:f,workspacePathFallback:d.path}),l=J(d,a,j.raw).agentName,m=I(d,l);return await N(k,a,h,d,l,m),k}return null}async function ad(a,e){let f=L(a);if(!f){for(let[c]of Object.entries(b.projects)){let b=bB(v(c),a);if(b){let a=dD(b);if(a?.session.state==="terminated")return{cleaned:!1,alreadyTerminated:!0}}}throw new d.Ag(a)}let{raw:g,sessionsDir:h,project:j,projectId:k}=f,l=bq(g);if(l?.session.state==="terminated")return{cleaned:!1,alreadyTerminated:!0};let m=e?.reason??"manually_killed",o=J(j,a,g).agentName;if(aa({projectId:k,sessionId:a,source:"session-manager",kind:"session.kill_started",summary:`kill started: ${a}`,data:{reason:m}}),g.runtimeHandle){let d=bg(g.runtimeHandle);if(d){let e=c.get("runtime",d.runtimeName??(j?j.runtime??b.defaults.runtime:b.defaults.runtime));if(e)try{await e.destroy(d)}catch(b){aa({projectId:k,sessionId:a,source:"session-manager",kind:"runtime.destroy_failed",level:"warn",summary:`runtime.destroy failed during kill: ${a}`,data:{runtime:d.runtimeName??null,reason:b instanceof Error?b.message:String(b)}})}}}let p=g.worktree;if(p&&i(j,k,p)){let d=j?I(j).workspace:c.get("workspace",b.defaults.workspace);if(d)try{await d.destroy(p)}catch(b){aa({projectId:k,sessionId:a,source:"session-manager",kind:"workspace.destroy_failed",level:"warn",summary:`workspace.destroy failed during kill: ${a}`,data:{workspace:d.name,reason:b instanceof Error?b.message:String(b)}})}}let q=!1;if(e?.purgeOpenCode===!0&&"opencode"===o){let b=cT(g.opencodeSessionId)??await dt(a,1e4);if(b)try{await dq(b),q=!0}catch(c){aa({projectId:k,sessionId:a,source:"session-manager",kind:"agent.opencode_purge_failed",level:"warn",summary:`opencode session purge failed: ${a}`,data:{opencodeSessionId:b,reason:c instanceof Error?c.message:String(c)}})}}let r="pr_merged"===m?"pr_merged_cleanup":"auto_cleanup"===m?"auto_cleanup":"manual_kill_requested",s=n(a,g,a=>{a.session.state="terminated",a.session.reason=m,a.session.terminatedAt=new Date().toISOString(),a.session.lastTransitionAt=a.session.terminatedAt,a.runtime.state=g.runtimeHandle||g.tmuxName?"missing":"exited",a.runtime.reason=r,a.runtime.lastObservedAt=new Date().toISOString()});return bE(h,a,{...bs(s),...q&&{opencodeSessionId:"",opencodeCleanedAt:new Date().toISOString()}}),z(),aa({projectId:k,sessionId:a,source:"session-manager",kind:"session.killed",summary:`killed: ${a}`,data:{reason:m}}),{cleaned:!0,alreadyTerminated:!1}}async function ae(a,c){let e={killed:[],skipped:[],errors:[]},f=await _(a),g=new Set,h=new Set,i=(a,b)=>`${a}:${b}`,j=a=>{let b=a.indexOf(":");return -1===b?{projectId:"",id:a}:{projectId:a.slice(0,b),id:a.slice(b+1)}},l=(a,b)=>{let c=i(a,b);h.delete(c),g.add(c)},m=(a,b)=>{let c=i(a,b);g.has(c)||h.add(c)},n=c?.purgeOpenCode!==!1;for(let a of f)try{let e=b.projects[a.projectId];if(!e||k(e,a.id,a.metadata)){m(a.projectId,a.id);continue}let f=I(e),g=!1,h=a.prs.length>0?a.prs:a.pr?[a.pr]:[];if(h.length>0&&f.scm)try{(await Promise.all(h.map(a=>f.scm.getPRState(a)))).every(a=>a===d.bz.CLOSED)&&(g=!0)}catch{}if(!g&&a.issueId&&f.tracker)try{await f.tracker.isCompleted(a.issueId,e)&&(g=!0)}catch{}if(!g&&a.runtimeHandle&&f.runtime)try{await f.runtime.isAlive(a.runtimeHandle)||(g=!0)}catch{}g?(c?.dryRun||await ad(a.id,{purgeOpenCode:n}),l(a.projectId,a.id)):m(a.projectId,a.id)}catch(c){let b=c instanceof Error?c.message:String(c);e.errors.push({sessionId:a.id,error:b}),aa({projectId:a.projectId,sessionId:a.id,source:"session-manager",kind:"session.cleanup_error",level:"warn",summary:`cleanup error: ${a.id}`,data:{reason:b}})}for(let[d,f]of Object.entries(b.projects)){if(a&&d!==a)continue;let b=v(d);for(let a of bI(b)){let h=i(d,a);if(g.has(h))continue;let j=bB(b,a);if(!j)continue;let o=dD(j);if(o?.session.state!=="terminated")continue;if(k(f,a,j)){m(d,a);continue}let p=J(f,a,j).agentName,q=cT(j.opencodeSessionId);if("opencode"===p&&j.opencodeCleanedAt){m(d,a);continue}if("opencode"===p&&q&&n){if(!c?.dryRun)try{await dq(q),bG(b,a,a=>({...a,opencodeSessionId:"",opencodeCleanedAt:new Date().toISOString()}),{activityEventSource:"session-manager"})}catch(c){let b=c instanceof Error?c.message:String(c);e.errors.push({sessionId:a,error:`Failed to delete OpenCode session ${q}: ${b}`}),aa({projectId:d,sessionId:a,source:"session-manager",kind:"agent.opencode_purge_failed",level:"warn",summary:`opencode session purge failed during cleanup: ${a}`,data:{opencodeSessionId:q,reason:b}});continue}l(d,a)}else m(d,a)}}let o=[...g,...h],p=new Map;for(let a of o){let{id:b}=j(a);p.set(b,(p.get(b)??0)+1)}let q=a=>{let{projectId:b,id:c}=j(a);return(p.get(c)??0)>1?`${b}:${c}`:c};return e.killed=[...g].map(q),e.skipped=[...h].map(q),e}async function af(a,e){let{raw:f,sessionsDir:g,project:h,projectId:i}=M(a),j=J(h,a,f).agentName;if("opencode"===j&&!cT(f.opencodeSessionId)){let b=await dt(a,1e4);b&&(f.opencodeSessionId=b,bE(g,a,{opencodeSessionId:b}),z())}let k=f.runtimeHandle?bg(f.runtimeHandle):null,l=k?.runtimeName??h.runtime??b.defaults.runtime,m=c.get("runtime",l);if(!m)throw Error(`No runtime plugin for session ${a}`);let n=c.get("agent",j);if(!n)throw Error(`No agent plugin for session ${a}`);let o=async a=>{try{return await m.getOutput(a,20)??""}catch{return""}},p=a=>{if(!a)return null;try{return n.detectActivity(a)}catch{return null}},q=a=>a.includes("Press up to edit queued messages"),r=async()=>{let a=cT(f.opencodeSessionId);if("opencode"!==j||!a)return;let b=await dr(1e4);return b.find(b=>b.id===a)?.updatedAt},s=async(a,b)=>{let c=a.runtimeHandle;if(!c)return;let d=Date.now()+b,e=null,f=0;for(;;){let[a,b,g,h]=await Promise.all([m.isAlive(c).catch(()=>!0),dA(n,c),o(c),"tmux"===c.runtimeName?dC(c.id):Promise.resolve(n.processName)]),i=g.trim().length>0,j=null===h||h===n.processName,k=i?g.trimEnd():null,l=null!==k&&k===e;if(a&&b&&j&&(q(g)||l)){if((f+=1)>=2)return}else f=0;if(e=k,Date.now()>=d)return;await dy(500)}},t=async a=>{let b=a.runtimeHandle;if(!b)return!1;let c=Date.now()+5e3;for(;;){let[a,d,e,f]=await Promise.all([m.isAlive(b).catch(()=>!0),dA(n,b),o(b),"tmux"===b.runtimeName?dC(b.id):Promise.resolve(n.processName)]),g=null===f||f===n.processName;if(a&&g&&(d||e.trim().length>0))return!0;if(Date.now()>=c)return!1;await dy(500)}},u=async(b,c)=>{let d;if("done"===c.lifecycle.session.state)throw Error(`Cannot send to session ${a}: ${b}`);try{d=await ah(a)}catch(d){let c=d instanceof Error?d.message:String(d);throw Error(`Cannot send to session ${a}: ${b} (${c})`,{cause:d})}if(!await t(d)){let c="restored session did not become ready for delivery";throw aa({projectId:i,sessionId:a,source:"session-manager",kind:"session.restore_failed",level:"error",summary:`restore for delivery failed: ${a}`,data:{stage:"ready_timeout",reason:c,trigger:"send"}}),Error(`Cannot send to session ${a}: ${b} (${c})`)}return d},v=async(b=!1)=>{let c=await ac(a);if(!c)throw new d.Ag(a);let e=c.runtimeHandle??{id:a,runtimeName:l,data:{}},f=c.runtimeHandle?c:{...c,runtimeHandle:e};if(b||(0,d.qX)(f))return u(b?"session needed to be restarted before delivery":"session is not running",f);let[g,h]=await Promise.all([m.isAlive(e).catch(()=>!0),dA(n,e)]);return("spawning"===f.status&&g&&(await s(f,2e4),[g,h]=await Promise.all([m.isAlive(e).catch(()=>!0),dA(n,e)])),g&&h)?f:u(g?"agent process is not running":"runtime is not alive",f)},w=async b=>{let c=b.runtimeHandle;if(!c)throw Error(`Session ${a} has no runtime handle`);let d=await o(c),f=p(d)??b.activity,g=await r();await m.sendMessage(c,e);for(let a=1;a<=6;a++){await dy(500);let a=await o(c),e=p(a)??b.activity,h=await r();if(void 0!==g&&void 0!==h&&h>g||q(a)||a.length>0&&a!==d||"active"!==f&&"active"===e||"waiting_input"!==f&&"waiting_input"===e)break}},x="prepare";try{let a=await v();try{x="initial",await w(a)}catch(b){if(!(void 0===a.restoredAt&&(0,d.qX)(a))){if(b instanceof Error)throw b;throw Error(String(b),{cause:b})}x="restore_retry",a=await v(!0);try{await w(a)}catch(a){if(a instanceof Error)throw a;throw Error(String(a),{cause:a})}}}catch(b){throw aa({projectId:i,sessionId:a,source:"session-manager",kind:"session.send_failed",level:"error",summary:`send failed: ${a}`,data:{stage:x,reason:b instanceof Error?b.message:String(b)}}),b}}async function ag(a,b,c){let e,f=b.trim();if(!f)throw Error("PR reference is required");let{raw:g,sessionsDir:h,project:i,projectId:k}=M(a);if(j(a,g,i.sessionPrefix))throw Error(`Session ${a} is an orchestrator session and cannot claim PRs`);let l=I(i,J(i,a,g).agentName).scm;if(!l?.resolvePR||!l.checkoutPR)throw Error(`SCM plugin ${i.scm?.plugin?`"${i.scm.plugin}" `:""}does not support claiming existing PRs`);let m=await l.resolvePR(f,i),o=await l.getPRState(m);if(o!==d.bz.OPEN)throw Error(`Cannot claim PR #${m.number} because it is ${o}`);let p=new Set;for(let{sessionName:b,raw:c}of E(k,i).filter(b=>b.sessionName!==a)){if(!c||j(b,c,i.sessionPrefix))continue;let a=new Set([c.pr,..."string"==typeof c.prs?c.prs.split(","):[]].map(a=>"string"==typeof a?a.trim():"").filter(Boolean)).has(m.url),d=c.branch===m.branch&&(c.prAutoDetect??"on")!=="off"&&"false"!==c.prAutoDetect;(a||d)&&p.add(b)}let q=[...p],r=g.worktree;if(!r)throw Error(`Session ${a} has no workspace to check out PR #${m.number}`);let s=await l.checkoutPR(m,r),t=n(a,g,a=>{a.pr.state="open",a.pr.reason="in_progress",a.pr.number=m.number,a.pr.url=m.url,a.pr.lastObservedAt=new Date().toISOString()}),u=be((g.prs??g.pr??"").split(",").filter(a=>a.trim()!==m.url)).join(","),v=u?`${m.url},${u}`:m.url,w={prEnrichment:"",prReviewComments:""};for(let a of Object.keys(g))(/^prEnrichment_\d+$/.test(a)||/^prReviewComments_\d+$/.test(a))&&(w[a]="");for(let b of(bE(h,a,{pr:m.url,prs:v,status:br(t),branch:m.branch,prAutoDetect:"",...w,...bs(t)}),z(),q)){let a=bB(h,b);if(!a)continue;let c=n(b,a,b=>{b.pr.state="none",b.pr.reason="not_created",b.pr.number=null,b.pr.url=null,b.pr.lastObservedAt=null,dv.has(a.status??"")&&(b.session.state="working",b.session.reason="task_in_progress")});bE(h,b,{pr:"",prs:"",prAutoDetect:"false",...dv.has(a.status??"")?{status:"working"}:{},...bs(c)}),z()}let x=!1;if(c?.assignOnGithub)if(l.assignPRToCurrentUser)try{await l.assignPRToCurrentUser(m),x=!0}catch(a){e=a instanceof Error?a.message:String(a)}else e=`SCM plugin "${l.name}" does not support assigning PRs`;return{sessionId:a,projectId:k,pr:m,branchChanged:s,githubAssigned:x,githubAssignmentError:e,takenOverFrom:q}}async function ah(a){let c,f,h=L(a);if(!h)throw new d.Ag(a);let i=h.raw,j=h.sessionsDir,k=h.project,l=h.projectId,n=J(k,a,i);if("opencode"===n.agentName&&!cT(i.opencodeSessionId)){let b=await dt(a,1e4);if(!b)throw new d.D8(a,"OpenCode session mapping is missing");i={...i,opencodeSessionId:b},bE(j,a,{opencodeSessionId:b})}let q=dE(a,i,{projectId:l,sessionPrefix:k.sessionPrefix,workspacePathFallback:k.path}),r=I(k,n.agentName);if(await P(q,r,!0,j),!(0,d.qX)(q)){let b=d.N_.has(q.status)?`status "${q.status}" is not restorable`:`session is not in a terminal state (status: "${q.status}", activity: "${q.activity}")`;throw aa({projectId:l,sessionId:a,source:"session-manager",kind:"session.restore_failed",level:"error",summary:`restore not allowed: ${a}`,data:{stage:"validation",status:q.status,activity:q.activity,reason:b}}),new d.D8(a,b)}if(!r.runtime)throw Error(`Runtime plugin '${k.runtime??b.defaults.runtime}' not found`);if(!r.agent)throw Error(`Agent plugin '${n.agentName}' not found`);let s=i.worktree||k.path;if(!(r.workspace?.exists?await r.workspace.exists(s):(0,e.existsSync)(s))){if(!r.workspace?.restore)throw aa({projectId:l,sessionId:a,source:"session-manager",kind:"session.restore_failed",level:"error",summary:`restore workspace failed: ${a}`,data:{stage:"workspace_restore",workspacePath:s,reason:"workspace plugin does not support restore"}}),new d.CK(s,"workspace plugin does not support restore");if(!q.branch)throw aa({projectId:l,sessionId:a,source:"session-manager",kind:"session.restore_failed",level:"error",summary:`restore workspace failed: ${a}`,data:{stage:"workspace_restore",workspacePath:s,reason:"branch metadata is missing"}}),new d.CK(s,"branch metadata is missing");try{let b=await r.workspace.restore({projectId:l,project:k,sessionId:a,branch:q.branch,worktreeDir:w(l)},s);r.workspace.postCreate&&await r.workspace.postCreate(b,k)}catch(b){throw aa({projectId:l,sessionId:a,source:"session-manager",kind:"session.restore_failed",level:"error",summary:`workspace restore failed: ${a}`,data:{stage:"workspace_restore",workspacePath:s,reason:b instanceof Error?b.message:String(b)}}),new d.CK(s,`restore failed: ${b instanceof Error?b.message:String(b)}`)}}if("opencode"===r.agent.name&&"orchestrator"===n.role){let b=u(l),c=(0,g.join)(b,`orchestrator-prompt-${a}.md`);if((0,e.existsSync)(c))try{c1(s,c)}catch(a){throw Error(`failed to restore OpenCode orchestrator AGENTS.md: ${a instanceof Error?a.message:String(a)}`,{cause:a})}}if("opencode"===r.agent.name&&"orchestrator"!==n.role){let b=u(l),d=(0,g.join)(b,`worker-prompt-${a}.md`);(0,e.existsSync)(d)&&(c=c2(b,a,[d]))}if(q.runtimeHandle)try{await r.runtime.destroy(q.runtimeHandle)}catch{}let t={...k,agentConfig:{...n.agentConfig,..."orchestrator"===n.role?{permissions:"permissionless"}:{},...q.metadata?.opencodeSessionId?{opencodeSessionId:q.metadata.opencodeSessionId}:{}}},v=(()=>{if("orchestrator"!==n.role)return;let b=u(l),c=(0,g.join)(b,`orchestrator-prompt-${a}.md`);return(0,e.existsSync)(c)?c:void 0})(),x={sessionId:a,projectConfig:t,workspacePath:s,issueId:q.issueId??void 0,permissions:"orchestrator"===n.role?"permissionless":n.permissions,model:n.model,subagent:n.subagent,...v&&{systemPromptFile:v}};if(r.agent.getRestoreCommand){let b=await r.agent.getRestoreCommand(q,t);if(b)f=b,bE(j,a,{restoreFallbackReason:""});else{let b=`${r.agent.name}.getRestoreCommand returned null`;bE(j,a,{restoreFallbackReason:b}),aa({projectId:l,sessionId:a,source:"session-manager",kind:"session.restore_fallback",level:"warn",summary:`using fresh launch instead of native restore: ${a}`,data:{agent:r.agent.name,reason:b}}),f=r.agent.getLaunchCommand(x)}}else f=r.agent.getLaunchCommand(x),bE(j,a,{restoreFallbackReason:""});let y=r.agent.getEnvironment(x);r.agent.preLaunchSetup&&await r.agent.preLaunchSetup(s);let A=i.tmuxName,B=await r.runtime.create({sessionId:A??a,workspacePath:s,launchCommand:f,environment:p({...y,...c?{OPENCODE_CONFIG:c}:{},...k.env??{},PATH:de(y.PATH??process.env.PATH),GH_PATH:db,...o(m.AGENT_GH_TRACE)&&{[m.AGENT_GH_TRACE]:o(m.AGENT_GH_TRACE)},[m.SESSION]:a,[m.DATA_DIR]:j,[m.SESSION_NAME]:a,...A&&{[m.TMUX_NAME]:A},[m.CALLER_TYPE]:"agent",...l&&{[m.PROJECT_ID]:l},[m.CONFIG_PATH]:b.configPath,...void 0!==b.port&&null!==b.port&&{[m.PORT]:String(b.port)}})}),C=new Date().toISOString(),D=bt(q.lifecycle);D.session.state="working",D.session.reason="task_in_progress",D.session.lastTransitionAt=C,D.session.terminatedAt=null,D.session.completedAt=null,D.runtime.state="alive",D.runtime.reason="process_running",D.runtime.handle=B,D.runtime.lastObservedAt=C,("merged"===D.pr.state||"closed"===D.pr.state)&&(D.pr.state="none",D.pr.reason="cleared_on_restore",D.pr.number=null,D.pr.url=null,D.pr.lastObservedAt=null),bE(j,a,{...bs(D),agent:n.agentName,restoredAt:C,mergedPendingCleanupSince:""}),z();let E=br(D),F={...q,status:E,activity:"active",workspacePath:s,runtimeHandle:B,restoredAt:new Date(C)};if(r.agent.postLaunchSetup)try{let b={...F.metadata??{}};await r.agent.postLaunchSetup(F);let c=F.metadata??{},d=Object.fromEntries(Object.entries(c).filter(([a,c])=>b[a]!==c));Object.keys(d).length>0&&(bE(j,a,d),z())}catch{}return F}return{spawn:async function(a){aa({projectId:a.projectId,source:"session-manager",kind:"session.spawn_started",summary:"spawn started",data:{agent:a.agent??void 0}});try{return await Q(a)}catch(b){throw aa({projectId:a.projectId,source:"session-manager",kind:"session.spawn_failed",level:"error",summary:"spawn failed",data:{reason:b instanceof Error?b.message:String(b)}}),b}},spawnOrchestrator:S,ensureOrchestrator:async function(a){let c=b.projects[a.projectId];if(!c)throw Error(`Unknown project: ${a.projectId}`);let d=c4(c),e=s.get(d);if(e)return e;let f=V(a).finally(()=>{s.delete(d)});return s.set(d,f),f},ensureMetaOrchestrator:async function(a){let b=a.name,c=x.get(b);if(c)return c;let d=Y(a).finally(()=>{x.delete(b)});return x.set(b,d),d},relaunchOrchestrator:async function(a){let c=b.projects[a.projectId];if(!c)throw Error(`Unknown project: ${a.projectId}`);let d=c4(c),e=t.get(d);if(e)return e;let f=$(a).finally(()=>{t.delete(d)});return t.set(d,f),f},restore:ah,list:_,listCached:ab,invalidateCache:z,get:ac,kill:ad,cleanup:ae,send:af,claimPR:ag,remap:async function(a,b=!1){let{raw:c,sessionsDir:d,project:e}=M(a);if("opencode"!==J(e,a,c).agentName)throw Error(`Session ${a} is not using the opencode agent`);let f=cT(c.opencodeSessionId),g=b?await dt(a,1e4):f??await dt(a,1e4);if(!g)throw Error(`OpenCode session mapping is missing for ${a}`);return bE(d,a,{opencodeSessionId:g}),g}}}let dG=new Map;function dH(a,b){let c=dG.get(a);return c||(c=b(),dG.set(a,c)),c}function dI(a,b){for(let c of b){if(!c)continue;let b=c.replace(/[.*+?^${}()|[\]\\]/g,"\\$&");if(RegExp(`^${b}-\\d+$`).test(a))return!0}return!1}async function dJ(a){let{runtimes:b,activeTrackedIds:c,graceMs:d=12e4,nowMs:e=Date.now(),reap:f=!1,log:g}=a,h=[],i=[],j=[];for(let{runtime:a,sessionPrefixes:k}of b){let b;if("function"==typeof a.listSessions){try{b=await a.listSessions()}catch{continue}for(let a of b)dI(a.id,k)&&h.push(a);for(let h of function(a){let{liveSessions:b,activeTrackedIds:c,sessionPrefixes:d,graceMs:e,nowMs:f}=a;return b.filter(a=>!(!dI(a.id,d)||c.has(a.id))&&("number"!=typeof a.createdAt||!(f-a.createdAt<e)))}({liveSessions:b,activeTrackedIds:c,sessionPrefixes:k,graceMs:d,nowMs:e}))if(i.push(h),f)try{await a.destroy({id:h.id,runtimeName:a.name,data:h.handleData??{}}),j.push({id:h.id,runtimeName:a.name,reaped:!0}),g?.(`reaped orphan runtime session ${h.id}`,{sessionId:h.id,runtime:a.name,reason:"no non-terminal tracked session"})}catch(c){let b=c instanceof Error?c.message:String(c);j.push({id:h.id,runtimeName:a.name,reaped:!1,error:b}),g?.(`failed to reap orphan runtime session ${h.id}`,{sessionId:h.id,runtime:a.name,error:b})}}}return{liveAoSessions:h,orphans:i,outcomes:j}}(0,E.promisify)(D.execFile);let dK={debug:10,info:20,warn:30,error:40};function dL(){return new Date().toISOString()}function dM(a){return a.replace(/[^a-zA-Z0-9_-]+/g,"-").replace(/^-+|-+$/g,"")||"component"}function dN(a,b){return dK[a]>=dK[function(a){let b=a?.trim().toLowerCase();return"debug"===b||"info"===b||"warn"===b||"error"===b?b:null}(o(m.LOG_LEVEL)?.trim().toLowerCase())??b.observability?.logLevel??"warn"]}function dO(a,b,c){((function(a){let b=a?.trim().toLowerCase();return b?"1"===b||"true"===b||"yes"===b||"on"===b||"0"!==b&&"false"!==b&&"no"!==b&&"off"!==b&&null:null})(o(m.OBSERVABILITY_STDERR))??a.observability?.stderr)&&dN(c,a)&&process.stderr.write(`${JSON.stringify({...b,level:c})}
939
+ `)}function dP(a){let b=(0,g.join)(function(a){let b=function(a){let b;try{b=(0,e.realpathSync)(a)}catch{b=(0,g.resolve)(a)}let c=(0,g.dirname)(b);return(0,f.createHash)("sha256").update(c).digest("hex").slice(0,12)}(a);return(0,g.join)(B("~/.agent-orchestrator"),`${b}-observability`)}(a.configPath),"processes");return(0,e.mkdirSync)(b,{recursive:!0}),b}function dQ(a,b){return(0,g.join)(dP(a),`${dM(b)}-${process.pid}.json`)}function dR(a){let b=a.replace(/\s+/g," ").trim();return b.length>256?`${b.slice(0,256)}…`:b}function dS(a){if(a)return function a(b,c=0){return null==b?b:"string"==typeof b?dR(b):"number"==typeof b||"boolean"==typeof b?b:c>=4?"[truncated]":Array.isArray(b)?b.slice(0,25).map(b=>a(b,c+1)):"object"==typeof b?Object.fromEntries(Object.entries(b).slice(0,25).map(([b,d])=>[b,/token|secret|password|cookie|authorization|api[-_]?key|prompt|message|note/i.test(b)?"[redacted]":a(d,c+1)])):String(b)}(a)}function dT(a){if(a)return dR(a)}function dU(a){if(a)return dR(a)}function dV(a,b,c){let d=`${a}.1`;(0,e.existsSync)(a)&&(0,e.statSync)(a).size>=c&&((0,e.existsSync)(d)&&(0,e.unlinkSync)(d),(0,e.renameSync)(a,d)),(0,e.appendFileSync)(a,`${JSON.stringify(b)}
940
+ `,"utf-8")}function dW(a,b){return b.localeCompare(a)}function dX(a){switch(a){case"error":return 3;case"warn":return 2;default:return 1}}function dY(a="ao"){return`${a}-${(0,f.randomUUID)()}`}function dZ(a,b){let c=dM(b);function d(b,d){try{var f,h;let i=dQ(a,c),j=function(a,b){if(!(0,e.existsSync)(a))return{version:1,component:b,pid:process.pid,updatedAt:dL(),metrics:{},traces:[],sessions:{},health:{}};try{let c=JSON.parse((0,e.readFileSync)(a,"utf-8"));return{version:1,component:b,pid:process.pid,updatedAt:"string"==typeof c.updatedAt?c.updatedAt:dL(),metrics:c.metrics&&"object"==typeof c.metrics?c.metrics:{},traces:Array.isArray(c.traces)?c.traces:[],sessions:c.sessions&&"object"==typeof c.sessions?c.sessions:{},health:c.health&&"object"==typeof c.health?c.health:{}}}catch{return{version:1,component:b,pid:process.pid,updatedAt:dL(),metrics:{},traces:[],sessions:{},health:{}}}}(i,c);b(j);let k=dQ(a,j.component);j.updatedAt=dL();let l=`${k}.tmp.${process.pid}.${Date.now()}`;(0,e.writeFileSync)(l,`${JSON.stringify(j,null,2)}
941
+ `,"utf-8"),(0,e.renameSync)(l,k),d&&dN(d.level,a)&&(f=d.payload,h=d.level,dV((0,g.join)(dP(a),`${dM(c)}-${process.pid}.ndjson`),{...f,level:h},5242880),dO(a,d.payload,d.level))}catch(d){let b={source:"ao-observability",timestamp:dL(),component:c,outcome:"failure",operation:"observability.write",reason:d instanceof Error?d.message:String(d)};try{let c=(0,g.join)(dP(a),"observability-errors.ndjson");dV(c,b,524288)}catch{}dO(a,b,"error")}}return{component:c,recordOperation(a){let b=dL(),e=a.operation??a.metric,g=a.level??("failure"===a.outcome?"error":"info"),h={id:(0,f.randomUUID)(),timestamp:b,component:c,operation:e,outcome:a.outcome,correlationId:a.correlationId,projectId:a.projectId,sessionId:a.sessionId,path:dU(a.path),reason:dT(a.reason),durationMs:a.durationMs,data:dS(a.data)};d(c=>{var d,f;let g=(d=a.metric,f=a.projectId,`${f??"unknown"}::${d}`),i=c.metrics[g]??{total:0,success:0,failure:0};if(i.total+=1,i.lastAt=b,"success"===a.outcome?(i.success+=1,i.lastSuccessAt=b):(i.failure+=1,i.lastFailureAt=b,i.lastFailureReason=dT(a.reason)),c.metrics[g]=i,c.traces=[h,...c.traces].sort((a,b)=>dW(a.timestamp,b.timestamp)).slice(0,80),a.sessionId){c.sessions[a.sessionId]={sessionId:a.sessionId,projectId:a.projectId,correlationId:a.correlationId,operation:e,outcome:a.outcome,updatedAt:b,reason:dT(a.reason)};let d=Object.entries(c.sessions).sort(([,a],[,b])=>dW(a.updatedAt,b.updatedAt));c.sessions=Object.fromEntries(d.slice(0,200))}},{level:g,payload:{source:"ao-observability",timestamp:b,component:c,metric:a.metric,operation:e,outcome:a.outcome,correlationId:a.correlationId,projectId:a.projectId,sessionId:a.sessionId,reason:dT(a.reason),durationMs:a.durationMs,path:dU(a.path),data:dS(a.data)}})},recordDiagnostic(a){let b=dL(),e=a.level??"info",g={id:(0,f.randomUUID)(),timestamp:b,component:c,operation:a.operation,outcome:"success",correlationId:a.correlationId,projectId:a.projectId,sessionId:a.sessionId,path:dU(a.path),data:{message:dR(a.message),...dS(a.data)}};d(c=>{if(c.traces=[g,...c.traces].sort((a,b)=>dW(a.timestamp,b.timestamp)).slice(0,80),a.sessionId){c.sessions[a.sessionId]={sessionId:a.sessionId,projectId:a.projectId,correlationId:a.correlationId,operation:a.operation,outcome:"success",updatedAt:b};let d=Object.entries(c.sessions).sort(([,a],[,b])=>dW(a.updatedAt,b.updatedAt));c.sessions=Object.fromEntries(d.slice(0,200))}},{level:e,payload:{source:"ao-observability",timestamp:b,component:c,operation:a.operation,correlationId:a.correlationId,projectId:a.projectId,sessionId:a.sessionId,path:dU(a.path),data:{message:dR(a.message),...dS(a.data)}}})},setHealth(a){let b=dL();d(d=>{d.health[a.surface]={surface:a.surface,status:a.status,updatedAt:b,component:c,projectId:a.projectId,correlationId:a.correlationId,reason:dT(a.reason),details:dS(a.details)}},{level:"error"===a.status?"error":"warn"===a.status?"warn":"info",payload:{source:"ao-observability",timestamp:b,component:c,surface:a.surface,status:a.status,projectId:a.projectId,correlationId:a.correlationId,reason:dT(a.reason),details:dS(a.details)}})}}}function d$(a){let b=dP(a),c={};for(let a of(0,e.readdirSync)(b)){let d;if(!a.endsWith(".json"))continue;let f=(0,g.join)(b,a);try{d=JSON.parse((0,e.readFileSync)(f,"utf-8"))}catch{continue}if(d&&"object"==typeof d){for(let[a,b]of Object.entries(d.metrics??{})){let{projectId:e,metric:f}=function(a){let b=a.indexOf("::");if(-1===b)return{metric:a};let c=a.slice(0,b);return{projectId:"unknown"===c?void 0:c,metric:a.slice(b+2)}}(a);if(!e)continue;let g=c[e]??(c[e]={projectId:e,updatedAt:d.updatedAt,metrics:{},health:{},recentTraces:[],sessions:{}});g.metrics[f]=function(a,b){let c={total:(a?.total??0)+(b.total??0),success:(a?.success??0)+(b.success??0),failure:(a?.failure??0)+(b.failure??0),lastAt:a?.lastAt,lastSuccessAt:a?.lastSuccessAt,lastFailureAt:a?.lastFailureAt,lastFailureReason:a?.lastFailureReason};return b.lastAt&&(!c.lastAt||b.lastAt>c.lastAt)&&(c.lastAt=b.lastAt),b.lastSuccessAt&&(!c.lastSuccessAt||b.lastSuccessAt>c.lastSuccessAt)&&(c.lastSuccessAt=b.lastSuccessAt),b.lastFailureAt&&(!c.lastFailureAt||b.lastFailureAt>c.lastFailureAt)&&(c.lastFailureAt=b.lastFailureAt,c.lastFailureReason=b.lastFailureReason),c}(g.metrics[f],b),d.updatedAt>g.updatedAt&&(g.updatedAt=d.updatedAt)}for(let a of d.traces??[]){if(!a.projectId)continue;let b=c[a.projectId]??(c[a.projectId]={projectId:a.projectId,updatedAt:a.timestamp,metrics:{},health:{},recentTraces:[],sessions:{}});b.recentTraces.push(a),a.timestamp>b.updatedAt&&(b.updatedAt=a.timestamp)}for(let a of Object.values(d.health??{})){let b=a.projectId;if(!b)continue;let d=c[b]??(c[b]={projectId:b,updatedAt:a.updatedAt,metrics:{},health:{},recentTraces:[],sessions:{}}),e=d.health[a.surface];(!e||a.updatedAt>=e.updatedAt)&&(d.health[a.surface]=a),a.updatedAt>d.updatedAt&&(d.updatedAt=a.updatedAt)}for(let a of Object.values(d.sessions??{})){if(!a.projectId)continue;let b=c[a.projectId]??(c[a.projectId]={projectId:a.projectId,updatedAt:a.updatedAt,metrics:{},health:{},recentTraces:[],sessions:{}}),d=b.sessions[a.sessionId];(!d||a.updatedAt>=d.updatedAt)&&(b.sessions[a.sessionId]=a),a.updatedAt>b.updatedAt&&(b.updatedAt=a.updatedAt)}}}let d="ok";for(let a of Object.values(c))for(let b of(a.recentTraces=a.recentTraces.sort((a,b)=>dW(a.timestamp,b.timestamp)).slice(0,80),Object.values(a.health)))dX(b.status)>dX(d)&&(d=b.status);return{generatedAt:dL(),overallStatus:d,projects:c}}let d_=[[/\bBearer\s+[A-Za-z0-9._~+/=-]{12,}\b/gi,"Bearer [redacted]"],[/\bgh[pousr]_[A-Za-z0-9_]{20,}\b/g,"[redacted]"],[/\bgithub_pat_[A-Za-z0-9_]{20,}\b/g,"[redacted]"],[/\bsk-(?:ant-)?(?:proj-|svcacct-)?[A-Za-z0-9_-]{16,}\b/g,"[redacted]"],[/\bxox[baprs]-[A-Za-z0-9-]{10,}\b/g,"[redacted]"],[/\bAKIA[0-9A-Z]{16}\b/g,"[redacted]"],[/\beyJ[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\.[A-Za-z0-9_-]{10,}\b/g,"[redacted]"],[/\b([A-Z][A-Z0-9_]*(?:TOKEN|PASSWORD|SECRET|AUTHORIZATION|COOKIE|API_KEY|APIKEY)[A-Z0-9_]*)=([^\s"'`]{6,})/g,"$1=[redacted]"]];function d0(a){let b=a.reason?function(a){let b=function(a){let b=a,c=0;for(;c<b.length;){let a=b.indexOf("://",c);if(-1===a)break;if(a<4){c=a+3;continue}let d=b.slice(Math.max(0,a-5),a).toLowerCase();if(!d.endsWith("http")&&!d.endsWith("https")){c=a+3;continue}let e=a+3,f=!1;for(;e<b.length;){let d=b.charCodeAt(e);if(d<=32||47===d)break;if(64===d){b=b.slice(0,a+3).toLowerCase()+"[redacted]"+b.slice(e),c=a+3+10+1,f=!0;break}e++}f||(c=a+3)}return b}(a.replace(/\s+/g," ").trim());for(let[a,c]of d_)b=b.replace(a,c);return b.length>300?`${b.slice(0,297)}...`:b}(a.reason):void 0,c={eventId:a.event.id,eventType:a.event.type,priority:a.event.priority,targetReference:a.target.reference,targetPlugin:a.target.pluginName,deliveryMethod:a.method??"notify"};a.observer.recordOperation({metric:"notification_delivery",operation:"notification.deliver",outcome:a.outcome,correlationId:dY("notification"),projectId:a.event.projectId,sessionId:a.event.sessionId,reason:b,data:c,level:"failure"===a.outcome?"warn":"info"}),a.observer.setHealth({surface:function(a){let b="",c=0,d=!1;for(let e of a){let a=e.charCodeAt(0);if(!(a>=48&&a<=57||a>=65&&a<=90||a>=97&&a<=122||"_"===e||"-"===e)){b.length>0&&!d&&(b+="-",d=!0);continue}("-"!==e||0!==b.length)&&(b+=e,d=!1,"-"!==e&&(c=b.length))}return b=b.slice(0,c),`notification.delivery.${b||"target"}`}(a.target.reference),status:"failure"===a.outcome?"warn":"ok",projectId:a.event.projectId,correlationId:dY("notification-health"),reason:b,details:c}),"failure"===a.outcome&&a.recordActivityEvent&&function(a,b){if(a.failureKind)try{var c;aa({projectId:a.event.projectId,sessionId:a.event.sessionId,source:"notifier",kind:(c=a.failureKind,"target_missing"===c?"notification.target_missing":"notification.delivery_failed"),level:"warn",summary:"target_missing"===a.failureKind?`notification target missing: ${a.target.reference}`:`notification delivery failed: ${a.target.reference}`,data:{eventId:a.event.id,eventType:a.event.type,priority:a.event.priority,targetReference:a.target.reference,targetPlugin:a.target.pluginName,deliveryMethod:a.method??"notify",errorMessage:b}})}catch{}}(a,b??"notification delivery failed")}let d1={"pr-closed":"pr.closed","ci-failed":"ci.failing","changes-requested":"review.changes_requested","bugbot-comments":"automated_review.found","merge-conflicts":"merge.conflicts","approved-and-green":"merge.ready","agent-stuck":"session.stuck","agent-needs-input":"session.needs_input","agent-exited":"session.killed","all-complete":"summary.all_complete","report-no-acknowledge":"report.no_acknowledge","report-stale":"report.stale","report-needs-input":"report.needs_input"};function d2(a){return"string"==typeof a&&a.trim().length>0?a:void 0}function d3(a){let b=d2(a.conclusion),c=d2(a.url);return{name:a.name,status:a.status,...b?{conclusion:b}:{},...c?{url:c}:{}}}function d4(a){return{schemaVersion:3,...d2(a.semanticType)?{semanticType:a.semanticType}:{},subject:function(a){let{context:b,sessionId:c,projectId:d}=a,e={session:{id:c,projectId:d}};if(b.pr){let a=d2(b.pr.branch),c=d2(b.pr.title),d=d2(b.pr.baseBranch),f=d2(b.pr.owner),g=d2(b.pr.repo);e.pr={number:b.pr.number,url:b.pr.url,...a?{branch:a}:{},...c?{title:c}:{},...d?{baseBranch:d}:{},...f?{owner:f}:{},...g?{repo:g}:{},..."boolean"==typeof b.pr.isDraft?{isDraft:b.pr.isDraft}:{}}}let f=d2(b.issueId);if(f){let a=d2(b.issueTitle);e.issue={id:f,...a?{title:a}:{}}}let g=d2(b.summary);g&&(e.summary=g);let h=d2(b.branch);return h&&(e.branch=h),e}(a)}}function d5(a,b){b&&("none"!==b.ciStatus&&(a.ci={...a.ci??{},status:a.ci?.status??b.ciStatus}),"none"!==b.reviewDecision&&(a.review={...a.review??{},decision:a.review?.decision??b.reviewDecision}),(b.mergeable||"boolean"==typeof b.hasConflicts||"boolean"==typeof b.isBehind||(b.blockers?.length??0)>0)&&(a.merge={...a.merge??{},ready:a.merge?.ready??b.mergeable,..."boolean"==typeof b.hasConflicts?{conflicts:a.merge?.conflicts??b.hasConflicts}:{},..."boolean"==typeof b.isBehind?{isBehind:b.isBehind}:{},...b.blockers&&b.blockers.length>0?{blockers:b.blockers}:{}}))}function d6(a,b,c){switch(b){case"ci.failing":a.ci={...a.ci??{},status:"failing"};break;case"review.pending":a.review={...a.review??{},decision:"pending"};break;case"review.approved":a.review={...a.review??{},decision:"approved"};break;case"review.changes_requested":a.review={...a.review??{},decision:"changes_requested"};break;case"merge.ready":a.merge={...a.merge??{},ready:!0,conflicts:c?.hasConflicts??!1,...a.subject.pr?.baseBranch?{baseBranch:a.subject.pr.baseBranch}:{}};break;case"merge.conflicts":a.merge={...a.merge??{},ready:!1,conflicts:!0,...a.subject.pr?.baseBranch?{baseBranch:a.subject.pr.baseBranch}:{}}}}function d7(a){var b,c;let d=(b=a.reactionKey,c=a.eventType,d1[b]??c),e=d4({...a,semanticType:d});return e.reaction={key:a.reactionKey,action:a.action},d5(e,a.enrichment),d6(e,d,a.enrichment),e}function d8(a){let b=a.match(/^(\d+)(s|m|h)$/);if(!b)return 0;let c=parseInt(b[1],10);switch(b[2]){case"s":return 1e3*c;case"m":return 6e4*c;case"h":return 36e5*c;default:return 0}}let d9=new Set(["ci-failed"]),ea=["rebase-merge","rebase-apply","CHERRY_PICK_HEAD","BISECT_LOG"];async function eb(a){try{return await (0,bU.stat)(a),!0}catch(a){if("object"==typeof a&&null!==a&&"code"in a&&"ENOENT"===a.code)return!1;throw a}}async function ec(a){return(await Promise.all(ea.map(b=>eb((0,g.join)(a,b))))).some(Boolean)}async function ed(a){let b=(0,g.join)(a,".git");if((await (0,bU.stat)(b)).isDirectory())return b;let c=(await (0,bU.readFile)(b,"utf8")).trim().match(/^gitdir:\s*(.+)$/i);if(!c)throw Error(`Invalid .git pointer in workspace: ${a}`);return(0,g.resolve)((0,g.dirname)(b),c[1].trim())}async function ee(a){let b;try{b=await ed(a)}catch{return{kind:"unavailable"}}try{let a=(await (0,bU.readFile)((0,g.join)(b,"HEAD"),"utf8")).trim(),c="ref: refs/heads/";if(!a.startsWith(c))return await ec(b)?{kind:"unavailable"}:{kind:"detached"};let d=a.slice(c.length).trim();if(d.length>0)return{kind:"branch",branch:d};return await ec(b)?{kind:"unavailable"}:{kind:"detached"}}catch{return{kind:"unavailable"}}}function ef(a){return a.includes("stuck")||a.includes("needs_input")||a.includes("errored")?"urgent":a.startsWith("summary.")?"info":a.includes("approved")||a.includes("ready")||a.includes("merged")||a.includes("completed")?"action":a.includes("fail")||a.includes("changes_requested")||a.includes("conflicts")?"warning":"info"}function eg(a,b){return{id:(0,f.randomUUID)(),type:a,priority:b.priority??ef(a),sessionId:b.sessionId,projectId:b.projectId,timestamp:new Date,message:b.message,data:b.data??{}}}function eh(a,b){switch(b){case"working":return"session.working";case"pr_open":return"pr.created";case"ci_failed":return"ci.failing";case"review_pending":return"review.pending";case"changes_requested":return"review.changes_requested";case"approved":return"review.approved";case"mergeable":return"merge.ready";case"merged":return"merge.completed";case"needs_input":return"session.needs_input";case"stuck":return"session.stuck";case"errored":return"session.errored";case"killed":return"session.killed";default:return null}}function ei(a,b){let c=bd("prs"in a&&Array.isArray(a.prs)?a.prs:a.pr?[a.pr]:[]).map(a=>{let c=b.get(`${a.owner}/${a.repo}#${a.number}`);return{url:a.url,title:c?.title??null,number:a.number,branch:a.branch,baseBranch:a.baseBranch,owner:a.owner,repo:a.repo,isDraft:a.isDraft}});return{pr:c[0]??null,prs:c,issueId:a.issueId,issueTitle:a.metadata.issueTitle??null,summary:a.agentInfo?.summary??null,branch:a.branch}}function ej(a){switch(a){case"pr.closed":return"pr-closed";case"ci.failing":return"ci-failed";case"review.changes_requested":return"changes-requested";case"automated_review.found":return"bugbot-comments";case"merge.conflicts":return"merge-conflicts";case"merge.ready":return"approved-and-green";case"session.stuck":return"agent-stuck";case"session.needs_input":return"agent-needs-input";case"session.killed":return"agent-exited";case"summary.all_complete":return"all-complete";default:return null}}function ek(a){let b=eh(void 0,a);if(!b)return"info";let c=ef(b);return"urgent"===c?"error":"warning"===c?"warn":"info"}function el(a){return(0,d.xn)(a)?{state:"unknown",failed:!1,indeterminate:!0}:{state:a?"alive":"dead",failed:!1}}function em(a){return"detecting"===a.session.state?a.session.reason:"not_created"!==a.pr.reason&&"in_progress"!==a.pr.reason?a.pr.reason:"process_running"!==a.runtime.reason?a.runtime.reason:a.session.reason}function en(a,b,c,d,e,f,g,h){return{oldStatus:c,newStatus:d,statusTransition:g,previousSessionState:a.session.state,newSessionState:b.session.state,previousSessionReason:a.session.reason,newSessionReason:b.session.reason,previousPRState:a.pr.state,newPRState:b.pr.state,previousPRReason:a.pr.reason,newPRReason:b.pr.reason,previousRuntimeState:a.runtime.state,newRuntimeState:b.runtime.state,previousRuntimeReason:a.runtime.reason,newRuntimeReason:b.runtime.reason,primaryReason:em(b),evidence:e,signalsConsulted:e.split(/\s+/).map(a=>a.trim()).filter(a=>a.length>0),detectingAttempts:f,recoveryAction:h?.result?.action??null,reactionKey:h?.key??null,reactionSuccess:h?.result?.success??null,escalated:h?.result?.escalated??null}}function eo(a){let{config:b,registry:c,sessionManager:e,projectId:f}=a,g=dZ(b,"lifecycle-manager"),h=new Map,i=new Map,j=new Map,k=null,l=!1,m=!1,n=0,o=new Map,p=new Map;function q(a){let b=bd(a.prs.length>0?a.prs:a.pr?[a.pr]:[]);return(b.length!==a.prs.length||a.pr!==(b[0]??null))&&(a.prs=b,a.pr=b[0]??null),b}function r(a,b){let c={};for(let d of Object.keys(a.metadata)){let a=d.match(/^(prEnrichment|prReviewComments)_(\d+)$/);if(!a)continue;let e=Number.parseInt(a[2],10);(Number.isNaN(e)||e>=b)&&(c[d]="")}return c}function s(a){if(a.pr)return p.get(`${a.pr.owner}/${a.pr.repo}#${a.pr.number}`)}let t=new Set,u=new Map;async function w(a){p.clear(),t=new Set;let d=new Map,e=new Map,h=new Set;for(let c of a){let a=b.projects[c.projectId];if(!a?.scm?.plugin||!a.repo)continue;let f=a.scm.plugin;d.has(f)||d.set(f,[]),e.has(f)||e.set(f,new Set),e.get(f).add(a.repo);let g=q(c);if(0!==g.length)for(let b of g){let c=`${b.owner}/${b.repo}`;c!==a.repo&&e.get(f).add(c);let g=`${b.owner}/${b.repo}#${b.number}`;if(h.has(g))continue;h.add(g);let i=d.get(f);i&&i.push(b)}}for(let[a,b]of d){let d=c.get("scm",a);if(!d?.enrichSessionsPRBatch)continue;let h=[...e.get(a)??[]],i=Date.now();try{for(let[c,e]of(await d.enrichSessionsPRBatch(b,{recordSuccess(c){let d=Date.now()-i;g?.recordOperation({metric:"graphql_batch",operation:"batch_enrichment",correlationId:dY("graphql-batch"),outcome:"success",projectId:f,durationMs:d,data:{plugin:a,prCount:b.length,prKeys:b.map(a=>`${a.owner}/${a.repo}#${a.number}`)},level:"info"})},recordFailure(c){let d=Date.now()-i;g?.recordOperation({metric:"graphql_batch",operation:"batch_enrichment",correlationId:dY("graphql-batch"),outcome:"failure",reason:c.error,level:"warn",data:{plugin:a,prCount:b.length,error:c.error,durationMs:d}})},log(b,c){g?.recordDiagnostic?.({operation:"batch_enrichment.log",correlationId:dY("graphql-batch"),projectId:f,message:c,level:b,data:{plugin:a,source:"ao-graphql-batch"}})},reportPRListUnchangedRepos(a){for(let b of a)t.add(b)}},h)))p.set(c,e)}catch(e){let c=e instanceof Error?e.message:String(e),d=dY("batch-enrichment");g?.recordOperation?.({metric:"lifecycle_poll",operation:"batch_enrichment",correlationId:d,outcome:"failure",reason:c,level:"warn",data:{plugin:a,prCount:b.length}}),aa({projectId:f,source:"scm",kind:"scm.batch_enrich_failed",level:"warn",summary:`batch_enrich failed for ${b.length} PR(s)`,data:{plugin:a,prCount:b.length,errorMessage:c}})}}for(let d of a){if(!d.branch||"off"===d.metadata.prAutoDetect||"false"===d.metadata.prAutoDetect||"orchestrator"===d.metadata.role||d.id.endsWith("-orchestrator"))continue;let a=q(d),e=new Set(a.map(a=>`${a.owner}/${a.repo}`)),f=b.projects[d.projectId]?.repo,h="closed"===d.lifecycle.pr.state;if(a.length>0&&f&&e.has(f)&&!h)continue;let i=b.projects[d.projectId];if(!i?.repo||!i.scm?.plugin||t.has(i.repo))continue;let j=c.get("scm",i.scm.plugin);if(j?.detectPR)try{let b=await j.detectPR(d,i);if(b){a.some(a=>a.owner===b.owner&&a.repo===b.repo&&a.number===b.number)||(d.prs=d.prs.filter(a=>a.owner!==b.owner||a.repo!==b.repo||a.number===b.number||p.get(`${a.owner}/${a.repo}#${a.number}`)?.state!=="closed").concat(b)),d.prs=bd(d.prs),d.pr=d.prs[0]??b;let c=v(d.projectId),e=[...new Set(d.prs.map(a=>a.url))].join(",");bE(c,d.id,{pr:d.pr.url,prs:e}),aa({projectId:d.projectId,sessionId:d.id,source:"scm",kind:"scm.detect_pr_succeeded",summary:`PR #${b.number} detected`,data:{plugin:i.scm.plugin,prNumber:b.number,prUrl:b.url,prOwner:b.owner,prRepo:b.repo}})}}catch(b){let a=b instanceof Error?b.message:String(b);g?.recordOperation?.({metric:"lifecycle_poll",operation:"scm.detect_pr",outcome:"failure",correlationId:dY("detect-pr"),projectId:d.projectId,sessionId:d.id,reason:a,level:"warn"}),aa({projectId:d.projectId,sessionId:d.id,source:"scm",kind:"scm.detect_pr_failed",level:"warn",summary:`detect_pr failed for ${d.id}`,data:{plugin:i.scm.plugin,errorMessage:a}})}}}function x(a,b){let c=C(a,"agent-stuck"),d=c?.threshold;if("string"!=typeof d)return!1;let e=d8(d);return!(e<=0)&&Date.now()-b.getTime()>e}async function y(a,c){var f,g;let h=b.projects[a.projectId];if(!h)return;let i=Object.values(b.projects).map(a=>a.sessionPrefix),j=bK(a.id,a.metadata,h.sessionPrefix,i),k=a.workspacePath;if(!("worker"===j&&null!==k&&(!a.pr||"closed"===a.lifecycle.pr.state)))return;let l=await ee(k);if("detached"===l.kind){null!==a.branch&&(a.branch=null,D(a,{branch:""}));return}if("branch"!==l.kind||l.branch===a.branch)return;let m=function(a,b){let c=`${a.projectId}:${b}`,d=o.get(c);return d&&d!==a.id?null:(o.set(c,a.id),c)}(a,l.branch);if(m)try{let g=c??await e.list(a.projectId);f=l.branch,g.some(c=>{if(c.id===a.id||c.projectId!==a.projectId||d.CM.has(c.status))return!1;let e=b.projects[c.projectId];return!!e&&"worker"===bK(c.id,c.metadata,e.sessionPrefix,i)&&c.branch===f})||(a.branch=l.branch,D(a,{branch:l.branch}))}finally{g=a.id,o.get(m)===g&&o.delete(m)}}async function z(a){let e=b.projects[a.projectId];if(!e)return{status:a.status,evidence:"project_missing",detectingAttempts:cK(a.metadata.detectingAttempts)};let f=bt(a.lifecycle),h=new Date().toISOString(),j=a.metadata.agent,k=j?c.get("agent",j):null,l=e.scm?.plugin?c.get("scm",e.scm.plugin):null,m=null,n=!1,o=a.status!==d.SB.SPAWNING,q=cK(a.metadata.detectingAttempts),r=a.metadata.detectingStartedAt||void 0,s=a.metadata.detectingEvidenceHash||void 0,t=(b={status:br(f),evidence:"lifecycle_commit",detecting:{attempts:q}})=>(b.prState&&(f.pr.state=b.prState,f.pr.lastObservedAt=h),b.prReason&&(f.pr.reason=b.prReason),b.sessionState&&b.sessionReason&&(f.session.state=b.sessionState,f.session.reason=b.sessionReason,f.session.lastTransitionAt=h,"working"===b.sessionState&&null===f.session.startedAt&&(f.session.startedAt=h),"done"===b.sessionState&&null===f.session.completedAt&&(f.session.completedAt=h),"terminated"===b.sessionState&&null===f.session.terminatedAt&&(f.session.terminatedAt=h)),bm(f),a.lifecycle=f,a.status=b.status,a.activitySignal=v,{status:b.status,evidence:b.evidence,detectingAttempts:b.detecting.attempts,detectingStartedAt:b.detecting.startedAt,detectingEvidenceHash:b.detecting.evidenceHash}),u={state:"unknown",failed:!1};if(a.runtimeHandle&&o){let d=c.get("runtime",e.runtime??b.defaults.runtime);if(d)try{let b=await d.isAlive(a.runtimeHandle);f.runtime.lastObservedAt=h,u={state:b?"alive":"dead",failed:!1},b?(f.runtime.state="alive",f.runtime.reason="process_running"):(f.runtime.state="missing",f.runtime.reason="tmux"===a.runtimeHandle.runtimeName?"tmux_missing":"process_missing")}catch(b){f.runtime.state="probe_failed",f.runtime.reason="probe_error",f.runtime.lastObservedAt=h,u={state:"unknown",failed:!0},aa({projectId:a.projectId,sessionId:a.id,source:"runtime",kind:"runtime.probe_failed",level:"warn",summary:`runtime.isAlive probe failed for ${a.id}`,data:{runtimeName:a.runtimeHandle.runtimeName,errorMessage:b instanceof Error?b.message:String(b)}})}}let v=bQ("unavailable"),w={state:"unknown",failed:!1},y=bT(v);if(k&&(a.runtimeHandle||a.workspacePath))try{if(k.recordActivity&&a.workspacePath&&a.runtimeHandle&&o)try{let d=c.get("runtime",e.runtime??b.defaults.runtime),f=d?await d.getOutput(a.runtimeHandle,10):"";f&&await k.recordActivity(a,f)}catch(b){g?.recordOperation?.({metric:"lifecycle_poll",operation:"activity.record",outcome:"failure",correlationId:dY("lifecycle-poll"),projectId:a.projectId,sessionId:a.id,reason:b instanceof Error?b.message:String(b),level:"warn"})}let l=await k.getActivityState(a,b.readyThresholdMs);if(l){v=bR(l,"native"),y=bT(v),f.runtime.lastObservedAt=h;let b=i.get(a.id);if(i.set(a.id,l.state),void 0!==b&&b!==l.state&&aa({projectId:a.projectId,sessionId:a.id,source:"lifecycle",kind:"activity.transition",summary:`${b} → ${l.state}`,data:{from:b,to:l.state}}),"missing"!==f.runtime.state&&"probe_failed"!==f.runtime.state&&(f.runtime.state="alive",f.runtime.reason="process_running"),"waiting_input"===l.state)return t({status:d.SB.NEEDS_INPUT,evidence:y,detecting:{attempts:0},sessionState:"needs_input",sessionReason:"awaiting_user_input"});"exited"===l.state&&o&&(w={state:"dead",failed:!1},f.runtime.state="exited",f.runtime.reason="process_missing"),bS(v)&&(m=v.timestamp,n="blocked"===v.activity)}else if(a.runtimeHandle&&o){v=bQ("null",{source:"native"}),y=bT(v);let g=c.get("runtime",e.runtime??b.defaults.runtime),i=g?await g.getOutput(a.runtimeHandle,10):"";if(i){let b=k.detectActivity(i);if(v=bR({state:b},"terminal"),y=bT(v),"waiting_input"===b)return t({status:d.SB.NEEDS_INPUT,evidence:y,detecting:{attempts:0},sessionState:"needs_input",sessionReason:"awaiting_user_input"});try{let b=await k.isProcessRunning(a.runtimeHandle);w=el(b),!1===b&&(f.runtime.state="exited",f.runtime.reason="process_missing",f.runtime.lastObservedAt=h)}catch(b){w={state:"unknown",failed:!0},aa({projectId:a.projectId,sessionId:a.id,source:"agent",kind:"agent.process_probe_failed",level:"warn",summary:`agent.isProcessRunning failed for ${a.id}`,data:{agentName:j,where:"fallback",errorMessage:b instanceof Error?b.message:String(b)}})}}}else v=bQ("null",{source:"native"}),y=bT(v)}catch(b){if(y=bT(v=bQ("probe_failure",{source:"native"})),aa({projectId:a.projectId,sessionId:a.id,source:"agent",kind:"agent.activity_probe_failed",level:"warn",summary:`activity probing failed for ${a.id}`,data:{agentName:j,errorMessage:b instanceof Error?b.message:String(b)}}),"stuck"===f.session.state||"needs_input"===f.session.state||"detecting"===f.session.state)return t({status:a.status,evidence:y,detecting:{attempts:q}});return t(cH({currentAttempts:q,idleWasBlocked:n,evidence:y,detectingStartedAt:r,previousEvidenceHash:s}))}if("unknown"===w.state&&!w.indeterminate&&a.runtimeHandle&&o&&k)try{let b=await k.isProcessRunning(a.runtimeHandle);w=el(b),!1===b&&(f.runtime.state="exited",f.runtime.reason="process_missing",f.runtime.lastObservedAt=h)}catch(b){w={state:"unknown",failed:!0},aa({projectId:a.projectId,sessionId:a.id,source:"agent",kind:"agent.process_probe_failed",level:"warn",summary:`agent.isProcessRunning failed for ${a.id}`,data:{agentName:j,where:"standalone",errorMessage:b instanceof Error?b.message:String(b)}})}if(w.indeterminate)return aa({projectId:a.projectId,sessionId:a.id,source:"agent",kind:"agent.process_probe_failed",level:"warn",summary:`agent.isProcessRunning indeterminate for ${a.id}`,data:{agentName:j,reason:"probe_indeterminate"}}),{status:a.status,evidence:a.metadata.lifecycleEvidence??"process_probe_indeterminate",detectingAttempts:q,detectingStartedAt:r,detectingEvidenceHash:s,skipMetadataWrite:!0};let z=function(a){let b=function(a,b=new Date){return"valid"===a.state&&a.timestamp instanceof Date&&null!==a.activity&&bN.has(a.activity)&&"stale"!==bP(a.timestamp,b)}(a.activitySignal);return a.runtimeProbe.failed||a.processProbe.failed?cH({currentAttempts:a.currentAttempts,idleWasBlocked:a.idleWasBlocked,evidence:`probe_failed runtime=${a.runtimeProbe.state} process=${a.processProbe.state} ${a.activityEvidence}`,detectingStartedAt:a.detectingStartedAt,previousEvidenceHash:a.previousEvidenceHash}):"dead"===a.runtimeProbe.state&&"alive"===a.processProbe.state||"alive"===a.runtimeProbe.state&&"dead"===a.processProbe.state||"dead"===a.runtimeProbe.state&&b?cH({currentAttempts:a.currentAttempts,idleWasBlocked:a.idleWasBlocked,evidence:`signal_disagreement runtime=${a.runtimeProbe.state} process=${a.processProbe.state} ${a.activityEvidence}`,reason:"dead"===a.runtimeProbe.state?"runtime_lost":"agent_process_exited",detectingStartedAt:a.detectingStartedAt,previousEvidenceHash:a.previousEvidenceHash}):"dead"===a.runtimeProbe.state&&"unknown"===a.processProbe.state&&a.canProbeRuntimeIdentity?cH({currentAttempts:a.currentAttempts,idleWasBlocked:a.idleWasBlocked,evidence:`runtime_dead process_unknown ${a.activityEvidence}`,reason:"runtime_lost",detectingStartedAt:a.detectingStartedAt,previousEvidenceHash:a.previousEvidenceHash}):"dead"!==a.runtimeProbe.state||"dead"!==a.processProbe.state||b?null:{status:d.SB.KILLED,evidence:`runtime_dead process_dead ${a.activityEvidence}`,detecting:{attempts:0},sessionState:"terminated",sessionReason:"runtime_lost"}}({currentAttempts:q,runtimeProbe:u,processProbe:w,canProbeRuntimeIdentity:o,activitySignal:v,activityEvidence:y,idleWasBlocked:n,detectingStartedAt:r,previousEvidenceHash:s});if(z)return t(z);if(a.pr&&l)try{let b=`${a.pr.owner}/${a.pr.repo}#${a.pr.number}`,c=p.get(b);"none"===f.pr.state&&(f.pr.state="open"),"not_created"===f.pr.reason&&(f.pr.reason="in_progress"),f.pr.number=a.pr.number,f.pr.url=a.pr.url,f.pr.lastObservedAt=h;let d=!!(null!==m&&bS(v))&&x(a,m);if(c){if(a.prs.length>1){let b=a.prs.map(a=>p.get(`${a.owner}/${a.repo}#${a.number}`)).filter(a=>void 0!==a);if(b.length===a.prs.length){let a={ciStatus:b.some(a=>"failing"===a.ciStatus)?"failing":b.every(a=>"passing"===a.ciStatus||"none"===a.ciStatus)?"passing":"pending",reviewDecision:b.some(a=>"changes_requested"===a.reviewDecision)?"changes_requested":b.every(a=>"approved"===a.reviewDecision)?"approved":b.every(a=>"none"===a.reviewDecision)?"none":"pending",state:b.every(a=>"merged"===a.state)?"merged":b.some(a=>"open"===a.state)?"open":"closed",mergeable:b.every(a=>a.mergeable),blockers:[...new Set(b.flatMap(a=>a.blockers??[]))],title:c.title,additions:c.additions,deletions:c.deletions,isDraft:b.some(a=>a.isDraft),hasConflicts:b.some(a=>a.hasConflicts),isBehind:b.some(a=>a.isBehind)};return t(cL(a,{shouldEscalateIdleToStuck:d,idleWasBlocked:n,activityEvidence:y}))}}if(a.prs.length<=1)return t(cL(c,{shouldEscalateIdleToStuck:d,idleWasBlocked:n,activityEvidence:y}))}try{if(a.prs.length>1){let b=await Promise.all(a.prs.map(a=>l.getPRState(a)));if(b.every(a=>"merged"===a||"closed"===a)){let a=b.every(a=>"merged"===a)?"merged":"closed";return t(cM({prState:a,ciStatus:"none",reviewDecision:"none",mergeable:!1,shouldEscalateIdleToStuck:d,idleWasBlocked:n,activityEvidence:y}))}}else{let b=await l.getPRState(a.pr);if("merged"===b||"closed"===b)return t(cM({prState:b,ciStatus:"none",reviewDecision:"none",mergeable:!1,shouldEscalateIdleToStuck:d,idleWasBlocked:n,activityEvidence:y}))}}catch(b){aa({projectId:a.projectId,sessionId:a.id,source:"scm",kind:"scm.poll_pr_failed",level:"warn",summary:`getPRState failed for PR #${a.pr.number}`,data:{plugin:e.scm?.plugin,prNumber:a.pr.number,prUrl:a.pr.url,errorMessage:b instanceof Error?b.message:String(b)}})}}catch(b){g?.recordOperation?.({metric:"lifecycle_poll",operation:"scm.poll_pr",outcome:"failure",correlationId:dY("lifecycle-poll"),projectId:a.projectId,sessionId:a.id,reason:b instanceof Error?b.message:String(b),level:"warn"})}let A=bY(a.metadata);if(A&&function(a,b=new Date,c=3e5,d=6e4){let e=Date.parse(a.timestamp);if(Number.isNaN(e))return!1;let f=b.getTime();return!(e>f+d)&&f-e<=c}(A)&&"orchestrator"!==f.session.kind&&"terminated"!==f.session.state&&"done"!==f.session.state){let a=function(a){switch(a){case"started":return{sessionState:"working",sessionReason:"agent_acknowledged"};case"working":case"draft_pr_created":return{sessionState:"working",sessionReason:"task_in_progress"};case"waiting":case"ready_for_review":return{sessionState:"idle",sessionReason:"awaiting_external_review"};case"needs_input":return{sessionState:"needs_input",sessionReason:"awaiting_user_input"};case"fixing_ci":return{sessionState:"working",sessionReason:"fixing_ci"};case"addressing_reviews":return{sessionState:"working",sessionReason:"resolving_review_comments"};case"pr_created":return{sessionState:"idle",sessionReason:"pr_created"};case"completed":return{sessionState:"idle",sessionReason:"research_complete"}}}(A.state);return t({status:br({...f,session:{...f.session,state:a.sessionState,reason:a.sessionReason}}),evidence:`agent_report:${A.state}`,detecting:{attempts:0},sessionState:a.sessionState,sessionReason:a.sessionReason})}return m&&bS(v)&&x(a,m)?t({status:d.SB.STUCK,evidence:`idle_beyond_threshold ${y}`,detecting:{attempts:0},sessionState:"stuck",sessionReason:n?"error_in_process":"probe_failure"}):"valid"!==v.state&&(a.status===d.SB.DETECTING||a.status===d.SB.STUCK||a.status===d.SB.NEEDS_INPUT||"detecting"===f.session.state||"stuck"===f.session.state||"needs_input"===f.session.state)?t("unavailable"!==v.state||"stuck"!==f.session.state||"probe_failure"!==f.session.reason||"alive"!==u.state||u.failed?{status:br(f),evidence:y,detecting:{attempts:0}}:{status:d.SB.DETECTING,evidence:y,detecting:{attempts:0},sessionState:"detecting",sessionReason:"probe_failure"}):t(a.status===d.SB.SPAWNING||a.status===d.SB.DETECTING||a.status===d.SB.STUCK||a.status===d.SB.NEEDS_INPUT?{status:d.SB.WORKING,evidence:y,detecting:{attempts:0},sessionState:"working",sessionReason:"task_in_progress"}:{status:a.status,evidence:y,detecting:{attempts:0}})}async function A(a,b,c){let{id:d,projectId:f}=a,g=`${d}:${b}`,h=j.get(g);if(h||(h={attempts:0,firstTriggered:new Date},j.set(g,h)),h.escalated)return{reactionType:b,success:!0,action:"escalated",escalated:!0};h.attempts++;let i=c.retries??1/0,k=c.escalateAfter,l=!1;if(h.attempts>i&&(l=!0),"string"==typeof k){let a=d8(k);a>0&&Date.now()-h.firstTriggered.getTime()>a&&(l=!0)}if("number"==typeof k&&h.attempts>k&&(l=!0),l){let e=h.attempts>i?"max_retries":"number"==typeof k&&h.attempts>k?"max_attempts":"max_duration",g=Date.now()-h.firstTriggered.getTime();aa({projectId:f,sessionId:d,source:"reaction",kind:"reaction.escalated",level:"warn",summary:`reaction ${b} escalated after ${h.attempts} attempts`,data:{reactionKey:b,attempts:h.attempts,durationSinceFirstMs:g,escalationCause:e}});let j=ei(a,p),l=eg("reaction.escalated",{sessionId:d,projectId:f,message:`Reaction '${b}' escalated after ${h.attempts} attempts`,data:function(a){let b=d7(a);return b.escalation={attempts:a.attempts,cause:a.cause,..."number"==typeof a.durationMs?{durationMs:a.durationMs}:{}},b}({eventType:"reaction.escalated",sessionId:d,projectId:f,context:j,reactionKey:b,action:"escalated",attempts:h.attempts,cause:e,durationMs:g,enrichment:s(a)})});return await M(l,c.priority??"urgent"),h.escalated=!0,{reactionType:b,success:!0,action:"escalated",escalated:!0}}let m=c.action??"notify";switch(m){case"send-to-agent":if(c.message)try{return await e.send(d,c.message),aa({projectId:f,sessionId:d,source:"reaction",kind:"reaction.action_succeeded",summary:`send-to-agent ${b}`,data:{reactionKey:b,action:"send-to-agent",attempts:h.attempts}}),{reactionType:b,success:!0,action:"send-to-agent",message:c.message,escalated:!1}}catch(a){return aa({projectId:f,sessionId:d,source:"reaction",kind:"reaction.send_to_agent_failed",level:"warn",summary:`send-to-agent failed for ${d}`,data:{reactionKey:b,attempts:h.attempts,errorMessage:a instanceof Error?a.message:String(a)}}),{reactionType:b,success:!1,action:"send-to-agent",escalated:!1}}break;case"notify":{let e=ei(a,p),g=eg("reaction.triggered",{sessionId:d,projectId:f,message:c.message??`Reaction '${b}' triggered notification`,data:d7({eventType:"reaction.triggered",sessionId:d,projectId:f,context:e,reactionKey:b,action:"notify",enrichment:s(a)})});return await M(g,c.priority??"info"),aa({projectId:f,sessionId:d,source:"reaction",kind:"reaction.action_succeeded",summary:`notify ${b}`,data:{reactionKey:b,action:"notify",attempts:h.attempts}}),{reactionType:b,success:!0,action:"notify",escalated:!1}}case"auto-merge":{let e=ei(a,p),g=eg("reaction.triggered",{sessionId:d,projectId:f,message:c.message??`Reaction '${b}' triggered auto-merge`,data:d7({eventType:"reaction.triggered",sessionId:d,projectId:f,context:e,reactionKey:b,action:"auto-merge",enrichment:s(a)})});return await M(g,"action"),aa({projectId:f,sessionId:d,source:"reaction",kind:"reaction.action_succeeded",summary:`auto-merge ${b}`,data:{reactionKey:b,action:"auto-merge",attempts:h.attempts}}),{reactionType:b,success:!0,action:"auto-merge",escalated:!1}}}return{reactionType:b,success:!1,action:m,escalated:!1}}function B(a,b){j.delete(`${a}:${b}`)}function C(a,c){let d=b.projects[a.projectId],e=b.reactions[c],f=d?.reactions?.[c];return(f?{...e,...f}:e)||null}function D(a,c){if(!b.projects[a.projectId])return;let d=v(a.projectId),f=bs(bt(a.lifecycle)),g={...c,...f};bE(d,a.id,g),e.invalidateCache();let h=Object.fromEntries(Object.entries(a.metadata).filter(([a])=>{let b=g[a];return void 0===b||""!==b}));for(let[a,b]of Object.entries(g))void 0!==b&&""!==b&&(h[a]=b);a.metadata=h,a.status=br(a.lifecycle)}function E(a){return[...a].sort().join(",")}async function F(a,f,g,h){let i,j=b.projects[a.projectId];if(!j||!a.pr)return;let k=j.scm?.plugin?c.get("scm",j.scm.plugin):null;if(!k)return;let l="changes-requested",m="bugbot-comments";if(d.CM.has(g)||"open"!==a.lifecycle.pr.state){B(a.id,l),B(a.id,m),u.delete(a.id),D(a,{lastPendingReviewFingerprint:"",lastPendingReviewDispatchHash:"",lastPendingReviewDispatchAt:"",lastAutomatedReviewFingerprint:"",lastAutomatedReviewDispatchHash:"",lastAutomatedReviewDispatchAt:""});return}if(h?.key!==l&&h?.key!==m){let b=u.get(a.id)??0;if(Date.now()-b<12e4)return}let n=[];try{if(k.getReviewThreads){let b=await k.getReviewThreads(a.pr);i=b.threads,n=b.reviews}else i=await k.getPendingComments(a.pr)}catch(b){aa({projectId:a.projectId,sessionId:a.id,source:"scm",kind:"scm.review_fetch_failed",level:"warn",summary:`review fetch failed for PR #${a.pr.number}`,data:{plugin:j.scm?.plugin,prNumber:a.pr.number,prUrl:a.pr.url,errorMessage:b instanceof Error?b.message:String(b)}});return}u.set(a.id,Date.now());{let b=i.filter(a=>!a.isBot),c=JSON.stringify({unresolvedThreads:b.length,unresolvedComments:b.map(a=>({url:a.url,path:a.path??"",author:a.author,body:a.body})),reviews:n.map(a=>({author:a.author,state:a.state,body:a.body})),commentsUpdatedAt:new Date().toISOString()});a.metadata.prReviewComments!==c&&D(a,{prReviewComments:c});let d=q(a),e=r(a,d.length);Object.keys(e).length>0&&D(a,e);for(let b=1;b<d.length;b++){let c,e,f=d[b];if(!f)continue;try{if(k.getReviewThreads){let a=await k.getReviewThreads(f);c=a.threads,e=a.reviews}else c=await k.getPendingComments(f),e=[]}catch{continue}let g=c.filter(a=>!a.isBot),h=JSON.stringify({unresolvedThreads:g.length,unresolvedComments:g.map(a=>({url:a.url,path:a.path??"",author:a.author,body:a.body})),reviews:e.map(a=>({author:a.author,state:a.state,body:a.body})),commentsUpdatedAt:new Date().toISOString()}),i=`prReviewComments_${b}`;a.metadata[i]!==h&&D(a,{[i]:h})}}let o=i.filter(a=>!a.isBot),p=i.filter(a=>a.isBot);{let b=E(o.map(a=>a.id)),c=a.metadata.lastPendingReviewFingerprint??"",d=a.metadata.lastPendingReviewDispatchHash??"";if(b!==c&&h?.key!==l&&B(a.id,l),b!==c&&D(a,{lastPendingReviewFingerprint:b}),b){if(b!==d){let c=C(a,l);if(c&&c.action&&(!1!==c.auto||"notify"===c.action)){let d=G(o,"reviewer",n),f=!1;if(h?.key===l&&"send-to-agent"===c.action)try{await e.send(a.id,d),f=!0}catch{}else{let b={...c,message:d};f=(await A(a,l,b)).success}f&&D(a,{lastPendingReviewDispatchHash:b,lastPendingReviewDispatchAt:new Date().toISOString()})}}}else B(a.id,l),D(a,{lastPendingReviewFingerprint:"",lastPendingReviewDispatchHash:"",lastPendingReviewDispatchAt:""})}{let b=E(p.map(a=>a.id)),c=a.metadata.lastAutomatedReviewFingerprint??"",d=a.metadata.lastAutomatedReviewDispatchHash??"";if(b!==c&&(B(a.id,m),D(a,{lastAutomatedReviewFingerprint:b})),b){if(b!==d){let c=C(a,m);if(c&&c.action&&(!1!==c.auto||"notify"===c.action)){let d=G(p,"bot"),f=!1;if(h?.key===m&&"send-to-agent"===c.action)try{await e.send(a.id,d),f=!0}catch{}else{let b={...c,message:d};f=(await A(a,m,b)).success}f&&D(a,{lastAutomatedReviewDispatchHash:b,lastAutomatedReviewDispatchAt:new Date().toISOString()})}}}else B(a.id,m),D(a,{lastAutomatedReviewFingerprint:"",lastAutomatedReviewDispatchHash:"",lastAutomatedReviewDispatchAt:""})}}function G(a,b,c=[]){let d=[],e=c.filter(a=>a.body&&a.body.trim().length>0);if(e.length>0)for(let a of e)d.push(`Review by @${a.author} (${a.state}):`),d.push(`"${a.body.trim()}"`,"");let f="reviewer"===b?`The following ${a.length} unresolved review comment(s) are on your PR (as of just now). You should not need to re-fetch this data unless you need additional context.`:`The following ${a.length} automated review comment(s) are on your PR (as of just now). You should not need to re-fetch this data unless you need additional context.`;d.push(f,"");for(let b=0;b<a.length;b++){let c=a[b],e=c.path?`${c.path}${c.line?`:${c.line}`:""}`:"(general)";d.push(`${b+1}. ${e} (@${c.author}): "${c.body}"`),c.url&&d.push(` ${c.url}`),c.threadId&&d.push(` Thread ID: ${c.threadId}`)}return d.push("","Address each comment, push fixes. Use the thread ID to resolve each thread directly after pushing. You should not need to re-fetch review data unless you need additional context beyond what is provided here."),d.join("\n")}function H(a){return"failed"===a.status||a.conclusion?.toUpperCase()==="FAILURE"}async function I(a,b,c){if(a.getCIFailureSummary)try{let d=await a.getCIFailureSummary(b,c);if(d?.failedJobs.length)return function(a){let b=["CI is failing on your PR.",""];for(let c of a.failedJobs){let a=c.failedStep?`${c.name} → ${c.failedStep}`:c.name;if(b.push(`Failed: ${a}`),b.push(`Failure URL: ${c.runUrl}`),c.logTail){let a=c.logTail.split(/\r?\n/).length,d=1===a?"line":"lines",e=c.logTail.split(/\r?\n/).map(a=>a.startsWith("```")?`\u200B${a}`:a).join("\n");b.push("",`Log tail (last ${a} ${d}):`,"```",e,"```")}b.push("")}return b.push("Fix the issues and push again."),b.join("\n")}(d)}catch{}let d=["CI checks are failing on your PR. Here are the failed checks:",""];for(let a of c){let b=a.conclusion??a.status,c=a.url?` — ${a.url}`:"";d.push(`- **${a.name}**: ${b}${c}`)}return d.push("","Investigate the failures, fix the issues, and push again."),d.join("\n")}async function J(a,b,c){let d=`${b.owner}/${b.repo}#${b.number}`,e=p.get(d),f=e?.ciChecks;if(void 0===f&&c.allowFetch)try{f=await a.getCIChecks(b)}catch{return null}let g=f?.filter(H)??[];return g.length>0?g:null}async function K(a,d,f,g){let h=b.projects[a.projectId];if(!h||!a.pr)return;let i=h.scm?.plugin?c.get("scm",h.scm.plugin):null;if(!i)return;let j="ci-failed";if("merged"===f||"killed"===f){B(a.id,j),D(a,{lastCIFailureFingerprint:"",lastCIFailureDispatchHash:"",lastCIFailureDispatchAt:""});return}if("ci_failed"!==f){a.metadata.lastCIFailureFingerprint&&(B(a.id,j),D(a,{lastCIFailureFingerprint:"",lastCIFailureDispatchHash:"",lastCIFailureDispatchAt:""}));return}let k=await J(i,a.pr,{allowFetch:!0});if(!k)return;let l=E(k.map(a=>`${a.name}:${a.status}:${a.conclusion??""}`)),m=a.metadata.lastCIFailureFingerprint??"",n=a.metadata.lastCIFailureDispatchHash??"";if(l!==m&&g?.key!==j&&B(a.id,j),l!==m&&D(a,{lastCIFailureFingerprint:l}),g?.key===j&&g.result?.success&&(!0===g.messageEnriched||"send-to-agent"!==g.result.action))return void D(a,{lastCIFailureDispatchHash:l,lastCIFailureDispatchAt:new Date().toISOString()});if(l===n)return;let o=C(a,j);if(o&&o.action&&(!1!==o.auto||"notify"===o.action)){let b=await I(i,a.pr,k);try{if("send-to-agent"===o.action)await e.send(a.id,b);else{let c=ei(a,p),d=eg("ci.failing",{sessionId:a.id,projectId:a.projectId,message:b,data:function(a){let b=d4({...a,semanticType:"ci.failing"});return b.ci={status:"failing",failedChecks:a.failedChecks.map(d3)},b}({sessionId:a.id,projectId:a.projectId,context:c,failedChecks:k})});await M(d,o.priority??"warning")}D(a,{lastCIFailureDispatchHash:l,lastCIFailureDispatchAt:new Date().toISOString()})}catch{}}}async function L(a,d){let e=b.projects[a.projectId];if(!e||!a.pr||!(e.scm?.plugin?c.get("scm",e.scm.plugin):null))return;let f="merge-conflicts";if("open"!==a.lifecycle.pr.state||"killed"===d){B(a.id,f),D(a,{lastMergeConflictDispatched:""});return}if("pr_open"!==d&&"ci_failed"!==d&&"review_pending"!==d&&"changes_requested"!==d&&"approved"!==d&&"mergeable"!==d)return;let g=`${a.pr.owner}/${a.pr.repo}#${a.pr.number}`,h=p.get(g);if(!h)return;let i=h.hasConflicts??!1,j=a.metadata.lastMergeConflictDispatched??"";if(i){if("true"===j)return;let b=C(a,f);if(b&&b.action&&(!1!==b.auto||"notify"===b.action))try{let c={...b,priority:b.priority??"warning"};if("send-to-agent"===b.action&&!b.message){let b=a.pr.baseBranch??"the default branch",d=h.isBehind?` is behind ${b} and`:"";c.message=`Your PR branch${d} has merge conflicts with ${b}. Rebase your branch on ${b}, resolve the conflicts, and push. You should not need to call gh for merge status unless you need additional context — this information is current.`}let d=await A(a,f,c);d.success&&"escalated"!==d.action&&D(a,{lastMergeConflictDispatched:"true"})}catch{}}else"true"===j&&(D(a,{lastMergeConflictDispatched:""}),B(a.id,f))}async function M(a,d){let e={...a,priority:d};for(let a of b.notificationRouting[d]??b.defaults.notifiers){let d=function(a,b){let c=a.notifiers?.[b];return c?.plugin?{reference:b,pluginName:c.plugin}:{reference:b,pluginName:b}}(b,a),f=c.get("notifier",d.reference)??c.get("notifier",d.pluginName);if(!f){d0({observer:g,event:e,target:d,outcome:"failure",method:"notify",reason:"notifier target not found",failureKind:"target_missing",recordActivityEvent:!0});continue}try{await f.notify(e),d0({observer:g,event:e,target:d,outcome:"success",method:"notify"})}catch(a){d0({observer:g,event:e,target:d,outcome:"failure",method:"notify",reason:a instanceof Error?a.message:String(a),failureKind:"delivery_failed",recordActivityEvent:!0})}}}async function N(a){if(a.status!==d.SB.MERGED)return;let{autoCleanupOnMerge:c=!0,mergeCleanupIdleGraceMs:f=3e5}=b.lifecycle??{};if(!c)return;let i=new Date().toISOString(),j=a.metadata.mergedPendingCleanupSince||i,k=Date.parse(j),l=!!Number.isFinite(k)&&Date.now()-k>=f,m=a.activity;if((m===d.u3.ACTIVE||m===d.u3.WAITING_INPUT||m===d.u3.BLOCKED)&&!l){a.metadata.mergedPendingCleanupSince||D(a,{mergedPendingCleanupSince:i}),g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.merge_cleanup.deferred",outcome:"success",correlationId:dY("lifecycle-merge-cleanup"),projectId:a.projectId,sessionId:a.id,reason:em(a.lifecycle),data:{activity:m,pendingSince:j,graceMs:f},level:"info"}),aa({projectId:a.projectId,sessionId:a.id,source:"lifecycle",kind:"session.auto_cleanup_deferred",summary:`auto-cleanup deferred for ${a.id}`,data:{activity:m,pendingElapsedMs:Number.isFinite(k)?Date.now()-k:null,graceMs:f}});return}let n=dY("lifecycle-merge-cleanup");try{let b=await e.kill(a.id,{purgeOpenCode:!0,reason:"pr_merged"});g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.merge_cleanup.completed",outcome:"success",correlationId:n,projectId:a.projectId,sessionId:a.id,reason:em(a.lifecycle),data:{cleaned:b.cleaned,alreadyTerminated:b.alreadyTerminated,graceElapsed:l,activity:m},level:"info"}),aa({projectId:a.projectId,sessionId:a.id,source:"lifecycle",kind:"session.auto_cleanup_completed",summary:`auto-cleanup completed for ${a.id}`,data:{cleaned:b.cleaned,alreadyTerminated:b.alreadyTerminated,graceElapsed:l,activity:m}}),h.delete(a.id)}catch(c){a.metadata.mergedPendingCleanupSince||D(a,{mergedPendingCleanupSince:i});let b=c instanceof Error?c.message:String(c);g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.merge_cleanup.failed",outcome:"failure",correlationId:n,projectId:a.projectId,sessionId:a.id,reason:b,level:"warn"}),aa({projectId:a.projectId,sessionId:a.id,source:"lifecycle",kind:"session.auto_cleanup_failed",level:"error",summary:`auto-cleanup failed for ${a.id}`,data:{errorMessage:b}})}}async function O(a){var e;let f,i=h.get(a.id)??(a.metadata?.status||a.status),j=bt(a.lifecycle),k=a.lifecycle.pr.state,l=await z(a);if(l.skipMetadataWrite)return void h.set(a.id,i);let n=l.status,o=a.metadata.lifecycle!==JSON.stringify(a.lifecycle),q=l.evidence,r=l.detectingAttempts>0?String(l.detectingAttempts):"",t=l.detectingStartedAt??"",u=l.detectingEvidenceHash??"",v=n===d.SB.STUCK&&(l.detectingAttempts>3||cG(t)),w=v?a.metadata.detectingEscalatedAt||new Date().toISOString():"";if(v&&!a.metadata.detectingEscalatedAt){let b=l.detectingAttempts>3?"max_attempts":"max_duration";aa({projectId:a.projectId,sessionId:a.id,source:"lifecycle",kind:"detecting.escalated",level:"warn",summary:`detecting → stuck via ${b}`,data:{attempts:l.detectingAttempts,cause:b,startedAt:t}})}let x={};if(a.metadata.lifecycleEvidence!==q&&(x.lifecycleEvidence=q),(a.metadata.detectingAttempts||"")!==r&&(x.detectingAttempts=r),(a.metadata.detectingStartedAt||"")!==t&&(x.detectingStartedAt=t),(a.metadata.detectingEvidenceHash||"")!==u&&(x.detectingEvidenceHash=u),(a.metadata.detectingEscalatedAt||"")!==w&&(x.detectingEscalatedAt=w),Object.keys(x).length>0&&D(a,x),a.pr){let b=`${a.pr.owner}/${a.pr.repo}#${a.pr.number}`,c=p.get(b);if(c)if("passing"===c.ciStatus){let b=Number(a.metadata.ciPassingStableCount??"0")+1;b>=2?(B(a.id,"ci-failed"),D(a,{ciPassingStableCount:""})):D(a,{ciPassingStableCount:String(b)})}else a.metadata.ciPassingStableCount&&D(a,{ciPassingStableCount:""})}if(n!==i){let e=dY("lifecycle-transition");h.set(a.id,n),D(a,{status:n}),aa({projectId:a.projectId,sessionId:a.id,source:"lifecycle",kind:"lifecycle.transition",level:"ci_failed"===n?"warn":"info",summary:`${i} → ${n}`,data:{from:i,to:n}}),g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.transition",outcome:"success",correlationId:e,projectId:a.projectId,sessionId:a.id,reason:em(a.lifecycle),data:en(j,a.lifecycle,i,n,l.evidence,l.detectingAttempts,!0),level:ek(n)}),d.CM.has(n)||(m=!1);let k=eh(void 0,i);if(k){let b=ej(k);b&&!d9.has(b)&&B(a.id,b)}let o=eh(i,n);if(o){let d=!1,h=ej(o);if(h){let k=C(a,h),m=!1;if("ci-failed"===h&&a.pr&&k?.action==="send-to-agent"){let d=b.projects[a.projectId],e=d?.scm?.plugin?c.get("scm",d.scm.plugin):null;if(e){let b=await J(e,a.pr,{allowFetch:!1});b&&(k={...k,message:await I(e,a.pr,b)},m=!0)}}if(k&&k.action&&(!1!==k.auto||"notify"===k.action)){let b=await A(a,h,k);f={key:h,result:b,messageEnriched:m},g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.transition.reaction",outcome:b.success?"success":"failure",correlationId:e,projectId:a.projectId,sessionId:a.id,reason:em(a.lifecycle),data:en(j,a.lifecycle,i,n,l.evidence,l.detectingAttempts,!0,f),level:b.success?"info":"warn"}),d=!0}}if(!d){let b=ef(o),c=ei(a,p),d=eg(o,{sessionId:a.id,projectId:a.projectId,message:`${a.id}: ${i} → ${n}`,data:function(a){let b=d4({...a,semanticType:a.eventType});return b.transition={kind:"session_status",from:a.oldStatus,to:a.newStatus},d5(b,a.enrichment),d6(b,a.eventType,a.enrichment),b}({eventType:o,sessionId:a.id,projectId:a.projectId,context:c,oldStatus:i,newStatus:n,enrichment:s(a)})});await M(d,b)}}}else h.set(a.id,n),o&&(D(a,{status:n}),g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.sync",outcome:"success",correlationId:dY("lifecycle-sync"),projectId:a.projectId,sessionId:a.id,reason:em(a.lifecycle),data:en(j,a.lifecycle,i,n,l.evidence,l.detectingAttempts,!1),level:ek(n)}));let y=k===(e=a.lifecycle.pr.state)?null:"closed"===e?"pr.closed":null;if(y){let b=!1,c=ej(y);if(c){let d=C(a,c);d&&d.action&&(!1!==d.auto||"notify"===d.action)&&(await A(a,c,d),b=!0)}if(!b){let b=ei(a,p),c=eg(y,{sessionId:a.id,projectId:a.projectId,message:`${a.id}: PR ${k} → ${a.lifecycle.pr.state}`,data:function(a){let b=d4({...a,semanticType:a.eventType});return b.transition={kind:"pr_state",from:a.oldPRState,to:a.newPRState},d5(b,a.enrichment),d6(b,a.eventType,a.enrichment),b}({eventType:y,sessionId:a.id,projectId:a.projectId,context:b,oldPRState:k,newPRState:a.lifecycle.pr.state,enrichment:s(a)})});await M(c,ef(y))}}if(a.agentInfo?.summary&&!a.agentInfo.summaryIsFallback&&!a.metadata.pinnedSummary){let b=a.agentInfo.summary.replace(/[\n\r]/g," ").trim();if(b.length>=5)try{D(a,{pinnedSummary:b})}catch{}}await Promise.allSettled([F(a,i,n,f),L(a,n),K(a,i,n,f)]),await P(a),await N(a)}async function P(a){let b=function(a,b={},c=new Date){if(cO.has(a.status)||a.lifecycle?.session.kind==="orchestrator")return null;let d={...cN,...b},e=bY(a.metadata),f=function(a,b,c,d){if(!d.checkBlocked||!b)return null;if("needs_input"===b.state){let a=Date.parse(b.timestamp),d=Number.isNaN(a)?void 0:c.getTime()-a;return{trigger:"agent_needs_input",message:`Agent needs input: ${b.note??"waiting for user decision"}`,checkedAt:c.toISOString(),report:b,timeSinceReportMs:d}}return null}(0,e,c,d);if(f)return f;let g=function(a,b,c,d){if(!d.checkAcknowledge||b)return null;let e=a.createdAt??a.metadata.createdAt;if(!e)return null;let f="string"==typeof e?Date.parse(e):e.getTime();if(Number.isNaN(f))return null;let g=c.getTime()-f;return g<d.acknowledgeTimeoutMs?null:{trigger:"no_acknowledge",message:`Agent has not acknowledged task after ${Math.round(g/6e4)} minutes`,checkedAt:c.toISOString(),report:null,timeSinceSpawnMs:g}}(a,e,c,d);if(g)return g;let h=function(a,b,c,d){if(!d.checkStale||!b)return null;let e=Date.parse(b.timestamp);if(Number.isNaN(e))return null;let f=c.getTime()-e;return f<d.staleReportTimeoutMs||"waiting"===b.state||"needs_input"===b.state?null:{trigger:"stale_report",message:`Agent report is stale (${Math.round(f/6e4)} minutes since last report)`,checkedAt:c.toISOString(),report:b,timeSinceReportMs:f}}(0,e,c,d);return h||null}(a),c=new Date().toISOString();if(!b||!b.trigger){a.metadata[cP.ACTIVE_TRIGGER]&&D(a,{[cP.LAST_AUDITED_AT]:c,[cP.ACTIVE_TRIGGER]:"",[cP.TRIGGER_ACTIVATED_AT]:"",[cP.TRIGGER_COUNT]:""});return}let d=function(a){switch(a){case"no_acknowledge":return"report-no-acknowledge";case"stale_report":return"report-stale";case"agent_needs_input":return"report-needs-input"}}(b.trigger),e=C(a,d),f=parseInt(a.metadata[cP.TRIGGER_COUNT]??"0",10),h=a.metadata[cP.ACTIVE_TRIGGER]!==b.trigger;D(a,{[cP.LAST_AUDITED_AT]:c,[cP.ACTIVE_TRIGGER]:b.trigger,[cP.TRIGGER_ACTIVATED_AT]:h?c:a.metadata[cP.TRIGGER_ACTIVATED_AT]??c,[cP.TRIGGER_COUNT]:String(h?1:f+1)}),g.recordOperation({metric:"lifecycle_poll",operation:"report_watcher.audit",outcome:"success",correlationId:dY("report-watcher"),projectId:a.projectId,sessionId:a.id,reason:b.trigger,data:{trigger:b.trigger,message:b.message,timeSinceSpawnMs:b.timeSinceSpawnMs,timeSinceReportMs:b.timeSinceReportMs,reportState:b.report?.state},level:"warn"}),h&&aa({projectId:a.projectId,sessionId:a.id,source:"report-watcher",kind:"report_watcher.triggered",level:"warn",summary:`${b.trigger} triggered`,data:{trigger:b.trigger,message:b.message,timeSinceSpawnMs:b.timeSinceSpawnMs,timeSinceReportMs:b.timeSinceReportMs,reportState:b.report?.state}}),h&&e&&!1!==e.auto&&await A(a,d,e)}async function Q(a){let e=Date.now();if(e-n<6e4)return;n=e;let h=new Set(a.filter(a=>!(0,d.zi)(a)).map(a=>a.id));for(let a of Object.keys(b.metaOrchestrators??{}))h.add(a);let i=f&&b.projects[f]?{[f]:b.projects[f]}:f?{}:b.projects,j=new Map;for(let a of Object.values(i)){if(!a.sessionPrefix)continue;let d=a.runtime??b.defaults.runtime,e=j.get(d);if(e){e.sessionPrefixes.push(a.sessionPrefix);continue}let f=c.get("runtime",d);f&&j.set(d,{runtime:f,sessionPrefixes:[a.sessionPrefix]})}if(0!==j.size)try{let a=await dJ({runtimes:[...j.values()],activeTrackedIds:h,graceMs:12e4,nowMs:e,reap:!0,log:(a,b)=>{aa({projectId:f,source:"lifecycle",kind:"lifecycle.runtime_orphan_reaped",level:"warn",summary:a,data:b})}});a.outcomes.length>0&&g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.reap_runtime_orphans",correlationId:dY("lifecycle-orphan-reap"),outcome:"success",projectId:f,data:{reaped:a.outcomes.filter(a=>a.reaped).length,failed:a.outcomes.filter(a=>!a.reaped).length,orphans:a.orphans.map(a=>a.id)},level:"info"})}catch{}}async function R(){let a=dY("lifecycle-poll"),c=Date.now();if(!l){l=!0;try{let k=await e.list(f),l=k.filter(a=>{if(!d.CM.has(a.status))return!0;let b=h.get(a.id);return void 0!==b&&b!==a.status});await Promise.allSettled(l.map(a=>y(a,k))),await w(l),await Promise.allSettled(l.map(a=>O(a))),function(a){for(let c of a){let a=q(c);if(!c.pr||!b.projects[c.projectId])continue;let d=v(c.projectId),e=r(c,a.length);Object.keys(e).length>0&&(bE(d,c.id,e),c.metadata=Object.fromEntries(Object.entries(c.metadata).filter(([a])=>void 0===e[a])));let f=`${c.pr.owner}/${c.pr.repo}#${c.pr.number}`,g=p.get(f);if(g){let a=JSON.stringify({state:g.state,ciStatus:g.ciStatus,reviewDecision:g.reviewDecision,mergeable:g.mergeable,title:g.title,additions:g.additions,deletions:g.deletions,isDraft:g.isDraft,hasConflicts:g.hasConflicts,isBehind:g.isBehind,blockers:g.blockers,ciChecks:g.ciChecks?.map(a=>({name:a.name,status:a.status,url:a.url})),enrichedAt:new Date().toISOString()});c.metadata.prEnrichment!==a&&(bE(d,c.id,{prEnrichment:a}),c.metadata.prEnrichment=a),void 0!==g.isDraft&&c.pr&&(c.pr.isDraft=g.isDraft)}for(let b=1;b<a.length;b++){let e=a[b];if(!e)continue;let f=`${e.owner}/${e.repo}#${e.number}`,g=p.get(f);if(!g)continue;let h=JSON.stringify({state:g.state,ciStatus:g.ciStatus,reviewDecision:g.reviewDecision,mergeable:g.mergeable,title:g.title,additions:g.additions,deletions:g.deletions,isDraft:g.isDraft,hasConflicts:g.hasConflicts,isBehind:g.isBehind,blockers:g.blockers,ciChecks:g.ciChecks?.map(a=>({name:a.name,status:a.status,url:a.url})),enrichedAt:new Date().toISOString()}),i=`prEnrichment_${b}`;c.metadata[i]!==h&&(bE(d,c.id,{[i]:h}),c.metadata[i]=h),void 0!==g.isDraft&&(e.isDraft=g.isDraft)}}}(l);let n=new Set(k.map(a=>a.id));for(let a of h.keys())n.has(a)||h.delete(a);for(let a of i.keys())n.has(a)||i.delete(a);for(let a of j.keys()){let b=a.split(":")[0];b&&!n.has(b)&&j.delete(a)}for(let a of u.keys())n.has(a)||u.delete(a);let o=k.filter(a=>!d.CM.has(a.status));if(k.length>0&&0===o.length&&!m){m=!0;let a=ej("summary.all_complete");if(a){let c=b.reactions[a];c&&c.action&&(!1!==c.auto||"notify"===c.action)&&await A({id:"system",projectId:"all",pr:null,issueId:null,branch:null,metadata:{},agentInfo:null},a,c)}}await Q(k),f&&(g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.poll",outcome:"success",correlationId:a,projectId:f,durationMs:Date.now()-c,data:{sessionCount:k.length,activeSessionCount:o.length},level:"info"}),g.setHealth({surface:"lifecycle.worker",status:"ok",projectId:f,correlationId:a,details:{projectId:f,sessionCount:k.length,activeSessionCount:o.length}}))}catch(d){let b=d instanceof Error?d.message:String(d);g.recordOperation({metric:"lifecycle_poll",operation:"lifecycle.poll",outcome:"failure",correlationId:a,projectId:f,durationMs:Date.now()-c,reason:b,level:"error"}),aa({projectId:f,source:"lifecycle",kind:"lifecycle.poll_failed",level:"error",summary:"poll cycle failed",data:{errorMessage:b,durationMs:Date.now()-c,projectScope:f??"all"}}),g.setHealth({surface:"lifecycle.worker",status:"error",projectId:f,correlationId:a,reason:b,details:f?{projectId:f}:{projectScope:"all"}})}finally{l=!1}}}return{start(a=3e4){k||(k=setInterval(()=>void R(),a),R())},stop(){k&&(clearInterval(k),k=null)},getStates:()=>new Map(h),async check(a){let b=await e.get(a);if(!b)throw Error(`Session ${a} not found`);await y(b),await w([b]),await O(b)}}}function ep(a){let b=function(a){let{config:b,projectId:c,project:d}=a,e=!!d.repo;return{projectId:c,projectName:d.name,projectRepo:d.repo??"not configured",projectDefaultBranch:d.defaultBranch,projectSessionPrefix:d.sessionPrefix,projectPath:d.path,dashboardPort:String(b.port??3e3),automatedReactionsSection:function(a){let b="*".repeat(2),c=a=>`${b}${a}${b}`,d=[];for(let[b,e]of Object.entries(a.reactions??{})){if(e.auto&&"send-to-agent"===e.action){d.push(`- ${c(b)}: Auto-sends instruction to agent (retries: ${e.retries??"none"}, escalates after: ${e.escalateAfter??"never"})`);continue}e.auto&&"notify"===e.action&&d.push(`- ${c(b)}: Notifies human (priority: ${e.priority??"info"})`)}return 0===d.length?"":d.join("\n")}(d),projectSpecificRulesSection:function(a){let b=a.orchestratorRules?.trim();return b||""}(d),repoConfiguredSection:e?"true":"",repoNotConfiguredSection:e?"":"true"}}(a);return(function(a,b){let c=a.replace(/\{\{([a-zA-Z0-9_]+)\}\}/g,"").match(/\{\{[^}]+\}\}/);if(c)throw Error(`Unresolved template placeholder: ${c[0]}`);return a.replace(/\{\{([a-zA-Z0-9_]+)\}\}/g,(a,c)=>{if(!Object.prototype.hasOwnProperty.call(b,c))throw Error(`Unresolved template placeholder: ${c}`);return b[c]})})(function(a,b){let c=[["REPO_CONFIGURED_SECTION_START","REPO_CONFIGURED_SECTION_END",b.repoConfiguredSection],["REPO_NOT_CONFIGURED_SECTION_START","REPO_NOT_CONFIGURED_SECTION_END",b.repoNotConfiguredSection],["AUTOMATED_REACTIONS_SECTION_START","AUTOMATED_REACTIONS_SECTION_END",b.automatedReactionsSection],["PROJECT_SPECIFIC_RULES_SECTION_START","PROJECT_SPECIFIC_RULES_SECTION_END",b.projectSpecificRulesSection]],d=a;for(let[a,b,e]of c){let c=`{{${a}}}`,f=`{{${b}}}`;for(;;){let a=d.indexOf(c),b=d.indexOf(f);if(-1===a&&-1===b)break;if(-1===a||-1===b||b<a)throw Error(`Malformed optional section block: expected ${c} before ${f}`);let g=b+f.length,h=d.slice(a+c.length,b);if(h.includes(c))throw Error(`Nested optional section blocks are not supported: ${c} before ${f}`);let i=e?h:"",j=d.slice(0,a),k=d.slice(g);d=i?j+i+k:function(a,b){let c=a.match(/\n*$/)?.[0]??"",d=b.match(/^\n*/)?.[0]??"",e=c.length+d.length>=2?"\n\n":c+d;return a.slice(0,a.length-c.length)+e+b.slice(d.length)}(j,k)}}return d}('# {{projectName}} Orchestrator\n\nYou are the **orchestrator agent** for the {{projectName}} project. Your only job is coordination: spawn workers, monitor them, and communicate results to the user. Every request you receive maps to one of those three actions.\n\nWhen a request arrives, your response should be one of:\n- **Spawn a worker** — `athene spawn` with a clear prompt describing the task\n- **Direct an existing worker** — `athene send <session> <message>` with specific instructions\n- **Report status** — summarise what workers have done or are doing\n\nIf you find yourself editing files, running git commands, or writing code, you are doing a worker\'s job. Stop and spawn a worker instead.\n\n## Non-Negotiable Rules\n\n- Investigations from the orchestrator session are **read-only**. Inspect status, logs, metadata, PR state, and worker output, but do not edit repository files or implement fixes from the orchestrator session.\n- Any code change, test run tied to implementation, git branch work, or PR creation must be delegated to a **worker session** via `athene spawn`.\n- The orchestrator session must never own a PR. Never claim a PR into the orchestrator session, and never treat the orchestrator as the worker responsible for implementation.\n- If an investigation discovers follow-up work, either spawn a worker session or direct an existing worker session with clear instructions.\n- **Never use Claude\'s native Task tool to spawn subagents** for implementation. Read-only Explore/Plan agents are the only permitted exception; all implementation work must go through `athene spawn` — this creates a properly tracked worker session with a worktree, branch, metadata, lifecycle polling, and dashboard visibility. A native Claude subagent has none of that and is invisible to the rest of the system.\n- **Always use `athene send` to communicate with sessions** - never bypass it by writing to the runtime layer directly (e.g. `tmux send-keys` / `tmux capture-pane` on Unix, or writing to the named pipe `\\\\.\\pipe\\ao-pty-<sessionId>` on Windows). Direct runtime access bypasses busy detection, retry logic, and input sanitization, and breaks multi-line input for some agents (e.g. Codex).\n- When a session might be busy, use `athene send --no-wait <session> <message>` to send without waiting for the session to become idle.\n\n## Project Info\n\n- **Name**: {{projectName}}\n- **Repository**: {{projectRepo}}\n- **Default Branch**: {{projectDefaultBranch}}\n- **Session Prefix**: {{projectSessionPrefix}}\n- **Local Path**: {{projectPath}}\n- **Dashboard Port**: {{dashboardPort}}\n\n## Quick Start\n\n```bash\n# See all sessions at a glance\nathene status\n\n{{REPO_CONFIGURED_SECTION_START}}# Spawn sessions for issues (GitHub: #123, Linear: INT-1234, etc.)\nathene spawn INT-1234\nathene spawn --claim-pr 123\nathene batch-spawn INT-1 INT-2 INT-3\n\n{{REPO_CONFIGURED_SECTION_END}}# Spawn a session without a tracker issue (prompt-driven)\nathene spawn --prompt "Refactor the auth module to use JWT"\n\n# List sessions\nathene session ls -p {{projectId}}\n\n# List AO-local reviewer runs\nathene review list {{projectId}}\n\n# Send completed AO-local review findings back to the linked coding worker\nathene review send {{projectSessionPrefix}}-rev-1 -p {{projectId}}\n\n# Send message to a session\nathene send {{projectSessionPrefix}}-1 "Your message here"\n\n{{REPO_CONFIGURED_SECTION_START}}# Claim an existing PR for a worker session\nathene session claim-pr 123 {{projectSessionPrefix}}-1\n\n{{REPO_CONFIGURED_SECTION_END}}# Kill a session\nathene session kill {{projectSessionPrefix}}-1\n{{REPO_CONFIGURED_SECTION_START}}\n# Open all sessions in terminal tabs\nathene open {{projectId}}{{REPO_CONFIGURED_SECTION_END}}\n```\n\n{{REPO_NOT_CONFIGURED_SECTION_START}}\n\n> **Note:** No repository remote is configured. Issue tracking, PR, and CI features are unavailable.\n> Add a `repo` field (owner/repo) to `agent-orchestrator.yaml` to enable them.\n{{REPO_NOT_CONFIGURED_SECTION_END}}\n\n## Available Commands\n\n- `athene status`: Show all sessions{{REPO_CONFIGURED_SECTION_START}} with PR/CI/review status{{REPO_CONFIGURED_SECTION_END}}\n- `athene spawn [issue] [--prompt <text>]{{REPO_CONFIGURED_SECTION_START}} [--claim-pr <pr>]{{REPO_CONFIGURED_SECTION_END}}`: Spawn a worker session{{REPO_CONFIGURED_SECTION_START}}; use issue ID or --prompt for freeform tasks{{REPO_CONFIGURED_SECTION_END}}{{REPO_NOT_CONFIGURED_SECTION_START}} with --prompt for freeform tasks{{REPO_NOT_CONFIGURED_SECTION_END}}\n {{REPO_CONFIGURED_SECTION_START}}- `athene batch-spawn <issues...>`: Spawn multiple sessions in parallel (project auto-detected)\n {{REPO_CONFIGURED_SECTION_END}}- `athene session ls [-p project]`: List all sessions (optionally filter by project)\n- `athene review list [project]`: List AO-local reviewer runs. These are review agents/runs, not coding worker sessions.\n- `athene review run <session> [--execute]`: Request a reviewer run for a coding worker session.\n- `athene review execute [project] [--run <run>]`: Execute a queued reviewer run.\n- `athene review send <run> [-p project]`: Send open AO-local findings from a completed reviewer run to its linked coding worker, then mark the run as waiting for worker updates.\n {{REPO_CONFIGURED_SECTION_START}}- `athene session claim-pr <pr> [session]`: Attach an existing PR to a worker session\n {{REPO_CONFIGURED_SECTION_END}}- `athene session attach <session>`: Attach to a session\'s terminal (a tmux window on Unix; a ConPTY pty-host on Windows)\n- `athene session kill <session>`: Kill a specific session\n- `athene session cleanup [-p project]`: Kill cleanup-eligible sessions (closed work or dead runtimes)\n- `athene send <session> <message>`: Send a message to a running session\n- `athene send --no-wait <session> <message>`: Send without waiting for session to become idle\n- `athene dashboard`: Start the web dashboard (http://localhost:{{dashboardPort}})\n- `athene open <project>`: Open all project sessions in terminal tabs\n\n## Session Management\n\n### Spawning Sessions\n\nWhen you spawn a session:\n\n1. A git worktree is created from `{{projectDefaultBranch}}`\n2. A feature branch is created (e.g., `feat/INT-1234` for issues, `session/<id>` for prompt-driven)\n3. A runtime session is started (e.g., `{{projectSessionPrefix}}-1`) — tmux session on Unix, ConPTY pty-host on Windows\n4. The agent is launched with context about the issue or prompt\n5. Metadata is written to the project-specific sessions directory\n\nA tracker issue is **not required**. Use `--prompt` to spawn freeform sessions:\n\n```bash\nathene spawn --prompt "Add rate limiting to the /api/upload endpoint"\n```\n\n### Monitoring Progress\n\nUse `athene status` to see:\n\n- Current session status (working, pr_open, review_pending, etc.)\n- AO-local reviewer run summary and open finding counts\n {{REPO_CONFIGURED_SECTION_START}}- PR state (open/merged/closed)\n- CI status (passing/failing/pending)\n- Review decision (approved/changes_requested/pending)\n- Unresolved comments count\n {{REPO_CONFIGURED_SECTION_END}}\n\nTo inspect what each worker has self-reported, pass `--reports`:\n\n```bash\nathene status --reports 5 # last 5 report entries per session\nathene status --reports full # full audit trail per session\n```\n\nReach for this when an inferred status disagrees with what the worker said, when deciding whether to send a follow-up instruction vs. wait, or when triaging a session that looks stuck.\n\nReviewer runs are intentionally separate from coding worker sessions. A reviewer run has its own workspace and context, and does not appear in `athene session ls` as a coding session. Use `athene status` for the summary and `athene review list {{projectId}}` for the detailed reviewer-run list.\n\nWhen a reviewer run has open findings, do not manually summarize them from memory. Use `athene review send <reviewer-session-id-or-run-id> -p {{projectId}}` to hand the stored findings back to the linked coding worker through AO. After sending, monitor the worker and request a new review once it reports the fixes are ready.\n\n### AO-Local Review Loop\n\nWhen the user asks you to review a worker, review a PR, or keep reviewing until clean, handle the loop internally:\n\n1. Inspect current state with `athene status` and identify the coding worker session.\n2. Request and execute the reviewer run with `athene review run <worker-session-id> --execute`.\n3. If the run is clean, report that the work is AO-review clean.\n4. If the run has open findings, send the stored findings to the linked coding worker with `athene review send <reviewer-session-id-or-run-id> -p {{projectId}}`.\n5. Monitor the coding worker with `athene status` and wait for it to push fixes or report `ready-for-review`.\n6. Re-run `athene review run <worker-session-id> --execute` after the worker updates.\n7. Continue until the review is clean, the worker is stuck, the user asks you to stop, or the configured review round limit is reached.\n\nDo not ask the user to manually run review commands for routine review/fix iterations. Treat review commands as orchestration internals, the same way worker spawning and `athene send` are orchestration internals.\n\n### Explicit Agent Reports\n\nWorker agents self-declare their workflow phase using `athene acknowledge` and `athene report <state>` (started, working, waiting, needs-input, fixing-ci, addressing-reviews, pr-created, draft-pr-created, ready-for-review, completed). These reports are persisted alongside the canonical lifecycle and may inform lifecycle inference, but do not replace runtime/activity/SCM-derived truth.\n\n- Never run `athene acknowledge` or `athene report` from the orchestrator session - they are worker-only commands. Read the audit trail with `athene status --reports` instead.\n- Fresh reports (<5 min) are useful hints when inference is weak, but runtime death, activity-based waiting_input, and SCM truth (merged/closed PR, CI failure, review decisions) still take precedence.\n- Use `--pr-url` / `--pr-number` on PR workflow reports when the agent knows them; merged/closed remain SCM-owned.\n- If an agent reports `waiting` but a PR actually merged, trust the PR state and follow up.\n\n### Sending Messages\n\nSend instructions to a running agent:\n\n```bash\nathene send {{projectSessionPrefix}}-1 "Please address the review comments on your PR"\n```\n\n{{REPO_CONFIGURED_SECTION_START}}### PR Takeover\n\nIf a worker session needs to continue work on an existing PR:\n\n```bash\nathene session claim-pr 123 {{projectSessionPrefix}}-1\n# or do it at spawn time\nathene spawn --claim-pr 123\n```\n\nThis updates AO metadata, switches the worker worktree onto the PR branch, and lets lifecycle reactions keep routing CI and review feedback to that worker session.\n\nNever claim a PR into `{{projectSessionPrefix}}-orchestrator`. If a PR needs implementation or takeover, delegate it to a worker session instead.\n{{REPO_CONFIGURED_SECTION_END}}\n\n### Investigation Workflow\n\nWhen debugging or triaging from the orchestrator session:\n\n1. Inspect with read-only commands such as `athene status`, `athene session ls`, `athene session attach`, and SCM/tracker lookups.\n2. Decide whether a worker already owns the work or a new worker is needed.\n3. Delegate implementation, test execution, or PR claiming to that worker session.\n4. Return to monitoring and coordination once the worker has the task.\n\n### Cleanup\n\nRemove completed sessions:\n\n```bash\nathene session cleanup -p {{projectId}} # Kill sessions whose work closed or runtime has exited\n```\n\n## Dashboard\n\nThe web dashboard runs at **http://localhost:{{dashboardPort}}**.\n\nFeatures:\n\n- Live session cards with activity status\n- PR table with CI checks and review state\n- Attention zones (merge ready, needs response, working, done)\n- One-click actions (send message, kill, merge PR)\n- Real-time updates via Server-Sent Events\n\n{{AUTOMATED_REACTIONS_SECTION_START}}\n\n## Automated Reactions\n\nThe system automatically handles these events:\n\n{{automatedReactionsSection}}\n{{AUTOMATED_REACTIONS_SECTION_END}}\n\n## Common Workflows\n\n{{REPO_CONFIGURED_SECTION_START}}### Bulk Issue Processing\n\n1. Get list of issues from tracker (GitHub/Linear/etc.)\n2. Use `athene batch-spawn` to spawn sessions for each issue\n3. Monitor with `athene status` or the dashboard\n4. Agents will fetch, implement, test, PR, and respond to reviews\n5. Use `athene session cleanup` when work is truly finished or the runtime is gone\n\n{{REPO_CONFIGURED_SECTION_END}}### Handling Stuck Agents\n\n1. Check `athene status` for sessions in "stuck" or "needs_input" state\n2. Attach with `athene session attach <session>` to see what they\'re doing\n3. Send clarification or instructions with `athene send <session> \'...\'`\n4. Or kill and respawn with fresh context if needed\n\n{{REPO_CONFIGURED_SECTION_START}}### PR Review Flow\n\n1. Agent creates PR and pushes\n2. CI runs automatically\n3. If CI fails: reaction auto-sends fix instructions to agent\n4. If reviewers request changes: reaction auto-sends comments to agent\n5. When approved + green: notify human to merge (unless auto-merge enabled)\n\n{{REPO_CONFIGURED_SECTION_END}}### Manual Intervention\n\nWhen an agent needs human judgment:\n\n1. You\'ll get a notification (desktop/slack/webhook)\n2. Check the dashboard or `athene status` for details\n3. Attach to the session if needed: `athene session attach <session>`\n4. Send instructions: `athene send <session> \'...\'`\n5. Or handle the human-only action yourself{{REPO_CONFIGURED_SECTION_START}} (merge PR, close issue, etc.){{REPO_CONFIGURED_SECTION_END}} while keeping implementation in worker sessions.\n\n## Tips\n\n1. **Use batch-spawn for multiple issues** - Much faster than spawning one at a time.\n\n2. **Check status before spawning** - Avoid creating duplicate sessions for issues already being worked on.\n\n3. **Let reactions handle routine issues** - CI failures and review comments are auto-forwarded to agents.\n\n4. **Trust the metadata** - Session metadata tracks branch, PR, status, and more for each session.\n\n5. **Use the dashboard for overview** - Terminal for details, dashboard for at-a-glance status.\n\n6. **Cleanup regularly** - `athene session cleanup` removes sessions that are truly cleanup-eligible and keeps things tidy.\n\n7. **Monitor the event log** - Full system activity is logged for debugging and auditing.\n\n8. **Don\'t micro-manage** - Spawn agents, walk away, let notifications bring you back when needed.\n\n{{PROJECT_SPECIFIC_RULES_SECTION_START}}\n\n## Project-Specific Rules\n\n{{projectSpecificRulesSection}}\n{{PROJECT_SPECIFIC_RULES_SECTION_END}}\n'.trim(),b),b).trim()}function eq(a){var b;let c=function(a){let b=a.config.metaOrchestrators?.[a.name];if(!b)throw Error(`Unknown meta orchestrator: ${a.name}`);let c=a.config.port??3e3,d="all"===b.scope?"all registered projects":`projects: ${b.scope.projects.join(", ")}`;return{metaName:a.name,dashboardUrl:`http://localhost:${c}/meta/${a.name}`,scopeDescription:d,discoverDescription:b.discover?"enabled — newly-registered projects appear in `athene meta-status` and the dashboard immediately (both read live config); this prompt's catalog above is a snapshot from meta-start, so restart the meta orchestrator to surface new projects here":"disabled",projectCatalog:function(a,b){let c=a.metaOrchestrators?.[b];if(!c)throw Error(`Unknown meta orchestrator: ${b}`);let d=function(a,b){let c=Object.entries(a.projects);if("all"===b.scope)return c;let d=new Set(b.scope.projects);return c.filter(([a])=>d.has(a))}(a,c);return 0===d.length?"_(no projects in scope yet)_":d.map(([a,b])=>{let c=b.repo??"no repo",d=b.sessionPrefix??a,e=b.description??"no description";return`- ${a} (${c}, prefix ${d}): ${e}`}).join("\n")}(a.config,a.name),rules:b.rules?.trim()??""}}(a);return(b=function(a,b,c){let d=`{{${b}_START}}`,e=`{{${b}_END}}`,f=a.indexOf(d),g=a.indexOf(e);if(-1===f&&-1===g)return a;if(-1===f||-1===g||g<f)throw Error(`Malformed optional section block: expected ${d} before ${e}`);let h=a.slice(0,f),i=a.slice(f+d.length,g),j=a.slice(g+e.length);return c?`${h}${i}${j}`:`${h}${j}`}('# {{metaName}} Meta Orchestrator\n\nYou are the **meta orchestrator** named `{{metaName}}`. Your only job is coordination across a portfolio of projects: route incoming work to the right project, spawn workers, monitor them, and communicate results to the user. Every request you receive maps to one of those three actions.\n\nWhen a request arrives, your response should be one of:\n- **Spawn a worker** into the target project — `athene spawn <project>` with a clear prompt describing the task\n- **Direct an existing worker** — `athene send <session> <message>` with specific instructions\n- **Report status** — summarise what workers have done or are doing across the portfolio\n\nIf you find yourself editing files, running git commands, or writing code, you are doing a worker\'s job. Stop and spawn a worker into the appropriate project instead.\n\n## Non-Negotiable Rules\n\n- Investigations from the meta orchestrator session are **read-only**. Inspect status, logs, metadata, PR state, and worker output across projects, but never edit repository files or implement fixes yourself.\n- Any code change, test run tied to implementation, git branch work, or PR creation must be delegated to a **worker session** in the target project via `athene spawn`.\n- The meta orchestrator must never own a PR. Never claim a PR into this session, and never treat yourself as the worker responsible for implementation.\n- You **coexist** with per-project orchestrators. Each per-project orchestrator manages only its own workers; you manage only the workers **you** dispatch. Do not assume control of another coordinator\'s workers.\n- **Never use Claude\'s native Task tool to spawn subagents.** All work must go through `athene spawn` so it becomes a properly tracked worker session (worktree, branch, metadata, lifecycle polling, dashboard visibility).\n- **Always use `athene send` to communicate with sessions** — never write to the runtime layer directly.\n\n## Scope\n\n- **Projects in scope**: {{scopeDescription}}\n- **Auto-discovery of new projects**: {{discoverDescription}}\n- **Your dashboard**: {{dashboardUrl}}\n\n## Project Catalog\n\nRoute primarily from this catalog. Each line is `projectId (repo, prefix): description`.\n\n{{projectCatalog}}\n\n## Routing: Metadata-First, Code-On-Demand\n\n1. **Match from the catalog first.** Use the project `description` and repo to decide where a piece of work belongs.\n2. **If the match is ambiguous, scout before committing.** Spawn one or more read-only **scout** workers into the candidate repos with an investigation-only prompt (e.g. "Read-only: does X live here? Report findings, change nothing."). A scout is just an ordinary worker — `athene spawn <project> --prompt "..."`. Once a scout confirms where the work belongs, **kill the scouts** (`athene session kill <id>`) and dispatch the real worker into the confirmed project.\n3. **Dispatch the real worker** into the target project with a plain `athene spawn`. Ownership is stamped **automatically**: because you run with `ATHENE_CALLER_TYPE=meta-orchestrator` (and `ATHENE_META_NAME={{metaName}}`), every `athene spawn` / `athene batch-spawn` you run tags the worker `ownerKind=meta` + `metaOwner={{metaName}}` so it appears in your fleet (`athene meta-status {{metaName}}` and your dashboard). You do not need to pass any owner flags. (To override, the internal `--owner-kind` / `--meta-owner` flags exist.)\n\n## Ownership & Visibility\n\n- Workers you dispatch are tagged `ownerKind=meta` and `metaOwner={{metaName}}`. They live in their **target project\'s** storage and are visible to BOTH you and that project\'s orchestrator.\n- Your dashboard ({{dashboardUrl}}) filters to the workers you own. You can still see other sessions in `athene status` to avoid collisions.\n\n## Anti-Collision Guard\n\nSpawning is protected by a shared guard so two coordinators never duplicate work:\n\n- **Issue-keyed work → HARD REFUSAL.** If any live session in the target project already owns that issue (regardless of owner), the spawn is refused with a clear message. Do not retry the same issue; inspect the existing session instead.\n- **Freeform `--prompt` work → ADVISORY.** There is no natural key, so the spawn surfaces existing live sessions and their tasks. **Check first** with `athene status` / `athene meta-status {{metaName}}` before dispatching freeform work to avoid duplicating an in-flight task.\n\n## Quick Start\n\n```bash\n# Your owned fleet across all in-scope projects (peers shown dimmed)\nathene meta-status {{metaName}}\n\n# Portfolio-wide status (all coordinators\' sessions)\nathene status\n\n# Dispatch a worker into a project (issue-keyed)\nathene spawn <project> INT-1234\n\n# Dispatch a freeform worker (check existing sessions first)\nathene spawn <project> --prompt "Refactor the auth module to use JWT"\n\n# Send a message to a worker\nathene send <prefix>-1 "Your message here"\n\n# Kill a worker (including scouts once they\'ve reported)\nathene session kill <prefix>-1\n```\n{{RULES_SECTION_START}}\n\n## Project-Specific Rules\n\n{{rules}}\n{{RULES_SECTION_END}}\n'.trim(),"RULES_SECTION",c.rules.length>0),b.replace(/\{\{([a-zA-Z0-9_]+)\}\}/g,(a,b)=>{if(!Object.prototype.hasOwnProperty.call(c,b))throw Error(`Unresolved template placeholder: ${b}`);return c[b]})).trim()}function er(a,b){let c=(0,e.readFileSync)(a,"utf-8"),d=(0,i.qg)(c)??{},f=d.metaOrchestrators??{};f[b.name]={scope:b.scope,discover:!0,...void 0!==b.agent?{agent:b.agent}:{}},d.metaOrchestrators=f,(0,e.writeFileSync)(a,(0,i.As)(d),"utf-8")}function es(a){return(0,g.join)(a,".ao","activity.jsonl")}async function et(a,b,c,d){let e=es(a);await (0,bU.mkdir)((0,g.dirname)(e),{recursive:!0});let f={ts:new Date().toISOString(),state:b,source:c,...void 0!==d&&("waiting_input"===b||"blocked"===b)&&{trigger:d}};await (0,bU.appendFile)(e,JSON.stringify(f)+"\n","utf-8")}async function eu(a){let b=es(a);try{let{open:a}=await Promise.resolve().then(c.t.bind(c,51455,19)),d=await a(b,"r");try{let a=await d.stat();if(0===a.size)return null;let b=Math.min(a.size,4096),c=Math.max(0,a.size-b),e=Buffer.alloc(b),{bytesRead:f}=await d.read(e,0,b,c);if(0===f)return null;let g=e.subarray(0,f).toString("utf-8").split("\n").filter(a=>a.trim());if(c>0&&g.length>1&&(g=g.slice(1)),0===g.length)return null;let h=null;for(let a=g.length-1;a>=0;a--)try{h=JSON.parse(g[a]);break}catch{continue}if(null===h||"object"!=typeof h||null===h||Array.isArray(h))return null;let i=h,j=new Set(["active","ready","idle","waiting_input","blocked","exited"]),k=new Set(["terminal","native","hook"]);if("string"!=typeof i.ts||"string"!=typeof i.state||"string"!=typeof i.source||!j.has(i.state)||!k.has(i.source))return null;return{entry:{ts:i.ts,state:i.state,source:i.source,..."string"==typeof i.trigger&&{trigger:i.trigger}},modifiedAt:a.mtime}}finally{await d.close()}}catch{return null}}function ev(a){if(!a)return null;let{entry:b}=a;if("waiting_input"===b.state||"blocked"===b.state){let a=new Date(b.ts);return Number.isNaN(a.getTime())?null:{state:b.state,timestamp:a}}return null}function ew(a,b,c){let d;if(!a)return null;let{entry:e}=a,f=new Date(e.ts);if(Number.isNaN(f.getTime()))return null;if("waiting_input"===e.state||"blocked"===e.state)return{state:e.state,timestamp:f};let g=Math.max(0,Date.now()-f.getTime());d=g<=b?"active":g<=c?"ready":"idle";let h={active:0,ready:1,idle:2},i=h[e.state]??2;return{state:(h[d]??2)>=i?d:e.state,timestamp:f}}async function ex(a,b,c){let{state:d,trigger:e}=function(a,b){let c=b(a),d="waiting_input"===c||"blocked"===c?a.trim().split("\n").slice(-3).join("\n"):void 0;return{state:c,trigger:d}}(b,c);if("waiting_input"!==d&&"blocked"!==d){let b=await eu(a);if(b&&b.entry.state===d&&Date.now()-b.modifiedAt.getTime()<2e4)return}await et(a,d,"terminal",e)}let ey=(0,E.promisify)(D.execFile);async function ez(a,b=60){try{let{stdout:c}=await ey("git",["log",`--since=${b} seconds ago`,"--format=%H"],{cwd:a,timeout:5e3});return c.trim().length>0}catch{return!1}}let eA=(0,E.promisify)(D.execFile),eB=null;async function eC(){if(eB)return eB;let a=await eD();return eB=a,a}async function eD(){let a=(0,g.join)((0,h.homedir)(),".ao","bin"),b=(process.env.PATH??"").split(g.delimiter).filter(b=>b&&b!==a),c="win32"===process.platform?(process.env.PATHEXT?.split(";").filter(Boolean)??[".EXE",".CMD",".BAT"]).map(a=>a.toLowerCase()):[""];for(let a of b)for(let b of c){let c=(0,g.join)(a,`gh${b}`);try{return await (0,bU.access)(c,e.constants.X_OK),c}catch{}}throw Error("gh CLI not found outside ~/.ao/bin. Install gh or set GH_PATH to the real binary.")}let eE=m.GH_TRACE_FILE;function eF(a){if(!a)return;let b=a.trim();if(!b)return;let c=Number.parseInt(b,10);return Number.isFinite(c)?c:void 0}let eG=new Set,eH=new Set;async function eI(a){let b=o(eE);if(!b)return;let c=(0,g.dirname)(b),d=`${JSON.stringify(a)}
942
+ `;try{eG.has(c)||(await (0,bU.mkdir)(c,{recursive:!0}),eG.add(c)),await (0,bU.appendFile)(b,d,"utf-8")}catch(a){if(!eH.has(b)){eH.add(b);let c=a instanceof Error?a.message:String(a);console.warn(`[gh-trace] Failed to write trace to ${b}: ${c}`)}}}function eJ(a,b,c,d){let{statusLine:e,headers:f}=function(a){let b={},c=a.replace(/\r/g,"").split("\n"),d=-1;for(let a=c.length-1;a>=0;a--)if(c[a]?.startsWith("HTTP/")){d=a;break}if(-1===d)return{headers:b};let e=c[d];for(let a=d+1;a<c.length;a++){let d=c[a];if(!d)break;let e=d.indexOf(":");if(-1===e)continue;let f=d.slice(0,e).trim().toLowerCase(),g=d.slice(e+1).trim();b[f]=g}return{statusLine:e,headers:b}}(c.stdout??""),g=e?Number.parseInt(e.replace(/^HTTP\/[0-9.]+\s+/,"").split(" ")[0]??"",10):void 0;return{timestamp:new Date().toISOString(),component:b.component,operation:b.operation??function(a){if(0===a.length)return"gh";if(1===a.length)return`gh.${a[0]}`;for(let b=1;b<a.length;b++){let c=a[b];if(!c||c.startsWith("-")){("--method"===c||"-X"===c||"-H"===c||"--header"===c||"-f"===c||"--raw-field"===c||"-F"===c||"--field"===c||"--input"===c||"-t"===c||"--template"===c)&&b++;continue}let d=c.split("/")[0].split("?")[0];return`gh.${a[0]}.${d}`}return`gh.${a[0]}`}(a),projectId:b.projectId,sessionId:b.sessionId,cwd:b.cwd,args:function(a){let b=new Set(["-H","--header"]),c=["token=","password=","secret=","authorization="];return a.map((d,e)=>{let f=e>0?a[e-1]:void 0;if(f&&b.has(f)&&/^authorization:/i.test(d))return"Authorization: [REDACTED]";if(/^-H/i.test(d)&&/authorization:/i.test(d))return"-HAuthorization: [REDACTED]";for(let a of c)if(d.toLowerCase().startsWith(a))return`${d.slice(0,a.length)}[REDACTED]`;if(f&&("-f"===f||"--raw-field"===f||"-F"===f||"--field"===f)){for(let a of c)if(d.toLowerCase().startsWith(a))return`${d.slice(0,a.length)}[REDACTED]`}return d})}(a),endpoint:function(a){if("api"===a[0])for(let b=1;b<a.length;b++){let c=a[b];if(c){if("--method"===c||"-X"===c||"-H"===c||"--header"===c||"-f"===c||"--raw-field"===c||"-F"===c||"--field"===c||"--input"===c){b++;continue}if(!c.startsWith("-"))return c}}}(a),method:function(a){for(let b=0;b<a.length;b++)if("--method"===a[b]||"-X"===a[b])return a[b+1];return"api"===a[0]?"GET":void 0}(a),ok:c.ok,exitCode:c.exitCode,signal:c.signal,durationMs:d,stdoutBytes:Buffer.byteLength(c.stdout??"","utf-8"),stderrBytes:Buffer.byteLength(c.stderr??"","utf-8"),statusLine:e,httpStatus:Number.isFinite(g)?g:void 0,etag:f.etag,rateLimitLimit:eF(f["x-ratelimit-limit"]),rateLimitRemaining:eF(f["x-ratelimit-remaining"]),rateLimitReset:eF(f["x-ratelimit-reset"]),rateLimitResource:f["x-ratelimit-resource"],...function(a,b){if(!b.includes("graphql")||!a.includes('"rateLimit"'))return{};let c=a.match(/\r?\n\r?\n([\s\S]*)$/),d=c?c[1]:a;try{let a=JSON.parse(d.trim()),b=a?.data?.rateLimit;if(!b)return{};return{graphqlCost:"number"==typeof b.cost?b.cost:void 0,graphqlRemaining:"number"==typeof b.remaining?b.remaining:void 0,graphqlResetAt:"string"==typeof b.resetAt?b.resetAt:void 0}}catch{return{}}}(c.stdout??"",a)}}async function eK(a,b,c=3e4){let d=Date.now();try{let e=await eC(),{stdout:f,stderr:g}=await eA(e,a,{...b.cwd?{cwd:b.cwd}:{},maxBuffer:0xa00000,timeout:c}),h=eJ(a,b,{ok:!0,stdout:f,stderr:g},Date.now()-d);return await eI(h),f.trim()}catch(e){let c=eJ(a,b,{ok:!1,stdout:"string"==typeof e.stdout?e.stdout:"",stderr:"string"==typeof e.stderr?e.stderr:"",exitCode:"number"==typeof e.exitCode?e.exitCode:"number"==typeof e.code?e.code:void 0,signal:"string"==typeof e.signal?e.signal:void 0},Date.now()-d);throw await eI(c),e}}let eL={BUG_REPORT:"bug_report",IMPROVEMENT_SUGGESTION:"improvement_suggestion"},eM=k.Yj().transform(a=>a.trim().replace(/\s+/g," ")).pipe(k.Yj().min(1));function eN(a,b,c){if("nightly"===c){let c=eP(a),d=eP(b);if(eO(c.prerelease)&&eO(d.prerelease))return a!==b}return function(a,b){let c=eP(a),d=eP(b);for(let a=0;a<3;a++){let b=c.parts[a]??0,e=d.parts[a]??0;if(Number.isNaN(b)||Number.isNaN(e))return!1;if(b<e)return!0;if(b>e)return!1}return(!!c.prerelease||!!d.prerelease)&&(!!c.prerelease&&!d.prerelease||(!!c.prerelease||!d.prerelease)&&0>function(a,b){let c=a.split("."),d=b.split("."),e=Math.max(c.length,d.length);for(let a=0;a<e;a++){let b=c[a],e=d[a];if(void 0===b)return -1;if(void 0===e)return 1;let f=/^\d+$/.test(b),g=/^\d+$/.test(e);if(f&&g){let a=Number(b),c=Number(e);if(a!==c)return a<c?-1:1}else if(f!==g)return f?-1:1;else if(b!==e)return -1}return 0}(c.prerelease??"",d.prerelease??""))}(a,b)}function eO(a){return"nightly"===a||a?.startsWith("nightly-")===!0||a?.startsWith("nightly.")===!0}function eP(a){let[b,...c]=a.split("-"),d=c.length>0?c.join("-"):void 0;return{parts:(b??"").split(".").map(Number),prerelease:d}}function eQ(){let a=function(){let a=process.env.XDG_CACHE_HOME||(0,g.join)((0,h.homedir)(),".cache");return(0,g.join)(a,"ao","update-check.json")}();if(!(0,e.existsSync)(a))return null;try{let b=(0,e.readFileSync)(a,"utf-8");return JSON.parse(b)}catch{return null}}function eR(){let a=(0,T.createRequire)((0,a3.fileURLToPath)("file:///home/runner/work/Athene/Athene/packages/core/dist/update-cache.js"));for(let b of["@made-by-moonlight/athene/package.json","@made-by-moonlight/athene-cli/package.json","@made-by-moonlight/athene-web/package.json"])try{let c=a(b);if("string"==typeof c.version&&"0.0.0"!==c.version)return c.version}catch{}return"0.0.0"}function eS(a){let b=am();if(!b?.projects[a])return;let{[a]:c,...d}=b.projects;if(b.projects=d,b.projectOrder){let c=b.projectOrder.filter(b=>b!==a);b.projectOrder=c.length>0?c:void 0}an(b)}function eT(){return(0,g.join)((0,h.homedir)(),".agent-orchestrator","windows-pty-hosts.json")}function eU(){let a=eT();if(!(0,e.existsSync)(a))return[];try{let b=JSON.parse((0,e.readFileSync)(a,"utf-8"));if(!Array.isArray(b))return[];return b.filter(a=>"object"==typeof a&&null!==a&&"string"==typeof a.sessionId&&"number"==typeof a.ptyHostPid&&"string"==typeof a.pipePath)}catch{return[]}}function eV(a){let b=eT();if(0===a.length){try{(0,e.unlinkSync)(b)}catch{}return}N(b,JSON.stringify(a,null,2))}function eW(a){let b=eU().filter(b=>b.sessionId!==a.sessionId);b.push({...a,registeredAt:new Date().toISOString()}),eV(b)}function eX(a){let b=eU(),c=b.filter(b=>b.sessionId!==a);c.length!==b.length&&eV(c)}function eY(){let a=eU(),b=a.filter(a=>(function(a){try{return process.kill(a,0),!0}catch(a){return"EPERM"===a.code}})(a.ptyHostPid));return b.length!==a.length&&eV(b),b}k.Ik({title:eM,body:eM,evidence:k.YO(eM).min(1),session:eM,source:eM,confidence:k.ai().finite().min(0).max(1)}).strict(),eL.BUG_REPORT,eL.IMPROVEMENT_SUGGESTION,k.Yj().regex(/^report_[A-Za-z0-9_-]+$/),k.Yj().datetime({offset:!0}),k.Yj().regex(/^[a-f0-9]{16}$/),(0,E.promisify)(D.execFile),new WeakSet},15407:(a,b,c)=>{"use strict";c.d(b,{Ag:()=>y,CK:()=>x,CM:()=>h,D8:()=>w,DD:()=>t,Fx:()=>v,Hk:()=>p,N_:()=>j,PE:()=>e,SB:()=>g,U1:()=>s,V1:()=>f,XG:()=>o,b8:()=>u,bz:()=>r,c5:()=>A,fg:()=>n,kw:()=>z,qX:()=>l,tT:()=>m,u3:()=>d,xn:()=>q,zi:()=>k});let d={ACTIVE:"active",READY:"ready",IDLE:"idle",WAITING_INPUT:"waiting_input",BLOCKED:"blocked",EXITED:"exited"},e=3e5,f=3e4,g={SPAWNING:"spawning",WORKING:"working",DETECTING:"detecting",PR_OPEN:"pr_open",CI_FAILED:"ci_failed",REVIEW_PENDING:"review_pending",CHANGES_REQUESTED:"changes_requested",APPROVED:"approved",MERGEABLE:"mergeable",MERGED:"merged",CLEANUP:"cleanup",NEEDS_INPUT:"needs_input",STUCK:"stuck",ERRORED:"errored",IDLE:"idle",KILLED:"killed",DONE:"done",TERMINATED:"terminated"},h=new Set(["killed","terminated","done","cleanup","errored","merged"]),i=new Set(["exited"]),j=new Set([]);function k(a){return a.lifecycle?"done"===a.lifecycle.session.state||"terminated"===a.lifecycle.session.state||"merged"===a.lifecycle.pr.state||"missing"===a.lifecycle.runtime.state||"exited"===a.lifecycle.runtime.state:h.has(a.status)||null!==a.activity&&i.has(a.activity)}function l(a){return a.lifecycle,k(a)&&!j.has(a.status)}function m(a,b,c){if(a.metadata?.role==="orchestrator")return!0;if(!b)return!1;let d=b.replace(/[.*+?^${}()|[\]\\]/g,"\\$&");if(a.id===`${b}-orchestrator`)return!0;if(!RegExp(`^${d}-orchestrator-\\d+$`).test(a.id))return!1;if(c){for(let d of c)if(d!==b&&RegExp(`^${d.replace(/[.*+?^${}()|[\]\\]/g,"\\$&")}-\\d+$`).test(a.id))return!1}return!0}function n(a,b,c){return a.metadata?.role==="meta-orchestrator"||m(a,b,c)}function o(a){return a.metadata?.metaOwner??null}let p="indeterminate";function q(a){return a===p}let r={OPEN:"open",MERGED:"merged",CLOSED:"closed"},s={PENDING:"pending",PASSING:"passing",FAILING:"failing",NONE:"none"};function t(a){if(a)return"permissionless"!==a&&"default"!==a&&"auto-edit"!==a&&"suggest"!==a?"skip"===a?"permissionless":void 0:a}function u(a){return"function"==typeof a.remap}function v(a){if(!a||"object"!=typeof a)return!1;let b=a.message?.toLowerCase()||"";return b.includes("issue")&&(b.includes("not found")||b.includes("does not exist"))||b.includes("no issue found")||b.includes("could not find issue")||b.includes("could not resolve to an issue")||b.includes("no issue with identifier")||b.includes("invalid issue format")}class w extends Error{constructor(a,b){super(`Session ${a} cannot be restored: ${b}`),this.sessionId=a,this.reason=b,this.name="SessionNotRestorableError"}}class x extends Error{constructor(a,b){super(`Workspace missing at ${a}${b?`: ${b}`:""}`),this.path=a,this.detail=b,this.name="WorkspaceMissingError"}}class y extends Error{constructor(a){super(`Session not found: ${a}`),this.sessionId=a,this.name="SessionNotFoundError"}}class z extends Error{constructor(a){super(a??"No agent-orchestrator.yaml found. Run `athene start` to create one."),this.name="ConfigNotFoundError"}}class A extends Error{constructor(a,b,c){super(b),this.projectId=a,this.reasonKind=c,this.name="ProjectResolveError"}}},26785:()=>{},90337:()=>{}};