@pasko70/pibo 1.0.5 → 1.2.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 (429) hide show
  1. package/README.md +106 -250
  2. package/context/codex-base-prompt.md +4 -0
  3. package/context/compute-worker.md +23 -0
  4. package/context/pibo-native-tooling.md +18 -0
  5. package/context/pibo-system-prompt.md +69 -8
  6. package/dist/api/simple-agent-api.js +136 -0
  7. package/dist/app-context.js +4 -0
  8. package/dist/apps/chat/agent-profiles.js +42 -5
  9. package/dist/apps/chat/agent-store.js +113 -16
  10. package/dist/apps/chat/chat-api-routes.js +311 -0
  11. package/dist/apps/chat/chat-capability-routes.js +90 -0
  12. package/dist/apps/chat/chat-files.js +178 -0
  13. package/dist/apps/chat/chat-request-normalizers.js +681 -0
  14. package/dist/apps/chat/chat-settings-routes.js +75 -0
  15. package/dist/apps/chat/chat-trace-helpers.js +94 -0
  16. package/dist/apps/chat/chat-user-skill-routes.js +149 -0
  17. package/dist/apps/chat/cron-api.js +213 -0
  18. package/dist/apps/chat/data/chat-data-mappers.js +74 -0
  19. package/dist/apps/chat/data/event-command-service.js +75 -0
  20. package/dist/apps/chat/data/navigation-query-service.js +11 -0
  21. package/dist/apps/chat/data/project-service.js +844 -0
  22. package/dist/apps/chat/data/read-state-service.js +42 -0
  23. package/dist/apps/chat/data/room-service.js +52 -0
  24. package/dist/apps/chat/data/session-query-service.js +63 -0
  25. package/dist/apps/chat/data/timeline-query-service.js +96 -0
  26. package/dist/apps/chat/event-log.js +1 -307
  27. package/dist/apps/chat/model-catalog.js +47 -0
  28. package/dist/apps/chat/output-compactor.js +126 -0
  29. package/dist/apps/chat/output-event-policy.js +17 -0
  30. package/dist/apps/chat/project-workflow-human-actions.js +347 -0
  31. package/dist/apps/chat/project-workflow-sessions.js +260 -0
  32. package/dist/apps/chat/provider-auth-actions.js +43 -0
  33. package/dist/apps/chat/ralph-api.js +156 -0
  34. package/dist/apps/chat/read-model.js +1 -218
  35. package/dist/apps/chat/rooms.js +1 -321
  36. package/dist/apps/chat/static-assets.js +996 -0
  37. package/dist/apps/chat/stream.js +29 -6
  38. package/dist/apps/chat/trace.js +179 -1003
  39. package/dist/apps/chat/types/event-store.js +1 -0
  40. package/dist/apps/chat/types/read-model.js +1 -0
  41. package/dist/apps/chat/types/rooms.js +36 -0
  42. package/dist/apps/chat/web-app.js +3168 -1811
  43. package/dist/apps/chat/workflow-catalog.js +572 -0
  44. package/dist/apps/chat/workflow-edge-compatibility.js +51 -0
  45. package/dist/apps/chat/workflow-json-schema-validation.js +335 -0
  46. package/dist/apps/chat/workflow-persistence-model.js +140 -0
  47. package/dist/apps/chat/workflow-persistence.js +633 -0
  48. package/dist/apps/chat/workflow-registered-ref-params.js +130 -0
  49. package/dist/apps/chat/workflow-registered-ref-pickers.js +179 -0
  50. package/dist/apps/chat/workflow-registered-ref-validation.js +210 -0
  51. package/dist/apps/chat/workflow-v2-security-validation.js +93 -0
  52. package/dist/apps/chat/workflow-validation-helpers.js +114 -0
  53. package/dist/apps/chat-ui/assets/{dist-CI0Xj2Cp.js → dist-B4lw9z4F.js} +1 -1
  54. package/dist/apps/chat-ui/assets/{dist-aMr2VYOu.js → dist-BbTaHWON.js} +1 -1
  55. package/dist/apps/chat-ui/assets/{dist-u2OzzOTm.js → dist-BcT_c1EJ.js} +1 -1
  56. package/dist/apps/chat-ui/assets/{dist-Di1ScJ22.js → dist-CGINd7XU.js} +1 -1
  57. package/dist/apps/chat-ui/assets/{dist-wiRpAHIv.js → dist-CrBzZkUp.js} +1 -1
  58. package/dist/apps/chat-ui/assets/{dist-CaNOvqMY.js → dist-CyyISotB.js} +1 -1
  59. package/dist/apps/chat-ui/assets/{dist-zgYUl2B-.js → dist-DFbnFNpX.js} +1 -1
  60. package/dist/apps/chat-ui/assets/{dist-CNlhGq5i.js → dist-DGLWQLX8.js} +1 -1
  61. package/dist/apps/chat-ui/assets/{dist-BGxHKHPX.js → dist-DfcIkFSN.js} +1 -1
  62. package/dist/apps/chat-ui/assets/{dist-DrM-H3e1.js → dist-sKDHTwaT.js} +1 -1
  63. package/dist/apps/chat-ui/assets/{dist-DpmEro5R.js → dist-y9D6la48.js} +1 -1
  64. package/dist/apps/chat-ui/assets/index-C25VYnyb.css +1 -0
  65. package/dist/apps/chat-ui/assets/index-CUkuvI3v.js +165 -0
  66. package/dist/apps/chat-ui/assets/pwa-images/android/launchericon-144x144.png +0 -0
  67. package/dist/apps/chat-ui/assets/pwa-images/android/launchericon-192x192.png +0 -0
  68. package/dist/apps/chat-ui/assets/pwa-images/android/launchericon-48x48.png +0 -0
  69. package/dist/apps/chat-ui/assets/pwa-images/android/launchericon-512x512.png +0 -0
  70. package/dist/apps/chat-ui/assets/pwa-images/android/launchericon-72x72.png +0 -0
  71. package/dist/apps/chat-ui/assets/pwa-images/android/launchericon-96x96.png +0 -0
  72. package/dist/apps/chat-ui/assets/pwa-images/ios/100.png +0 -0
  73. package/dist/apps/chat-ui/assets/pwa-images/ios/1024.png +0 -0
  74. package/dist/apps/chat-ui/assets/pwa-images/ios/114.png +0 -0
  75. package/dist/apps/chat-ui/assets/pwa-images/ios/120.png +0 -0
  76. package/dist/apps/chat-ui/assets/pwa-images/ios/128.png +0 -0
  77. package/dist/apps/chat-ui/assets/pwa-images/ios/144.png +0 -0
  78. package/dist/apps/chat-ui/assets/pwa-images/ios/152.png +0 -0
  79. package/dist/apps/chat-ui/assets/pwa-images/ios/16.png +0 -0
  80. package/dist/apps/chat-ui/assets/pwa-images/ios/167.png +0 -0
  81. package/dist/apps/chat-ui/assets/pwa-images/ios/180.png +0 -0
  82. package/dist/apps/chat-ui/assets/pwa-images/ios/192.png +0 -0
  83. package/dist/apps/chat-ui/assets/pwa-images/ios/20.png +0 -0
  84. package/dist/apps/chat-ui/assets/pwa-images/ios/256.png +0 -0
  85. package/dist/apps/chat-ui/assets/pwa-images/ios/29.png +0 -0
  86. package/dist/apps/chat-ui/assets/pwa-images/ios/32.png +0 -0
  87. package/dist/apps/chat-ui/assets/pwa-images/ios/40.png +0 -0
  88. package/dist/apps/chat-ui/assets/pwa-images/ios/50.png +0 -0
  89. package/dist/apps/chat-ui/assets/pwa-images/ios/512.png +0 -0
  90. package/dist/apps/chat-ui/assets/pwa-images/ios/57.png +0 -0
  91. package/dist/apps/chat-ui/assets/pwa-images/ios/58.png +0 -0
  92. package/dist/apps/chat-ui/assets/pwa-images/ios/60.png +0 -0
  93. package/dist/apps/chat-ui/assets/pwa-images/ios/64.png +0 -0
  94. package/dist/apps/chat-ui/assets/pwa-images/ios/72.png +0 -0
  95. package/dist/apps/chat-ui/assets/pwa-images/ios/76.png +0 -0
  96. package/dist/apps/chat-ui/assets/pwa-images/ios/80.png +0 -0
  97. package/dist/apps/chat-ui/assets/pwa-images/ios/87.png +0 -0
  98. package/dist/apps/chat-ui/assets/pwa-images/windows/LargeTile.scale-100.png +0 -0
  99. package/dist/apps/chat-ui/assets/pwa-images/windows/LargeTile.scale-125.png +0 -0
  100. package/dist/apps/chat-ui/assets/pwa-images/windows/LargeTile.scale-150.png +0 -0
  101. package/dist/apps/chat-ui/assets/pwa-images/windows/LargeTile.scale-200.png +0 -0
  102. package/dist/apps/chat-ui/assets/pwa-images/windows/LargeTile.scale-400.png +0 -0
  103. package/dist/apps/chat-ui/assets/pwa-images/windows/SmallTile.scale-100.png +0 -0
  104. package/dist/apps/chat-ui/assets/pwa-images/windows/SmallTile.scale-125.png +0 -0
  105. package/dist/apps/chat-ui/assets/pwa-images/windows/SmallTile.scale-150.png +0 -0
  106. package/dist/apps/chat-ui/assets/pwa-images/windows/SmallTile.scale-200.png +0 -0
  107. package/dist/apps/chat-ui/assets/pwa-images/windows/SmallTile.scale-400.png +0 -0
  108. package/dist/apps/chat-ui/assets/pwa-images/windows/SplashScreen.scale-100.png +0 -0
  109. package/dist/apps/chat-ui/assets/pwa-images/windows/SplashScreen.scale-125.png +0 -0
  110. package/dist/apps/chat-ui/assets/pwa-images/windows/SplashScreen.scale-150.png +0 -0
  111. package/dist/apps/chat-ui/assets/pwa-images/windows/SplashScreen.scale-200.png +0 -0
  112. package/dist/apps/chat-ui/assets/pwa-images/windows/SplashScreen.scale-400.png +0 -0
  113. package/dist/apps/chat-ui/assets/pwa-images/windows/Square150x150Logo.scale-100.png +0 -0
  114. package/dist/apps/chat-ui/assets/pwa-images/windows/Square150x150Logo.scale-125.png +0 -0
  115. package/dist/apps/chat-ui/assets/pwa-images/windows/Square150x150Logo.scale-150.png +0 -0
  116. package/dist/apps/chat-ui/assets/pwa-images/windows/Square150x150Logo.scale-200.png +0 -0
  117. package/dist/apps/chat-ui/assets/pwa-images/windows/Square150x150Logo.scale-400.png +0 -0
  118. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-16.png +0 -0
  119. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-20.png +0 -0
  120. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-24.png +0 -0
  121. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-256.png +0 -0
  122. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-30.png +0 -0
  123. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-32.png +0 -0
  124. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-36.png +0 -0
  125. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-40.png +0 -0
  126. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-44.png +0 -0
  127. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-48.png +0 -0
  128. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-60.png +0 -0
  129. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-64.png +0 -0
  130. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-72.png +0 -0
  131. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-80.png +0 -0
  132. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-lightunplated_targetsize-96.png +0 -0
  133. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-16.png +0 -0
  134. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-20.png +0 -0
  135. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-24.png +0 -0
  136. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-256.png +0 -0
  137. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-30.png +0 -0
  138. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-32.png +0 -0
  139. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-36.png +0 -0
  140. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-40.png +0 -0
  141. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-44.png +0 -0
  142. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-48.png +0 -0
  143. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-60.png +0 -0
  144. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-64.png +0 -0
  145. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-72.png +0 -0
  146. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-80.png +0 -0
  147. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.altform-unplated_targetsize-96.png +0 -0
  148. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.scale-100.png +0 -0
  149. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.scale-125.png +0 -0
  150. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.scale-150.png +0 -0
  151. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.scale-200.png +0 -0
  152. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.scale-400.png +0 -0
  153. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-16.png +0 -0
  154. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-20.png +0 -0
  155. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-24.png +0 -0
  156. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-256.png +0 -0
  157. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-30.png +0 -0
  158. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-32.png +0 -0
  159. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-36.png +0 -0
  160. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-40.png +0 -0
  161. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-44.png +0 -0
  162. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-48.png +0 -0
  163. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-60.png +0 -0
  164. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-64.png +0 -0
  165. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-72.png +0 -0
  166. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-80.png +0 -0
  167. package/dist/apps/chat-ui/assets/pwa-images/windows/Square44x44Logo.targetsize-96.png +0 -0
  168. package/dist/apps/chat-ui/assets/pwa-images/windows/StoreLogo.scale-100.png +0 -0
  169. package/dist/apps/chat-ui/assets/pwa-images/windows/StoreLogo.scale-125.png +0 -0
  170. package/dist/apps/chat-ui/assets/pwa-images/windows/StoreLogo.scale-150.png +0 -0
  171. package/dist/apps/chat-ui/assets/pwa-images/windows/StoreLogo.scale-200.png +0 -0
  172. package/dist/apps/chat-ui/assets/pwa-images/windows/StoreLogo.scale-400.png +0 -0
  173. package/dist/apps/chat-ui/assets/pwa-images/windows/Wide310x150Logo.scale-100.png +0 -0
  174. package/dist/apps/chat-ui/assets/pwa-images/windows/Wide310x150Logo.scale-125.png +0 -0
  175. package/dist/apps/chat-ui/assets/pwa-images/windows/Wide310x150Logo.scale-150.png +0 -0
  176. package/dist/apps/chat-ui/assets/pwa-images/windows/Wide310x150Logo.scale-200.png +0 -0
  177. package/dist/apps/chat-ui/assets/pwa-images/windows/Wide310x150Logo.scale-400.png +0 -0
  178. package/dist/apps/chat-ui/index.html +8 -3
  179. package/dist/apps/chat-ui/manifest.webmanifest +25 -0
  180. package/dist/apps/chat-ui/sw.js +41 -0
  181. package/dist/apps/cli-ui/InkSessionApp.js +1218 -0
  182. package/dist/apps/cli-ui/InkTerminalLine.js +53 -0
  183. package/dist/apps/cli-ui/InkTerminalRow.js +304 -0
  184. package/dist/apps/cli-ui/InkTerminalView.js +25 -0
  185. package/dist/apps/cli-ui/cliSessionsCommand.js +232 -0
  186. package/dist/apps/cli-ui/index.js +8 -0
  187. package/dist/apps/cli-ui/inkColors.js +67 -0
  188. package/dist/apps/cli-ui/inkJson.js +244 -0
  189. package/dist/apps/cli-ui/inkMarkdown.js +122 -0
  190. package/dist/apps/context-files-ui/assets/{dist-DFi2YGux.js → dist-BOiGdrG-.js} +1 -1
  191. package/dist/apps/context-files-ui/assets/{dist-DyfSeBMu.js → dist-DK01b7x4.js} +1 -1
  192. package/dist/apps/context-files-ui/assets/{dist-CwbH_3RN.js → dist-DPG9jOQ-.js} +1 -1
  193. package/dist/apps/context-files-ui/assets/{dist-dTBsFYAl.js → dist-Dp5AH00p.js} +1 -1
  194. package/dist/apps/context-files-ui/assets/{dist-CxRLRmMx.js → dist-DqYw0LH7.js} +1 -1
  195. package/dist/apps/context-files-ui/assets/{dist-MyZgX9K2.js → dist-TF5iO5ML.js} +1 -1
  196. package/dist/apps/context-files-ui/assets/{dist-DQXzt2Ng.js → dist-TbjAhles.js} +1 -1
  197. package/dist/apps/context-files-ui/assets/{dist-YwR9dpb-.js → dist-ZsBbt0uY.js} +1 -1
  198. package/dist/apps/context-files-ui/assets/{dist-CKQF1zEu.js → dist-kmsvtHkH.js} +1 -1
  199. package/dist/apps/context-files-ui/assets/{dist-BJW3917N.js → dist-vnd7PMu3.js} +1 -1
  200. package/dist/apps/context-files-ui/assets/{index-BwRDoHMC.css → index-B92tL3Pp.css} +1 -1
  201. package/dist/apps/context-files-ui/assets/{index-GwvjXytt.js → index-BhAWD3dv.js} +2 -2
  202. package/dist/apps/context-files-ui/index.html +2 -2
  203. package/dist/auth/better-auth.js +2 -1
  204. package/dist/auth/login-actions.js +251 -0
  205. package/dist/auth/openai-codex-usage.js +147 -0
  206. package/dist/bin/pibo.js +0 -0
  207. package/dist/bin/rg.js +15 -0
  208. package/dist/cli-session/fakeSessionSource.js +804 -0
  209. package/dist/cli-session/index.js +3 -0
  210. package/dist/cli-session/localSessionSource.js +1144 -0
  211. package/dist/cli-session/sessionSource.js +13 -0
  212. package/dist/cli.js +142 -14
  213. package/dist/compute/cli.js +415 -0
  214. package/dist/compute/docker.js +827 -0
  215. package/dist/compute/resource-health.js +333 -0
  216. package/dist/compute/resource-policy.js +98 -0
  217. package/dist/config/config.js +9 -5
  218. package/dist/core/context-build.js +677 -0
  219. package/dist/core/model-defaults.js +51 -9
  220. package/dist/core/pibo-home.js +8 -0
  221. package/dist/core/profiles.js +48 -0
  222. package/dist/core/provider-telemetry.js +222 -0
  223. package/dist/core/routed-session.js +441 -47
  224. package/dist/core/runtime-telemetry.js +853 -0
  225. package/dist/core/runtime.js +103 -15
  226. package/dist/core/session-errors.js +47 -0
  227. package/dist/core/session-model.js +39 -0
  228. package/dist/core/session-router.js +292 -62
  229. package/dist/core/shared-app.js +17 -0
  230. package/dist/core/skill-expansion.js +43 -0
  231. package/dist/core/system-prompt-template.js +9 -9
  232. package/dist/core/telemetry-staleness.js +128 -0
  233. package/dist/core/test-output-compaction.js +145 -0
  234. package/dist/core/user-settings.js +73 -0
  235. package/dist/cron/channel.js +28 -0
  236. package/dist/cron/cli.js +230 -0
  237. package/dist/cron/plugin.js +11 -0
  238. package/dist/cron/schedule.js +214 -0
  239. package/dist/cron/service.js +177 -0
  240. package/dist/cron/store.js +349 -0
  241. package/dist/cron/types.js +1 -0
  242. package/dist/data/cli.js +184 -0
  243. package/dist/data/event-log.js +106 -0
  244. package/dist/data/final-app-space-cutover-migration.js +728 -0
  245. package/dist/data/ingest-service.js +389 -0
  246. package/dist/data/message-store.js +62 -0
  247. package/dist/data/navigation-store.js +75 -0
  248. package/dist/data/observation-store.js +46 -0
  249. package/dist/data/payload-store.js +144 -0
  250. package/dist/data/pibo-store.js +59 -0
  251. package/dist/data/schema.js +434 -0
  252. package/dist/data/session-store.js +63 -0
  253. package/dist/data/shared-app-migration.js +757 -0
  254. package/dist/data/sqlite-schema.js +12 -0
  255. package/dist/data/telemetry-preview.js +65 -0
  256. package/dist/data/telemetry-queries.js +212 -0
  257. package/dist/data/telemetry-retention.js +50 -0
  258. package/dist/data/telemetry-rows.js +158 -0
  259. package/dist/data/telemetry.js +357 -0
  260. package/dist/debug/delta-compaction.js +99 -0
  261. package/dist/debug/detail-format.js +86 -0
  262. package/dist/debug/events.js +149 -29
  263. package/dist/debug/failures.js +162 -0
  264. package/dist/debug/index.js +655 -30
  265. package/dist/debug/messages.js +185 -0
  266. package/dist/debug/next-commands.js +6 -0
  267. package/dist/debug/payloads.js +123 -0
  268. package/dist/debug/pty.js +924 -0
  269. package/dist/debug/session.js +45 -15
  270. package/dist/debug/sql.js +1 -1
  271. package/dist/debug/stores.js +18 -13
  272. package/dist/debug/summary.js +72 -0
  273. package/dist/debug/telemetry.js +649 -0
  274. package/dist/debug/tools.js +168 -0
  275. package/dist/debug/trace-render-check.js +151 -0
  276. package/dist/debug/trace.js +152 -27
  277. package/dist/debug/web-artifacts.js +63 -0
  278. package/dist/debug/web-options.js +313 -0
  279. package/dist/debug/web-render-analysis.js +310 -0
  280. package/dist/debug/web-snapshot-browser-scripts.js +303 -0
  281. package/dist/debug/web-streaming-benchmark-analysis.js +605 -0
  282. package/dist/debug/web-streaming-browser-library.js +928 -0
  283. package/dist/debug/web-streaming-browser-scripts.js +242 -0
  284. package/dist/debug/web-streaming-provider-telemetry.js +194 -0
  285. package/dist/debug/web-streaming-report.js +493 -0
  286. package/dist/debug/web-streaming-types.js +1 -0
  287. package/dist/debug/web.js +574 -0
  288. package/dist/gateway/backup.js +83 -0
  289. package/dist/gateway/cli.js +511 -0
  290. package/dist/gateway/fallback.js +155 -0
  291. package/dist/gateway/pidfile.js +84 -0
  292. package/dist/gateway/protocol.js +16 -0
  293. package/dist/gateway/server.js +174 -17
  294. package/dist/gateway/tool.js +54 -51
  295. package/dist/gateway/web.js +74 -2
  296. package/dist/index.js +3 -1
  297. package/dist/local/client.js +3 -3
  298. package/dist/local/extension.js +8 -5
  299. package/dist/plugins/builtin.js +252 -49
  300. package/dist/plugins/chat-vscode-web.js +28 -0
  301. package/dist/plugins/codex-compat.js +0 -41
  302. package/dist/plugins/context-files.js +98 -18
  303. package/dist/plugins/dev-auth.js +124 -0
  304. package/dist/plugins/native-tooling.js +15 -0
  305. package/dist/plugins/registry.js +66 -2
  306. package/dist/plugins/web-annotations.js +27 -0
  307. package/dist/providers/minimax.js +70 -0
  308. package/dist/providers/openai-compat.js +48 -0
  309. package/dist/ralph/channel.js +8 -0
  310. package/dist/ralph/cli.js +152 -0
  311. package/dist/ralph/plugin.js +14 -0
  312. package/dist/ralph/service.js +271 -0
  313. package/dist/ralph/stopping.js +151 -0
  314. package/dist/ralph/store.js +450 -0
  315. package/dist/ralph/templates.js +200 -0
  316. package/dist/ralph/types.js +1 -0
  317. package/dist/reliability/store.js +42 -26
  318. package/dist/runs/registry.js +72 -35
  319. package/dist/session-ui/commandCatalog.js +193 -0
  320. package/dist/session-ui/commandResults.js +95 -0
  321. package/dist/session-ui/index.js +7 -0
  322. package/dist/session-ui/ownerViewModel.js +27 -0
  323. package/dist/session-ui/roomSessionViewModel.js +69 -0
  324. package/dist/session-ui/statusViewModel.js +127 -0
  325. package/dist/session-ui/terminalCards.js +210 -0
  326. package/dist/session-ui/terminalRows.js +937 -0
  327. package/dist/session-ui/terminalValue.js +45 -0
  328. package/dist/sessions/pibo-data-store.js +178 -0
  329. package/dist/sessions/sqlite-store.js +78 -12
  330. package/dist/sessions/store.js +11 -4
  331. package/dist/sessions/workflow-session-kind.js +20 -0
  332. package/dist/setup/cli.js +567 -0
  333. package/dist/shared/trace-async-agent-runs.js +127 -0
  334. package/dist/shared/trace-engine.js +96 -0
  335. package/dist/shared/trace-event-projection.js +679 -0
  336. package/dist/shared/trace-live-reducer.js +191 -0
  337. package/dist/shared/trace-nodes.js +76 -0
  338. package/dist/shared/trace-order.js +11 -10
  339. package/dist/shared/trace-patch-nodes.js +83 -0
  340. package/dist/shared/trace-run-notifications.js +69 -0
  341. package/dist/shared/trace-subagent-links.js +46 -0
  342. package/dist/shared/trace-transcript.js +303 -0
  343. package/dist/shared/trace-types.js +1 -0
  344. package/dist/shared-app.js +4 -0
  345. package/dist/signals/aggregate.js +65 -0
  346. package/dist/signals/events.js +1 -0
  347. package/dist/signals/projector.js +158 -0
  348. package/dist/signals/registry.js +513 -0
  349. package/dist/signals/store.js +1 -0
  350. package/dist/signals/types.js +1 -0
  351. package/dist/skills/cli.js +117 -0
  352. package/dist/tools/agent-browser-leases.js +219 -0
  353. package/dist/tools/agent-browser-wrapper.js +99 -0
  354. package/dist/tools/browser-pool.js +623 -0
  355. package/dist/tools/browser-use-cdp.js +56 -4
  356. package/dist/tools/browser-use-leases.js +215 -37
  357. package/dist/tools/browser-use-wrapper.js +508 -65
  358. package/dist/tools/cdp-client.js +189 -0
  359. package/dist/tools/guides.js +203 -4
  360. package/dist/tools/index.js +666 -16
  361. package/dist/tools/npm-runtime.js +136 -0
  362. package/dist/tools/registry.js +107 -8
  363. package/dist/tools/runtime/index.js +3 -0
  364. package/dist/tools/runtime/node-backend.js +225 -0
  365. package/dist/tools/runtime/node-worker-source.js +206 -0
  366. package/dist/tools/runtime/python-backend.js +227 -0
  367. package/dist/tools/runtime/python-worker-source.js +178 -0
  368. package/dist/tools/runtime/registry.js +255 -0
  369. package/dist/tools/runtime/tool.js +168 -0
  370. package/dist/tools/runtime/types.js +1 -0
  371. package/dist/tools/web-search.js +2 -1
  372. package/dist/user-skills/installer.js +214 -0
  373. package/dist/user-skills/manager.js +35 -0
  374. package/dist/user-skills/store.js +267 -0
  375. package/dist/user-skills/types.js +1 -0
  376. package/dist/web/auth.js +5 -1
  377. package/dist/web/channel.js +86 -0
  378. package/dist/web/http.js +79 -14
  379. package/dist/web-annotations/api.js +348 -0
  380. package/dist/web-annotations/attachments.js +201 -0
  381. package/dist/web-annotations/cdp.js +1107 -0
  382. package/dist/web-annotations/index.js +7 -0
  383. package/dist/web-annotations/store.js +407 -0
  384. package/dist/web-annotations/tools.js +350 -0
  385. package/dist/web-annotations/types.js +34 -0
  386. package/dist/web-annotations/validation.js +288 -0
  387. package/docs/README.md +23 -0
  388. package/docs/ops/install-developer-host.md +112 -0
  389. package/docs/ops/install-user-host.md +76 -0
  390. package/docs/ops/upgrade-user-to-developer-host.md +69 -0
  391. package/package.json +24 -10
  392. package/{.codex/skills → skills/builtin}/pi-agent-harness/SKILL.md +24 -24
  393. package/skills/builtin/pibo-docker-system/SKILL.md +170 -0
  394. package/skills/builtin/pibo-spec-writing/SKILL.md +330 -0
  395. package/skills/builtin/prd/SKILL.md +143 -0
  396. package/skills/builtin/ralph-loop/SKILL.md +359 -0
  397. package/skills/builtin/ralph-prd-json/SKILL.md +123 -0
  398. package/skills/builtin/skill-creator/LICENSE.txt +202 -0
  399. package/skills/builtin/skill-creator/SKILL.md +513 -0
  400. package/skills/builtin/skill-creator/agents/analyzer.md +274 -0
  401. package/skills/builtin/skill-creator/agents/comparator.md +202 -0
  402. package/skills/builtin/skill-creator/agents/grader.md +223 -0
  403. package/skills/builtin/skill-creator/assets/eval_review.html +146 -0
  404. package/skills/builtin/skill-creator/eval-viewer/generate_review.py +471 -0
  405. package/skills/builtin/skill-creator/eval-viewer/viewer.html +1325 -0
  406. package/skills/builtin/skill-creator/references/schemas.md +430 -0
  407. package/skills/builtin/skill-creator/scripts/__init__.py +0 -0
  408. package/skills/builtin/skill-creator/scripts/aggregate_benchmark.py +401 -0
  409. package/skills/builtin/skill-creator/scripts/generate_report.py +326 -0
  410. package/skills/builtin/skill-creator/scripts/improve_description.py +247 -0
  411. package/skills/builtin/skill-creator/scripts/package_skill.py +136 -0
  412. package/skills/builtin/skill-creator/scripts/quick_validate.py +103 -0
  413. package/skills/builtin/skill-creator/scripts/run_eval.py +310 -0
  414. package/skills/builtin/skill-creator/scripts/run_loop.py +328 -0
  415. package/skills/builtin/skill-creator/scripts/utils.py +47 -0
  416. package/skills/builtin/web-annotations/SKILL.md +93 -0
  417. package/dist/apps/chat-ui/assets/index-B_E935fP.js +0 -151
  418. package/dist/apps/chat-ui/assets/index-Dk-opWl3.css +0 -1
  419. package/dist/env.js +0 -32
  420. package/dist/plugins/core-tools.js +0 -94
  421. package/dist/plugins/example.js +0 -67
  422. package/dist/plugins/remote-agent.js +0 -9
  423. package/dist/remote/channel.js +0 -176
  424. package/dist/remote/client.js +0 -92
  425. package/dist/remote/examples/tui-controller.js +0 -263
  426. package/dist/remote/protocol.js +0 -55
  427. package/dist/remote/session-client.js +0 -189
  428. package/dist/sessions/bindings.js +0 -41
  429. /package/{.codex/skills → skills/builtin}/pi-agent-harness/agents/openai.yaml +0 -0
