@quickchatai/pi-quickreview 0.0.0-stage → 1.1.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 (689) hide show
  1. package/LICENSE +23 -0
  2. package/README.md +75 -2
  3. package/assets/agents/pass-abstraction.md +64 -0
  4. package/assets/agents/pass-ask-human.md +134 -0
  5. package/assets/agents/pass-backcompat.md +67 -0
  6. package/assets/agents/pass-baseline.md +61 -0
  7. package/assets/agents/pass-behaviour-delta.md +64 -0
  8. package/assets/agents/pass-bounds.md +36 -0
  9. package/assets/agents/pass-claims.md +31 -0
  10. package/assets/agents/pass-concurrency.md +168 -0
  11. package/assets/agents/pass-consistency.md +57 -0
  12. package/assets/agents/pass-contracts.md +30 -0
  13. package/assets/agents/pass-data-safety.md +54 -0
  14. package/assets/agents/pass-deferred.md +35 -0
  15. package/assets/agents/pass-delivery.md +37 -0
  16. package/assets/agents/pass-duplication.md +60 -0
  17. package/assets/agents/pass-intent.md +63 -0
  18. package/assets/agents/pass-lint-conformance.md +46 -0
  19. package/assets/agents/pass-maintainability.md +67 -0
  20. package/assets/agents/pass-placement.md +68 -0
  21. package/assets/agents/pass-prod-risk.md +24 -0
  22. package/assets/agents/pass-rollout.md +32 -0
  23. package/assets/agents/pass-roundtrip.md +46 -0
  24. package/assets/agents/pass-security.md +31 -0
  25. package/assets/agents/pass-simplicity.md +68 -0
  26. package/assets/agents/pass-statelessness.md +27 -0
  27. package/assets/agents/pass-style.md +37 -0
  28. package/assets/agents/pass-sweep.md +57 -0
  29. package/assets/agents/pass-tests.md +58 -0
  30. package/assets/agents/pass-ui.md +23 -0
  31. package/assets/agents/pass-validate.md +50 -0
  32. package/assets/agents/pass-widened.md +46 -0
  33. package/assets/agents/scan/pass-scan.md +86 -0
  34. package/assets/config.example.toml +1067 -0
  35. package/assets/deploy/reviewer/AGENTS.override.md +12 -0
  36. package/assets/profiles/default/README.md +21 -0
  37. package/assets/profiles/default/addenda/.gitkeep +0 -0
  38. package/assets/profiles/default/profile.toml +17 -0
  39. package/assets/profiles/example-django/README.md +21 -0
  40. package/assets/profiles/example-django/addenda/10-migration-discipline.md +13 -0
  41. package/assets/profiles/example-django/addenda/20-new-column-nullability.md +12 -0
  42. package/assets/profiles/example-django/addenda/30-test-doctrine.md +12 -0
  43. package/assets/profiles/example-django/addenda/40-orm-usage.md +19 -0
  44. package/assets/profiles/example-django/addenda/50-declared-shape.md +10 -0
  45. package/assets/profiles/example-django/addenda/60-config-placement.md +14 -0
  46. package/assets/profiles/example-django/heuristics.toml +24 -0
  47. package/assets/profiles/example-django/profile.toml +9 -0
  48. package/assets/profiles/fast/README.md +24 -0
  49. package/assets/profiles/fast/profile.toml +59 -0
  50. package/assets/profiles/minimal/README.md +17 -0
  51. package/assets/profiles/minimal/addenda/.gitkeep +0 -0
  52. package/assets/profiles/minimal/profile.toml +8 -0
  53. package/assets/profiles/snappy/README.md +24 -0
  54. package/assets/profiles/snappy/addenda/10-race-as-question.md +6 -0
  55. package/assets/profiles/snappy/profile.toml +46 -0
  56. package/assets/prompts/companion-day-open.md +46 -0
  57. package/assets/prompts/companion-first-run.md +104 -0
  58. package/assets/prompts/companion.md +821 -0
  59. package/assets/prompts/conversation-system.md +117 -0
  60. package/assets/prompts/eod-sweep.md +120 -0
  61. package/assets/prompts/onboarding.md +74 -0
  62. package/assets/prompts/pass-common.md +52 -0
  63. package/assets/prompts/pass-quality-common.md +22 -0
  64. package/assets/prompts/round-first.md +874 -0
  65. package/assets/prompts/round-follow-up.md +991 -0
  66. package/assets/prompts/round-re-review.md +889 -0
  67. package/assets/prompts/round-recheck.md +196 -0
  68. package/assets/prompts/round-staleness.md +856 -0
  69. package/assets/schemas/review-result.v1.json +391 -0
  70. package/assets/schemas/scan-result.v1.json +421 -0
  71. package/assets/schemas/version.v1.json +57 -0
  72. package/assets/seed-manifest.json +19 -0
  73. package/assets/seeds/agents/pass-baseline.md +61 -0
  74. package/assets/seeds/agents/pass-contracts.md +30 -0
  75. package/assets/seeds/agents/pass-data-safety.md +54 -0
  76. package/assets/seeds/agents/pass-delivery.md +37 -0
  77. package/assets/seeds/agents/pass-prod-risk.md +24 -0
  78. package/assets/seeds/agents/pass-security.md +31 -0
  79. package/assets/seeds/agents/pass-statelessness.md +27 -0
  80. package/assets/seeds/agents/pass-ui.md +23 -0
  81. package/assets/seeds/agents/pass-validate.md +50 -0
  82. package/assets/seeds/prompts/conversation-system.md +117 -0
  83. package/assets/seeds/prompts/eod-sweep.md +120 -0
  84. package/assets/seeds/prompts/pass-common.md +52 -0
  85. package/dist/extensions/bash-guard.d.ts +467 -0
  86. package/dist/extensions/bash-guard.d.ts.map +1 -0
  87. package/dist/extensions/bash-guard.js +3058 -0
  88. package/dist/extensions/bash-guard.js.map +1 -0
  89. package/dist/extensions/finding-clusters.d.ts +33 -0
  90. package/dist/extensions/finding-clusters.d.ts.map +1 -0
  91. package/dist/extensions/finding-clusters.js +218 -0
  92. package/dist/extensions/finding-clusters.js.map +1 -0
  93. package/dist/extensions/ledger-pin.d.ts +76 -0
  94. package/dist/extensions/ledger-pin.d.ts.map +1 -0
  95. package/dist/extensions/ledger-pin.js +331 -0
  96. package/dist/extensions/ledger-pin.js.map +1 -0
  97. package/dist/extensions/lens.d.ts +43 -0
  98. package/dist/extensions/lens.d.ts.map +1 -0
  99. package/dist/extensions/lens.js +150 -0
  100. package/dist/extensions/lens.js.map +1 -0
  101. package/dist/extensions/pi-tool.d.ts +22 -0
  102. package/dist/extensions/pi-tool.d.ts.map +1 -0
  103. package/dist/extensions/pi-tool.js +20 -0
  104. package/dist/extensions/pi-tool.js.map +1 -0
  105. package/dist/extensions/quickreview.d.ts +21 -0
  106. package/dist/extensions/quickreview.d.ts.map +1 -0
  107. package/dist/extensions/quickreview.js +132 -0
  108. package/dist/extensions/quickreview.js.map +1 -0
  109. package/dist/src/anchors.d.ts +54 -0
  110. package/dist/src/anchors.d.ts.map +1 -0
  111. package/dist/src/anchors.js +127 -0
  112. package/dist/src/anchors.js.map +1 -0
  113. package/dist/src/assetroot.d.ts +16 -0
  114. package/dist/src/assetroot.d.ts.map +1 -0
  115. package/dist/src/assetroot.js +77 -0
  116. package/dist/src/assetroot.js.map +1 -0
  117. package/dist/src/authwatch.d.ts +61 -0
  118. package/dist/src/authwatch.d.ts.map +1 -0
  119. package/dist/src/authwatch.js +210 -0
  120. package/dist/src/authwatch.js.map +1 -0
  121. package/dist/src/budget.d.ts +15 -0
  122. package/dist/src/budget.d.ts.map +1 -0
  123. package/dist/src/budget.js +32 -0
  124. package/dist/src/budget.js.map +1 -0
  125. package/dist/src/casebudget.d.ts +3 -0
  126. package/dist/src/casebudget.d.ts.map +1 -0
  127. package/dist/src/casebudget.js +3 -0
  128. package/dist/src/casebudget.js.map +1 -0
  129. package/dist/src/cigate.d.ts +116 -0
  130. package/dist/src/cigate.d.ts.map +1 -0
  131. package/dist/src/cigate.js +176 -0
  132. package/dist/src/cigate.js.map +1 -0
  133. package/dist/src/codespan.d.ts +46 -0
  134. package/dist/src/codespan.d.ts.map +1 -0
  135. package/dist/src/codespan.js +75 -0
  136. package/dist/src/codespan.js.map +1 -0
  137. package/dist/src/contextpack.d.ts +56 -0
  138. package/dist/src/contextpack.d.ts.map +1 -0
  139. package/dist/src/contextpack.js +195 -0
  140. package/dist/src/contextpack.js.map +1 -0
  141. package/dist/src/contract.d.ts +8 -0
  142. package/dist/src/contract.d.ts.map +1 -0
  143. package/dist/src/contract.js +21 -0
  144. package/dist/src/contract.js.map +1 -0
  145. package/dist/src/coverage.d.ts +32 -0
  146. package/dist/src/coverage.d.ts.map +1 -0
  147. package/dist/src/coverage.js +85 -0
  148. package/dist/src/coverage.js.map +1 -0
  149. package/dist/src/datafence.d.ts +19 -0
  150. package/dist/src/datafence.d.ts.map +1 -0
  151. package/dist/src/datafence.js +60 -0
  152. package/dist/src/datafence.js.map +1 -0
  153. package/dist/src/dedup.d.ts +65 -0
  154. package/dist/src/dedup.d.ts.map +1 -0
  155. package/dist/src/dedup.js +459 -0
  156. package/dist/src/dedup.js.map +1 -0
  157. package/dist/src/depsources.d.ts +304 -0
  158. package/dist/src/depsources.d.ts.map +1 -0
  159. package/dist/src/depsources.js +3367 -0
  160. package/dist/src/depsources.js.map +1 -0
  161. package/dist/src/diffinput.d.ts +10 -0
  162. package/dist/src/diffinput.d.ts.map +1 -0
  163. package/dist/src/diffinput.js +172 -0
  164. package/dist/src/diffinput.js.map +1 -0
  165. package/dist/src/doubtwords.d.ts +10 -0
  166. package/dist/src/doubtwords.d.ts.map +1 -0
  167. package/dist/src/doubtwords.js +13 -0
  168. package/dist/src/doubtwords.js.map +1 -0
  169. package/dist/src/ecosystem.d.ts +148 -0
  170. package/dist/src/ecosystem.d.ts.map +1 -0
  171. package/dist/src/ecosystem.js +338 -0
  172. package/dist/src/ecosystem.js.map +1 -0
  173. package/dist/src/engine/agentdir.d.ts +5 -0
  174. package/dist/src/engine/agentdir.d.ts.map +1 -0
  175. package/dist/src/engine/agentdir.js +21 -0
  176. package/dist/src/engine/agentdir.js.map +1 -0
  177. package/dist/src/engine/auth.d.ts +214 -0
  178. package/dist/src/engine/auth.d.ts.map +1 -0
  179. package/dist/src/engine/auth.js +374 -0
  180. package/dist/src/engine/auth.js.map +1 -0
  181. package/dist/src/engine/budget.d.ts +60 -0
  182. package/dist/src/engine/budget.d.ts.map +1 -0
  183. package/dist/src/engine/budget.js +113 -0
  184. package/dist/src/engine/budget.js.map +1 -0
  185. package/dist/src/engine/capfd.d.ts +6 -0
  186. package/dist/src/engine/capfd.d.ts.map +1 -0
  187. package/dist/src/engine/capfd.js +21 -0
  188. package/dist/src/engine/capfd.js.map +1 -0
  189. package/dist/src/engine/caseout.d.ts +66 -0
  190. package/dist/src/engine/caseout.d.ts.map +1 -0
  191. package/dist/src/engine/caseout.js +107 -0
  192. package/dist/src/engine/caseout.js.map +1 -0
  193. package/dist/src/engine/context.d.ts +57 -0
  194. package/dist/src/engine/context.d.ts.map +1 -0
  195. package/dist/src/engine/context.js +212 -0
  196. package/dist/src/engine/context.js.map +1 -0
  197. package/dist/src/engine/envmap.d.ts +13 -0
  198. package/dist/src/engine/envmap.d.ts.map +1 -0
  199. package/dist/src/engine/envmap.js +372 -0
  200. package/dist/src/engine/envmap.js.map +1 -0
  201. package/dist/src/engine/extfiles.d.ts +7 -0
  202. package/dist/src/engine/extfiles.d.ts.map +1 -0
  203. package/dist/src/engine/extfiles.js +23 -0
  204. package/dist/src/engine/extfiles.js.map +1 -0
  205. package/dist/src/engine/keyroute.d.ts +21 -0
  206. package/dist/src/engine/keyroute.d.ts.map +1 -0
  207. package/dist/src/engine/keyroute.js +58 -0
  208. package/dist/src/engine/keyroute.js.map +1 -0
  209. package/dist/src/engine/lens/cache-group.d.ts +20 -0
  210. package/dist/src/engine/lens/cache-group.d.ts.map +1 -0
  211. package/dist/src/engine/lens/cache-group.js +31 -0
  212. package/dist/src/engine/lens/cache-group.js.map +1 -0
  213. package/dist/src/engine/lens/cache-run.d.ts +65 -0
  214. package/dist/src/engine/lens/cache-run.d.ts.map +1 -0
  215. package/dist/src/engine/lens/cache-run.js +159 -0
  216. package/dist/src/engine/lens/cache-run.js.map +1 -0
  217. package/dist/src/engine/lens/deadline.d.ts +54 -0
  218. package/dist/src/engine/lens/deadline.d.ts.map +1 -0
  219. package/dist/src/engine/lens/deadline.js +111 -0
  220. package/dist/src/engine/lens/deadline.js.map +1 -0
  221. package/dist/src/engine/lens/engine-tools.d.ts +13 -0
  222. package/dist/src/engine/lens/engine-tools.d.ts.map +1 -0
  223. package/dist/src/engine/lens/engine-tools.js +37 -0
  224. package/dist/src/engine/lens/engine-tools.js.map +1 -0
  225. package/dist/src/engine/lens/env.d.ts +23 -0
  226. package/dist/src/engine/lens/env.d.ts.map +1 -0
  227. package/dist/src/engine/lens/env.js +42 -0
  228. package/dist/src/engine/lens/env.js.map +1 -0
  229. package/dist/src/engine/lens/launch-plan.d.ts +63 -0
  230. package/dist/src/engine/lens/launch-plan.d.ts.map +1 -0
  231. package/dist/src/engine/lens/launch-plan.js +203 -0
  232. package/dist/src/engine/lens/launch-plan.js.map +1 -0
  233. package/dist/src/engine/lens/leaf-cache.d.ts +22 -0
  234. package/dist/src/engine/lens/leaf-cache.d.ts.map +1 -0
  235. package/dist/src/engine/lens/leaf-cache.js +115 -0
  236. package/dist/src/engine/lens/leaf-cache.js.map +1 -0
  237. package/dist/src/engine/lens/permits.d.ts +14 -0
  238. package/dist/src/engine/lens/permits.d.ts.map +1 -0
  239. package/dist/src/engine/lens/permits.js +18 -0
  240. package/dist/src/engine/lens/permits.js.map +1 -0
  241. package/dist/src/engine/lens/registry.d.ts +55 -0
  242. package/dist/src/engine/lens/registry.d.ts.map +1 -0
  243. package/dist/src/engine/lens/registry.js +140 -0
  244. package/dist/src/engine/lens/registry.js.map +1 -0
  245. package/dist/src/engine/lens/round-lens.d.ts +16 -0
  246. package/dist/src/engine/lens/round-lens.d.ts.map +1 -0
  247. package/dist/src/engine/lens/round-lens.js +46 -0
  248. package/dist/src/engine/lens/round-lens.js.map +1 -0
  249. package/dist/src/engine/lens/runlens.d.ts +103 -0
  250. package/dist/src/engine/lens/runlens.d.ts.map +1 -0
  251. package/dist/src/engine/lens/runlens.js +538 -0
  252. package/dist/src/engine/lens/runlens.js.map +1 -0
  253. package/dist/src/engine/lens/section.d.ts +19 -0
  254. package/dist/src/engine/lens/section.d.ts.map +1 -0
  255. package/dist/src/engine/lens/section.js +40 -0
  256. package/dist/src/engine/lens/section.js.map +1 -0
  257. package/dist/src/engine/lens/semaphore.d.ts +13 -0
  258. package/dist/src/engine/lens/semaphore.d.ts.map +1 -0
  259. package/dist/src/engine/lens/semaphore.js +44 -0
  260. package/dist/src/engine/lens/semaphore.js.map +1 -0
  261. package/dist/src/engine/lens/tool.d.ts +34 -0
  262. package/dist/src/engine/lens/tool.d.ts.map +1 -0
  263. package/dist/src/engine/lens/tool.js +345 -0
  264. package/dist/src/engine/lens/tool.js.map +1 -0
  265. package/dist/src/engine/lens/wave.d.ts +63 -0
  266. package/dist/src/engine/lens/wave.d.ts.map +1 -0
  267. package/dist/src/engine/lens/wave.js +95 -0
  268. package/dist/src/engine/lens/wave.js.map +1 -0
  269. package/dist/src/engine/livesessions.d.ts +21 -0
  270. package/dist/src/engine/livesessions.d.ts.map +1 -0
  271. package/dist/src/engine/livesessions.js +57 -0
  272. package/dist/src/engine/livesessions.js.map +1 -0
  273. package/dist/src/engine/livewire.d.ts +18 -0
  274. package/dist/src/engine/livewire.d.ts.map +1 -0
  275. package/dist/src/engine/livewire.js +31 -0
  276. package/dist/src/engine/livewire.js.map +1 -0
  277. package/dist/src/engine/openable.d.ts +37 -0
  278. package/dist/src/engine/openable.d.ts.map +1 -0
  279. package/dist/src/engine/openable.js +120 -0
  280. package/dist/src/engine/openable.js.map +1 -0
  281. package/dist/src/engine/pisdk.d.ts +226 -0
  282. package/dist/src/engine/pisdk.d.ts.map +1 -0
  283. package/dist/src/engine/pisdk.js +552 -0
  284. package/dist/src/engine/pisdk.js.map +1 -0
  285. package/dist/src/engine/port.d.ts +144 -0
  286. package/dist/src/engine/port.d.ts.map +1 -0
  287. package/dist/src/engine/port.js +16 -0
  288. package/dist/src/engine/port.js.map +1 -0
  289. package/dist/src/engine/prompts.d.ts +159 -0
  290. package/dist/src/engine/prompts.d.ts.map +1 -0
  291. package/dist/src/engine/prompts.js +339 -0
  292. package/dist/src/engine/prompts.js.map +1 -0
  293. package/dist/src/engine/render.d.ts +10 -0
  294. package/dist/src/engine/render.d.ts.map +1 -0
  295. package/dist/src/engine/render.js +23 -0
  296. package/dist/src/engine/render.js.map +1 -0
  297. package/dist/src/engine/reviewruntime.d.ts +13 -0
  298. package/dist/src/engine/reviewruntime.d.ts.map +1 -0
  299. package/dist/src/engine/reviewruntime.js +35 -0
  300. package/dist/src/engine/reviewruntime.js.map +1 -0
  301. package/dist/src/engine/reviewsdk.d.ts +75 -0
  302. package/dist/src/engine/reviewsdk.d.ts.map +1 -0
  303. package/dist/src/engine/reviewsdk.js +180 -0
  304. package/dist/src/engine/reviewsdk.js.map +1 -0
  305. package/dist/src/engine/round.d.ts +166 -0
  306. package/dist/src/engine/round.d.ts.map +1 -0
  307. package/dist/src/engine/round.js +543 -0
  308. package/dist/src/engine/round.js.map +1 -0
  309. package/dist/src/engine/roundagents.d.ts +17 -0
  310. package/dist/src/engine/roundagents.d.ts.map +1 -0
  311. package/dist/src/engine/roundagents.js +49 -0
  312. package/dist/src/engine/roundagents.js.map +1 -0
  313. package/dist/src/engine/roundevents.d.ts +110 -0
  314. package/dist/src/engine/roundevents.d.ts.map +1 -0
  315. package/dist/src/engine/roundevents.js +276 -0
  316. package/dist/src/engine/roundevents.js.map +1 -0
  317. package/dist/src/engine/roundsdk.d.ts +33 -0
  318. package/dist/src/engine/roundsdk.d.ts.map +1 -0
  319. package/dist/src/engine/roundsdk.js +76 -0
  320. package/dist/src/engine/roundsdk.js.map +1 -0
  321. package/dist/src/engine/sdkruntime.d.ts +23 -0
  322. package/dist/src/engine/sdkruntime.d.ts.map +1 -0
  323. package/dist/src/engine/sdkruntime.js +340 -0
  324. package/dist/src/engine/sdkruntime.js.map +1 -0
  325. package/dist/src/engine/select.d.ts +16 -0
  326. package/dist/src/engine/select.d.ts.map +1 -0
  327. package/dist/src/engine/select.js +32 -0
  328. package/dist/src/engine/select.js.map +1 -0
  329. package/dist/src/engine/sessionwrap.d.ts +4 -0
  330. package/dist/src/engine/sessionwrap.d.ts.map +1 -0
  331. package/dist/src/engine/sessionwrap.js +31 -0
  332. package/dist/src/engine/sessionwrap.js.map +1 -0
  333. package/dist/src/engine/toolfence.d.ts +90 -0
  334. package/dist/src/engine/toolfence.d.ts.map +1 -0
  335. package/dist/src/engine/toolfence.js +378 -0
  336. package/dist/src/engine/toolfence.js.map +1 -0
  337. package/dist/src/engine/tooluid.d.ts +128 -0
  338. package/dist/src/engine/tooluid.d.ts.map +1 -0
  339. package/dist/src/engine/tooluid.js +401 -0
  340. package/dist/src/engine/tooluid.js.map +1 -0
  341. package/dist/src/envstrip.d.ts +10 -0
  342. package/dist/src/envstrip.d.ts.map +1 -0
  343. package/dist/src/envstrip.js +15 -0
  344. package/dist/src/envstrip.js.map +1 -0
  345. package/dist/src/escalationprompt.d.ts +22 -0
  346. package/dist/src/escalationprompt.d.ts.map +1 -0
  347. package/dist/src/escalationprompt.js +54 -0
  348. package/dist/src/escalationprompt.js.map +1 -0
  349. package/dist/src/execfn.d.ts +29 -0
  350. package/dist/src/execfn.d.ts.map +1 -0
  351. package/dist/src/execfn.js +55 -0
  352. package/dist/src/execfn.js.map +1 -0
  353. package/dist/src/finding-chain.d.ts +40 -0
  354. package/dist/src/finding-chain.d.ts.map +1 -0
  355. package/dist/src/finding-chain.js +76 -0
  356. package/dist/src/finding-chain.js.map +1 -0
  357. package/dist/src/finding-row.d.ts +24 -0
  358. package/dist/src/finding-row.d.ts.map +1 -0
  359. package/dist/src/finding-row.js +26 -0
  360. package/dist/src/finding-row.js.map +1 -0
  361. package/dist/src/findingkey.d.ts +99 -0
  362. package/dist/src/findingkey.d.ts.map +1 -0
  363. package/dist/src/findingkey.js +210 -0
  364. package/dist/src/findingkey.js.map +1 -0
  365. package/dist/src/findingsrecord.d.ts +175 -0
  366. package/dist/src/findingsrecord.d.ts.map +1 -0
  367. package/dist/src/findingsrecord.js +410 -0
  368. package/dist/src/findingsrecord.js.map +1 -0
  369. package/dist/src/followup-mode.d.ts +4 -0
  370. package/dist/src/followup-mode.d.ts.map +1 -0
  371. package/dist/src/followup-mode.js +6 -0
  372. package/dist/src/followup-mode.js.map +1 -0
  373. package/dist/src/gate.d.ts +199 -0
  374. package/dist/src/gate.d.ts.map +1 -0
  375. package/dist/src/gate.js +315 -0
  376. package/dist/src/gate.js.map +1 -0
  377. package/dist/src/ghcred.d.ts +58 -0
  378. package/dist/src/ghcred.d.ts.map +1 -0
  379. package/dist/src/ghcred.js +139 -0
  380. package/dist/src/ghcred.js.map +1 -0
  381. package/dist/src/githubAuth.d.ts +32 -0
  382. package/dist/src/githubAuth.d.ts.map +1 -0
  383. package/dist/src/githubAuth.js +116 -0
  384. package/dist/src/githubAuth.js.map +1 -0
  385. package/dist/src/githubcore.d.ts +20 -0
  386. package/dist/src/githubcore.d.ts.map +1 -0
  387. package/dist/src/githubcore.js +20 -0
  388. package/dist/src/githubcore.js.map +1 -0
  389. package/dist/src/glob.d.ts +11 -0
  390. package/dist/src/glob.d.ts.map +1 -0
  391. package/dist/src/glob.js +69 -0
  392. package/dist/src/glob.js.map +1 -0
  393. package/dist/src/guards.d.ts +93 -0
  394. package/dist/src/guards.d.ts.map +1 -0
  395. package/dist/src/guards.js +306 -0
  396. package/dist/src/guards.js.map +1 -0
  397. package/dist/src/heartbeat.d.ts +29 -0
  398. package/dist/src/heartbeat.d.ts.map +1 -0
  399. package/dist/src/heartbeat.js +87 -0
  400. package/dist/src/heartbeat.js.map +1 -0
  401. package/dist/src/heuristics.d.ts +247 -0
  402. package/dist/src/heuristics.d.ts.map +1 -0
  403. package/dist/src/heuristics.js +927 -0
  404. package/dist/src/heuristics.js.map +1 -0
  405. package/dist/src/homes.d.ts +181 -0
  406. package/dist/src/homes.d.ts.map +1 -0
  407. package/dist/src/homes.js +242 -0
  408. package/dist/src/homes.js.map +1 -0
  409. package/dist/src/hunkheader.d.ts +11 -0
  410. package/dist/src/hunkheader.d.ts.map +1 -0
  411. package/dist/src/hunkheader.js +18 -0
  412. package/dist/src/hunkheader.js.map +1 -0
  413. package/dist/src/include.d.ts +435 -0
  414. package/dist/src/include.d.ts.map +1 -0
  415. package/dist/src/include.js +1692 -0
  416. package/dist/src/include.js.map +1 -0
  417. package/dist/src/launchvocab.d.ts +36 -0
  418. package/dist/src/launchvocab.d.ts.map +1 -0
  419. package/dist/src/launchvocab.js +59 -0
  420. package/dist/src/launchvocab.js.map +1 -0
  421. package/dist/src/ledgercarry.d.ts +24 -0
  422. package/dist/src/ledgercarry.d.ts.map +1 -0
  423. package/dist/src/ledgercarry.js +109 -0
  424. package/dist/src/ledgercarry.js.map +1 -0
  425. package/dist/src/lensids.d.ts +7 -0
  426. package/dist/src/lensids.d.ts.map +1 -0
  427. package/dist/src/lensids.js +53 -0
  428. package/dist/src/lensids.js.map +1 -0
  429. package/dist/src/lensplanning.d.ts +8 -0
  430. package/dist/src/lensplanning.d.ts.map +1 -0
  431. package/dist/src/lensplanning.js +126 -0
  432. package/dist/src/lensplanning.js.map +1 -0
  433. package/dist/src/lensresult.d.ts +94 -0
  434. package/dist/src/lensresult.d.ts.map +1 -0
  435. package/dist/src/lensresult.js +162 -0
  436. package/dist/src/lensresult.js.map +1 -0
  437. package/dist/src/lenstuning.d.ts +97 -0
  438. package/dist/src/lenstuning.d.ts.map +1 -0
  439. package/dist/src/lenstuning.js +326 -0
  440. package/dist/src/lenstuning.js.map +1 -0
  441. package/dist/src/lintconfig.d.ts +31 -0
  442. package/dist/src/lintconfig.d.ts.map +1 -0
  443. package/dist/src/lintconfig.js +543 -0
  444. package/dist/src/lintconfig.js.map +1 -0
  445. package/dist/src/live/events.d.ts +188 -0
  446. package/dist/src/live/events.d.ts.map +1 -0
  447. package/dist/src/live/events.js +136 -0
  448. package/dist/src/live/events.js.map +1 -0
  449. package/dist/src/live/writer.d.ts +54 -0
  450. package/dist/src/live/writer.d.ts.map +1 -0
  451. package/dist/src/live/writer.js +516 -0
  452. package/dist/src/live/writer.js.map +1 -0
  453. package/dist/src/localreview.d.ts +128 -0
  454. package/dist/src/localreview.d.ts.map +1 -0
  455. package/dist/src/localreview.js +426 -0
  456. package/dist/src/localreview.js.map +1 -0
  457. package/dist/src/loosenedtests.d.ts +13 -0
  458. package/dist/src/loosenedtests.d.ts.map +1 -0
  459. package/dist/src/loosenedtests.js +188 -0
  460. package/dist/src/loosenedtests.js.map +1 -0
  461. package/dist/src/memoryport.d.ts +264 -0
  462. package/dist/src/memoryport.d.ts.map +1 -0
  463. package/dist/src/memoryport.js +445 -0
  464. package/dist/src/memoryport.js.map +1 -0
  465. package/dist/src/migrations.d.ts +106 -0
  466. package/dist/src/migrations.d.ts.map +1 -0
  467. package/dist/src/migrations.js +373 -0
  468. package/dist/src/migrations.js.map +1 -0
  469. package/dist/src/oneshot.d.ts +12 -0
  470. package/dist/src/oneshot.d.ts.map +1 -0
  471. package/dist/src/oneshot.js +8 -0
  472. package/dist/src/oneshot.js.map +1 -0
  473. package/dist/src/packing.d.ts +11 -0
  474. package/dist/src/packing.d.ts.map +1 -0
  475. package/dist/src/packing.js +31 -0
  476. package/dist/src/packing.js.map +1 -0
  477. package/dist/src/passes.d.ts +16 -0
  478. package/dist/src/passes.d.ts.map +1 -0
  479. package/dist/src/passes.js +104 -0
  480. package/dist/src/passes.js.map +1 -0
  481. package/dist/src/passtasks.d.ts +68 -0
  482. package/dist/src/passtasks.d.ts.map +1 -0
  483. package/dist/src/passtasks.js +360 -0
  484. package/dist/src/passtasks.js.map +1 -0
  485. package/dist/src/pathinside.d.ts +5 -0
  486. package/dist/src/pathinside.d.ts.map +1 -0
  487. package/dist/src/pathinside.js +9 -0
  488. package/dist/src/pathinside.js.map +1 -0
  489. package/dist/src/pibuiltins.d.ts +36 -0
  490. package/dist/src/pibuiltins.d.ts.map +1 -0
  491. package/dist/src/pibuiltins.js +83 -0
  492. package/dist/src/pibuiltins.js.map +1 -0
  493. package/dist/src/plankey.d.ts +4 -0
  494. package/dist/src/plankey.d.ts.map +1 -0
  495. package/dist/src/plankey.js +10 -0
  496. package/dist/src/plankey.js.map +1 -0
  497. package/dist/src/planner.d.ts +375 -0
  498. package/dist/src/planner.d.ts.map +1 -0
  499. package/dist/src/planner.js +722 -0
  500. package/dist/src/planner.js.map +1 -0
  501. package/dist/src/plugin/args.d.ts +19 -0
  502. package/dist/src/plugin/args.d.ts.map +1 -0
  503. package/dist/src/plugin/args.js +107 -0
  504. package/dist/src/plugin/args.js.map +1 -0
  505. package/dist/src/plugin/index.d.ts +3 -0
  506. package/dist/src/plugin/index.d.ts.map +1 -0
  507. package/dist/src/plugin/index.js +14 -0
  508. package/dist/src/plugin/index.js.map +1 -0
  509. package/dist/src/plugin/login.d.ts +39 -0
  510. package/dist/src/plugin/login.d.ts.map +1 -0
  511. package/dist/src/plugin/login.js +73 -0
  512. package/dist/src/plugin/login.js.map +1 -0
  513. package/dist/src/plugin/review.d.ts +27 -0
  514. package/dist/src/plugin/review.d.ts.map +1 -0
  515. package/dist/src/plugin/review.js +298 -0
  516. package/dist/src/plugin/review.js.map +1 -0
  517. package/dist/src/plugin/runner.d.ts +6 -0
  518. package/dist/src/plugin/runner.d.ts.map +1 -0
  519. package/dist/src/plugin/runner.js +65 -0
  520. package/dist/src/plugin/runner.js.map +1 -0
  521. package/dist/src/plugin/scan.d.ts +79 -0
  522. package/dist/src/plugin/scan.d.ts.map +1 -0
  523. package/dist/src/plugin/scan.js +348 -0
  524. package/dist/src/plugin/scan.js.map +1 -0
  525. package/dist/src/plugin/session.d.ts +56 -0
  526. package/dist/src/plugin/session.d.ts.map +1 -0
  527. package/dist/src/plugin/session.js +2 -0
  528. package/dist/src/plugin/session.js.map +1 -0
  529. package/dist/src/plugin/setup.d.ts +19 -0
  530. package/dist/src/plugin/setup.d.ts.map +1 -0
  531. package/dist/src/plugin/setup.js +142 -0
  532. package/dist/src/plugin/setup.js.map +1 -0
  533. package/dist/src/plugin/versiongate.d.ts +26 -0
  534. package/dist/src/plugin/versiongate.d.ts.map +1 -0
  535. package/dist/src/plugin/versiongate.js +83 -0
  536. package/dist/src/plugin/versiongate.js.map +1 -0
  537. package/dist/src/postingkey.d.ts +8 -0
  538. package/dist/src/postingkey.d.ts.map +1 -0
  539. package/dist/src/postingkey.js +25 -0
  540. package/dist/src/postingkey.js.map +1 -0
  541. package/dist/src/postingpolicy.d.ts +108 -0
  542. package/dist/src/postingpolicy.d.ts.map +1 -0
  543. package/dist/src/postingpolicy.js +341 -0
  544. package/dist/src/postingpolicy.js.map +1 -0
  545. package/dist/src/pr-identity.d.ts +3 -0
  546. package/dist/src/pr-identity.d.ts.map +1 -0
  547. package/dist/src/pr-identity.js +9 -0
  548. package/dist/src/pr-identity.js.map +1 -0
  549. package/dist/src/prdelta.d.ts +181 -0
  550. package/dist/src/prdelta.d.ts.map +1 -0
  551. package/dist/src/prdelta.js +501 -0
  552. package/dist/src/prdelta.js.map +1 -0
  553. package/dist/src/pricing.d.ts +94 -0
  554. package/dist/src/pricing.d.ts.map +1 -0
  555. package/dist/src/pricing.js +209 -0
  556. package/dist/src/pricing.js.map +1 -0
  557. package/dist/src/priorfindings.d.ts +167 -0
  558. package/dist/src/priorfindings.d.ts.map +1 -0
  559. package/dist/src/priorfindings.js +445 -0
  560. package/dist/src/priorfindings.js.map +1 -0
  561. package/dist/src/priortasks.d.ts +31 -0
  562. package/dist/src/priortasks.d.ts.map +1 -0
  563. package/dist/src/priortasks.js +119 -0
  564. package/dist/src/priortasks.js.map +1 -0
  565. package/dist/src/profilelookup.d.ts +59 -0
  566. package/dist/src/profilelookup.d.ts.map +1 -0
  567. package/dist/src/profilelookup.js +98 -0
  568. package/dist/src/profilelookup.js.map +1 -0
  569. package/dist/src/profileoverrides.d.ts +91 -0
  570. package/dist/src/profileoverrides.d.ts.map +1 -0
  571. package/dist/src/profileoverrides.js +313 -0
  572. package/dist/src/profileoverrides.js.map +1 -0
  573. package/dist/src/profiles.d.ts +144 -0
  574. package/dist/src/profiles.d.ts.map +1 -0
  575. package/dist/src/profiles.js +604 -0
  576. package/dist/src/profiles.js.map +1 -0
  577. package/dist/src/promptdoc.d.ts +3 -0
  578. package/dist/src/promptdoc.d.ts.map +1 -0
  579. package/dist/src/promptdoc.js +18 -0
  580. package/dist/src/promptdoc.js.map +1 -0
  581. package/dist/src/prtarget.d.ts +70 -0
  582. package/dist/src/prtarget.d.ts.map +1 -0
  583. package/dist/src/prtarget.js +181 -0
  584. package/dist/src/prtarget.js.map +1 -0
  585. package/dist/src/recheckorder.d.ts +32 -0
  586. package/dist/src/recheckorder.d.ts.map +1 -0
  587. package/dist/src/recheckorder.js +5 -0
  588. package/dist/src/recheckorder.js.map +1 -0
  589. package/dist/src/reviewapi.d.ts +207 -0
  590. package/dist/src/reviewapi.d.ts.map +1 -0
  591. package/dist/src/reviewapi.js +939 -0
  592. package/dist/src/reviewapi.js.map +1 -0
  593. package/dist/src/reviewbotfindings.d.ts +33 -0
  594. package/dist/src/reviewbotfindings.d.ts.map +1 -0
  595. package/dist/src/reviewbotfindings.js +80 -0
  596. package/dist/src/reviewbotfindings.js.map +1 -0
  597. package/dist/src/reviewconfig.d.ts +741 -0
  598. package/dist/src/reviewconfig.d.ts.map +1 -0
  599. package/dist/src/reviewconfig.js +797 -0
  600. package/dist/src/reviewconfig.js.map +1 -0
  601. package/dist/src/reviewdelta.d.ts +51 -0
  602. package/dist/src/reviewdelta.d.ts.map +1 -0
  603. package/dist/src/reviewdelta.js +119 -0
  604. package/dist/src/reviewdelta.js.map +1 -0
  605. package/dist/src/reviewdest.d.ts +86 -0
  606. package/dist/src/reviewdest.d.ts.map +1 -0
  607. package/dist/src/reviewdest.js +142 -0
  608. package/dist/src/reviewdest.js.map +1 -0
  609. package/dist/src/reviewerstub.d.ts +12 -0
  610. package/dist/src/reviewerstub.d.ts.map +1 -0
  611. package/dist/src/reviewerstub.js +28 -0
  612. package/dist/src/reviewerstub.js.map +1 -0
  613. package/dist/src/reviewhost.d.ts +58 -0
  614. package/dist/src/reviewhost.d.ts.map +1 -0
  615. package/dist/src/reviewhost.js +135 -0
  616. package/dist/src/reviewhost.js.map +1 -0
  617. package/dist/src/reviewpost.d.ts +79 -0
  618. package/dist/src/reviewpost.d.ts.map +1 -0
  619. package/dist/src/reviewpost.js +233 -0
  620. package/dist/src/reviewpost.js.map +1 -0
  621. package/dist/src/reviewrender.d.ts +154 -0
  622. package/dist/src/reviewrender.d.ts.map +1 -0
  623. package/dist/src/reviewrender.js +480 -0
  624. package/dist/src/reviewrender.js.map +1 -0
  625. package/dist/src/reviewstate.d.ts +62 -0
  626. package/dist/src/reviewstate.d.ts.map +1 -0
  627. package/dist/src/reviewstate.js +167 -0
  628. package/dist/src/reviewstate.js.map +1 -0
  629. package/dist/src/reviewstore.d.ts +17 -0
  630. package/dist/src/reviewstore.d.ts.map +1 -0
  631. package/dist/src/reviewstore.js +105 -0
  632. package/dist/src/reviewstore.js.map +1 -0
  633. package/dist/src/round-progress.d.ts +120 -0
  634. package/dist/src/round-progress.d.ts.map +1 -0
  635. package/dist/src/round-progress.js +172 -0
  636. package/dist/src/round-progress.js.map +1 -0
  637. package/dist/src/round-stage-deadlines.d.ts +12 -0
  638. package/dist/src/round-stage-deadlines.d.ts.map +1 -0
  639. package/dist/src/round-stage-deadlines.js +10 -0
  640. package/dist/src/round-stage-deadlines.js.map +1 -0
  641. package/dist/src/session-command.d.ts +19 -0
  642. package/dist/src/session-command.d.ts.map +1 -0
  643. package/dist/src/session-command.js +20 -0
  644. package/dist/src/session-command.js.map +1 -0
  645. package/dist/src/settledread.d.ts +61 -0
  646. package/dist/src/settledread.d.ts.map +1 -0
  647. package/dist/src/settledread.js +135 -0
  648. package/dist/src/settledread.js.map +1 -0
  649. package/dist/src/severity.d.ts +167 -0
  650. package/dist/src/severity.d.ts.map +1 -0
  651. package/dist/src/severity.js +364 -0
  652. package/dist/src/severity.js.map +1 -0
  653. package/dist/src/severityrank.d.ts +8 -0
  654. package/dist/src/severityrank.d.ts.map +1 -0
  655. package/dist/src/severityrank.js +16 -0
  656. package/dist/src/severityrank.js.map +1 -0
  657. package/dist/src/standing-review.d.ts +45 -0
  658. package/dist/src/standing-review.d.ts.map +1 -0
  659. package/dist/src/standing-review.js +43 -0
  660. package/dist/src/standing-review.js.map +1 -0
  661. package/dist/src/storerows.d.ts +225 -0
  662. package/dist/src/storerows.d.ts.map +1 -0
  663. package/dist/src/storerows.js +7 -0
  664. package/dist/src/storerows.js.map +1 -0
  665. package/dist/src/styleguide.d.ts +25 -0
  666. package/dist/src/styleguide.d.ts.map +1 -0
  667. package/dist/src/styleguide.js +272 -0
  668. package/dist/src/styleguide.js.map +1 -0
  669. package/dist/src/sweepstatus.d.ts +42 -0
  670. package/dist/src/sweepstatus.d.ts.map +1 -0
  671. package/dist/src/sweepstatus.js +97 -0
  672. package/dist/src/sweepstatus.js.map +1 -0
  673. package/dist/src/templates.d.ts +243 -0
  674. package/dist/src/templates.d.ts.map +1 -0
  675. package/dist/src/templates.js +847 -0
  676. package/dist/src/templates.js.map +1 -0
  677. package/dist/src/types.d.ts +639 -0
  678. package/dist/src/types.d.ts.map +1 -0
  679. package/dist/src/types.js +90 -0
  680. package/dist/src/types.js.map +1 -0
  681. package/dist/src/unifieddiff.d.ts +22 -0
  682. package/dist/src/unifieddiff.d.ts.map +1 -0
  683. package/dist/src/unifieddiff.js +176 -0
  684. package/dist/src/unifieddiff.js.map +1 -0
  685. package/dist/src/yieldloop.d.ts +2 -0
  686. package/dist/src/yieldloop.d.ts.map +1 -0
  687. package/dist/src/yieldloop.js +14 -0
  688. package/dist/src/yieldloop.js.map +1 -0
  689. package/package.json +60 -4
