auramaxx 0.0.12 → 0.0.13

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 (334) hide show
  1. package/.next/BUILD_ID +1 -1
  2. package/.next/app-build-manifest.json +244 -227
  3. package/.next/app-path-routes-manifest.json +11 -10
  4. package/.next/build-manifest.json +14 -14
  5. package/.next/prerender-manifest.json +49 -25
  6. package/.next/react-loadable-manifest.json +41 -41
  7. package/.next/routes-manifest.json +6 -0
  8. package/.next/server/app/_not-found/page_client-reference-manifest.js +1 -1
  9. package/.next/server/app/_not-found.html +1 -1
  10. package/.next/server/app/_not-found.rsc +12 -12
  11. package/.next/server/app/api/[...doc]/page_client-reference-manifest.js +1 -1
  12. package/.next/server/app/api/agent-requests/route_client-reference-manifest.js +1 -1
  13. package/.next/server/app/api/apps/install/route_client-reference-manifest.js +1 -1
  14. package/.next/server/app/api/apps/manifests/route_client-reference-manifest.js +1 -1
  15. package/.next/server/app/api/apps/static/[...path]/route_client-reference-manifest.js +1 -1
  16. package/.next/server/app/api/docs/plain/route_client-reference-manifest.js +1 -1
  17. package/.next/server/app/api/events/route.js +1 -19
  18. package/.next/server/app/api/events/route_client-reference-manifest.js +1 -1
  19. package/.next/server/app/api/import-from-openclaw/[channel]/route_client-reference-manifest.js +1 -1
  20. package/.next/server/app/api/import-from-openclaw/route_client-reference-manifest.js +1 -1
  21. package/.next/server/app/api/import-from-openclaw/validate/[channel]/route_client-reference-manifest.js +1 -1
  22. package/.next/server/app/api/page_client-reference-manifest.js +1 -1
  23. package/.next/server/app/api/restart/route_client-reference-manifest.js +1 -1
  24. package/.next/server/app/api/update/route.js +63 -1
  25. package/.next/server/app/api/update/route.js.nft.json +1 -1
  26. package/.next/server/app/api/update/route_client-reference-manifest.js +1 -1
  27. package/.next/server/app/api/version/route_client-reference-manifest.js +1 -1
  28. package/.next/server/app/api/workspace/[id]/apps/[wid]/route_client-reference-manifest.js +1 -1
  29. package/.next/server/app/api/workspace/[id]/apps/route_client-reference-manifest.js +1 -1
  30. package/.next/server/app/api/workspace/[id]/export/route_client-reference-manifest.js +1 -1
  31. package/.next/server/app/api/workspace/[id]/route_client-reference-manifest.js +1 -1
  32. package/.next/server/app/api/workspace/config/route_client-reference-manifest.js +1 -1
  33. package/.next/server/app/api/workspace/import/route_client-reference-manifest.js +1 -1
  34. package/.next/server/app/api/workspace/route_client-reference-manifest.js +1 -1
  35. package/.next/server/app/app-legacy-do-not-use/page.js +1 -1
  36. package/.next/server/app/app-legacy-do-not-use/page.js.nft.json +1 -1
  37. package/.next/server/app/app-legacy-do-not-use/page_client-reference-manifest.js +1 -1
  38. package/.next/server/app/app-legacy-do-not-use.html +1 -1
  39. package/.next/server/app/app-legacy-do-not-use.rsc +14 -14
  40. package/.next/server/app/approve/[actionId]/page.js +1 -1
  41. package/.next/server/app/approve/[actionId]/page_client-reference-manifest.js +1 -1
  42. package/.next/server/app/docs/[...doc]/page_client-reference-manifest.js +1 -1
  43. package/.next/server/app/docs/page_client-reference-manifest.js +1 -1
  44. package/.next/server/app/health/page_client-reference-manifest.js +1 -1
  45. package/.next/server/app/health.html +1 -1
  46. package/.next/server/app/health.rsc +13 -13
  47. package/.next/server/app/hello/page_client-reference-manifest.js +1 -1
  48. package/.next/server/app/hello.html +1 -1
  49. package/.next/server/app/hello.rsc +14 -14
  50. package/.next/server/app/index.html +1 -1
  51. package/.next/server/app/index.rsc +18 -21
  52. package/.next/server/app/page.js +3 -3
  53. package/.next/server/app/page.js.nft.json +1 -1
  54. package/.next/server/app/page_client-reference-manifest.js +1 -1
  55. package/.next/server/app/privacy/page_client-reference-manifest.js +1 -1
  56. package/.next/server/app/privacy.html +1 -1
  57. package/.next/server/app/privacy.rsc +13 -13
  58. package/.next/server/app/share/[token]/page_client-reference-manifest.js +1 -1
  59. package/.next/server/app/terms/page_client-reference-manifest.js +1 -1
  60. package/.next/server/app/terms.html +1 -1
  61. package/.next/server/app/terms.rsc +13 -13
  62. package/.next/server/app/yo/page.js +2 -0
  63. package/.next/server/app/yo/page.js.nft.json +1 -0
  64. package/.next/server/app/yo/page_client-reference-manifest.js +1 -0
  65. package/.next/server/app/yo.html +1 -0
  66. package/.next/server/app/yo.meta +7 -0
  67. package/.next/server/app/yo.rsc +23 -0
  68. package/.next/server/app-paths-manifest.json +11 -10
  69. package/.next/server/chunks/2145.js +1 -1
  70. package/.next/server/chunks/2460.js +1 -1
  71. package/.next/server/chunks/5246.js +1 -1
  72. package/.next/server/chunks/5678.js +1 -1
  73. package/.next/server/chunks/5784.js +1 -1
  74. package/.next/server/chunks/6086.js +2 -20
  75. package/.next/server/chunks/{5553.js → 6415.js} +2 -2
  76. package/.next/server/chunks/7935.js +2 -2
  77. package/.next/server/functions-config-manifest.json +1 -1
  78. package/.next/server/instrumentation.js +1 -1
  79. package/.next/server/middleware-build-manifest.js +1 -1
  80. package/.next/server/middleware-react-loadable-manifest.js +1 -1
  81. package/.next/server/pages/404.html +1 -1
  82. package/.next/server/pages/500.html +1 -1
  83. package/.next/server/server-reference-manifest.json +1 -1
  84. package/.next/server/webpack-runtime.js +1 -1
  85. package/.next/static/WshFGr6RxGYP6AbWuT9OG/_buildManifest.js +1 -0
  86. package/.next/static/chunks/1168.aaac1edbb597fe5a.js +1 -0
  87. package/.next/static/chunks/1255-7999eac54f80a49f.js +1 -0
  88. package/.next/static/chunks/142-fa9752f53a551f63.js +1 -0
  89. package/.next/static/chunks/2505.d54ccadc42f4e3d1.js +1 -0
  90. package/.next/static/chunks/2619-04bc32f026a0d946.js +1 -0
  91. package/.next/static/chunks/2927.7e00cc878d9a3f52.js +1 -0
  92. package/.next/static/chunks/3573-1b41d7b8a000d015.js +1 -0
  93. package/.next/static/chunks/3609.ded5a5306e18af9c.js +1 -0
  94. package/.next/static/chunks/3667-1db7bd03948e60df.js +1 -0
  95. package/.next/static/chunks/3826.a73d4a88d8c09030.js +1 -0
  96. package/.next/static/chunks/{3a91511d-648a2ba3dad7df0c.js → 3a91511d-ba215c0b5dc21ba9.js} +1 -1
  97. package/.next/static/chunks/4256.48407d9abad5ea33.js +1 -0
  98. package/.next/static/chunks/4685-7f53bbfc4a9845eb.js +1 -0
  99. package/.next/static/chunks/4901-ba6a32818662e70a.js +1 -0
  100. package/.next/static/chunks/4919-7e7cdd5efc9f2110.js +1 -0
  101. package/.next/static/chunks/4bd1b696-100b9d70ed4e49c1.js +1 -0
  102. package/.next/static/chunks/5336-233ec7ab3807267c.js +1 -0
  103. package/.next/static/chunks/5442-b5bb869e832e8967.js +1 -0
  104. package/.next/static/chunks/6233-97a810aa272af547.js +1 -0
  105. package/.next/static/chunks/626.a5109d16f9eca1f6.js +1 -0
  106. package/.next/static/chunks/6872-faea0f088ab2d450.js +1 -0
  107. package/.next/static/chunks/7338-3ce17a93614f1d77.js +59 -0
  108. package/.next/static/chunks/7394-4bdb1feefad1a74a.js +1 -0
  109. package/.next/static/chunks/7616-1129bcb3eee8d315.js +1 -0
  110. package/.next/static/chunks/786-26deffb41572cbb3.js +1 -0
  111. package/.next/static/chunks/8273-8e92d34180669ca9.js +1 -0
  112. package/.next/static/chunks/8357.5dee1e0c4e5bb091.js +1 -0
  113. package/.next/static/chunks/9062-2bc2d089f9c9c6ba.js +1 -0
  114. package/.next/static/chunks/9380.f198afbf0c6b5369.js +1 -0
  115. package/.next/static/chunks/app/_not-found/page-5a8c6a29f762fa58.js +1 -0
  116. package/.next/static/chunks/app/api/[...doc]/page-f0852f35f0fd1d44.js +1 -0
  117. package/.next/static/chunks/app/api/agent-requests/route-cf84f975aad4c719.js +1 -0
  118. package/.next/static/chunks/app/api/apps/install/route-cf84f975aad4c719.js +1 -0
  119. package/.next/static/chunks/app/api/apps/manifests/route-cf84f975aad4c719.js +1 -0
  120. package/.next/static/chunks/app/api/apps/static/[...path]/route-cf84f975aad4c719.js +1 -0
  121. package/.next/static/chunks/app/api/docs/plain/route-cf84f975aad4c719.js +1 -0
  122. package/.next/static/chunks/app/api/events/route-cf84f975aad4c719.js +1 -0
  123. package/.next/static/chunks/app/api/import-from-openclaw/[channel]/route-cf84f975aad4c719.js +1 -0
  124. package/.next/static/chunks/app/api/import-from-openclaw/route-cf84f975aad4c719.js +1 -0
  125. package/.next/static/chunks/app/api/import-from-openclaw/validate/[channel]/route-cf84f975aad4c719.js +1 -0
  126. package/.next/static/chunks/app/api/page-cc59bebcc0d2c01d.js +1 -0
  127. package/.next/static/chunks/app/api/restart/route-cf84f975aad4c719.js +1 -0
  128. package/.next/static/chunks/app/api/update/route-cf84f975aad4c719.js +1 -0
  129. package/.next/static/chunks/app/api/version/route-cf84f975aad4c719.js +1 -0
  130. package/.next/static/chunks/app/api/workspace/[id]/apps/[wid]/route-cf84f975aad4c719.js +1 -0
  131. package/.next/static/chunks/app/api/workspace/[id]/apps/route-cf84f975aad4c719.js +1 -0
  132. package/.next/static/chunks/app/api/workspace/[id]/export/route-cf84f975aad4c719.js +1 -0
  133. package/.next/static/chunks/app/api/workspace/[id]/route-cf84f975aad4c719.js +1 -0
  134. package/.next/static/chunks/app/api/workspace/config/route-cf84f975aad4c719.js +1 -0
  135. package/.next/static/chunks/app/api/workspace/import/route-cf84f975aad4c719.js +1 -0
  136. package/.next/static/chunks/app/api/workspace/route-cf84f975aad4c719.js +1 -0
  137. package/.next/static/chunks/app/app-legacy-do-not-use/page-e5dc864e92d90ca7.js +1 -0
  138. package/.next/static/chunks/app/approve/[actionId]/page-2acca1f490424f21.js +1 -0
  139. package/.next/static/chunks/app/docs/[...doc]/page-8e2a2d036caab242.js +1 -0
  140. package/.next/static/chunks/app/docs/page-acf872a03ff79893.js +1 -0
  141. package/.next/static/chunks/app/error-66f983b7769dabfa.js +1 -0
  142. package/.next/static/chunks/app/health/page-c9185854ed9c86d0.js +1 -0
  143. package/.next/static/chunks/app/hello/page-74c9f4deaa4b03dd.js +1 -0
  144. package/.next/static/chunks/app/layout-af8d9969c7aeb758.js +1 -0
  145. package/.next/static/chunks/app/page-16dfcd1c7cc88bcc.js +1 -0
  146. package/.next/static/chunks/app/privacy/page-8e2d17079355c2cc.js +1 -0
  147. package/.next/static/chunks/app/share/[token]/page-5dd9b0418eee411f.js +1 -0
  148. package/.next/static/chunks/app/terms/page-8e2d17079355c2cc.js +1 -0
  149. package/.next/static/chunks/app/yo/layout-cf84f975aad4c719.js +1 -0
  150. package/.next/static/chunks/app/yo/page-719dc5f213fdfb30.js +1 -0
  151. package/.next/static/chunks/framework-a32a2a465584c0bc.js +1 -0
  152. package/.next/static/chunks/main-0f0f9142f74e7215.js +1 -0
  153. package/.next/static/chunks/main-app-24f0c92ba10af457.js +1 -0
  154. package/.next/static/chunks/pages/_app-4b3fb5e477a0267f.js +1 -0
  155. package/.next/static/chunks/pages/_error-c970d8b55ace1b48.js +1 -0
  156. package/.next/static/chunks/{webpack-768de8b7d6a7a27a.js → webpack-79ad58260e9b10b4.js} +1 -1
  157. package/.next/static/css/83cd401584ab787f.css +3 -0
  158. package/.next/trace +28 -28
  159. package/.next/types/app/yo/layout.ts +84 -0
  160. package/.next/types/app/yo/page.ts +84 -0
  161. package/.next/types/routes.d.ts +4 -2
  162. package/.next/types/validator.ts +18 -0
  163. package/bin/auramaxx.js +9 -24
  164. package/docs/ARCHITECTURE.md +1 -1
  165. package/docs/AUTH.md +6 -3
  166. package/docs/CLI.md +2 -0
  167. package/docs/MCP.md +2 -0
  168. package/docs/credentials.md +2 -0
  169. package/package.json +1 -1
  170. package/prisma/migrations/20260227214000_update_agent_action_ttl_defaults/migration.sql +19 -0
  171. package/public/0a167e5e-4f52-4715-ae23-bf63d259a6b1.png +0 -0
  172. package/public/141ec92c-6780-4b23-838f-9a7bf1e91bb8.png +0 -0
  173. package/public/3afc4935-92cb-42af-9624-0b1341c12a5e.png +0 -0
  174. package/public/43947df5-dbcf-4e49-ab8b-41b9162c0410.png +0 -0
  175. package/public/5aeae9ce-0d38-49ea-8fd1-167892a04a85.png +0 -0
  176. package/public/660e4ea3-a3a6-4be4-a8ca-2cb74c51dfb5.png +0 -0
  177. package/public/733f02d7-6b58-4ba6-a5c8-d062cd205e1d.png +0 -0
  178. package/public/a32d65cb-95b0-4977-be6b-cf69f515afbe.png +0 -0
  179. package/public/agent1.png +0 -0
  180. package/public/agent10.png +0 -0
  181. package/public/agent2.png +0 -0
  182. package/public/agent3.png +0 -0
  183. package/public/agent4.png +0 -0
  184. package/public/agent5.png +0 -0
  185. package/public/agent6.png +0 -0
  186. package/public/agent7.png +0 -0
  187. package/public/agent8.png +0 -0
  188. package/public/agent9.png +0 -0
  189. package/public/c4938305-b811-4ccc-91db-94d309734827.png +0 -0
  190. package/public/f2ca6825-a4f3-4107-815c-51ee740dfc09.png +0 -0
  191. package/public/llm.txt +2 -0
  192. package/public/llms.txt +39 -0
  193. package/public/ss-dark1.png +0 -0
  194. package/public/ss-dark1.webp +0 -0
  195. package/public/ss-dark2.png +0 -0
  196. package/public/ss-dark2.webp +0 -0
  197. package/public/ss-dark3.png +0 -0
  198. package/public/ss-dark3.webp +0 -0
  199. package/public/ss-light1.png +0 -0
  200. package/public/ss-light1.webp +0 -0
  201. package/public/ss-light2.png +0 -0
  202. package/public/ss-light2.webp +0 -0
  203. package/public/ss-light3.png +0 -0
  204. package/public/ss-light3.webp +0 -0
  205. package/shared/agent-profile-schema.ts +81 -0
  206. package/shared/credential-field-schema.ts +12 -0
  207. package/skills/auramaxx/SKILL.md +71 -691
  208. package/src/app/UnlockPageClient.tsx +1939 -0
  209. package/src/app/api/page.tsx +8 -9
  210. package/src/app/api/update/route.ts +105 -36
  211. package/src/app/approve/[actionId]/page.tsx +4 -1
  212. package/src/app/docs/DocsPageContent.tsx +3 -3
  213. package/src/app/globals.css +94 -0
  214. package/src/app/layout.tsx +1 -0
  215. package/src/app/page.tsx +25 -1935
  216. package/src/app/yo/layout.tsx +29 -0
  217. package/src/app/yo/page.tsx +528 -0
  218. package/src/components/HumanActionBar.tsx +34 -8
  219. package/src/components/agent/AgentSidebar.tsx +3 -1
  220. package/src/components/agent/CredentialAgent.tsx +5 -1
  221. package/src/components/agent/CredentialDetail.tsx +32 -1
  222. package/src/components/agent/CredentialForm.tsx +94 -7
  223. package/src/components/agent/CredentialRow.tsx +8 -1
  224. package/src/components/agent/credentialFormName.ts +22 -1
  225. package/src/components/agent/types.ts +2 -2
  226. package/src/components/design-system/Modal.tsx +14 -1
  227. package/src/hooks/useUpdateChecker.ts +17 -1
  228. package/src/lib/pino.ts +77 -8
  229. package/src/server/cli/commands/actions.ts +1 -1
  230. package/src/server/cli/commands/agent.ts +110 -65
  231. package/src/server/cli/commands/approve.ts +1 -1
  232. package/src/server/cli/commands/auth.ts +81 -20
  233. package/src/server/cli/commands/token.ts +2 -2
  234. package/src/server/cli/lib/escalation.ts +109 -24
  235. package/src/server/cli/lib/process.ts +2 -1
  236. package/src/server/cli/socket.ts +1 -1
  237. package/src/server/index.ts +2 -0
  238. package/src/server/lib/agent-profile-records.ts +72 -0
  239. package/src/server/lib/credential-transport.ts +27 -11
  240. package/src/server/lib/defaults.ts +3 -3
  241. package/src/server/lib/escalation-responder.ts +1 -1
  242. package/src/server/lib/resolve-action.ts +2 -2
  243. package/src/server/mcp/server.ts +6 -1
  244. package/src/server/node_modules/.vite/vitest/da39a3ee5e6b4b0d3255bfef95601890afd80709/results.json +1 -1
  245. package/src/server/routes/actions.ts +2 -2
  246. package/src/server/routes/agent-profiles.ts +82 -0
  247. package/src/server/routes/auth.ts +39 -4
  248. package/src/server/routes/credentials.ts +18 -0
  249. package/src/server/tests/cli/agent-auth.test.ts +20 -39
  250. package/src/server/tests/cli/agent.test.ts +18 -0
  251. package/src/server/tests/cli/auth-action-flag.test.ts +3 -2
  252. package/src/server/tests/cli/bin-entrypoint.test.ts +35 -11
  253. package/src/server/tests/cli/escalation.test.ts +7 -3
  254. package/src/server/tests/cli/process.test.ts +3 -3
  255. package/src/server/tests/cli/socket.test.ts +2 -2
  256. package/src/server/tests/endpoints/actions.test.ts +2 -2
  257. package/src/server/tests/endpoints/agent-profiles.test.ts +117 -0
  258. package/src/server/tests/endpoints/auth.test.ts +34 -0
  259. package/src/server/tests/lib/credential-transport.test.ts +68 -2
  260. package/src/server/tests/lib/defaults.test.ts +2 -2
  261. package/src/server/tests/lib/escalation-responder.test.ts +2 -2
  262. package/src/server/tests/setup.ts +7 -0
  263. package/src/server/tsconfig.tsbuildinfo +1 -1
  264. package/src/server/types.ts +1 -1
  265. package/.next/static/chunks/1168.63dbb444a33b1867.js +0 -1
  266. package/.next/static/chunks/1255-e8718b02724690dd.js +0 -1
  267. package/.next/static/chunks/142-aeaf7ffa9c53516d.js +0 -1
  268. package/.next/static/chunks/2505.22aaa333fd65908f.js +0 -1
  269. package/.next/static/chunks/2619-3c9e02e22d10480a.js +0 -1
  270. package/.next/static/chunks/2927.e7e9e2a1b8d2dc61.js +0 -1
  271. package/.next/static/chunks/3573-27e17f4ff2dd86ed.js +0 -1
  272. package/.next/static/chunks/3609.6f8e0ecd6de9566c.js +0 -1
  273. package/.next/static/chunks/3667-d6770121629db38b.js +0 -1
  274. package/.next/static/chunks/3826.7dfe96467cd74e45.js +0 -1
  275. package/.next/static/chunks/4256.50cb375c979ffd5a.js +0 -1
  276. package/.next/static/chunks/4685-3f8d92f574366fec.js +0 -1
  277. package/.next/static/chunks/4901-54c1ac380b7b43bb.js +0 -1
  278. package/.next/static/chunks/4919-fe6f1553abfc9420.js +0 -1
  279. package/.next/static/chunks/4bd1b696-f785427dddbba9fb.js +0 -1
  280. package/.next/static/chunks/5336-bd251f91235f7c11.js +0 -1
  281. package/.next/static/chunks/5442-be197c885bf12079.js +0 -1
  282. package/.next/static/chunks/5553-c8b86fe3513fce04.js +0 -59
  283. package/.next/static/chunks/6233-44e6fe57a552a816.js +0 -1
  284. package/.next/static/chunks/626.2583673a0386a81b.js +0 -1
  285. package/.next/static/chunks/6872-6442f2f5cce36ce5.js +0 -1
  286. package/.next/static/chunks/7411-3ca797c21b722ccd.js +0 -1
  287. package/.next/static/chunks/7616-b8bd37ce1f735d6f.js +0 -1
  288. package/.next/static/chunks/786-9ed39f96091b2be4.js +0 -1
  289. package/.next/static/chunks/8273-922091226ba84a94.js +0 -1
  290. package/.next/static/chunks/8357.6159472717ff7d11.js +0 -1
  291. package/.next/static/chunks/9062-3eb1607c96486f88.js +0 -1
  292. package/.next/static/chunks/9380.93f361baab2eefdf.js +0 -1
  293. package/.next/static/chunks/app/_not-found/page-c3b87025baf0a9c2.js +0 -1
  294. package/.next/static/chunks/app/api/[...doc]/page-790c4b33ba1fde4a.js +0 -1
  295. package/.next/static/chunks/app/api/agent-requests/route-e83b12cbab2e8707.js +0 -1
  296. package/.next/static/chunks/app/api/apps/install/route-e83b12cbab2e8707.js +0 -1
  297. package/.next/static/chunks/app/api/apps/manifests/route-e83b12cbab2e8707.js +0 -1
  298. package/.next/static/chunks/app/api/apps/static/[...path]/route-e83b12cbab2e8707.js +0 -1
  299. package/.next/static/chunks/app/api/docs/plain/route-e83b12cbab2e8707.js +0 -1
  300. package/.next/static/chunks/app/api/events/route-e83b12cbab2e8707.js +0 -1
  301. package/.next/static/chunks/app/api/import-from-openclaw/[channel]/route-e83b12cbab2e8707.js +0 -1
  302. package/.next/static/chunks/app/api/import-from-openclaw/route-e83b12cbab2e8707.js +0 -1
  303. package/.next/static/chunks/app/api/import-from-openclaw/validate/[channel]/route-e83b12cbab2e8707.js +0 -1
  304. package/.next/static/chunks/app/api/page-b53f9aa17a4c5201.js +0 -1
  305. package/.next/static/chunks/app/api/restart/route-e83b12cbab2e8707.js +0 -1
  306. package/.next/static/chunks/app/api/update/route-e83b12cbab2e8707.js +0 -1
  307. package/.next/static/chunks/app/api/version/route-e83b12cbab2e8707.js +0 -1
  308. package/.next/static/chunks/app/api/workspace/[id]/apps/[wid]/route-e83b12cbab2e8707.js +0 -1
  309. package/.next/static/chunks/app/api/workspace/[id]/apps/route-e83b12cbab2e8707.js +0 -1
  310. package/.next/static/chunks/app/api/workspace/[id]/export/route-e83b12cbab2e8707.js +0 -1
  311. package/.next/static/chunks/app/api/workspace/[id]/route-e83b12cbab2e8707.js +0 -1
  312. package/.next/static/chunks/app/api/workspace/config/route-e83b12cbab2e8707.js +0 -1
  313. package/.next/static/chunks/app/api/workspace/import/route-e83b12cbab2e8707.js +0 -1
  314. package/.next/static/chunks/app/api/workspace/route-e83b12cbab2e8707.js +0 -1
  315. package/.next/static/chunks/app/app-legacy-do-not-use/page-0052191daef60036.js +0 -1
  316. package/.next/static/chunks/app/approve/[actionId]/page-45cd3b8fa062d5e5.js +0 -1
  317. package/.next/static/chunks/app/docs/[...doc]/page-632ac406200b66fe.js +0 -1
  318. package/.next/static/chunks/app/docs/page-b7556394709b43df.js +0 -1
  319. package/.next/static/chunks/app/error-3d6057da512253d8.js +0 -1
  320. package/.next/static/chunks/app/health/page-80c985cd72328b74.js +0 -1
  321. package/.next/static/chunks/app/hello/page-fd71babcd192729b.js +0 -1
  322. package/.next/static/chunks/app/layout-285c6ef3f16bae63.js +0 -1
  323. package/.next/static/chunks/app/page-85017185df14c37b.js +0 -1
  324. package/.next/static/chunks/app/privacy/page-faf36cd0dde6dfa3.js +0 -1
  325. package/.next/static/chunks/app/share/[token]/page-22d51d6c5a47bb75.js +0 -1
  326. package/.next/static/chunks/app/terms/page-faf36cd0dde6dfa3.js +0 -1
  327. package/.next/static/chunks/framework-e60c938074ff7136.js +0 -1
  328. package/.next/static/chunks/main-447abf206d7ebd2f.js +0 -1
  329. package/.next/static/chunks/main-app-f63b86bdbf5b7b88.js +0 -1
  330. package/.next/static/chunks/pages/_app-6c8c2371b16a04b8.js +0 -1
  331. package/.next/static/chunks/pages/_error-94812ad32cad7365.js +0 -1
  332. package/.next/static/css/eb25c6452113486f.css +0 -3
  333. package/.next/static/zCR6u3S4dIjlCtV80nNsp/_buildManifest.js +0 -1
  334. /package/.next/static/{zCR6u3S4dIjlCtV80nNsp → WshFGr6RxGYP6AbWuT9OG}/_ssgManifest.js +0 -0