@@ -23,6 +23,7 @@ fresh_profile=0
23
23
  starts_browser=0
24
24
  show_help=0
25
25
  headed=0
26
+ pibo_ensure_chrome=0
26
27
  sanitized_args=
27
28
 
28
29
  append_arg() {
@@ -122,6 +123,218 @@ except Exception:
122
123
  PY
123
124
  }
124
125
 
126
+ find_chrome_pids_for_profile() {
127
+ user_data_dir=$1
128
+ "$python_cmd" - "$user_data_dir" <<'PYFINDCHROME'
129
+ import os
130
+ import shlex
131
+ import subprocess
132
+ import sys
133
+
134
+ managed_dir = os.path.normpath(os.path.abspath(sys.argv[1]))
135
+ browser_names = {"chrome", "google-chrome", "chromium", "chromium-browser"}
136
+
137
+ def normalize_path(value):
138
+ return os.path.normpath(os.path.abspath(value))
139
+
140
+ def has_managed_user_data_dir(args):
141
+ for index, arg in enumerate(args):
142
+ if arg.startswith("--user-data-dir="):
143
+ return normalize_path(arg.split("=", 1)[1]) == managed_dir
144
+ if arg == "--user-data-dir" and index + 1 < len(args):
145
+ return normalize_path(args[index + 1]) == managed_dir
146
+ return False
147
+
148
+ try:
149
+ output = subprocess.check_output(["ps", "-eo", "pid=,args="], text=True, stderr=subprocess.DEVNULL)
150
+ except Exception:
151
+ raise SystemExit(0)
152
+
153
+ for line in output.splitlines():
154
+ line = line.strip()
155
+ if not line:
156
+ continue
157
+ pid_text, _, command = line.partition(" ")
158
+ if not pid_text.isdigit() or not command:
159
+ continue
160
+ try:
161
+ args = shlex.split(command)
162
+ except ValueError:
163
+ continue
164
+ if not args:
165
+ continue
166
+ command_name = os.path.basename(args[0]).lower()
167
+ if command_name not in browser_names:
168
+ continue
169
+ if has_managed_user_data_dir(args):
170
+ print(pid_text)
171
+ PYFINDCHROME
172
+ }
173
+
174
+ find_recorded_browser_targets_for_profile() {
175
+ user_data_dir=$1
176
+ pid_file=$2
177
+ pool_state_file=$3
178
+ "$python_cmd" - "$user_data_dir" "$pid_file" "$pool_state_file" <<'PYRECORDED'
179
+ import json
180
+ import os
181
+ import sys
182
+ from pathlib import Path
183
+
184
+ managed_dir = os.path.normpath(os.path.abspath(sys.argv[1]))
185
+ pid_file = Path(sys.argv[2])
186
+ pool_state_file = Path(sys.argv[3])
187
+
188
+ def normalize_path(value):
189
+ return os.path.normpath(os.path.abspath(value))
190
+
191
+ def print_target(source, pid, pgid=""):
192
+ try:
193
+ pid_text = str(int(str(pid).strip()))
194
+ except Exception:
195
+ return
196
+ if int(pid_text) <= 0:
197
+ return
198
+ pgid_text = ""
199
+ if pgid not in (None, ""):
200
+ try:
201
+ pgid_text = str(int(str(pgid).strip()))
202
+ except Exception:
203
+ pgid_text = ""
204
+ print(f"{source}\t{pid_text}\t{pgid_text}")
205
+
206
+ try:
207
+ data = json.loads(pool_state_file.read_text())
208
+ if normalize_path(str(data.get("userDataDir", ""))) == managed_dir:
209
+ print_target("pool-state", data.get("pid"), data.get("processGroupId"))
210
+ except FileNotFoundError:
211
+ pass
212
+ except Exception:
213
+ pass
214
+
215
+ try:
216
+ print_target("cdp-pid-file", pid_file.read_text())
217
+ except FileNotFoundError:
218
+ pass
219
+ except Exception:
220
+ pass
221
+ PYRECORDED
222
+ }
223
+
224
+ process_group_for_pid() {
225
+ pid=$1
226
+ ps -o pgid= -p "$pid" 2>/dev/null | tr -d ' '
227
+ }
228
+
229
+ process_is_running() {
230
+ pid=$1
231
+ if ! kill -0 "$pid" 2>/dev/null; then
232
+ return 1
233
+ fi
234
+ state=$(ps -o stat= -p "$pid" 2>/dev/null | tr -d ' ' | cut -c1)
235
+ [ "$state" != "Z" ]
236
+ }
237
+
238
+ wait_for_pid_exit() {
239
+ pid=$1
240
+ attempts=0
241
+ while [ "$attempts" -lt "\${PIBO_BROWSER_POOL_TERM_WAIT_ATTEMPTS:-10}" ]; do
242
+ if ! process_is_running "$pid"; then
243
+ return 0
244
+ fi
245
+ attempts=$((attempts + 1))
246
+ sleep "\${PIBO_BROWSER_POOL_TERM_WAIT_SECONDS:-0.1}"
247
+ done
248
+ return 1
249
+ }
250
+
251
+ terminate_managed_browser_target() {
252
+ source=$1
253
+ pid=$2
254
+ recorded_pgid=$3
255
+ if [ -z "$pid" ] || ! process_is_running "$pid"; then
256
+ return 0
257
+ fi
258
+
259
+ actual_pgid=$(process_group_for_pid "$pid")
260
+ target_group=
261
+ if [ -n "$recorded_pgid" ] && [ "$actual_pgid" = "$recorded_pgid" ]; then
262
+ target_group=$recorded_pgid
263
+ elif [ -n "$actual_pgid" ] && [ "$actual_pgid" = "$pid" ]; then
264
+ target_group=$actual_pgid
265
+ fi
266
+
267
+ if [ -n "$target_group" ]; then
268
+ echo "pibo browser-use: terminating stale Chrome process group $target_group for managed profile ($source pid $pid)..." >&2
269
+ kill -TERM "-$target_group" 2>/dev/null || true
270
+ if ! wait_for_pid_exit "$pid"; then
271
+ kill -KILL "-$target_group" 2>/dev/null || true
272
+ wait_for_pid_exit "$pid" || true
273
+ fi
274
+ return 0
275
+ fi
276
+
277
+ echo "pibo browser-use: terminating stale Chrome process $pid for managed profile ($source)..." >&2
278
+ kill -TERM "$pid" 2>/dev/null || true
279
+ if ! wait_for_pid_exit "$pid"; then
280
+ kill -KILL "$pid" 2>/dev/null || true
281
+ wait_for_pid_exit "$pid" || true
282
+ fi
283
+ }
284
+
285
+ pid_file_process_is_dead() {
286
+ pid_file=$1
287
+ if [ ! -s "$pid_file" ]; then
288
+ return 0
289
+ fi
290
+ recorded_pid=$(cat "$pid_file" 2>/dev/null || true)
291
+ if [ -z "$recorded_pid" ]; then
292
+ return 0
293
+ fi
294
+ ! process_is_running "$recorded_pid"
295
+ }
296
+
297
+ kill_stale_chrome_for_profile() {
298
+ user_data_dir=$1
299
+ safe_session=$(printf '%s' "$session" | tr -c 'A-Za-z0-9_.-' '_')
300
+ state_dir=\${BROWSER_USE_HOME:-$HOME/.browser-use}/pibo-cdp
301
+ pid_file=$state_dir/$safe_session.pid
302
+ port_file=$state_dir/$safe_session.port
303
+ paths=$(browser_pool_paths)
304
+ pool_state_file=$(printf '%s\n' "$paths" | sed -n '1p')
305
+
306
+ # Prefer recorded pool/CDP pid metadata before falling back to exact profile matching.
307
+ recorded_targets=$(find_recorded_browser_targets_for_profile "$user_data_dir" "$pid_file" "$pool_state_file")
308
+ if [ -n "$recorded_targets" ]; then
309
+ while IFS='\t' read -r source recorded_pid recorded_pgid; do
310
+ terminate_managed_browser_target "$source" "$recorded_pid" "$recorded_pgid"
311
+ done <<EOFRECORDED
312
+ $recorded_targets
313
+ EOFRECORDED
314
+ fi
315
+
316
+ # Then terminate any Chrome/Chromium process using this exact managed profile directory.
317
+ stale_pids=$(find_chrome_pids_for_profile "$user_data_dir")
318
+ for stale_pid in $stale_pids; do
319
+ terminate_managed_browser_target "profile-match" "$stale_pid" ""
320
+ done
321
+
322
+ # Remove stale lock files if the managed browser is confirmed gone.
323
+ sleep 0.2
324
+ if [ -z "$(find_chrome_pids_for_profile "$user_data_dir")" ]; then
325
+ for stale_file in SingletonLock SingletonCookie SingletonSocket; do
326
+ if [ -f "$user_data_dir/$stale_file" ]; then
327
+ rm -f "$user_data_dir/$stale_file" 2>/dev/null || true
328
+ fi
329
+ done
330
+ fi
331
+
332
+ # Remove stale CDP pid/port files only after their recorded process is gone.
333
+ if pid_file_process_is_dead "$pid_file"; then
334
+ rm -f "$pid_file" "$port_file" 2>/dev/null || true
335
+ fi
336
+ }
337
+
125
338
  persistent_chrome_url_if_alive() {
126
339
  safe_session=$(printf '%s' "$session" | tr -c 'A-Za-z0-9_.-' '_')
127
340
  state_dir=\${BROWSER_USE_HOME:-$HOME/.browser-use}/pibo-cdp
@@ -135,12 +348,14 @@ persistent_chrome_url_if_alive() {
135
348
  printf 'http://127.0.0.1:%s\\n' "$chrome_port"
136
349
  return 0
137
350
  fi
351
+ # Clean up stale state files when process is dead or CDP unreachable
352
+ rm -f "$pid_file" "$port_file" 2>/dev/null || true
138
353
  fi
139
354
 
140
355
  return 1
141
356
  }
142
357
 
143
- ensure_persistent_chrome() {
358
+ start_persistent_chrome() {
144
359
  safe_session=$(printf '%s' "$session" | tr -c 'A-Za-z0-9_.-' '_')
145
360
  state_dir=\${BROWSER_USE_HOME:-$HOME/.browser-use}/pibo-cdp
146
361
  mkdir -p "$state_dir"
@@ -148,15 +363,10 @@ ensure_persistent_chrome() {
148
363
  port_file=$state_dir/$safe_session.port
149
364
  log_file=$state_dir/$safe_session.chrome.log
150
365
 
151
- if cdp_url=$(persistent_chrome_url_if_alive); then
152
- printf '%s\\n' "$cdp_url"
153
- return
154
- fi
155
-
156
366
  chrome_bin=$(find_chrome)
157
367
  if [ -z "$chrome_bin" ]; then
158
- echo "pibo browser-use: could not find Chrome; install Chrome or use $fresh_flag for Browser Use managed Chromium." >&2
159
- exit 1
368
+ echo "pibo browser-use: could not find Chrome; managed browser-pool acquire cannot start a browser. Install Chrome/Chromium or use $fresh_flag for Browser Use managed Chromium." >&2
369
+ return 1
160
370
  fi
161
371
 
162
372
  user_data_dir=\${PIBO_BROWSER_USE_CHROME_USER_DATA_DIR:-}
@@ -165,68 +375,279 @@ ensure_persistent_chrome() {
165
375
  fi
166
376
 
167
377
  mkdir -p "$user_data_dir"
168
- profile_directory=$(resolve_profile_directory "$user_data_dir" "$default_profile")
169
- chrome_port=$(find_free_port)
170
- headless_arg=
171
- if [ "$headed" -eq 0 ]; then
172
- headless_arg=--headless=new
173
- fi
174
- if command -v setsid >/dev/null 2>&1; then
175
- setsid "$chrome_bin" \\
176
- --user-data-dir="$user_data_dir" \\
177
- --profile-directory="$profile_directory" \\
178
- --remote-debugging-port="$chrome_port" \\
179
- --no-first-run \\
180
- --no-default-browser-check \\
181
- --disable-default-apps \\
182
- --no-sandbox \\
183
- --disable-setuid-sandbox \\
184
- --disable-dev-shm-usage \\
185
- $headless_arg \\
186
- about:blank >"$log_file" 2>&1 &
187
- else
188
- nohup "$chrome_bin" \\
189
- --user-data-dir="$user_data_dir" \\
190
- --profile-directory="$profile_directory" \\
191
- --remote-debugging-port="$chrome_port" \\
192
- --no-first-run \\
193
- --no-default-browser-check \\
194
- --disable-default-apps \\
195
- --no-sandbox \\
196
- --disable-setuid-sandbox \\
197
- --disable-dev-shm-usage \\
198
- $headless_arg \\
199
- about:blank >"$log_file" 2>&1 &
200
- fi
201
- chrome_pid=$!
202
378
 
203
- ready=0
204
- if [ "\${PIBO_BROWSER_USE_SKIP_CDP_WAIT:-}" = "1" ]; then
205
- ready=1
206
- fi
207
- attempt=0
208
- while [ "$ready" -ne 1 ] && [ "$attempt" -lt 50 ]; do
209
- if pibo_cdp_is_ready "$chrome_port"; then
379
+ retry=0
380
+ while [ "$retry" -lt 2 ]; do
381
+ kill_stale_chrome_for_profile "$user_data_dir"
382
+ profile_directory=$(resolve_profile_directory "$user_data_dir" "$default_profile")
383
+ chrome_port=$(find_free_port)
384
+ headless_arg=
385
+ if [ "$headed" -eq 0 ]; then
386
+ headless_arg=--headless=new
387
+ fi
388
+ rm -f "$log_file"
389
+ if command -v setsid >/dev/null 2>&1; then
390
+ setsid "$chrome_bin" \
391
+ --user-data-dir="$user_data_dir" \
392
+ --profile-directory="$profile_directory" \
393
+ --remote-debugging-port="$chrome_port" \
394
+ --no-first-run \
395
+ --no-default-browser-check \
396
+ --disable-default-apps \
397
+ --no-sandbox \
398
+ --disable-setuid-sandbox \
399
+ --disable-dev-shm-usage \
400
+ $headless_arg \
401
+ about:blank >"$log_file" 2>&1 &
402
+ else
403
+ nohup "$chrome_bin" \
404
+ --user-data-dir="$user_data_dir" \
405
+ --profile-directory="$profile_directory" \
406
+ --remote-debugging-port="$chrome_port" \
407
+ --no-first-run \
408
+ --no-default-browser-check \
409
+ --disable-default-apps \
410
+ --no-sandbox \
411
+ --disable-setuid-sandbox \
412
+ --disable-dev-shm-usage \
413
+ $headless_arg \
414
+ about:blank >"$log_file" 2>&1 &
415
+ fi
416
+ chrome_pid=$!
417
+
418
+ ready=0
419
+ if [ "\${PIBO_BROWSER_USE_SKIP_CDP_WAIT:-}" = "1" ]; then
210
420
  ready=1
211
- break
212
421
  fi
213
- if ! kill -0 "$chrome_pid" 2>/dev/null; then
214
- break
422
+ attempt=0
423
+ while [ "$ready" -ne 1 ] && [ "$attempt" -lt 50 ]; do
424
+ if pibo_cdp_is_ready "$chrome_port"; then
425
+ ready=1
426
+ break
427
+ fi
428
+ if ! kill -0 "$chrome_pid" 2>/dev/null; then
429
+ break
430
+ fi
431
+ attempt=$((attempt + 1))
432
+ sleep 0.1
433
+ done
434
+
435
+ if [ "$ready" -eq 1 ]; then
436
+ printf '%s\n' "$chrome_pid" > "$pid_file"
437
+ printf '%s\n' "$chrome_port" > "$port_file"
438
+ printf 'pibo browser-use: started Chrome profile "%s" (%s/%s) on CDP port %s.\n' "$default_profile" "$user_data_dir" "$profile_directory" "$chrome_port" >&2
439
+ printf '%s\n%s\nhttp://127.0.0.1:%s\n%s\n' "$chrome_pid" "$chrome_port" "$chrome_port" "$user_data_dir"
440
+ return 0
215
441
  fi
216
- attempt=$((attempt + 1))
217
- sleep 0.1
218
- done
219
442
 
220
- if [ "$ready" -ne 1 ]; then
221
- echo "pibo browser-use: Chrome did not expose CDP on port $chrome_port." >&2
443
+ echo "pibo browser-use: Chrome did not expose CDP on port $chrome_port (attempt $retry)." >&2
222
444
  sed -n '1,80p' "$log_file" >&2 2>/dev/null || true
223
- exit 1
445
+ if grep -q "SingletonLock" "$log_file" 2>/dev/null; then
446
+ echo "pibo browser-use: retrying after lock cleanup..." >&2
447
+ fi
448
+ retry=$((retry + 1))
449
+ sleep 0.5
450
+ done
451
+
452
+ echo "pibo browser-use: Chrome failed to start after retries." >&2
453
+ return 1
454
+ }
455
+
456
+ browser_pool_safe_segment() {
457
+ printf '%s' "$1" | tr -c 'A-Za-z0-9_.-' '_'
458
+ }
459
+
460
+ browser_pool_worker_id() {
461
+ printf '%s\n' "\${PIBO_BROWSER_POOL_WORKER_ID:-\${PIBO_COMPUTE_WORKER_ID:-\${HOSTNAME:-local}}}"
462
+ }
463
+
464
+ browser_pool_id() {
465
+ printf '%s\n' "\${PIBO_BROWSER_POOL_ID:-default}"
466
+ }
467
+
468
+ browser_pool_root() {
469
+ printf '%s\n' "\${PIBO_BROWSER_POOL_ROOT:-\${BROWSER_USE_HOME:-$HOME/.browser-use}/pibo-browser-pool}"
470
+ }
471
+
472
+ browser_pool_paths() {
473
+ worker=$(browser_pool_safe_segment "$(browser_pool_worker_id)")
474
+ pool=$(browser_pool_safe_segment "$(browser_pool_id)")
475
+ base=$(browser_pool_root)/browser-pools/$worker/$pool
476
+ printf '%s\n%s\n' "$base/state.json" "$base/state.lock"
477
+ }
478
+
479
+ browser_pool_read_summary() {
480
+ state_file=$1
481
+ "$python_cmd" - "$state_file" <<'PYSUMMARY'
482
+ import json
483
+ import sys
484
+ from pathlib import Path
485
+ path = Path(sys.argv[1])
486
+ try:
487
+ data = json.loads(path.read_text())
488
+ except FileNotFoundError:
489
+ print("missing")
490
+ raise SystemExit(0)
491
+ except Exception as exc:
492
+ print("malformed")
493
+ print(str(exc))
494
+ raise SystemExit(0)
495
+ for key in ("state", "pid", "cdpPort", "cdpUrl", "userDataDir", "activeLeaseId", "activeLeaseCount", "idleExpiresAt", "holder"):
496
+ value = data.get(key, "")
497
+ print(value if value is not None else "")
498
+ PYSUMMARY
499
+ }
500
+
501
+ browser_pool_lease_is_busy() {
502
+ active_lease=$1
503
+ requested_lease=$2
504
+ idle_expires_at=$3
505
+ if [ -z "$active_lease" ] || [ "$active_lease" = "$requested_lease" ]; then
506
+ return 1
224
507
  fi
508
+ "$python_cmd" - "$idle_expires_at" <<'PYBUSY'
509
+ import sys
510
+ from datetime import datetime, timezone
511
+ value = sys.argv[1]
512
+ if not value:
513
+ raise SystemExit(0)
514
+ try:
515
+ expires_at = datetime.fromisoformat(value.replace("Z", "+00:00"))
516
+ except Exception:
517
+ raise SystemExit(0)
518
+ if expires_at.tzinfo is None:
519
+ expires_at = expires_at.replace(tzinfo=timezone.utc)
520
+ raise SystemExit(1 if expires_at <= datetime.now(timezone.utc) else 0)
521
+ PYBUSY
522
+ }
225
523
 
226
- printf '%s\\n' "$chrome_pid" > "$pid_file"
227
- printf '%s\\n' "$chrome_port" > "$port_file"
228
- printf 'pibo browser-use: started Chrome profile "%s" (%s/%s) on CDP port %s.\\n' "$default_profile" "$user_data_dir" "$profile_directory" "$chrome_port" >&2
229
- printf 'http://127.0.0.1:%s\\n' "$chrome_port"
524
+ browser_pool_write_state() {
525
+ state_file=$1
526
+ lifecycle_state=$2
527
+ chrome_pid=$3
528
+ chrome_port=$4
529
+ cdp_url=$5
530
+ user_data_dir=$6
531
+ active_lease_id=$7
532
+ holder=$8
533
+ last_error=$9
534
+ "$python_cmd" - "$state_file" "$(browser_pool_worker_id)" "$(browser_pool_id)" "\${PIBO_BROWSER_POOL_MAX_PROCESSES:-1}" "$lifecycle_state" "$chrome_pid" "$chrome_port" "$cdp_url" "$user_data_dir" "$active_lease_id" "$holder" "$last_error" <<'PYSTATE'
535
+ import json
536
+ import os
537
+ import sys
538
+ from datetime import datetime, timedelta, timezone
539
+ from pathlib import Path
540
+ state_file = Path(sys.argv[1])
541
+ worker_id, pool_id, max_processes, lifecycle_state = sys.argv[2:6]
542
+ pid, port, cdp_url, user_data_dir, lease_id, holder, last_error = sys.argv[6:13]
543
+ now = datetime.now(timezone.utc)
544
+ record = {
545
+ "workerId": worker_id,
546
+ "poolId": pool_id,
547
+ "maxBrowserProcesses": int(max_processes or "1"),
548
+ "state": lifecycle_state,
549
+ "lastUsedAt": now.isoformat(timespec="milliseconds").replace("+00:00", "Z"),
550
+ }
551
+ if pid:
552
+ record["pid"] = int(pid)
553
+ record["processGroupId"] = int(pid)
554
+ if port:
555
+ record["cdpPort"] = int(port)
556
+ if cdp_url:
557
+ record["cdpUrl"] = cdp_url
558
+ if user_data_dir:
559
+ record["userDataDir"] = user_data_dir
560
+ if lease_id:
561
+ record["activeLeaseId"] = lease_id
562
+ record["activeLeaseCount"] = 1
563
+ record["cleanupStatus"] = "not-attempted"
564
+ record["idleExpiresAt"] = (now + timedelta(milliseconds=int(os.environ.get("PIBO_BROWSER_POOL_IDLE_TIMEOUT_MS", "600000")))).isoformat(timespec="milliseconds").replace("+00:00", "Z")
565
+ else:
566
+ record["activeLeaseCount"] = 0
567
+ if holder:
568
+ record["holder"] = holder
569
+ if last_error:
570
+ record["lastError"] = last_error
571
+ state_file.parent.mkdir(parents=True, exist_ok=True)
572
+ tmp = state_file.with_name(f"{state_file.name}.{os.getpid()}.tmp")
573
+ tmp.write_text(json.dumps(record, indent=2) + "\\n")
574
+ tmp.replace(state_file)
575
+ PYSTATE
576
+ }
577
+
578
+ browser_pool_acquire() {
579
+ paths=$(browser_pool_paths)
580
+ state_file=$(printf '%s\n' "$paths" | sed -n '1p')
581
+ lock_dir=$(printf '%s\n' "$paths" | sed -n '2p')
582
+ mkdir -p "$(dirname "$state_file")"
583
+ safe_session=$(browser_pool_safe_segment "$session")
584
+ lease_id=\${PIBO_BROWSER_POOL_LEASE_ID:-browser-use:$safe_session}
585
+ holder=\${PIBO_BROWSER_POOL_HOLDER:-browser-use:$session}
586
+ attempts=0
587
+ while ! mkdir "$lock_dir" 2>/dev/null; do
588
+ attempts=$((attempts + 1))
589
+ if [ "$attempts" -ge "\${PIBO_BROWSER_POOL_LOCK_ATTEMPTS:-100}" ]; then
590
+ echo "pibo browser-use: managed browser-pool acquire timed out waiting for $lock_dir" >&2
591
+ return 1
592
+ fi
593
+ sleep 0.05
594
+ done
595
+ trap 'rm -rf "$lock_dir"' EXIT INT TERM
596
+
597
+ summary=$(browser_pool_read_summary "$state_file")
598
+ summary_state=$(printf '%s\n' "$summary" | sed -n '1p')
599
+ if [ "$summary_state" = "malformed" ]; then
600
+ malformed_reason=$(printf '%s\n' "$summary" | sed -n '2p')
601
+ browser_pool_write_state "$state_file" dirty "" "" "" "" "" "$holder" "Malformed browser pool state: $malformed_reason"
602
+ elif [ "$summary_state" != "missing" ]; then
603
+ recorded_state=$summary_state
604
+ recorded_pid=$(printf '%s\n' "$summary" | sed -n '2p')
605
+ recorded_port=$(printf '%s\n' "$summary" | sed -n '3p')
606
+ recorded_cdp_url=$(printf '%s\n' "$summary" | sed -n '4p')
607
+ recorded_user_data_dir=$(printf '%s\n' "$summary" | sed -n '5p')
608
+ recorded_active_lease_id=$(printf '%s\n' "$summary" | sed -n '6p')
609
+ recorded_idle_expires_at=$(printf '%s\n' "$summary" | sed -n '8p')
610
+ recorded_holder=$(printf '%s\n' "$summary" | sed -n '9p')
611
+ if [ "$recorded_state" = "leased" ] && browser_pool_lease_is_busy "$recorded_active_lease_id" "$lease_id" "$recorded_idle_expires_at" && [ -n "$recorded_pid" ] && [ -n "$recorded_port" ] && [ -n "$recorded_cdp_url" ] && kill -0 "$recorded_pid" 2>/dev/null && pibo_cdp_is_ready "$recorded_port"; then
612
+ busy_reason="pool-exhausted: browser pool $(browser_pool_id) is already leased by $recorded_active_lease_id until \${recorded_idle_expires_at:-unknown}"
613
+ echo "pibo browser-use: $busy_reason" >&2
614
+ rm -rf "$lock_dir"
615
+ trap - EXIT INT TERM
616
+ return 1
617
+ fi
618
+ if [ "$recorded_state" != "dirty" ] && [ -n "$recorded_pid" ] && [ -n "$recorded_port" ] && [ -n "$recorded_cdp_url" ] && kill -0 "$recorded_pid" 2>/dev/null && pibo_cdp_is_ready "$recorded_port"; then
619
+ browser_pool_write_state "$state_file" leased "$recorded_pid" "$recorded_port" "$recorded_cdp_url" "$recorded_user_data_dir" "$lease_id" "$holder" ""
620
+ rm -rf "$lock_dir"
621
+ trap - EXIT INT TERM
622
+ printf '%s\n' "$recorded_cdp_url"
623
+ return 0
624
+ fi
625
+ browser_pool_write_state "$state_file" stale "$recorded_pid" "$recorded_port" "$recorded_cdp_url" "$recorded_user_data_dir" "" "$holder" "Recorded browser is not alive or CDP is unreachable"
626
+ fi
627
+
628
+ start_result=$(start_persistent_chrome) || {
629
+ browser_pool_write_state "$state_file" dirty "" "" "" "" "" "$holder" "Managed browser start failed"
630
+ rm -rf "$lock_dir"
631
+ trap - EXIT INT TERM
632
+ return 1
633
+ }
634
+ chrome_pid=$(printf '%s\n' "$start_result" | sed -n '1p')
635
+ chrome_port=$(printf '%s\n' "$start_result" | sed -n '2p')
636
+ cdp_url=$(printf '%s\n' "$start_result" | sed -n '3p')
637
+ user_data_dir=$(printf '%s\n' "$start_result" | sed -n '4p')
638
+ browser_pool_write_state "$state_file" leased "$chrome_pid" "$chrome_port" "$cdp_url" "$user_data_dir" "$lease_id" "$holder" ""
639
+ rm -rf "$lock_dir"
640
+ trap - EXIT INT TERM
641
+ printf '%s\n' "$cdp_url"
642
+ }
643
+
644
+ ensure_persistent_chrome() {
645
+ if cdp_url=$(browser_pool_acquire); then
646
+ printf '%s\n' "$cdp_url"
647
+ return 0
648
+ fi
649
+ echo "pibo browser-use: managed browser-pool acquire failed; refusing to start an unmanaged browser." >&2
650
+ exit 1
230
651
  }
231
652
 
232
653
  while [ "$#" -gt 0 ]; do
@@ -273,6 +694,10 @@ while [ "$#" -gt 0 ]; do
273
694
  --session=*)
274
695
  session=\${arg#--session=}
275
696
  ;;
697
+ --pibo-ensure-chrome)
698
+ pibo_ensure_chrome=1
699
+ continue
700
+ ;;
276
701
  -*)
277
702
  ;;
278
703
  open|click|type|input|scroll|back|screenshot|state|switch|close-tab|keys|select|upload|eval|extract|hover|dblclick|rightclick|cookies|wait|get|python)
@@ -285,11 +710,18 @@ while [ "$#" -gt 0 ]; do
285
710
  append_arg "$arg"
286
711
  done
287
712
 
713
+ if [ "$pibo_ensure_chrome" -eq 1 ]; then
714
+ cdp_url=$(ensure_persistent_chrome)
715
+ printf '%s\\n' "$cdp_url"
716
+ exit 0
717
+ fi
718
+
288
719
  if [ "$show_help" -eq 1 ]; then
289
720
  {
290
721
  echo "Pibo browser-use wrapper:"
291
722
  echo " New browser-use daemon sessions default to persistent Chrome profile \\"$default_profile\\" via CDP."
292
723
  echo " Use $fresh_flag to start a fresh temporary browser profile."
724
+ echo " Use --pibo-ensure-chrome to only start Chrome and print the CDP URL."
293
725
  echo ""
294
726
  } >&2
295
727
  fi
@@ -303,19 +735,30 @@ $sanitized_args
303
735
  EOF
304
736
  fi
305
737
 
738
+ # Prepend --session if the user did not pass it explicitly and a non-default session is set.
739
+ has_session_arg=0
740
+ for a in "$@"; do
741
+ case "$a" in
742
+ --session|--session=*) has_session_arg=1; break ;;
743
+ esac
744
+ done
745
+ if [ "$has_session_arg" -eq 0 ] && [ "$session" != "default" ]; then
746
+ set -- --session "$session" "$@"
747
+ fi
748
+
306
749
  session_pid_file=\${BROWSER_USE_HOME:-$HOME/.browser-use}/$session.pid
307
750
  session_alive=0
308
751
  if [ -s "$session_pid_file" ]; then
309
752
  session_pid=$(cat "$session_pid_file" 2>/dev/null || true)
310
753
  if [ -n "$session_pid" ] && kill -0 "$session_pid" 2>/dev/null; then
311
754
  session_alive=1
755
+ else
756
+ # Clean up stale session pid file
757
+ rm -f "$session_pid_file" 2>/dev/null || true
312
758
  fi
313
759
  fi
314
760
 
315
761
  if [ "$starts_browser" -eq 1 ] && [ "$explicit_profile" -eq 0 ] && [ "$fresh_profile" -eq 0 ]; then
316
- if [ "$session_alive" -eq 1 ] && persistent_chrome_url_if_alive >/dev/null; then
317
- exec "$real_browser_use" "$@"
318
- fi
319
762
  if [ "$session_alive" -eq 1 ]; then
320
763
  "$real_browser_use" --session "$session" close >/dev/null 2>&1 || true
321
764
  sleep 0.2