@@ -0,0 +1,378 @@
1
+ // The in-process file tools' fence. The SDK session's read, grep, find,
2
+ // ls, edit and write tools run inside the Node process that holds the GitHub
3
+ // token and the login, as the run uid, so a path they are given must not lead
4
+ // to the places that hold them:
5
+ //
6
+ // /proc/* the token holder's own environ, mem, cmdline and fds
7
+ // /run/qcr-in where the caller staged the token (read once and unlinked,
8
+ // but the mount is the caller's)
9
+ // the agent dir the run's login copy, models and settings
10
+ // credentials the secrets dirs (the App key, the webhook secret, the
11
+ // OpenViking keys), the IPC run dirs and the sessions'
12
+ // ovcli.conf (credentialPaths)
13
+ //
14
+ // The model's bash runs as another uid (tooluid.ts) and so cannot reach them;
15
+ // these tools can. Plain path matching is not enough: bash, as the tool uid,
16
+ // can plant a symlink in the worktree that points at a fenced path. So the
17
+ // fence resolves the target first: the real path of the file, or, for one that
18
+ // does not exist yet (a write), of its parent directory, following a dangling
19
+ // final symlink too (a write follows it). Both the path as given and the
20
+ // resolved one must be clear of the fence.
21
+ //
22
+ // The tools are built with pi's own `operations` hook, so each file is opened
23
+ // by this module: a read opens the file first and checks what the descriptor
24
+ // really is (/proc/self/fd), so a symlink swapped in after the path check
25
+ // still lands on a refusal. grep and find hand their search root to ripgrep
26
+ // and fd, which pi starts itself as the run uid and do not follow symlinks;
27
+ // those two are checked before the tool runs: the root, and that no fenced
28
+ // path lies below it.
29
+ import { constants, lstatSync, readlinkSync, realpathSync } from "node:fs";
30
+ import { mkdir, open, stat, readdir, access } from "node:fs/promises";
31
+ import { basename, dirname, isAbsolute, join, resolve } from "node:path";
32
+ import { fileURLToPath } from "node:url";
33
+ import { defaultSecretPathContext } from "../../extensions/bash-guard.js";
34
+ /** What no file tool may reach, besides the run's agent dirs. `/qcr-login` is
35
+ * where the wrapper and the Action mount the owner's login volume: its
36
+ * auth.json holds the long-lived refresh token and is group-readable by the
37
+ * run uid, whose group the in-process file tools (unlike the tool uid's bash)
38
+ * keep. */
39
+ export const FENCED_PATHS = ["/proc", "/dev/fd", "/run/qcr-in", "/qcr-login"];
40
+ /** The directories `env` names as the login's source: the process's own pi
41
+ * agent dir (`PI_CODING_AGENT_DIR`, which a review copies into its private
42
+ * agent dir) and the scan's `QCR_SCAN_AUTH_SRC`. The round's copy is the
43
+ * host's agent dir, fenced separately. */
44
+ export function loginSourceDirs(env) {
45
+ return ["PI_CODING_AGENT_DIR", "QCR_SCAN_AUTH_SRC"]
46
+ .map((k) => env[k]?.trim())
47
+ .filter((v) => v !== undefined && v !== "" && isAbsolute(v));
48
+ }
49
+ /**
50
+ * The credentials an `env` points at, which no file tool may reach:
51
+ *
52
+ * - every secrets dir this install could be using: the App's private key, the
53
+ * webhook secret and the OpenViking keys live there. The list is the bash
54
+ * guard's own (`defaultSecretPathContext`, which mirrors the install
55
+ * locator: `$QCR_SECRETS_MOUNT`, the container mount, `$QC_SECRETS_DIR`,
56
+ * `<config home>/secrets`, a `[github] secrets_dir` read from
57
+ * `$QCR_CONFIG`, and the legacy dir), so the shell belt and this fence
58
+ * name the same places;
59
+ * - the daemon's IPC run dirs (the socket and the capability launch files);
60
+ * - the memory CLI config the env names (`OPENVIKING_CLI_CONFIG_FILE`, the
61
+ * sessions' ovcli.conf): it holds the reviewer key, which the in-process
62
+ * memory extension reads itself and the model has no use for.
63
+ *
64
+ * Our own code reads these with plain fs calls, never through the tools, so
65
+ * fencing them takes nothing away from it. Every absolute path, deduplicated;
66
+ * a path that does not exist is fenced lexically and by its resolved prefix.
67
+ */
68
+ export function credentialPaths(...envs) {
69
+ const out = new Set();
70
+ for (const env of envs) {
71
+ const ctx = defaultSecretPathContext(env, "/");
72
+ for (const d of [...ctx.dirs, ...(ctx.runDirs ?? [])])
73
+ out.add(d);
74
+ const ovcli = env["OPENVIKING_CLI_CONFIG_FILE"]?.trim();
75
+ if (ovcli !== undefined && isAbsolute(ovcli))
76
+ out.add(resolve(ovcli));
77
+ }
78
+ return [...out];
79
+ }
80
+ /** The names of the file tools behind the fence. */
81
+ export const FENCED_TOOLS = ["read", "grep", "find", "ls", "edit", "write"];
82
+ /** A path the fence refuses; `message` is what the model reads. */
83
+ export class ToolFenceError extends Error {
84
+ constructor(path) {
85
+ super(`${path}: access refused (it leads into a fenced path)`);
86
+ this.name = "ToolFenceError";
87
+ }
88
+ }
89
+ const MAX_LINKS = 40;
90
+ function within(path, root) {
91
+ return path === root || path.startsWith(root.endsWith("/") ? root : root + "/");
92
+ }
93
+ /** The real path of `p`, which need not exist: the longest existing prefix is
94
+ * resolved, and a dangling symlink is followed to where it would lead. */
95
+ function realOrIntended(p, links = 0) {
96
+ if (links > MAX_LINKS)
97
+ throw new Error(`${p}: too many levels of symbolic links`);
98
+ try {
99
+ return realpathSync(p);
100
+ }
101
+ catch (e) {
102
+ if (e.code !== "ENOENT")
103
+ throw e;
104
+ }
105
+ const parent = dirname(p);
106
+ if (parent === p)
107
+ return p;
108
+ let link;
109
+ try {
110
+ if (lstatSync(p).isSymbolicLink())
111
+ link = readlinkSync(p);
112
+ }
113
+ catch {
114
+ // not there at all
115
+ }
116
+ const base = realOrIntended(parent, links + 1);
117
+ if (link !== undefined)
118
+ return realOrIntended(resolve(base, link), links + 1);
119
+ return join(base, basename(p));
120
+ }
121
+ /** A fence over the fixed paths and the given directories. */
122
+ export function createToolFence(o = {}) {
123
+ const roots = () => {
124
+ const out = new Set();
125
+ for (const r of [...FENCED_PATHS, ...(o.dirs ?? [])]) {
126
+ out.add(r);
127
+ try {
128
+ out.add(realpathSync(r));
129
+ }
130
+ catch {
131
+ // not there: the lexical form is all there is
132
+ }
133
+ }
134
+ return [...out];
135
+ };
136
+ const fenced = (p) => roots().some((r) => within(p, r));
137
+ return {
138
+ check(path) {
139
+ const abs = resolve(path);
140
+ let real;
141
+ try {
142
+ real = realOrIntended(abs);
143
+ }
144
+ catch (e) {
145
+ // A path that cannot be resolved cannot be shown clear of the fence.
146
+ if (e instanceof ToolFenceError)
147
+ throw e;
148
+ throw new ToolFenceError(path);
149
+ }
150
+ if (fenced(abs) || fenced(real))
151
+ throw new ToolFenceError(path);
152
+ },
153
+ checkTree(path) {
154
+ this.check(path);
155
+ const abs = resolve(path);
156
+ const real = realOrIntended(abs);
157
+ if (roots().some((r) => within(r, abs) || within(r, real)))
158
+ throw new ToolFenceError(path);
159
+ },
160
+ checkOpened(fd, path) {
161
+ let real;
162
+ try {
163
+ real = realpathSync(`/proc/self/fd/${fd}`);
164
+ }
165
+ catch {
166
+ return;
167
+ }
168
+ if (fenced(real))
169
+ throw new ToolFenceError(path);
170
+ },
171
+ checkWrite(path) {
172
+ this.check(path);
173
+ const guard = o.protectedWrite;
174
+ if (guard === undefined)
175
+ return;
176
+ const abs = resolve(path);
177
+ let real;
178
+ try {
179
+ real = realOrIntended(abs);
180
+ }
181
+ catch {
182
+ throw new ToolFenceError(path);
183
+ }
184
+ if (real !== abs && guard(real))
185
+ throw new ToolFenceError(path);
186
+ },
187
+ checkWriteOpened(fd, path) {
188
+ this.checkOpened(fd, path);
189
+ const guard = o.protectedWrite;
190
+ if (guard === undefined)
191
+ return;
192
+ let real;
193
+ try {
194
+ real = realpathSync(`/proc/self/fd/${fd}`);
195
+ }
196
+ catch {
197
+ return;
198
+ }
199
+ if (real !== resolve(path) && guard(real))
200
+ throw new ToolFenceError(path);
201
+ },
202
+ };
203
+ }
204
+ // ---- the paths as pi reads them -------------------------------------------------
205
+ // pi's UNICODE_SPACES (utils/paths.js): the no-break and typographic spaces
206
+ const SPACE_CODES = [
207
+ 0x00a0,
208
+ ...Array.from({ length: 11 }, (_, i) => 0x2000 + i),
209
+ 0x202f,
210
+ 0x205f,
211
+ 0x3000,
212
+ ];
213
+ const UNICODE_SPACES = new RegExp(`[${SPACE_CODES.map((c) => String.fromCharCode(c)).join("")}]`, "g");
214
+ /** A tool's `path` argument as pi resolves it (utils/paths.js resolvePath with
215
+ * unicode spaces and the `@` prefix normalised, `~` and file: URLs expanded).
216
+ * `home` is the home pi expands `~` against, as the host resolved it; without
217
+ * one a `~` path cannot be shown clear of the fence and is refused. */
218
+ export function toolPath(input, cwd, home) {
219
+ let p = input.replace(UNICODE_SPACES, " ");
220
+ if (p.startsWith("@"))
221
+ p = p.slice(1);
222
+ if ((p === "~" || p.startsWith("~/")) && home === undefined)
223
+ throw new ToolFenceError(input);
224
+ if (p === "~")
225
+ p = home;
226
+ else if (p.startsWith("~/"))
227
+ p = join(home, p.slice(2));
228
+ else if (/^file:\/\//.test(p))
229
+ p = fileURLToPath(p);
230
+ return isAbsolute(p) ? resolve(p) : resolve(cwd, p);
231
+ }
232
+ // ---- the operations ---------------------------------------------------------------
233
+ const MIME_SNIFF_BYTES = 4100;
234
+ /** Opens `path` for reading, checks what was opened, and gives the handle. */
235
+ async function openChecked(fence, path, flags) {
236
+ fence.check(path);
237
+ const fh = await open(path, flags);
238
+ try {
239
+ fence.checkOpened(fh.fd, path);
240
+ }
241
+ catch (e) {
242
+ await fh.close();
243
+ throw e;
244
+ }
245
+ return fh;
246
+ }
247
+ async function readChecked(fence, path) {
248
+ const fh = await openChecked(fence, path, constants.O_RDONLY);
249
+ try {
250
+ return await fh.readFile();
251
+ }
252
+ finally {
253
+ await fh.close();
254
+ }
255
+ }
256
+ async function writeChecked(fence, path, content) {
257
+ // No truncation at open: nothing is cut before the descriptor is known to be
258
+ // clear — of the fence, and of a protected target a symlink led it to (a link
259
+ // swapped in after the path check still lands on a refusal here).
260
+ fence.checkWrite(path);
261
+ const fh = await open(path, constants.O_WRONLY | constants.O_CREAT);
262
+ try {
263
+ fence.checkWriteOpened(fh.fd, path);
264
+ }
265
+ catch (e) {
266
+ await fh.close();
267
+ throw e;
268
+ }
269
+ try {
270
+ await fh.truncate(0);
271
+ await fh.writeFile(content, "utf-8");
272
+ }
273
+ finally {
274
+ await fh.close();
275
+ }
276
+ }
277
+ function readOperations(fence, sniff) {
278
+ return {
279
+ readFile: (p) => readChecked(fence, p),
280
+ access: async (p) => {
281
+ fence.check(p);
282
+ await access(p, constants.R_OK);
283
+ },
284
+ detectImageMimeType: async (p) => {
285
+ if (sniff === null)
286
+ return null;
287
+ const fh = await openChecked(fence, p, constants.O_RDONLY);
288
+ try {
289
+ const buf = Buffer.alloc(MIME_SNIFF_BYTES);
290
+ const { bytesRead } = await fh.read(buf, 0, MIME_SNIFF_BYTES, 0);
291
+ return sniff(buf.subarray(0, bytesRead)) ?? null;
292
+ }
293
+ finally {
294
+ await fh.close();
295
+ }
296
+ },
297
+ };
298
+ }
299
+ function editOperations(fence) {
300
+ return {
301
+ readFile: (p) => readChecked(fence, p),
302
+ writeFile: (p, content) => writeChecked(fence, p, content),
303
+ access: async (p) => {
304
+ fence.check(p);
305
+ await access(p, constants.R_OK | constants.W_OK);
306
+ },
307
+ };
308
+ }
309
+ function writeOperations(fence) {
310
+ return {
311
+ writeFile: (p, content) => writeChecked(fence, p, content),
312
+ mkdir: async (dir) => {
313
+ fence.checkWrite(dir);
314
+ await mkdir(dir, { recursive: true });
315
+ },
316
+ };
317
+ }
318
+ function grepOperations(fence) {
319
+ return {
320
+ isDirectory: async (p) => {
321
+ fence.check(p);
322
+ return (await stat(p)).isDirectory();
323
+ },
324
+ readFile: async (p) => (await readChecked(fence, p)).toString("utf-8"),
325
+ };
326
+ }
327
+ function lsOperations(fence) {
328
+ const checked = (f) => async (p) => {
329
+ fence.check(p);
330
+ return f(p);
331
+ };
332
+ return {
333
+ exists: async (p) => {
334
+ fence.check(p);
335
+ try {
336
+ await access(p);
337
+ return true;
338
+ }
339
+ catch {
340
+ return false;
341
+ }
342
+ },
343
+ stat: checked((p) => stat(p)),
344
+ readdir: checked((p) => readdir(p)),
345
+ };
346
+ }
347
+ /** The `operations` of each file tool that takes them, every file opened through
348
+ * the fence. `sniff` tells images from their first bytes; without it a file is
349
+ * always read as text. find has none: it starts fd on its search root. */
350
+ export function fencedOperations(fence, sniff) {
351
+ return {
352
+ read: readOperations(fence, sniff),
353
+ grep: grepOperations(fence),
354
+ ls: lsOperations(fence),
355
+ edit: editOperations(fence),
356
+ write: writeOperations(fence),
357
+ };
358
+ }
359
+ /** `def` with a check of its `path` argument ahead of its execution: the
360
+ * refusal says what it is, and the tools that start ripgrep and fd (which
361
+ * `operations` does not reach) are covered. */
362
+ export function guardedTool(def, fence, cwd, home) {
363
+ const run = def.execute;
364
+ return {
365
+ ...def,
366
+ execute: (id, params, signal, onUpdate, ctx) => {
367
+ const given = params.path;
368
+ const root = toolPath(typeof given === "string" && given !== "" ? given : ".", ctx?.cwd || cwd, home);
369
+ // grep and find walk the whole tree under the root.
370
+ if (def.name === "grep" || def.name === "find")
371
+ fence.checkTree(root);
372
+ else
373
+ fence.check(root);
374
+ return run(id, params, signal, onUpdate, ctx);
375
+ },
376
+ };
377
+ }
378
+ //# sourceMappingURL=toolfence.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"toolfence.js","sourceRoot":"","sources":["../../../src/engine/toolfence.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,128 @@
1
+ import type { BashOperations } from "@earendil-works/pi-coding-agent";
2
+ /** The names the image's entrypoint sets when the model's tools must run as
3
+ * another uid than this process. */
4
+ export declare const TOOL_UID_ENVS: readonly ["QCR_TOOL_UID", "QCR_TOOL_GID", "QCR_TOOL_UID_REQUIRED"];
5
+ /** The uid and gid the model's tools run as: non-zero numeric ids. */
6
+ export interface ToolIds {
7
+ uid: string;
8
+ gid: string;
9
+ }
10
+ /** What the environment says about the tool uid: the ids to run the tools as, or
11
+ * null where nothing asks for a separation, or why none can be made. Where the
12
+ * ids are named they win, whatever else is set. */
13
+ export declare function toolIdsOf(env: NodeJS.ProcessEnv): ToolIds | {
14
+ refused: string;
15
+ } | null;
16
+ /** setpriv's switches for the tool uid: its uid and gid with no supplementary
17
+ * groups, no capability, and no way to gain one. Does not include `--`. */
18
+ export declare function setprivSwitches(ids: ToolIds): string[];
19
+ /** How a child that runs the model's tools is started: through setpriv where the
20
+ * image asks for the tool uid, unchanged where nothing does, refused where the
21
+ * entrypoint could not arrange it. */
22
+ export declare function toolIsolation(bin: string, argv: string[], procEnv?: NodeJS.ProcessEnv): {
23
+ bin: string;
24
+ argv: string[];
25
+ isolated: boolean;
26
+ } | {
27
+ refused: string;
28
+ };
29
+ /** The gate in front of a host that runs the model's tools.
30
+ *
31
+ * A host that starts them itself through the tool uid (`isolated`: the SDK
32
+ * runtime's bash, a debug round's pi) passes where the ids are numeric and
33
+ * non-zero, and is refused where the entrypoint could not arrange the split.
34
+ *
35
+ * A host that cannot (its tools are children of a process that runs in this
36
+ * uid, such as the native lens tool's pi children) refuses wherever the image
37
+ * asks for the separation, unless the shared uid is accepted. `host` words the
38
+ * refusal for the caller. */
39
+ export declare function checkToolUid(env: NodeJS.ProcessEnv, host?: {
40
+ what: string;
41
+ instead: string;
42
+ isolated?: boolean;
43
+ }): void;
44
+ /**
45
+ * Opens `dir` and everything in it to the tool uid's group: group read and
46
+ * write on files, and group access on directories, each entry handed to the
47
+ * tool gid (`QCR_TOOL_GID`) where that is not this process's own gid (the
48
+ * bot's tools run in a gid of their own; the cli's share the run
49
+ * gid). For a process that runs as the tool uid and needs what the run uid
50
+ * made private (a debug round's pi reading its agent dir); the owner's bits
51
+ * stay. Symbolic links are left as they are, and a missing dir is nothing to
52
+ * share.
53
+ */
54
+ export declare function shareWithToolGroup(dir: string, env?: NodeJS.ProcessEnv): void;
55
+ /**
56
+ * The environment a command run as the tool uid needs on top of the one it was
57
+ * given: git's `safe.directory = *` in the command scope.
58
+ *
59
+ * The repositories the model reads (the worktrees, the base clone) belong to the
60
+ * run uid, and git refuses a repository another uid owns ("dubious ownership").
61
+ * The image's system config says `*`, but a review session pins git's system
62
+ * scope off (src/sessions.ts sessionGitConfigPins), and `safe.directory` is read
63
+ * only from a protected scope: system, global or command. So it rides the
64
+ * command scope (GIT_CONFIG_COUNT/KEY_n/VALUE_n), appended after any entries the
65
+ * env already carries, never in place of them. It widens nothing: the
66
+ * repositories are the run uid's, which the tool uid trusts by construction.
67
+ */
68
+ export declare function toolUidEnv(env: NodeJS.ProcessEnv): NodeJS.ProcessEnv;
69
+ /** The umask a tool-uid command runs under: group-writable files, which is how
70
+ * the run uid and the tool uid (one gid, two uids) share what either writes. */
71
+ export declare const TOOL_UMASK = 2;
72
+ /** The setpriv the spawner runs, which holds the ambient SETUID/SETGID: an
73
+ * absolute path in a system dir. A PATH entry the tool uid can write must not
74
+ * be able to plant the binary the next command runs with those capabilities.
75
+ * Null where no system dir has one. */
76
+ export declare function trustedSetpriv(exists?: (p: string) => boolean, env?: NodeJS.ProcessEnv): string | null;
77
+ /**
78
+ * The bot's setid helper, named by `QCR_SETPRIV_BIN`: the image's
79
+ * own copy of setpriv that carries CAP_SETUID/CAP_SETGID as FILE capabilities
80
+ * and only a gate group may run (docker/Dockerfile). The always-on bot runs as
81
+ * its own uid, not root, so `docker exec` into it keeps landing as that uid; it
82
+ * reaches the tool uid through this helper instead of ambient capabilities
83
+ * (docker/entrypoint.sh's daemon mode). The model's tools never get it: they run
84
+ * with no_new_privs, under which a file capability grants nothing, and without
85
+ * the gate group.
86
+ *
87
+ * Trusted only as a root-owned regular file in a root-owned directory, neither
88
+ * writable by group or others: the run uid must not be able to swap the binary
89
+ * it hands its capabilities to. Null where the env names none; `refused` where
90
+ * it names one that fails those checks.
91
+ */
92
+ export declare function setidHelperOf(env: NodeJS.ProcessEnv, stat?: (p: string) => {
93
+ uid: number;
94
+ mode: number;
95
+ isFile(): boolean;
96
+ isDirectory(): boolean;
97
+ } | undefined): {
98
+ path: string;
99
+ } | {
100
+ refused: string;
101
+ } | null;
102
+ /** The stdio of a command: nothing in, its output out, and each of `inherit`
103
+ * handed to it at the SAME fd number. Node closes every descriptor a child is
104
+ * not listed with, so an fd a command (or a script under it) must read has to be
105
+ * named here. */
106
+ export declare function commandStdio(inherit: readonly number[]): Array<"ignore" | "pipe" | number>;
107
+ /**
108
+ * The SDK bash tool's execution, with the model's command run as the tool uid.
109
+ *
110
+ * The command is `setpriv … -- bash -c <command>` in a process group of its
111
+ * own, the umask set first (TOOL_UMASK) and git's safe.directory in its env
112
+ * (toolUidEnv). A timeout or an abort ends that group through setpriv too: the run uid
113
+ * may not signal a process of another uid (kill(2): the sender's uid must match
114
+ * the target's real or saved uid, and this process holds no CAP_KILL), so pi's
115
+ * own kill of the tree would silently do nothing and the command would run on.
116
+ * The saved uid cannot be left as the run uid to allow it: the tool could then
117
+ * switch back.
118
+ *
119
+ * `inherit` lists descriptors every command gets at the same number (the
120
+ * bot worker's IPC capability).
121
+ */
122
+ export declare function isolatedBashOperations(ids: ToolIds, setprivBin?: string, inherit?: readonly number[]): BashOperations;
123
+ /** The same execution with no uid change, for a host whose commands must
124
+ * inherit descriptors (`inherit`): pi's own local operations start a command
125
+ * with nothing but stdio. The command runs in a process group of its own, which
126
+ * a timeout or an abort ends. */
127
+ export declare function inheritingBashOperations(inherit: readonly number[]): BashOperations;
128
+ //# sourceMappingURL=tooluid.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"tooluid.d.ts","sourceRoot":"","sources":["../../../src/engine/tooluid.ts"],"names":[],"mappings":"AA6BA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iCAAiC,CAAC;AAEtE;oCACoC;AACpC,eAAO,MAAM,aAAa,oEAAqE,CAAC;AAEhG,sEAAsE;AACtE,MAAM,WAAW,OAAO;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,GAAG,EAAE,MAAM,CAAC;CACb;AAID;;mDAEmD;AACnD,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,CAAC,UAAU,GAAG,OAAO,GAAG;IAAE,OAAO,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAiBtF;AAED;2EAC2E;AAC3E,wBAAgB,eAAe,CAAC,GAAG,EAAE,OAAO,GAAG,MAAM,EAAE,CAStD;AAED;;sCAEsC;AACtC,wBAAgB,aAAa,CAC3B,GAAG,EAAE,MAAM,EACX,IAAI,EAAE,MAAM,EAAE,EACd,OAAO,GAAE,MAAM,CAAC,UAAwB,GACvC;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,EAAE,CAAC;IAAC,QAAQ,EAAE,OAAO,CAAA;CAAE,GAAG;IAAE,OAAO,EAAE,MAAM,CAAA;CAAE,CAY1E;AAED;;;;;;;;;6BAS6B;AAC7B,wBAAgB,YAAY,CAC1B,GAAG,EAAE,MAAM,CAAC,UAAU,EACtB,IAAI,GAAE;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,EAAE,OAAO,CAAA;CAGxD,GACA,IAAI,CAaN;AAED;;;;;;;;;GASG;AACH,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,GAAE,MAAM,CAAC,UAAwB,GAAG,IAAI,CAe1F;AAED;;;;;;;;;;;;GAYG;AACH,wBAAgB,UAAU,CAAC,GAAG,EAAE,MAAM,CAAC,UAAU,GAAG,MAAM,CAAC,UAAU,CASpE;AAED;gFACgF;AAChF,eAAO,MAAM,UAAU,IAAQ,CAAC;AAYhC;;;uCAGuC;AACvC,wBAAgB,cAAc,CAC5B,MAAM,GAAE,CAAC,CAAC,EAAE,MAAM,KAAK,OAAoB,EAC3C,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,MAAM,GAAG,IAAI,CAIf;AAED;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,aAAa,CAC3B,GAAG,EAAE,MAAM,CAAC,UAAU,EACtB,IAAI,GAAE,CACJ,CAAC,EAAE,MAAM,KACN;IAAE,GAAG,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,IAAI,OAAO,CAAC;IAAC,WAAW,IAAI,OAAO,CAAA;CAAE,GAAG,SACvC,GACxC;IAAE,IAAI,EAAE,MAAM,CAAA;CAAE,GAAG;IAAE,OAAO,EAAE,MAAM,CAAA;CAAE,GAAG,IAAI,CAiB/C;AAuBD;;;iBAGiB;AACjB,wBAAgB,YAAY,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,GAAG,KAAK,CAAC,QAAQ,GAAG,MAAM,GAAG,MAAM,CAAC,CAQ1F;AAmFD;;;;;;;;;;;;;;GAcG;AACH,wBAAgB,sBAAsB,CACpC,GAAG,EAAE,OAAO,EACZ,UAAU,CAAC,EAAE,MAAM,EACnB,OAAO,GAAE,SAAS,MAAM,EAAO,GAC9B,cAAc,CAsChB;AAED;;;iCAGiC;AACjC,wBAAgB,wBAAwB,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,GAAG,cAAc,CAenF"}