@@ -0,0 +1,29 @@
1
+ import type { Metadata } from 'next';
2
+ import type { ReactNode } from 'react';
3
+
4
+ const SEO_TITLE = 'auramaxx.sh';
5
+ const SEO_DESCRIPTION = 'THE APPLE KEYCHAIN FOR AI AGENTS. share passwpords, api keys, and credit cards with OpenClaw, Claude, Codex, Gemini,etc';
6
+
7
+ export const metadata: Metadata = {
8
+ title: SEO_TITLE,
9
+ description: SEO_DESCRIPTION,
10
+ alternates: {
11
+ canonical: '/yo',
12
+ },
13
+ openGraph: {
14
+ type: 'website',
15
+ url: '/yo',
16
+ siteName: SEO_TITLE,
17
+ title: SEO_TITLE,
18
+ description: SEO_DESCRIPTION,
19
+ },
20
+ twitter: {
21
+ card: 'summary_large_image',
22
+ title: SEO_TITLE,
23
+ description: SEO_DESCRIPTION,
24
+ },
25
+ };
26
+
27
+ export default function YoLayout({ children }: { children: ReactNode }) {
28
+ return children;
29
+ }
@@ -0,0 +1,528 @@
1
+ 'use client';
2
+
3
+ import Link from 'next/link';
4
+ import { useRouter } from 'next/navigation';
5
+ import { CSSProperties, useEffect, useMemo, useState } from 'react';
6
+ import DocsThemeToggle from '@/components/docs/DocsThemeToggle';
7
+ import { Button } from '@/components/design-system';
8
+ import { useTheme } from '@/hooks/useTheme';
9
+
10
+ type InstallMode = 'npm' | 'npx';
11
+
12
+ const INSTALL_COMMANDS: Record<InstallMode, string> = {
13
+ npm: 'npm install -g auramaxx',
14
+ npx: 'npx -y auramaxx',
15
+ };
16
+ const COMMAND_ACCENT_TOKEN = 'auramaxx';
17
+ const SCREENSHOT_SLIDES_LIGHT = ['/ss-light1.webp', '/ss-light2.webp', '/ss-light3.webp'] as const;
18
+ const SCREENSHOT_SLIDES_DARK = ['/ss-dark1.webp', '/ss-dark2.webp', '/ss-dark3.webp'] as const;
19
+ const SCREENSHOT_SLIDE_INTERVAL_MS = 5600;
20
+ const MARQUEE_REPEAT_COUNT = 4;
21
+
22
+ const SPRITE_SHEETS = [
23
+ {
24
+ src: '/agent9.png',
25
+ label: 'Agent 1',
26
+ width: 'clamp(24px, 3.8vw, 40px)',
27
+ height: 'clamp(34px, 5.6vw, 58px)',
28
+ baselineOffset: 'clamp(4px, 0.8vw, 8px)',
29
+ spriteY: '0%',
30
+ cropBottom: '4px',
31
+ },
32
+ {
33
+ src: '/agent10.png',
34
+ label: 'Agent 2',
35
+ width: 'clamp(28px, 4.4vw, 46px)',
36
+ height: 'clamp(40px, 6.4vw, 66px)',
37
+ baselineOffset: '0px',
38
+ spriteY: '0%',
39
+ cropBottom: '0px',
40
+ },
41
+ {
42
+ src: '/agent1.png',
43
+ label: 'Agent 3',
44
+ width: 'clamp(28px, 4.4vw, 46px)',
45
+ height: 'clamp(40px, 6.4vw, 66px)',
46
+ baselineOffset: '0px',
47
+ spriteY: '0%',
48
+ cropBottom: '0px',
49
+ },
50
+ {
51
+ src: '/agent2.png',
52
+ label: 'Agent 4',
53
+ width: 'clamp(28px, 4.4vw, 46px)',
54
+ height: 'clamp(40px, 6.4vw, 66px)',
55
+ baselineOffset: '0px',
56
+ spriteY: '0%',
57
+ cropBottom: '0px',
58
+ },
59
+ {
60
+ src: '/agent3.png',
61
+ label: 'Agent 5',
62
+ width: 'clamp(28px, 4.4vw, 46px)',
63
+ height: 'clamp(40px, 6.4vw, 66px)',
64
+ baselineOffset: '0px',
65
+ spriteY: '0%',
66
+ cropBottom: '0px',
67
+ },
68
+ {
69
+ src: '/agent4.png',
70
+ label: 'Agent 6',
71
+ width: 'clamp(28px, 4.4vw, 46px)',
72
+ height: 'clamp(40px, 6.4vw, 66px)',
73
+ baselineOffset: '0px',
74
+ spriteY: '0%',
75
+ cropBottom: '0px',
76
+ },
77
+ {
78
+ src: '/agent5.png',
79
+ label: 'Agent 7',
80
+ width: 'clamp(28px, 4.4vw, 46px)',
81
+ height: 'clamp(40px, 6.4vw, 66px)',
82
+ baselineOffset: '0px',
83
+ spriteY: '0%',
84
+ cropBottom: '0px',
85
+ },
86
+ {
87
+ src: '/agent6.png',
88
+ label: 'Agent 8',
89
+ width: 'clamp(28px, 4.4vw, 46px)',
90
+ height: 'clamp(40px, 6.4vw, 66px)',
91
+ baselineOffset: '0px',
92
+ spriteY: '0%',
93
+ cropBottom: '0px',
94
+ },
95
+ {
96
+ src: '/agent7.png',
97
+ label: 'Agent 9',
98
+ width: 'clamp(28px, 4.4vw, 46px)',
99
+ height: 'clamp(40px, 6.4vw, 66px)',
100
+ baselineOffset: '0px',
101
+ spriteY: '0%',
102
+ cropBottom: '0px',
103
+ },
104
+ {
105
+ src: '/agent8.png',
106
+ label: 'Agent 10',
107
+ width: 'clamp(28px, 4.4vw, 46px)',
108
+ height: 'clamp(40px, 6.4vw, 66px)',
109
+ baselineOffset: '0px',
110
+ spriteY: '0%',
111
+ cropBottom: '0px',
112
+ },
113
+ ] as const;
114
+
115
+ function hashSeed(value: string): number {
116
+ let hash = 0;
117
+ for (let i = 0; i < value.length; i += 1) {
118
+ hash = ((hash << 5) - hash) + value.charCodeAt(i);
119
+ hash |= 0;
120
+ }
121
+ return Math.abs(hash);
122
+ }
123
+
124
+ function seededUnit(seed: number): number {
125
+ const x = Math.sin(seed) * 10000;
126
+ return x - Math.floor(x);
127
+ }
128
+
129
+ function getSpriteScatterStyle(src: string, index: number, rowIndex = 0): CSSProperties {
130
+ const base = hashSeed(src) + (index * 97) + (rowIndex * 131);
131
+ const x = (seededUnit(base + 1) - 0.5) * 8;
132
+ const y = (seededUnit(base + 2) - 0.5) * 4 + (rowIndex === 0 ? -1.5 : 1.5);
133
+ const r = (seededUnit(base + 3) - 0.5) * 5;
134
+ const ml = (seededUnit(base + 4) - 0.5) * 8;
135
+ const mr = (seededUnit(base + 5) - 0.5) * 8;
136
+ const scale = 0.72 + (seededUnit(base + 6) * 0.06);
137
+
138
+ return {
139
+ marginLeft: `${Math.round(ml)}px`,
140
+ marginRight: `${Math.round(mr)}px`,
141
+ transform: `translate(${x.toFixed(1)}px, ${y.toFixed(1)}px) rotate(${r.toFixed(1)}deg) scale(${scale.toFixed(3)})`,
142
+ };
143
+ }
144
+
145
+ export default function YoPage() {
146
+ const router = useRouter();
147
+ const { colorMode } = useTheme();
148
+ const [installMode, setInstallMode] = useState<InstallMode>('npm');
149
+ const [hideHomeLink, setHideHomeLink] = useState(false);
150
+ const [slideIndex, setSlideIndex] = useState(0);
151
+ const [copied, setCopied] = useState(false);
152
+ const [isMobile, setIsMobile] = useState(false);
153
+ const installCommand = useMemo(() => INSTALL_COMMANDS[installMode], [installMode]);
154
+ const screenshotSlides = useMemo(
155
+ () => (colorMode === 'dark' ? SCREENSHOT_SLIDES_DARK : SCREENSHOT_SLIDES_LIGHT),
156
+ [colorMode],
157
+ );
158
+ const marqueeSprites = useMemo(
159
+ () => Array.from({ length: MARQUEE_REPEAT_COUNT }, () => SPRITE_SHEETS).flat(),
160
+ [],
161
+ );
162
+
163
+ useEffect(() => {
164
+ const hostname = window.location.hostname.toLowerCase();
165
+ setHideHomeLink(hostname === 'auramaxx.sh' || hostname === 'www.auramaxx.sh');
166
+ }, []);
167
+
168
+ useEffect(() => {
169
+ const syncViewport = () => {
170
+ setIsMobile(window.innerWidth < 768);
171
+ };
172
+ syncViewport();
173
+ window.addEventListener('resize', syncViewport);
174
+ return () => window.removeEventListener('resize', syncViewport);
175
+ }, []);
176
+
177
+ useEffect(() => {
178
+ const interval = window.setInterval(() => {
179
+ setSlideIndex((current) => (current + 1) % screenshotSlides.length);
180
+ }, SCREENSHOT_SLIDE_INTERVAL_MS);
181
+ return () => window.clearInterval(interval);
182
+ }, [screenshotSlides]);
183
+
184
+ useEffect(() => {
185
+ if (!copied) {
186
+ return undefined;
187
+ }
188
+ const timeout = window.setTimeout(() => {
189
+ setCopied(false);
190
+ }, 1500);
191
+ return () => window.clearTimeout(timeout);
192
+ }, [copied]);
193
+
194
+ useEffect(() => {
195
+ setSlideIndex(0);
196
+ }, [colorMode]);
197
+
198
+ const slideCount = screenshotSlides.length;
199
+ const getSlideSlot = (relative: number): 'left' | 'center' | 'right' | 'hidden' => {
200
+ if (relative === 0) return 'center';
201
+ if (relative === 1) return 'right';
202
+ if (relative === slideCount - 1) return 'left';
203
+ return 'hidden';
204
+ };
205
+
206
+ const getSlideStyle = (slot: 'left' | 'center' | 'right' | 'hidden', relative: number): CSSProperties => {
207
+ const mobileBase = 'translate(-50%, -42%)';
208
+ const desktopBase = 'translate(-50%, -50%)';
209
+ if (slot === 'center') {
210
+ return {
211
+ zIndex: 20,
212
+ opacity: 1,
213
+ transform: isMobile
214
+ ? `${mobileBase} translate3d(0, 0, 0) scale(1)`
215
+ : `${desktopBase} translate3d(0, 0, 0) scale(1)`,
216
+ };
217
+ }
218
+
219
+ if (slot === 'left') {
220
+ return {
221
+ zIndex: 10,
222
+ opacity: 0.92,
223
+ transform: isMobile
224
+ ? `${mobileBase} translate3d(0, clamp(-250px, -23vh, -136px), 0) scale(0.66)`
225
+ : `${desktopBase} translate3d(clamp(-430px, -30vw, -220px), 0, 0) scale(0.68)`,
226
+ };
227
+ }
228
+
229
+ if (slot === 'right') {
230
+ return {
231
+ zIndex: 10,
232
+ opacity: 0.92,
233
+ transform: isMobile
234
+ ? `${mobileBase} translate3d(0, clamp(136px, 23vh, 250px), 0) scale(0.66)`
235
+ : `${desktopBase} translate3d(clamp(220px, 30vw, 430px), 0, 0) scale(0.68)`,
236
+ };
237
+ }
238
+
239
+ const direction = relative <= slideCount / 2 ? 1 : -1;
240
+ return {
241
+ zIndex: 0,
242
+ opacity: 0,
243
+ transform: isMobile
244
+ ? `${mobileBase} translate3d(0, ${direction > 0 ? '360px' : '-360px'}, 0) scale(0.56)`
245
+ : `${desktopBase} translate3d(${direction > 0 ? '520px' : '-520px'}, 0, 0) scale(0.58)`,
246
+ };
247
+ };
248
+
249
+ const handleCopy = async () => {
250
+ try {
251
+ await navigator.clipboard.writeText(installCommand);
252
+ setCopied(true);
253
+ } catch {
254
+ setCopied(false);
255
+ }
256
+ };
257
+
258
+ return (
259
+ <main className="min-h-screen bg-[var(--color-background,#f4f4f5)] relative overflow-hidden" data-testid="yo-page-shell">
260
+ <div className="fixed inset-0 pointer-events-none z-0 overflow-hidden" aria-hidden="true">
261
+ <div className="absolute inset-0 bg-grid-adaptive bg-[size:4rem_4rem] opacity-30" />
262
+ <div className="absolute inset-0 tyvek-texture opacity-40 mix-blend-multiply" />
263
+
264
+ <div className="absolute bottom-[5%] right-[5%] opacity-5 select-none" data-testid="yo-background-branding">
265
+ <h1 className="text-[15vw] font-bold leading-none text-[var(--color-text,#0a0a0a)] font-mono tracking-tighter text-right">
266
+ AURAMAXX
267
+ </h1>
268
+ </div>
269
+
270
+ <div className="absolute top-10 left-10 w-32 h-32 border-l-4 border-t-4 border-[var(--color-text,#0a0a0a)] opacity-10">
271
+ <div className="absolute top-2 left-2 w-4 h-4 bg-[var(--color-text,#0a0a0a)]" />
272
+ </div>
273
+ <div className="absolute bottom-10 right-10 w-32 h-32 border-r-4 border-b-4 border-[var(--color-text,#0a0a0a)] opacity-10 flex items-end justify-end">
274
+ <div className="absolute bottom-2 right-2 w-4 h-4 bg-[var(--color-text,#0a0a0a)]" />
275
+ </div>
276
+ </div>
277
+
278
+ <div className="fixed top-5 right-4 sm:top-7 sm:right-6 z-30 flex items-center gap-2 sm:gap-3 font-mono text-[9px] sm:text-[10px] tracking-widest">
279
+ <Link href="/docs" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">DOCS</Link>
280
+ <Link href="/api" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">API</Link>
281
+ {!hideHomeLink && (
282
+ <Link href="/" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">HOME</Link>
283
+ )}
284
+ <a href="https://github.com/Aura-Industry/auramaxx" target="_blank" rel="noopener noreferrer" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">GITHUB</a>
285
+ <a href="https://x.com/npxauramaxx" target="_blank" rel="noopener noreferrer" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">X</a>
286
+ <a href="https://x.com/hi_im_nico" target="_blank" rel="noopener noreferrer" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">HELP</a>
287
+ <DocsThemeToggle />
288
+ </div>
289
+
290
+ <div className="fixed bottom-4 right-4 sm:bottom-6 sm:right-6 z-30 flex items-center gap-3 font-mono text-[9px] sm:text-[10px] tracking-widest">
291
+ <Link href="/privacy" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">
292
+ PRIVACY POLICY
293
+ </Link>
294
+ <Link href="/terms" className="text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors">
295
+ TERMS
296
+ </Link>
297
+ </div>
298
+
299
+ <div className="fixed top-4 left-4 sm:top-6 sm:left-6 z-30 flex items-center gap-2 sm:gap-3">
300
+ <Link href="/" className="w-8 h-8 sm:w-10 sm:h-10 block hover:opacity-80 transition-opacity" aria-label="AuraMaxx home">
301
+ <img src="/logo.webp" alt="AuraMaxx" className="w-full h-full object-contain" />
302
+ </Link>
303
+ <div className="hidden sm:flex sm:flex-col sm:leading-tight">
304
+ <Link href="/" className="font-black text-sm tracking-tight text-[var(--color-text,#0a0a0a)] hover:opacity-80 transition-opacity">
305
+ AURAMAXX
306
+ </Link>
307
+ <a
308
+ href="https://x.com/hi_im_nico"
309
+ target="_blank"
310
+ rel="noopener noreferrer"
311
+ className="text-[10px] text-[var(--color-text-muted,#6b7280)] hover:text-[var(--color-text,#0a0a0a)] transition-colors"
312
+ >
313
+ by @hi_im_nico, with love
314
+ </a>
315
+ </div>
316
+ </div>
317
+
318
+ <div className="fixed top-20 left-1/2 z-20 w-full max-w-4xl -translate-x-1/2 px-4 pointer-events-none sm:top-24">
319
+ <div className="mx-auto w-full max-w-[min(94vw,740px)] bg-[var(--color-surface,#f4f4f2)] clip-specimen border-mech shadow-mech overflow-hidden font-mono corner-marks pointer-events-auto">
320
+ <div className="px-4 py-2 border-b border-[var(--color-border,#d4d4d8)] bg-[var(--color-surface-alt,#fafafa)] flex items-center justify-between">
321
+ <span className="font-sans font-bold text-[10px] text-[var(--color-text,#0a0a0a)] uppercase tracking-tight">
322
+ AURAMAXX
323
+ </span>
324
+ <span className="ml-auto font-mono text-[10px] tracking-[0.12em] uppercase text-[var(--color-text-muted,#6b7280)]">
325
+ npx auramaxx
326
+ </span>
327
+ </div>
328
+ <div className="px-4 py-4 text-center sm:px-6 sm:py-5">
329
+ <h2 className="font-mono text-[clamp(12px,3.2vw,30px)] font-semibold tracking-[0.03em] leading-none text-[var(--color-text,#0a0a0a)]">
330
+ <span className="block whitespace-nowrap">THE APPLE KEYCHAIN FOR AI AGENTS</span>
331
+ <span className="mt-2 block whitespace-nowrap">
332
+ SECURE.LOCAL.OPEN-SOURCE.
333
+ </span>
334
+ </h2>
335
+ <p className="mt-2 font-mono text-[11px] sm:text-[12px] tracking-wide text-[var(--color-text-muted,#6b7280)]">
336
+ It&apos;s me, AI. You are absolutely right. I want to auramaxx with your credit cards.
337
+ </p>
338
+ <div className="mt-4 flex items-center justify-center gap-2">
339
+ <Button
340
+ variant="primary"
341
+ size="sm"
342
+ onClick={() => router.push('/docs')}
343
+ >
344
+ VIEW DOCS
345
+ </Button>
346
+ <Button
347
+ variant="secondary"
348
+ size="sm"
349
+ onClick={() => window.open('https://github.com/Aura-Industry/auramaxx', '_blank', 'noopener,noreferrer')}
350
+ >
351
+ GITHUB
352
+ </Button>
353
+ </div>
354
+ </div>
355
+ </div>
356
+ </div>
357
+
358
+ <div className="absolute inset-0 z-[1] pointer-events-none flex items-center justify-center overflow-hidden" aria-hidden="true">
359
+ <div className="relative h-[min(82vh,900px)] w-[136vw] md:h-[min(74vh,860px)] md:w-[min(112vw,1720px)]">
360
+ {screenshotSlides.map((src, index) => {
361
+ const relative = (index - slideIndex + slideCount) % slideCount;
362
+ const slot = getSlideSlot(relative);
363
+ const style = getSlideStyle(slot, relative);
364
+ const edgeFadeStyle: CSSProperties = isMobile
365
+ ? (slot === 'left'
366
+ ? {
367
+ WebkitMaskImage: 'linear-gradient(to bottom, transparent 0%, black 28%, black 100%)',
368
+ maskImage: 'linear-gradient(to bottom, transparent 0%, black 28%, black 100%)',
369
+ }
370
+ : slot === 'right'
371
+ ? {
372
+ WebkitMaskImage: 'linear-gradient(to top, transparent 0%, black 28%, black 100%)',
373
+ maskImage: 'linear-gradient(to top, transparent 0%, black 28%, black 100%)',
374
+ }
375
+ : {})
376
+ : (slot === 'left'
377
+ ? {
378
+ WebkitMaskImage: 'linear-gradient(to right, transparent 0%, black 30%, black 100%)',
379
+ maskImage: 'linear-gradient(to right, transparent 0%, black 30%, black 100%)',
380
+ }
381
+ : slot === 'right'
382
+ ? {
383
+ WebkitMaskImage: 'linear-gradient(to left, transparent 0%, black 30%, black 100%)',
384
+ maskImage: 'linear-gradient(to left, transparent 0%, black 30%, black 100%)',
385
+ }
386
+ : {});
387
+ return (
388
+ <div
389
+ key={src}
390
+ className="absolute left-1/2 top-1/2 overflow-hidden transition-[transform,opacity] duration-[1700ms] ease-[cubic-bezier(0.22,1,0.36,1)] will-change-transform"
391
+ style={{
392
+ width: isMobile ? 'min(152vw, 1080px)' : 'min(80vw, 1320px)',
393
+ height: isMobile ? 'min(74vh, 760px)' : 'min(70vh, 800px)',
394
+ ...style,
395
+ }}
396
+ >
397
+ <div className="relative h-full w-full" style={edgeFadeStyle}>
398
+ <img src={src} alt="" className="h-full w-full object-contain" />
399
+ {isMobile && slot !== 'center' && (
400
+ <div
401
+ className="absolute inset-0 pointer-events-none"
402
+ style={{ background: colorMode === 'dark' ? 'rgba(0,0,0,0.12)' : 'rgba(255,255,255,0.1)' }}
403
+ />
404
+ )}
405
+ </div>
406
+ </div>
407
+ );
408
+ })}
409
+ </div>
410
+ </div>
411
+
412
+ <section className="relative z-10 min-h-screen p-4">
413
+ <div className="w-full max-w-4xl">
414
+ <div
415
+ className="fixed bottom-14 left-1/2 z-20 w-[min(94vw,620px)] -translate-x-1/2 overflow-hidden border border-[#222222] bg-[#111111] md:bottom-16"
416
+ data-testid="yo-install-panel"
417
+ >
418
+ <div className="flex items-center justify-between border-b border-[#2a2a2a] bg-[#1a1a1a] px-3 py-2">
419
+ <div className="flex items-center gap-1.5" aria-hidden="true">
420
+ <span className="h-2.5 w-2.5 rounded-full bg-[#ff5f57]" />
421
+ <span className="h-2.5 w-2.5 rounded-full bg-[#ffbd2e]" />
422
+ <span className="h-2.5 w-2.5 rounded-full bg-[#28c840]" />
423
+ </div>
424
+ <span className="font-mono text-[9px] tracking-widest uppercase text-[#8b8b8b]">MIT</span>
425
+ </div>
426
+
427
+ <div className="flex items-center border-b border-[#2a2a2a] bg-[#121212]">
428
+ <button
429
+ type="button"
430
+ onClick={() => setInstallMode('npm')}
431
+ aria-pressed={installMode === 'npm'}
432
+ className={`px-4 py-2 font-mono text-[10px] tracking-widest uppercase transition-colors ${
433
+ installMode === 'npm'
434
+ ? 'bg-[#0a0a0a] text-[#f5f5f5]'
435
+ : 'text-[#8b8b8b] hover:text-[#f5f5f5] hover:bg-[#1b1b1b]'
436
+ }`}
437
+ >
438
+ npm
439
+ </button>
440
+ <button
441
+ type="button"
442
+ onClick={() => setInstallMode('npx')}
443
+ aria-pressed={installMode === 'npx'}
444
+ className={`px-4 py-2 font-mono text-[10px] tracking-widest uppercase transition-colors ${
445
+ installMode === 'npx'
446
+ ? 'bg-[#0a0a0a] text-[#f5f5f5]'
447
+ : 'text-[#8b8b8b] hover:text-[#f5f5f5] hover:bg-[#1b1b1b]'
448
+ }`}
449
+ >
450
+ npx
451
+ </button>
452
+ </div>
453
+
454
+ <div className="flex items-center bg-[#0a0a0a] px-4 py-4">
455
+ <div className="flex min-w-0 items-center gap-1.5">
456
+ <code className="block min-w-0 overflow-x-auto whitespace-nowrap font-mono text-sm md:text-base text-[#9ca3af]">
457
+ <span className="mr-2 text-[#7d8590]">$</span>
458
+ {installCommand.endsWith(COMMAND_ACCENT_TOKEN) ? (
459
+ <>
460
+ {installCommand.slice(0, -COMMAND_ACCENT_TOKEN.length)}
461
+ <span className="text-[var(--color-accent,#34d399)]">{COMMAND_ACCENT_TOKEN}</span>
462
+ </>
463
+ ) : (
464
+ installCommand
465
+ )}
466
+ </code>
467
+ <button
468
+ type="button"
469
+ onClick={handleCopy}
470
+ aria-label={copied ? 'Copied command' : 'Copy command'}
471
+ title={copied ? 'Copied' : 'Copy'}
472
+ className={`shrink-0 flex h-5 w-5 items-center justify-center transition-colors ${
473
+ copied ? 'text-[#86efac]' : 'text-[#a3a3a3] hover:text-[#d4d4d4]'
474
+ }`}
475
+ >
476
+ {copied ? (
477
+ <svg viewBox="0 0 16 16" className="h-3.5 w-3.5" aria-hidden="true">
478
+ <path
479
+ fill="currentColor"
480
+ d="M13.78 3.97a.75.75 0 0 1 0 1.06L6.97 11.84a.75.75 0 0 1-1.06 0L2.22 8.16a.75.75 0 1 1 1.06-1.06l3.16 3.16 6.28-6.28a.75.75 0 0 1 1.06 0Z"
481
+ />
482
+ </svg>
483
+ ) : (
484
+ <svg viewBox="0 0 16 16" className="h-3.5 w-3.5" aria-hidden="true">
485
+ <path
486
+ fill="currentColor"
487
+ d="M10 1.75A1.75 1.75 0 0 1 11.75 3.5v.75h.75A1.75 1.75 0 0 1 14.25 6v6.5A1.75 1.75 0 0 1 12.5 14.25H6A1.75 1.75 0 0 1 4.25 12.5v-.75H3.5A1.75 1.75 0 0 1 1.75 10V3.5A1.75 1.75 0 0 1 3.5 1.75H10Zm2.5 4H6A.25.25 0 0 0 5.75 6v6.5c0 .14.11.25.25.25h6.5a.25.25 0 0 0 .25-.25V6a.25.25 0 0 0-.25-.25Zm-2.5-2.5H3.5a.25.25 0 0 0-.25.25V10c0 .14.11.25.25.25h.75V6A1.75 1.75 0 0 1 6 4.25h4.25V3.5a.25.25 0 0 0-.25-.25Z"
488
+ />
489
+ </svg>
490
+ )}
491
+ </button>
492
+ </div>
493
+ </div>
494
+
495
+ <div className="border-t border-[#2a2a2a] bg-[#0b0b0b] px-3 py-2.5 md:px-4 md:py-3" data-testid="yo-sprite-row">
496
+ <div className="overflow-hidden">
497
+ <div className="yo-mobile-agent-marquee flex w-max items-end gap-1.5 md:gap-2">
498
+ {marqueeSprites.map((sprite, index) => {
499
+ const baseIndex = index % SPRITE_SHEETS.length;
500
+ const scatter = getSpriteScatterStyle(sprite.src, baseIndex, 0);
501
+ return (
502
+ <div key={`${sprite.src}-${index}`} style={scatter}>
503
+ <div
504
+ className="yo-sprite"
505
+ style={{
506
+ backgroundImage: `url('${sprite.src}')`,
507
+ animationDelay: `${baseIndex * -150}ms, ${baseIndex * -300}ms`,
508
+ width: sprite.width,
509
+ height: sprite.height,
510
+ marginBottom: sprite.baselineOffset,
511
+ backgroundPositionY: sprite.spriteY,
512
+ clipPath: `inset(0 0 ${sprite.cropBottom} 0)`,
513
+ } as CSSProperties}
514
+ role="img"
515
+ aria-label={`${sprite.label} sprite`}
516
+ />
517
+ </div>
518
+ );
519
+ })}
520
+ </div>
521
+ </div>
522
+ </div>
523
+ </div>
524
+ </div>
525
+ </section>
526
+ </main>
527
+ );
528
+ }
@@ -499,6 +499,7 @@ export const HumanActionBar: React.FC<HumanActionBarProps> = ({
499
499
  const [detailExpanded, setDetailExpanded] = useState(false);
500
500
  const [rawExpanded, setRawExpanded] = useState(false);
501
501
  const [bulkApproving, setBulkApproving] = useState(false);
502
+ const [bulkRejecting, setBulkRejecting] = useState(false);
502
503
  const [bulkFailureSummary, setBulkFailureSummary] = useState<string | null>(null);
503
504
  const pending = requests.filter(r => r.status === 'pending' && r.type !== 'notify');
504
505
  const panelRef = useRef<HTMLDivElement>(null);
@@ -534,25 +535,30 @@ export const HumanActionBar: React.FC<HumanActionBarProps> = ({
534
535
  const firstApprovalScope = resolveApprovalScope(first, firstMeta);
535
536
  const firstApproving = actionLoading === `resolve-${first.id}` || actionLoading === `approve-${first.id}`;
536
537
  const firstRejecting = actionLoading === `reject-${first.id}`;
537
- const firstLoading = firstApproving || firstRejecting || bulkApproving;
538
+ const firstLoading = firstApproving || firstRejecting || bulkApproving || bulkRejecting;
538
539
  const firstHasMismatch = hasDiscrepancies(first);
539
540
  const firstBorderColor = firstHasMismatch
540
541
  ? 'var(--color-warning, #f59e0b)'
541
542
  : 'var(--color-danger, #ef4444)';
542
543
 
543
- const handleApproveAll = async () => {
544
- if (bulkApproving) return;
544
+ const handleResolveAll = async (approved: boolean) => {
545
+ if (bulkApproving || bulkRejecting) return;
545
546
  const targets = pending.map((request) => request.id);
546
547
  if (targets.length === 0) return;
547
548
 
549
+ const actionLabel = approved ? 'APPROVE ALL' : 'REJECT ALL';
548
550
  setBulkFailureSummary(null);
549
- setBulkApproving(true);
551
+ if (approved) {
552
+ setBulkApproving(true);
553
+ } else {
554
+ setBulkRejecting(true);
555
+ }
550
556
  setExpanded(false);
551
557
 
552
558
  const failures: Array<{ id: string; message: string }> = [];
553
559
  for (const id of targets) {
554
560
  try {
555
- const result = await resolveAction(id, true);
561
+ const result = await resolveAction(id, approved);
556
562
  const failure = resolveFailureMessage(result);
557
563
  if (failure) {
558
564
  failures.push({ id, message: failure });
@@ -571,12 +577,19 @@ export const HumanActionBar: React.FC<HumanActionBarProps> = ({
571
577
  .map((failure) => `${failure.id} (${failure.message})`)
572
578
  .join(', ');
573
579
  const more = failures.length > 3 ? ` +${failures.length - 3} more` : '';
574
- setBulkFailureSummary(`APPROVE ALL completed with ${failures.length} failed: ${shown}${more}`);
580
+ setBulkFailureSummary(`${actionLabel} completed with ${failures.length} failed: ${shown}${more}`);
575
581
  }
576
582
 
577
- setBulkApproving(false);
583
+ if (approved) {
584
+ setBulkApproving(false);
585
+ } else {
586
+ setBulkRejecting(false);
587
+ }
578
588
  };
579
589
 
590
+ const handleApproveAll = async () => handleResolveAll(true);
591
+ const handleRejectAll = async () => handleResolveAll(false);
592
+
580
593
  return (
581
594
  <div className="relative z-30" ref={panelRef}>
582
595
  {/* Expanded stack — grows upward */}
@@ -614,7 +627,7 @@ export const HumanActionBar: React.FC<HumanActionBarProps> = ({
614
627
  resolveAction={resolveAction}
615
628
  actionLoading={actionLoading}
616
629
  showBorder={i < pending.length - 2}
617
- bulkLocked={bulkApproving}
630
+ bulkLocked={bulkApproving || bulkRejecting}
618
631
  />
619
632
  ))}
620
633
  </div>
@@ -741,6 +754,19 @@ export const HumanActionBar: React.FC<HumanActionBarProps> = ({
741
754
  APPROVE ALL
742
755
  </Button>
743
756
  )}
757
+ {pending.length > 1 && (
758
+ <Button
759
+ variant="danger"
760
+ size="sm"
761
+ onClick={() => void handleRejectAll()}
762
+ disabled={firstLoading}
763
+ loading={bulkRejecting}
764
+ icon={!bulkRejecting ? <X size={10} /> : undefined}
765
+ className="h-7 px-2"
766
+ >
767
+ REJECT ALL
768
+ </Button>
769
+ )}
744
770
  <Button
745
771
  variant="primary"
746
772
  size="sm"
@@ -1,7 +1,7 @@
1
1
  'use client';
2
2
 
3
3
  import React, { useEffect, useMemo, useRef, useState } from 'react';
4
- import { Layers, Key, CreditCard, FileText, Star, Tag, Lock, Unlock, Plus, RefreshCw, Terminal, ShieldCheck, Archive, Trash2, ChevronRight, Wallet } from 'lucide-react';
4
+ import { Layers, Key, CreditCard, FileText, Star, Tag, Lock, Unlock, Plus, RefreshCw, Terminal, ShieldCheck, Archive, Trash2, ChevronRight, Wallet, Globe } from 'lucide-react';
5
5
  import { Button, DownloadButton } from '@/components/design-system';
6
6
  import type { AgentInfo, AgentFilters, CategoryFilter, CredentialType } from './types';
7
7
 
@@ -35,6 +35,7 @@ interface AgentSidebarProps {
35
35
  const categories: { key: CategoryFilter; label: string; icon: React.FC<{ size: number; className?: string }> }[] = [
36
36
  { key: 'all', label: 'All Credentials', icon: Layers },
37
37
  { key: 'login', label: 'Logins', icon: Key },
38
+ { key: 'sso', label: 'SSO Logins', icon: Globe },
38
39
  { key: 'card', label: 'Cards', icon: CreditCard },
39
40
  { key: 'plain_note', label: 'Plain Notes', icon: FileText },
40
41
  { key: 'note', label: 'Secret Notes', icon: FileText },
@@ -46,6 +47,7 @@ const categories: { key: CategoryFilter; label: string; icon: React.FC<{ size: n
46
47
 
47
48
  const CATEGORY_CREATE_TYPE: Partial<Record<CategoryFilter, CredentialCreatePrefillType>> = {
48
49
  login: 'login',
50
+ sso: 'sso',
49
51
  card: 'card',
50
52
  plain_note: 'plain_note',
51
53
  note: 'note',