@allbluecn/web-app 0.22.4 → 0.23.1

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 (500) hide show
  1. package/package.json +4 -14
  2. package/src/__tests__/integration/login-email-acceptance.test.ts +16 -0
  3. package/src/__tests__/story-view.test.ts +33 -1
  4. package/src/components/agents/__tests__/agent-bindings-tab.test.tsx +221 -0
  5. package/src/components/agents/__tests__/agents-page.test.tsx +284 -0
  6. package/src/components/agents/agent-bindings-tab.tsx +59 -45
  7. package/src/components/agents/agent-form-dialog.tsx +3 -3
  8. package/src/components/agents/agent-selector.tsx +2 -3
  9. package/src/components/agents/agents-page.tsx +66 -31
  10. package/src/components/agents/slash-skill-menu.tsx +2 -3
  11. package/src/components/auth/__tests__/session-guard.test.tsx +74 -0
  12. package/src/components/auth/session-guard.tsx +8 -0
  13. package/src/components/billing/login-prompt-dialog.tsx +1 -1
  14. package/src/components/billing/subscription-provider.tsx +2 -16
  15. package/src/components/bug/__tests__/peek-modes.test.tsx +8 -0
  16. package/src/components/bug/__tests__/subgroup-header.test.tsx +202 -40
  17. package/src/components/bug/peek-panel.tsx +5 -3
  18. package/src/components/bug/views/bug-list/group.tsx +12 -2
  19. package/src/components/bug/views/bug-list/index.tsx +94 -67
  20. package/src/components/command/command-palette.tsx +10 -9
  21. package/src/components/design/canvas/document/frame-custom-presets.ts +9 -1
  22. package/src/components/design/canvas/panels/toolbar.tsx +21 -22
  23. package/src/components/design/canvas/react/__tests__/canvas-context-load-echo.test.tsx +199 -0
  24. package/src/components/design/canvas/react/__tests__/hooks.test.tsx +17 -3
  25. package/src/components/design/canvas/react/canvas-context.tsx +47 -26
  26. package/src/components/design/canvas/react/hooks.ts +39 -34
  27. package/src/components/design/editor/layout/__tests__/collab-param-wiring.test.tsx +17 -0
  28. package/src/components/design/editor/layout/__tests__/context-menu.test.tsx +17 -1
  29. package/src/components/design/editor/layout/__tests__/no-page-save-toast.test.tsx +17 -0
  30. package/src/components/design/editor/layout/__tests__/persistence-restore.test.tsx +17 -1
  31. package/src/components/design/editor/layout/__tests__/ssr-localstorage-smoke.test.tsx +17 -1
  32. package/src/components/design/editor/layout/design-editor-layout.tsx +13 -2
  33. package/src/components/design/editor/layout/hooks/use-design-auto-save.ts +3 -19
  34. package/src/components/devtools/devtools-panel.tsx +56 -0
  35. package/src/components/forms/__tests__/create-app-form.test.tsx +131 -0
  36. package/src/components/forms/app-field-error.tsx +21 -1
  37. package/src/components/forms/app-field.tsx +8 -8
  38. package/src/components/forms/app-submit.tsx +12 -9
  39. package/src/components/forms/create-app-form.tsx +124 -0
  40. package/src/components/forms/index.ts +2 -3
  41. package/src/components/harness/__tests__/gallery-behavior.test.tsx +37 -1
  42. package/src/components/harness/__tests__/harness-workbench-first-send.test.tsx +4 -1
  43. package/src/components/harness/__tests__/message-actions.test.tsx +7 -6
  44. package/src/components/harness/__tests__/use-video-generation.test.tsx +165 -0
  45. package/src/components/harness/ai-chat-history/index.tsx +5 -3
  46. package/src/components/harness/gallery/gallery-card.tsx +57 -35
  47. package/src/components/harness/gallery/gallery-grid.tsx +32 -15
  48. package/src/components/harness/gallery/gallery-types.ts +19 -0
  49. package/src/components/harness/gallery/gallery-video-card.tsx +54 -0
  50. package/src/components/harness/gallery/types.ts +2 -0
  51. package/src/components/harness/gallery/use-video-generation.ts +95 -0
  52. package/src/components/harness/harness-workbench-page.tsx +2 -3
  53. package/src/components/harness/message-actions.tsx +5 -3
  54. package/src/components/hotkeys/shortcuts-panel.tsx +28 -13
  55. package/src/components/iteration/__tests__/burndown-chart.test.tsx +118 -0
  56. package/src/components/iteration/burndown-chart.tsx +54 -23
  57. package/src/components/knowledge/editor/__tests__/knowledge-doc-editor-collab.test.tsx +96 -0
  58. package/src/components/knowledge/editor/knowledge-doc-editor.tsx +56 -1
  59. package/src/components/knowledge/editor/mindmap-doc-editor.tsx +12 -0
  60. package/src/components/knowledge/editor/use-auto-save-channels.ts +3 -1
  61. package/src/components/layout/sidebar-03/__tests__/nav-workspace.test.tsx +0 -4
  62. package/src/components/layout/sidebar-03/nav-knowledge.tsx +11 -11
  63. package/src/components/layout/sidebar-03/nav-main.tsx +12 -15
  64. package/src/components/layout/sidebar-03/nav-notifications.tsx +5 -8
  65. package/src/components/layout/sidebar-03/nav-workspace.tsx +11 -9
  66. package/src/components/notifications/__tests__/settings-notifications.test.tsx +158 -0
  67. package/src/components/notifications/settings-notifications.tsx +37 -13
  68. package/src/components/notifications/team-notifications.tsx +10 -14
  69. package/src/components/settings/personal-team/account/__tests__/account-client.test.tsx +170 -0
  70. package/src/components/settings/personal-team/account/account-client.tsx +44 -7
  71. package/src/components/settings/personal-team/team/team-client.tsx +17 -19
  72. package/src/components/shared-kit/list-kit/__tests__/frozen-header.test.ts +210 -41
  73. package/src/components/shared-kit/list-kit/frozen-header.ts +134 -21
  74. package/src/components/shared-kit/list-kit/kanban/frozen-header.ts +20 -27
  75. package/src/components/story/__tests__/peek-panel-patch-sync.test.tsx +8 -0
  76. package/src/components/story/__tests__/story-list-table.test.tsx +214 -0
  77. package/src/components/story/columns.tsx +11 -2
  78. package/src/components/story/peek-panel.tsx +4 -2
  79. package/src/components/story/story-list-table.tsx +16 -1
  80. package/src/components/story/views/story-list/__tests__/frozen-headers.test.tsx +186 -0
  81. package/src/components/story/views/story-list/group.tsx +12 -1
  82. package/src/components/story/views/story-list/index.tsx +101 -68
  83. package/src/components/testcase/__tests__/case-row.test.tsx +134 -2
  84. package/src/components/testcase/__tests__/peek-panel.test.tsx +8 -0
  85. package/src/components/testcase/__tests__/step-editor.test.tsx +106 -0
  86. package/src/components/testcase/list/grouped-list.tsx +50 -22
  87. package/src/components/testcase/peek-panel.tsx +7 -4
  88. package/src/components/testcase/step-editor.tsx +196 -150
  89. package/src/components/tiptap/notion-like/editor-extensions.ts +0 -3
  90. package/src/components/tiptap/notion-like/notion-like-editor-header.tsx +1 -31
  91. package/src/components/tiptap/notion-like/notion-like-editor.tsx +32 -1
  92. package/src/components/workspace/__tests__/dialogs/create-workspace-dialog.test.tsx +2 -28
  93. package/src/components/workspace/__tests__/dialogs/edit-workspace-dialog.test.tsx +2 -28
  94. package/src/components/workspace/dialogs/create-workspace-dialog.tsx +45 -43
  95. package/src/components/workspace/dialogs/edit-workspace-dialog.tsx +38 -36
  96. package/src/design-engine/engine/engine-decor.ts +2 -0
  97. package/src/design-engine/engine/engine-path.ts +2 -0
  98. package/src/hooks/__tests__/use-unsaved-guard.test.tsx +180 -0
  99. package/src/hooks/use-notifications.ts +9 -16
  100. package/src/hooks/use-unsaved-guard.tsx +87 -0
  101. package/src/lib/__tests__/pacer.test.ts +33 -96
  102. package/src/lib/__tests__/query-defaults.test.ts +169 -0
  103. package/src/lib/__tests__/query-global-error.test.ts +256 -0
  104. package/src/lib/anyhub/anyhub-store.ts +2 -2
  105. package/src/lib/changelog/sdk-versions.ts +2 -10
  106. package/src/lib/collab/presence-store.ts +5 -5
  107. package/src/lib/collab/use-presence-list-refresh.ts +2 -2
  108. package/src/lib/collab/use-share-presence.ts +2 -2
  109. package/src/lib/collections/query-keys.ts +7 -2
  110. package/src/lib/commands/__tests__/command-palette-state.test.ts +12 -14
  111. package/src/lib/commands/__tests__/registry.test.ts +6 -3
  112. package/src/lib/commands/command-palette-state.ts +8 -31
  113. package/src/lib/hotkeys/__tests__/registry.test.ts +71 -18
  114. package/src/lib/hotkeys/registry.ts +188 -85
  115. package/src/lib/hotkeys/types.ts +1 -13
  116. package/src/lib/pacer.ts +1 -79
  117. package/src/lib/queries/README.md +67 -0
  118. package/src/lib/queries/__tests__/agents-queries.test.ts +101 -0
  119. package/src/lib/queries/__tests__/compliance-queries.test.ts +136 -0
  120. package/src/lib/queries/__tests__/notifications-queries.test.ts +175 -0
  121. package/src/lib/queries/__tests__/team-queries.test.ts +87 -0
  122. package/src/lib/queries/agents.ts +40 -0
  123. package/src/lib/queries/compliance.ts +69 -0
  124. package/src/lib/queries/notifications.ts +63 -0
  125. package/src/lib/queries/team.ts +39 -0
  126. package/src/lib/query-defaults.ts +8 -0
  127. package/src/lib/query-global-error.ts +128 -0
  128. package/src/lib/remote-auth-client.ts +16 -0
  129. package/src/paraglide/README.md +1 -1
  130. package/src/paraglide/messages/_index.d.ts +11 -0
  131. package/src/paraglide/messages/_index.js +5659 -88285
  132. package/src/paraglide/messages/common_error_generic.d.ts +16 -0
  133. package/src/paraglide/messages/common_error_generic.js +29 -0
  134. package/src/paraglide/messages/common_unsaved_body.d.ts +16 -0
  135. package/src/paraglide/messages/common_unsaved_body.js +29 -0
  136. package/src/paraglide/messages/common_unsaved_leave.d.ts +16 -0
  137. package/src/paraglide/messages/common_unsaved_leave.js +29 -0
  138. package/src/paraglide/messages/common_unsaved_stay.d.ts +16 -0
  139. package/src/paraglide/messages/common_unsaved_stay.js +29 -0
  140. package/src/paraglide/messages/common_unsaved_title.d.ts +16 -0
  141. package/src/paraglide/messages/common_unsaved_title.js +29 -0
  142. package/src/paraglide/messages/gallery_videofailed1.d.ts +17 -0
  143. package/src/paraglide/messages/gallery_videofailed1.js +30 -0
  144. package/src/paraglide/messages/gallery_videogenerating1.d.ts +17 -0
  145. package/src/paraglide/messages/gallery_videogenerating1.js +30 -0
  146. package/src/paraglide/messages/gallery_videomissingprompt2.d.ts +17 -0
  147. package/src/paraglide/messages/gallery_videomissingprompt2.js +30 -0
  148. package/src/paraglide/messages/gallery_videoprogress1.d.ts +19 -0
  149. package/src/paraglide/messages/gallery_videoprogress1.js +30 -0
  150. package/src/paraglide/messages/gallery_videostop1.d.ts +17 -0
  151. package/src/paraglide/messages/gallery_videostop1.js +30 -0
  152. package/src/paraglide/messages/story_table_resizecolumn1.d.ts +17 -0
  153. package/src/paraglide/messages/story_table_resizecolumn1.js +30 -0
  154. package/src/providers/index.tsx +5 -50
  155. package/src/routeTree.gen.ts +21 -0
  156. package/src/router.tsx +21 -8
  157. package/src/routes/__root.tsx +2 -1
  158. package/src/routes/__tests__/-edition-routing.test.tsx +6 -1
  159. package/src/routes/_login/forgot-password/route.lazy.tsx +7 -6
  160. package/src/routes/_login/login/route.lazy.tsx +10 -9
  161. package/src/routes/_login/register/route.lazy.tsx +19 -18
  162. package/src/routes/_login/reset-password/route.lazy.tsx +10 -9
  163. package/src/routes/_nav/knowledge/compliance/$id.lazy.tsx +9 -12
  164. package/src/routes/_nav/knowledge/compliance/index.lazy.tsx +16 -13
  165. package/src/routes/_nav/knowledge/laws/$id.lazy.tsx +1 -1
  166. package/src/routes/_nav/notifications/route.tsx +6 -16
  167. package/src/routes/_nav/settings/-settings-tabs.tsx +9 -12
  168. package/src/routes/api/generate/__tests__/media.test.ts +378 -0
  169. package/src/routes/api/generate/media.ts +179 -0
  170. package/src/server/__tests__/agent-client-graph.test.ts +0 -1
  171. package/src/server/__tests__/agent-crud.test.ts +37 -4
  172. package/src/server/__tests__/bug-groups-two-level.test.ts +34 -1
  173. package/src/server/__tests__/chat-conversations.test.ts +37 -4
  174. package/src/server/__tests__/chat-list-messages.test.ts +40 -7
  175. package/src/server/__tests__/csv-export.test.ts +36 -3
  176. package/src/server/__tests__/desktop-bootstrap.test.ts +189 -0
  177. package/src/server/__tests__/remote-auth.test.ts +72 -0
  178. package/src/server/__tests__/skill-crud.test.ts +37 -4
  179. package/src/server/__tests__/sso-domain.test.ts +1 -1
  180. package/src/server/__tests__/sso-rate-limit-singleton.test.ts +123 -0
  181. package/src/server/__tests__/task-serverfn-crud.test.ts +35 -2
  182. package/src/server/__tests__/task-serverfn-queries.test.ts +35 -2
  183. package/src/server/__tests__/testcase-board.test.ts +38 -5
  184. package/src/server/__tests__/testcase-bulk.test.ts +38 -5
  185. package/src/server/__tests__/testcase-list-scope.test.ts +38 -5
  186. package/src/server/ai-gateway/__tests__/ai-output-guard.test.ts +126 -2
  187. package/src/server/ai-gateway/__tests__/chat-stream-builder-code-mode.test.ts +4 -0
  188. package/src/server/ai-gateway/__tests__/chat-stream-builder-memory.test.ts +4 -0
  189. package/src/server/ai-gateway/__tests__/chat-stream-builder-sandbox.test.ts +4 -0
  190. package/src/server/ai-gateway/__tests__/chat-stream-builder-skills.test.ts +4 -0
  191. package/src/server/ai-gateway/__tests__/pgvector-memory-adapter.test.ts +30 -0
  192. package/src/server/ai-gateway/__tests__/pgvector-memory-conformance.test.ts +92 -0
  193. package/src/server/ai-gateway/__tests__/source-mode.test.ts +49 -8
  194. package/src/server/ai-gateway/ai-output-guard.ts +50 -2
  195. package/src/server/ai-gateway/chat-stream-builder.ts +3 -0
  196. package/src/server/ai-gateway/media/index.ts +36 -29
  197. package/src/server/ai-gateway/media/trim-input.ts +52 -0
  198. package/src/server/ai-gateway/memory/pgvector-adapter.ts +27 -13
  199. package/src/server/ai-gateway/sandbox/__tests__/harness-sandbox.test.ts +252 -41
  200. package/src/server/ai-gateway/sandbox/harness-sandbox.ts +6 -67
  201. package/src/server/ai-gateway/source-mode.ts +24 -8
  202. package/src/server/desktop-bootstrap.ts +74 -0
  203. package/src/server/lib/__tests__/rate-limit.test.ts +0 -1
  204. package/src/server/lib/rate-limit.ts +0 -2
  205. package/src/server/middlewares/__tests__/auth-context.test.ts +156 -0
  206. package/src/server/middlewares/auth-context.ts +62 -0
  207. package/src/server/remote-auth.ts +58 -31
  208. package/src/server/serverFns/__tests__/ai-hosted-models.test.ts +47 -15
  209. package/src/server/serverFns/__tests__/ai-source-mode.test.ts +45 -15
  210. package/src/server/serverFns/__tests__/billing.test.ts +37 -2
  211. package/src/server/serverFns/__tests__/collab-snapshot.test.ts +41 -14
  212. package/src/server/serverFns/__tests__/collab.test.ts +41 -14
  213. package/src/server/serverFns/__tests__/compliance.test.ts +33 -1
  214. package/src/server/serverFns/__tests__/email-verification.test.ts +35 -1
  215. package/src/server/serverFns/__tests__/knowledge-breadcrumb.test.ts +46 -6
  216. package/src/server/serverFns/__tests__/knowledge-delete.test.ts +42 -14
  217. package/src/server/serverFns/__tests__/knowledge-kb-projects.test.ts +46 -6
  218. package/src/server/serverFns/__tests__/knowledge-public-compliance.test.ts +36 -2
  219. package/src/server/serverFns/__tests__/knowledge-readable-kb.test.ts +42 -10
  220. package/src/server/serverFns/__tests__/knowledge-search.test.ts +45 -9
  221. package/src/server/serverFns/__tests__/legal-code-canonical.test.ts +36 -2
  222. package/src/server/serverFns/__tests__/link-preview.test.ts +38 -4
  223. package/src/server/serverFns/__tests__/notifications-list.test.ts +36 -3
  224. package/src/server/serverFns/__tests__/ownership-merge.test.ts +38 -4
  225. package/src/server/serverFns/__tests__/project-delete-transaction.test.ts +39 -2
  226. package/src/server/serverFns/__tests__/project-kb.test.ts +34 -1
  227. package/src/server/serverFns/__tests__/project-member-idor.test.ts +34 -1
  228. package/src/server/serverFns/__tests__/project-team-assign.test.ts +34 -1
  229. package/src/server/serverFns/__tests__/read-write-merge.test.ts +38 -4
  230. package/src/server/serverFns/__tests__/story-comments.test.ts +38 -4
  231. package/src/server/serverFns/__tests__/story-crud-archive-detail.test.ts +38 -4
  232. package/src/server/serverFns/__tests__/story-crud-labels-users.test.ts +37 -3
  233. package/src/server/serverFns/__tests__/story-crud.test.ts +36 -3
  234. package/src/server/serverFns/__tests__/story-links.test.ts +38 -4
  235. package/src/server/serverFns/__tests__/story-reactions.test.ts +38 -4
  236. package/src/server/serverFns/__tests__/story-tree.test.ts +38 -4
  237. package/src/server/serverFns/__tests__/team-accept.test.ts +34 -1
  238. package/src/server/serverFns/__tests__/team-invitation.test.ts +34 -1
  239. package/src/server/serverFns/__tests__/team-join-request.test.ts +34 -1
  240. package/src/server/serverFns/__tests__/team-members.test.ts +34 -1
  241. package/src/server/serverFns/__tests__/team-ownership-merge.test.ts +34 -1
  242. package/src/server/serverFns/__tests__/update-bug-guard.test.ts +37 -3
  243. package/src/server/serverFns/__tests__/update-document-guard.test.ts +38 -4
  244. package/src/server/serverFns/__tests__/update-page-guard.test.ts +40 -4
  245. package/src/server/serverFns/__tests__/update-seats.test.ts +33 -1
  246. package/src/server/serverFns/__tests__/update-story-guard.test.ts +36 -3
  247. package/src/server/serverFns/__tests__/update-testcase-guard.test.ts +37 -3
  248. package/src/server/serverFns/__tests__/workspace-kb-idor.test.ts +36 -2
  249. package/src/server/serverFns/__tests__/workspace-kb.test.ts +36 -2
  250. package/src/server/serverFns/__tests__/workspace.test.ts +34 -1
  251. package/src/server/serverFns/activity.ts +10 -14
  252. package/src/server/serverFns/agents/agent-crud.ts +16 -15
  253. package/src/server/serverFns/agents/bindings.ts +12 -13
  254. package/src/server/serverFns/agents/skill-crud.ts +16 -15
  255. package/src/server/serverFns/ai/code-mode-readiness.ts +3 -4
  256. package/src/server/serverFns/ai/search-capability.ts +3 -4
  257. package/src/server/serverFns/anyhub/app.ts +10 -14
  258. package/src/server/serverFns/anyhub/index.ts +7 -10
  259. package/src/server/serverFns/anyhub/install.ts +4 -4
  260. package/src/server/serverFns/anyhub/permissions.ts +10 -14
  261. package/src/server/serverFns/anyhub/proxy.ts +4 -6
  262. package/src/server/serverFns/auth/email-verification.ts +4 -5
  263. package/src/server/serverFns/auth/session.ts +9 -0
  264. package/src/server/serverFns/billing.ts +18 -28
  265. package/src/server/serverFns/blob-upload.ts +6 -9
  266. package/src/server/serverFns/bug/__tests__/bug-access-tokens.test.ts +34 -1
  267. package/src/server/serverFns/bug/__tests__/bug-activities.test.ts +34 -1
  268. package/src/server/serverFns/bug/__tests__/bug-comments.test.ts +34 -1
  269. package/src/server/serverFns/bug/__tests__/bug-crud.test.ts +34 -1
  270. package/src/server/serverFns/bug/__tests__/bug-fix.test.ts +34 -1
  271. package/src/server/serverFns/bug/__tests__/bug-groups.test.ts +34 -1
  272. package/src/server/serverFns/bug/__tests__/bug-reactions.test.ts +34 -1
  273. package/src/server/serverFns/bug/__tests__/bug-reorder.test.ts +39 -5
  274. package/src/server/serverFns/bug/__tests__/bug-repro.test.ts +34 -1
  275. package/src/server/serverFns/bug/__tests__/bug-story.test.ts +34 -1
  276. package/src/server/serverFns/bug/__tests__/bug-webhooks.test.ts +34 -1
  277. package/src/server/serverFns/bug/bug-access-tokens.ts +16 -22
  278. package/src/server/serverFns/bug/bug-activities.ts +4 -6
  279. package/src/server/serverFns/bug/bug-collect-tokens.ts +13 -18
  280. package/src/server/serverFns/bug/bug-comments.ts +13 -18
  281. package/src/server/serverFns/bug/bug-crud/detail.ts +10 -14
  282. package/src/server/serverFns/bug/bug-crud.ts +28 -38
  283. package/src/server/serverFns/bug/bug-display-options.ts +8 -11
  284. package/src/server/serverFns/bug/bug-export.ts +5 -7
  285. package/src/server/serverFns/bug/bug-fix.ts +10 -14
  286. package/src/server/serverFns/bug/bug-groups.ts +10 -14
  287. package/src/server/serverFns/bug/bug-reactions.ts +10 -14
  288. package/src/server/serverFns/bug/bug-reorder.ts +4 -6
  289. package/src/server/serverFns/bug/bug-repro.ts +8 -11
  290. package/src/server/serverFns/bug/bug-story-bulk.ts +13 -18
  291. package/src/server/serverFns/bug/bug-story.ts +10 -14
  292. package/src/server/serverFns/bug/bug-views.ts +12 -18
  293. package/src/server/serverFns/bug/bug-webhooks.ts +13 -18
  294. package/src/server/serverFns/bug/test-bug-confirm.ts +7 -10
  295. package/src/server/serverFns/changelog/__tests__/fetch.test.ts +40 -1
  296. package/src/server/serverFns/changelog/fetch.ts +4 -6
  297. package/src/server/serverFns/chat/conversations.ts +17 -28
  298. package/src/server/serverFns/chat/list-messages.ts +4 -7
  299. package/src/server/serverFns/collab-presence.ts +11 -13
  300. package/src/server/serverFns/collab-snapshot.ts +6 -7
  301. package/src/server/serverFns/collab.ts +7 -7
  302. package/src/server/serverFns/compliance.ts +8 -8
  303. package/src/server/serverFns/design/__tests__/comments.test.ts +54 -10
  304. package/src/server/serverFns/design/__tests__/designs.test.ts +39 -16
  305. package/src/server/serverFns/design/__tests__/page-versions.test.ts +52 -14
  306. package/src/server/serverFns/design/__tests__/shares-password.test.ts +44 -14
  307. package/src/server/serverFns/design/__tests__/shares.test.ts +44 -14
  308. package/src/server/serverFns/design/__tests__/versions.test.ts +44 -14
  309. package/src/server/serverFns/design/ai/__tests__/agent-conversations.test.ts +50 -21
  310. package/src/server/serverFns/design/ai/__tests__/providers.test.ts +42 -8
  311. package/src/server/serverFns/design/ai/agent-conversations.ts +19 -26
  312. package/src/server/serverFns/design/ai/fill-annotation.ts +5 -7
  313. package/src/server/serverFns/design/ai/generate-prototype.ts +5 -7
  314. package/src/server/serverFns/design/ai/hosted-models.ts +4 -5
  315. package/src/server/serverFns/design/ai/providers.ts +30 -39
  316. package/src/server/serverFns/design/ai/source-mode.ts +10 -12
  317. package/src/server/serverFns/design/comments.ts +14 -13
  318. package/src/server/serverFns/design/designs.ts +13 -19
  319. package/src/server/serverFns/design/page-versions.ts +17 -18
  320. package/src/server/serverFns/design/pages.ts +17 -18
  321. package/src/server/serverFns/design/reviews.ts +8 -9
  322. package/src/server/serverFns/design/shares-password.ts +13 -19
  323. package/src/server/serverFns/design/shares.ts +22 -31
  324. package/src/server/serverFns/design/versions.ts +8 -9
  325. package/src/server/serverFns/harness/__tests__/attach-prototype.spec.ts +52 -2
  326. package/src/server/serverFns/harness/__tests__/attach-to-kb.spec.ts +52 -2
  327. package/src/server/serverFns/harness/__tests__/attach-to-story-ssrf.spec.ts +52 -2
  328. package/src/server/serverFns/harness/__tests__/attach-to-story.spec.ts +52 -2
  329. package/src/server/serverFns/harness/__tests__/cancel-run.test.ts +40 -15
  330. package/src/server/serverFns/harness/__tests__/extract-attachment.spec.ts +52 -2
  331. package/src/server/serverFns/harness/__tests__/gallery.spec.ts +76 -12
  332. package/src/server/serverFns/harness/__tests__/github-workspace.spec.ts +38 -6
  333. package/src/server/serverFns/harness/__tests__/media-prototype.spec.ts +50 -6
  334. package/src/server/serverFns/harness/__tests__/media.spec.ts +55 -11
  335. package/src/server/serverFns/harness/__tests__/sandbox-policy.test.ts +41 -16
  336. package/src/server/serverFns/harness/__tests__/workspace-files.test.ts +41 -16
  337. package/src/server/serverFns/harness/attach-prototype.ts +4 -4
  338. package/src/server/serverFns/harness/attach-to-kb.ts +4 -4
  339. package/src/server/serverFns/harness/attach-to-story.ts +4 -4
  340. package/src/server/serverFns/harness/cancel-run.ts +4 -6
  341. package/src/server/serverFns/harness/extract-attachment.ts +3 -4
  342. package/src/server/serverFns/harness/gallery.ts +19 -23
  343. package/src/server/serverFns/harness/github-workspace.ts +14 -21
  344. package/src/server/serverFns/harness/media.ts +18 -117
  345. package/src/server/serverFns/harness/sandbox-policy.ts +11 -10
  346. package/src/server/serverFns/harness/search-mention-candidates.ts +4 -6
  347. package/src/server/serverFns/harness/workspace-files.ts +19 -26
  348. package/src/server/serverFns/iteration/__tests__/iteration-auto-schedule.test.ts +35 -3
  349. package/src/server/serverFns/iteration/__tests__/iteration-crud.test.ts +35 -3
  350. package/src/server/serverFns/iteration/__tests__/iteration-stories.test.ts +35 -3
  351. package/src/server/serverFns/iteration/__tests__/iteration-transfer.test.ts +35 -3
  352. package/src/server/serverFns/iteration/iteration-auto-schedule.ts +7 -10
  353. package/src/server/serverFns/iteration/iteration-burndown.ts +4 -6
  354. package/src/server/serverFns/iteration/iteration-crud.ts +26 -35
  355. package/src/server/serverFns/iteration/iteration-stories.ts +10 -14
  356. package/src/server/serverFns/iteration/iteration-transfer.ts +4 -6
  357. package/src/server/serverFns/knowledge/public/bookmarks/categories.ts +11 -15
  358. package/src/server/serverFns/knowledge/public/bookmarks/create.ts +4 -6
  359. package/src/server/serverFns/knowledge/public/bookmarks/delete.ts +5 -7
  360. package/src/server/serverFns/knowledge/public/bookmarks/detail.ts +4 -6
  361. package/src/server/serverFns/knowledge/public/bookmarks/favorite.ts +4 -6
  362. package/src/server/serverFns/knowledge/public/bookmarks/list.ts +4 -6
  363. package/src/server/serverFns/knowledge/public/bookmarks/refresh-favicon.ts +4 -6
  364. package/src/server/serverFns/knowledge/public/bookmarks/share.ts +4 -6
  365. package/src/server/serverFns/knowledge/public/bookmarks/sync-github.ts +5 -7
  366. package/src/server/serverFns/knowledge/public/bookmarks/unshare.ts +4 -6
  367. package/src/server/serverFns/knowledge/public/bookmarks/update.ts +6 -8
  368. package/src/server/serverFns/knowledge/public/compliance/create.ts +4 -6
  369. package/src/server/serverFns/knowledge/public/compliance/delete.ts +5 -7
  370. package/src/server/serverFns/knowledge/public/compliance/detail.ts +4 -6
  371. package/src/server/serverFns/knowledge/public/compliance/list.ts +4 -6
  372. package/src/server/serverFns/knowledge/public/compliance/share.ts +4 -6
  373. package/src/server/serverFns/knowledge/public/compliance/unshare.ts +4 -6
  374. package/src/server/serverFns/knowledge/public/compliance/update.ts +5 -7
  375. package/src/server/serverFns/knowledge/public/dictionary/create.ts +4 -6
  376. package/src/server/serverFns/knowledge/public/dictionary/delete.ts +5 -7
  377. package/src/server/serverFns/knowledge/public/dictionary/detail.ts +4 -6
  378. package/src/server/serverFns/knowledge/public/dictionary/list.ts +4 -6
  379. package/src/server/serverFns/knowledge/public/dictionary/share.ts +4 -6
  380. package/src/server/serverFns/knowledge/public/dictionary/unshare.ts +4 -6
  381. package/src/server/serverFns/knowledge/public/dictionary/update.ts +5 -7
  382. package/src/server/serverFns/knowledge/public/entity-tags.ts +4 -6
  383. package/src/server/serverFns/knowledge/public/favorite.ts +7 -10
  384. package/src/server/serverFns/knowledge/public/legal/create.ts +4 -6
  385. package/src/server/serverFns/knowledge/public/legal/delete.ts +5 -7
  386. package/src/server/serverFns/knowledge/public/legal/detail.ts +4 -6
  387. package/src/server/serverFns/knowledge/public/legal/list.ts +4 -6
  388. package/src/server/serverFns/knowledge/public/legal/share.ts +4 -6
  389. package/src/server/serverFns/knowledge/public/legal/unshare.ts +4 -6
  390. package/src/server/serverFns/knowledge/public/legal/update.ts +5 -7
  391. package/src/server/serverFns/knowledge-index.ts +12 -16
  392. package/src/server/serverFns/knowledge.ts +50 -67
  393. package/src/server/serverFns/notifications.ts +25 -34
  394. package/src/server/serverFns/plugins/harness-plugins.ts +16 -23
  395. package/src/server/serverFns/project/module-overview.ts +7 -10
  396. package/src/server/serverFns/project.ts +48 -68
  397. package/src/server/serverFns/references/create.ts +4 -6
  398. package/src/server/serverFns/references/resolve.ts +4 -6
  399. package/src/server/serverFns/references/search.ts +4 -6
  400. package/src/server/serverFns/share/design/[designId]/events.ts +4 -6
  401. package/src/server/serverFns/sso.ts +1 -1
  402. package/src/server/serverFns/story/__tests__/bulk.test.ts +34 -1
  403. package/src/server/serverFns/story/__tests__/story-assoc.test.ts +34 -1
  404. package/src/server/serverFns/story/__tests__/story-attachments.test.ts +34 -1
  405. package/src/server/serverFns/story/__tests__/story-crud-date-key.test.ts +42 -17
  406. package/src/server/serverFns/story/__tests__/story-dependencies.test.ts +34 -1
  407. package/src/server/serverFns/story/__tests__/story-gantt-deps.test.ts +34 -1
  408. package/src/server/serverFns/story/__tests__/story-groups.test.ts +34 -1
  409. package/src/server/serverFns/story/__tests__/story-read-path-authz.test.ts +40 -4
  410. package/src/server/serverFns/story/__tests__/story-search.test.ts +34 -1
  411. package/src/server/serverFns/story/__tests__/story-transfer.test.ts +34 -1
  412. package/src/server/serverFns/story/link-preview.ts +5 -7
  413. package/src/server/serverFns/story/story-assoc.ts +28 -38
  414. package/src/server/serverFns/story/story-attachments.ts +7 -10
  415. package/src/server/serverFns/story/story-children.ts +4 -6
  416. package/src/server/serverFns/story/story-comments.ts +13 -18
  417. package/src/server/serverFns/story/story-crud/activities.ts +4 -6
  418. package/src/server/serverFns/story/story-crud/archive.ts +7 -10
  419. package/src/server/serverFns/story/story-crud/bulk.ts +10 -14
  420. package/src/server/serverFns/story/story-crud/detail.ts +7 -10
  421. package/src/server/serverFns/story/story-crud/label-suggest.ts +4 -6
  422. package/src/server/serverFns/story/story-crud/labels.ts +6 -9
  423. package/src/server/serverFns/story/story-crud/user-brief.ts +4 -6
  424. package/src/server/serverFns/story/story-crud.ts +13 -18
  425. package/src/server/serverFns/story/story-dependencies.ts +16 -22
  426. package/src/server/serverFns/story/story-groups.ts +10 -14
  427. package/src/server/serverFns/story/story-links.ts +13 -18
  428. package/src/server/serverFns/story/story-reactions.ts +13 -18
  429. package/src/server/serverFns/story/story-search.ts +7 -10
  430. package/src/server/serverFns/story/story-transfer.ts +10 -14
  431. package/src/server/serverFns/story/story-tree.ts +7 -10
  432. package/src/server/serverFns/story-display-options.ts +7 -8
  433. package/src/server/serverFns/story-view.ts +12 -18
  434. package/src/server/serverFns/tasks/task-crud.ts +13 -17
  435. package/src/server/serverFns/tasks/task-queries.ts +12 -18
  436. package/src/server/serverFns/team.ts +46 -66
  437. package/src/server/serverFns/testcase/__tests__/automation.test.ts +38 -5
  438. package/src/server/serverFns/testcase/__tests__/evidence-upload.test.ts +37 -3
  439. package/src/server/serverFns/testcase/__tests__/generation.test.ts +38 -5
  440. package/src/server/serverFns/testcase/__tests__/plans.test.ts +36 -3
  441. package/src/server/serverFns/testcase/__tests__/regression.test.ts +36 -3
  442. package/src/server/serverFns/testcase/__tests__/run-cases.test.ts +36 -3
  443. package/src/server/serverFns/testcase/__tests__/runs.test.ts +36 -3
  444. package/src/server/serverFns/testcase/__tests__/stats.test.ts +36 -3
  445. package/src/server/serverFns/testcase/__tests__/testcase-board.test.ts +39 -5
  446. package/src/server/serverFns/testcase/__tests__/testcase-crud.test.ts +36 -3
  447. package/src/server/serverFns/testcase/__tests__/testcase-folders.test.ts +36 -3
  448. package/src/server/serverFns/testcase/__tests__/testcase-groups.test.ts +38 -5
  449. package/src/server/serverFns/testcase/automation.ts +13 -17
  450. package/src/server/serverFns/testcase/bulk.ts +10 -14
  451. package/src/server/serverFns/testcase/evidence-upload.ts +5 -7
  452. package/src/server/serverFns/testcase/generation.ts +10 -13
  453. package/src/server/serverFns/testcase/plans.ts +23 -31
  454. package/src/server/serverFns/testcase/regression.ts +7 -10
  455. package/src/server/serverFns/testcase/run-cases.ts +13 -18
  456. package/src/server/serverFns/testcase/runs.ts +13 -18
  457. package/src/server/serverFns/testcase/stats.ts +13 -18
  458. package/src/server/serverFns/testcase/testcase-activities.ts +4 -6
  459. package/src/server/serverFns/testcase/testcase-board.ts +4 -6
  460. package/src/server/serverFns/testcase/testcase-crud.ts +20 -27
  461. package/src/server/serverFns/testcase/testcase-display-options.ts +8 -11
  462. package/src/server/serverFns/testcase/testcase-export.ts +5 -7
  463. package/src/server/serverFns/testcase/testcase-filter-views.ts +12 -18
  464. package/src/server/serverFns/testcase/testcase-folders.ts +16 -22
  465. package/src/server/serverFns/testcase/testcase-groups.ts +4 -6
  466. package/src/server/serverFns/testcase/testcase-reorder.ts +4 -6
  467. package/src/server/serverFns/translation.ts +4 -6
  468. package/src/server/serverFns/user/avatar.ts +4 -6
  469. package/src/server/serverFns/user/settings.ts +4 -6
  470. package/src/server/serverFns/user/update-locale.ts +4 -6
  471. package/src/server/serverFns/workspace-kb.ts +26 -35
  472. package/src/server/serverFns/workspace.ts +43 -59
  473. package/src/server/serverFns/ws.ts +4 -6
  474. package/src/server/serverfn-public-allowlist.ts +117 -0
  475. package/src/server/story/types.ts +0 -1
  476. package/src/server/sync/__tests__/scopes.test.ts +64 -0
  477. package/src/server/sync/scopes.ts +7 -0
  478. package/src/server/testcase/__tests__/auto-bug.test.ts +44 -12
  479. package/src/__tests__/bench/baselines/format-timestamp.json +0 -44
  480. package/src/__typeprobe__.d.ts +0 -4
  481. package/src/components/forms/app-form-dialog.tsx +0 -126
  482. package/src/components/forms/hooks/use-form-submit.ts +0 -57
  483. package/src/components/forms/types.ts +0 -34
  484. package/src/components/harness/code/workspace-picker.tsx +0 -239
  485. package/src/components/tiptap/extensions/local-file/insert-local-file.ts +0 -35
  486. package/src/components/tiptap/extensions/local-file/local-file-node.ts +0 -71
  487. package/src/devframe-docks/ai-chat-iframe.tsx +0 -29
  488. package/src/devframe-docks/session-iframe.tsx +0 -90
  489. package/src/lib/__tests__/desktop-detect.test.ts +0 -19
  490. package/src/lib/collections/index.ts +0 -22
  491. package/src/lib/collections/knowledge/index.ts +0 -18
  492. package/src/lib/collections/knowledge/knowledge-bases-collection.ts +0 -34
  493. package/src/lib/collections/reference/bookmark-categories-collection.ts +0 -31
  494. package/src/lib/collections/reference/labels-collection.ts +0 -31
  495. package/src/lib/collections/reference/projects-collection.ts +0 -31
  496. package/src/lib/collections/reference/users-brief-collection.ts +0 -35
  497. package/src/lib/collections/reference/workspaces-collection.ts +0 -34
  498. package/src/lib/desktop-detect.ts +0 -29
  499. package/src/paraglide/messages/en.js +0 -28260
  500. package/src/paraglide/messages/zh.js +0 -28258
@@ -20,23 +20,54 @@ const mocks = vi.hoisted(() => ({
20
20
  }));
21
21
 
22
22
  vi.mock("@tanstack/react-start", () => ({
23
- createServerFn: () => ({
24
- validator(schema: { parse: (v: unknown) => unknown }) {
25
- const api = {
26
- _validator: schema,
27
- handler(fn: Function) {
28
- const validator = (this as { _validator?: { parse: (v: unknown) => unknown } })
29
- ._validator;
30
- return async (args: { data?: unknown }) => {
31
- let data = args?.data;
32
- if (validator && data !== undefined) data = validator.parse(data);
33
- return fn({ data });
34
- };
35
- },
36
- };
37
- return api;
38
- },
39
- }),
23
+ // 迁移后经 .middleware([authContextMiddleware]) 注入 context.user:
24
+ // mock 依序执行 middleware 的 server 段(复现框架 executeMiddleware 的
25
+ // context 合并语义),真实鉴权链由被 mock 的 auth-helpers/getRequest 承接
26
+ createServerFn: () => {
27
+ const api: any = {
28
+ _middlewares: [] as any[],
29
+ middleware(mws: any[]) {
30
+ api._middlewares.push(...mws);
31
+ return api;
32
+ },
33
+ validator(schema: { parse: (v: unknown) => unknown }) {
34
+ api._validator = schema;
35
+ return api;
36
+ },
37
+ handler(fn: Function) {
38
+ return async (args: { data?: unknown }) => {
39
+ let data = args?.data;
40
+ if (api._validator && data !== undefined) data = api._validator.parse(data);
41
+ let context: any = {};
42
+ for (const mw of api._middlewares) {
43
+ const serverFn = mw?.options?.server;
44
+ if (!serverFn) continue;
45
+ const result = await serverFn({
46
+ data,
47
+ context,
48
+ method: "POST",
49
+ serverFnMeta: {},
50
+ signal: new AbortController().signal,
51
+ next: async (inner: any) => ({ context: { ...context, ...(inner?.context ?? {}) } }),
52
+ });
53
+ context = result.context;
54
+ }
55
+ return fn({ data, context });
56
+ };
57
+ },
58
+ };
59
+ return api;
60
+ },
61
+ // auth-context.ts 依赖 createMiddleware({ type: "function" }).server(fn):
62
+ // mock 产出与真实 middleware 同构的 { options: { server } } 形状
63
+ createMiddleware: (opts: any) => {
64
+ const mw: any = { options: { type: opts?.type } };
65
+ mw.server = (fn: Function) => {
66
+ mw.options.server = fn;
67
+ return mw;
68
+ };
69
+ return mw;
70
+ },
40
71
  }));
41
72
 
42
73
  vi.mock("@tanstack/react-start/server", () => ({
@@ -63,10 +94,8 @@ vi.mock("@/server/design/access", () => ({
63
94
  assertDesignOwner: mocks.assertDesignOwner,
64
95
  }));
65
96
 
66
- // getServerSeam 来自 @allbluecn/kernel(真实包),这里替 requireAuth 打桩
67
- vi.mock("@allbluecn/kernel", () => ({
68
- getServerSeam: () => ({ requireAuth: mocks.requireAuth }),
69
- }));
97
+ // 迁移后 requireAuth 消费入口:authContextMiddleware 内部调用
98
+ vi.mock("@/server/auth-helpers", () => ({ requireAuth: mocks.requireAuth }));
70
99
 
71
100
  import {
72
101
  clearAgentConversationsFn,
@@ -22,24 +22,54 @@ const mocks = vi.hoisted(() => ({
22
22
  }));
23
23
 
24
24
  vi.mock("@tanstack/react-start", () => ({
25
+ // 迁移后经 .middleware([authContextMiddleware]) 注入 context.user:
26
+ // mock 依序执行 middleware 的 server 段(复现框架 executeMiddleware 的
27
+ // context 合并语义),真实鉴权链由被 mock 的 auth-helpers/getRequest 承接
25
28
  createServerFn: () => {
26
- const api = {
27
- _validator: undefined as { parse: (v: unknown) => unknown } | undefined,
29
+ const api: any = {
30
+ _middlewares: [] as any[],
31
+ middleware(mws: any[]) {
32
+ api._middlewares.push(...mws);
33
+ return api;
34
+ },
28
35
  validator(schema: { parse: (v: unknown) => unknown }) {
29
- this._validator = schema;
30
- return this;
36
+ api._validator = schema;
37
+ return api;
31
38
  },
32
39
  handler(fn: Function) {
33
- const validator = this._validator;
34
40
  return async (args: { data?: unknown }) => {
35
41
  let data = args?.data;
36
- if (validator && data !== undefined) data = validator.parse(data);
37
- return fn({ data });
42
+ if (api._validator && data !== undefined) data = api._validator.parse(data);
43
+ let context: any = {};
44
+ for (const mw of api._middlewares) {
45
+ const serverFn = mw?.options?.server;
46
+ if (!serverFn) continue;
47
+ const result = await serverFn({
48
+ data,
49
+ context,
50
+ method: "POST",
51
+ serverFnMeta: {},
52
+ signal: new AbortController().signal,
53
+ next: async (inner: any) => ({ context: { ...context, ...(inner?.context ?? {}) } }),
54
+ });
55
+ context = result.context;
56
+ }
57
+ return fn({ data, context });
38
58
  };
39
59
  },
40
60
  };
41
61
  return api;
42
62
  },
63
+ // auth-context.ts 依赖 createMiddleware({ type: "function" }).server(fn):
64
+ // mock 产出与真实 middleware 同构的 { options: { server } } 形状
65
+ createMiddleware: (opts: any) => {
66
+ const mw: any = { options: { type: opts?.type } };
67
+ mw.server = (fn: Function) => {
68
+ mw.options.server = fn;
69
+ return mw;
70
+ };
71
+ return mw;
72
+ },
43
73
  }));
44
74
 
45
75
  vi.mock("@tanstack/react-start/server", () => ({
@@ -82,9 +112,13 @@ vi.mock("@/server/ai-gateway", () => ({
82
112
  fetchProviderModels: mocks.fetchProviderModels,
83
113
  }));
84
114
 
115
+ // 迁移后 requireAuth 消费入口:authContextMiddleware 内部调用
116
+ vi.mock("@/server/auth-helpers", () => ({
117
+ requireAuth: mocks.requireAuth,
118
+ }));
119
+
85
120
  vi.mock("@allbluecn/kernel", () => ({
86
121
  getServerSeam: () => ({
87
- requireAuth: mocks.requireAuth,
88
122
  requireUserInDb: mocks.requireUserInDb,
89
123
  }),
90
124
  // 本测试经 providers.ts → adapter.ts(invalidateAiConfigCache)引入 seam 注册调用
@@ -16,10 +16,9 @@
16
16
  // along with this program. If not, see <https://www.gnu.org/licenses/>.
17
17
 
18
18
  import { createServerFn } from "@tanstack/react-start"
19
- import { getRequest } from "@tanstack/react-start/server"
19
+ import { authContextMiddleware } from "@/server/middlewares/auth-context"
20
20
  import { z } from "zod"
21
21
  import { getPrisma } from "@allbluecn/database/get-prisma"
22
- import { getServerSeam } from "@allbluecn/kernel"
23
22
  import { assertDesignOwner } from "@/server/design/access"
24
23
 
25
24
  // 会话消息一次返回上限:Agent 会话量级有限,封顶防异常长会话一次性大返回
@@ -27,13 +26,12 @@ const MESSAGES_LIMIT = 500
27
26
 
28
27
  /** 列出用户在某个 PRD 下的所有 Agent 会话 */
29
28
  export const listAgentConversationsFn = createServerFn({ method: "GET" })
29
+ .middleware([authContextMiddleware])
30
30
  .validator(z.object({ designId: z.string() }))
31
- .handler(async ({ data }) => {
31
+ .handler(async ({ data, context }) => {
32
32
  const prisma = await getPrisma()
33
- const request = getRequest()
34
- const session = await getServerSeam().requireAuth(request)
35
33
  return prisma.agentConversation.findMany({
36
- where: { userId: session.user.id, designId: data.designId },
34
+ where: { userId: context.user.id, designId: data.designId },
37
35
  orderBy: { updatedAt: "desc" },
38
36
  select: { id: true, title: true, createdAt: true, updatedAt: true },
39
37
  })
@@ -41,12 +39,11 @@ export const listAgentConversationsFn = createServerFn({ method: "GET" })
41
39
 
42
40
  /** 新建会话 */
43
41
  export const createAgentConversationFn = createServerFn({ method: "POST" })
42
+ .middleware([authContextMiddleware])
44
43
  .validator(z.object({ designId: z.string(), title: z.string().optional() }))
45
- .handler(async ({ data }) => {
44
+ .handler(async ({ data, context }) => {
46
45
  const prisma = await getPrisma()
47
- const request = getRequest()
48
- const session = await getServerSeam().requireAuth(request)
49
- const userId = session.user.id
46
+ const userId = context.user.id
50
47
  // designId 是客户端任意传入的关联键,创建前校验属主,防向他人 design 挂垃圾会话行
51
48
  await assertDesignOwner(data.designId, userId)
52
49
  return prisma.agentConversation.create({
@@ -60,25 +57,23 @@ export const createAgentConversationFn = createServerFn({ method: "POST" })
60
57
 
61
58
  /** 删除单个会话(含消息,级联删除) */
62
59
  export const deleteAgentConversationFn = createServerFn({ method: "POST" })
60
+ .middleware([authContextMiddleware])
63
61
  .validator(z.object({ id: z.string() }))
64
- .handler(async ({ data }) => {
62
+ .handler(async ({ data, context }) => {
65
63
  const prisma = await getPrisma()
66
- const request = getRequest()
67
- const session = await getServerSeam().requireAuth(request)
68
64
  await prisma.agentConversation.deleteMany({
69
- where: { id: data.id, userId: session.user.id },
65
+ where: { id: data.id, userId: context.user.id },
70
66
  })
71
67
  return { deleted: true }
72
68
  })
73
69
 
74
70
  /** 清除某 PRD 下的全部会话 */
75
71
  export const clearAgentConversationsFn = createServerFn({ method: "POST" })
72
+ .middleware([authContextMiddleware])
76
73
  .validator(z.object({ designId: z.string() }))
77
- .handler(async ({ data }) => {
74
+ .handler(async ({ data, context }) => {
78
75
  const prisma = await getPrisma()
79
- const request = getRequest()
80
- const session = await getServerSeam().requireAuth(request)
81
- const userId = session.user.id
76
+ const userId = context.user.id
82
77
  // 与 create 同口径:designId 非本人 design 时拒绝,避免以他人 designId 维度清写
83
78
  await assertDesignOwner(data.designId, userId)
84
79
  await prisma.agentConversation.deleteMany({
@@ -89,13 +84,12 @@ export const clearAgentConversationsFn = createServerFn({ method: "POST" })
89
84
 
90
85
  /** 获取会话消息 */
91
86
  export const getAgentMessagesFn = createServerFn({ method: "GET" })
87
+ .middleware([authContextMiddleware])
92
88
  .validator(z.object({ conversationId: z.string() }))
93
- .handler(async ({ data }) => {
89
+ .handler(async ({ data, context }) => {
94
90
  const prisma = await getPrisma()
95
- const request = getRequest()
96
- const session = await getServerSeam().requireAuth(request)
97
91
  const conv = await prisma.agentConversation.findFirst({
98
- where: { id: data.conversationId, userId: session.user.id },
92
+ where: { id: data.conversationId, userId: context.user.id },
99
93
  select: { id: true },
100
94
  })
101
95
  if (!conv) throw new Error("会话不存在")
@@ -117,6 +111,7 @@ export const getAgentMessagesFn = createServerFn({ method: "GET" })
117
111
 
118
112
  /** 保存消息到会话 */
119
113
  export const saveAgentMessageFn = createServerFn({ method: "POST" })
114
+ .middleware([authContextMiddleware])
120
115
  .validator(
121
116
  z.object({
122
117
  conversationId: z.string(),
@@ -126,12 +121,10 @@ export const saveAgentMessageFn = createServerFn({ method: "POST" })
126
121
  isError: z.boolean().default(false),
127
122
  }),
128
123
  )
129
- .handler(async ({ data }) => {
124
+ .handler(async ({ data, context }) => {
130
125
  const prisma = await getPrisma()
131
- const request = getRequest()
132
- const session = await getServerSeam().requireAuth(request)
133
126
  const conv = await prisma.agentConversation.findFirst({
134
- where: { id: data.conversationId, userId: session.user.id },
127
+ where: { id: data.conversationId, userId: context.user.id },
135
128
  select: { id: true },
136
129
  })
137
130
  if (!conv) throw new Error("会话不存在")
@@ -16,9 +16,8 @@
16
16
  // along with this program. If not, see <https://www.gnu.org/licenses/>.
17
17
 
18
18
  import { createServerFn } from "@tanstack/react-start"
19
- import { getRequest } from "@tanstack/react-start/server"
19
+ import { authContextMiddleware } from "@/server/middlewares/auth-context"
20
20
  import { z } from "zod"
21
- import { getServerSeam } from "@allbluecn/kernel"
22
21
  import { checkAiRateLimit } from "@/server/lib/rate-limit"
23
22
  import { runChatWithModel } from "@/server/ai-gateway"
24
23
  import { buildFillPrompt } from "@/server/design/annotation-prompt"
@@ -60,12 +59,11 @@ function stripCodeFence(raw: string): string {
60
59
  }
61
60
 
62
61
  export const fillAnnotationFn = createServerFn({ method: "POST" })
62
+ .middleware([authContextMiddleware])
63
63
  .validator(inputSchema)
64
- .handler(async ({ data }) => {
65
- const request = getRequest()
66
- const session = await getServerSeam().requireAuth(request)
64
+ .handler(async ({ data, context }) => {
67
65
  // 托管 AI 计费调用,与同域 generatePrototype 同口径 per-user 频控
68
- await checkAiRateLimit(session.user.id, "fillAnnotation")
66
+ await checkAiRateLimit(context.user.id, "fillAnnotation")
69
67
 
70
68
  const systemPrompts = await buildFillPrompt({
71
69
  type: data.componentType,
@@ -79,7 +77,7 @@ export const fillAnnotationFn = createServerFn({ method: "POST" })
79
77
  [{ role: "user", content: "请根据组件信息填充注释模板。" }],
80
78
  {
81
79
  systemPrompts,
82
- userId: session.user.id,
80
+ userId: context.user.id,
83
81
  model: data.model,
84
82
  },
85
83
  )
@@ -16,9 +16,8 @@
16
16
  // along with this program. If not, see <https://www.gnu.org/licenses/>.
17
17
 
18
18
  import { createServerFn } from "@tanstack/react-start"
19
- import { getRequest } from "@tanstack/react-start/server"
19
+ import { authContextMiddleware } from "@/server/middlewares/auth-context"
20
20
  import { z } from "zod"
21
- import { getServerSeam } from "@allbluecn/kernel"
22
21
  import { checkAiRateLimit } from "@/server/lib/rate-limit"
23
22
  import { runChatAsAgent } from "@/server/ai-gateway"
24
23
  import { prototypeSchema, extractJsonObject, type PrototypeResult } from "@/server/ai-gateway/media/prototype-schema"
@@ -33,14 +32,13 @@ const inputSchema = z.object({
33
32
  })
34
33
 
35
34
  export const generatePrototypeFn = createServerFn({ method: "POST" })
35
+ .middleware([authContextMiddleware])
36
36
  .validator(inputSchema)
37
- .handler(async ({ data }) => {
37
+ .handler(async ({ data, context }) => {
38
38
  // 降级路径(FS-8.3):AI 不支持流式输出的模型走本非流式入口。
39
39
  // 流式主路径为 SSE 路由 /api/design/prototype(routes/api/design/prototype/route.ts),
40
40
  // 前端按模型能力选择通道;本入口保留旧一次性 JSON 返回形态,不删除。
41
- const request = getRequest()
42
- const session = await getServerSeam().requireAuth(request)
43
- await checkAiRateLimit(session.user.id, "generatePrototype")
41
+ await checkAiRateLimit(context.user.id, "generatePrototype")
44
42
  const { prompt, model } = data
45
43
 
46
44
  const types = [...serverRegisteredTypes()]
@@ -56,7 +54,7 @@ export const generatePrototypeFn = createServerFn({ method: "POST" })
56
54
  "design.prototype",
57
55
  [{ role: "user", content: prompt }],
58
56
  {
59
- userId: session.user.id,
57
+ userId: context.user.id,
60
58
  model,
61
59
  promptVars: { schemaHint: buildSceneSchemaHint(types), catalog },
62
60
  },
@@ -16,14 +16,13 @@
16
16
  // along with this program. If not, see <https://www.gnu.org/licenses/>.
17
17
 
18
18
  import { createServerFn } from '@tanstack/react-start'
19
- import { getRequest } from '@tanstack/react-start/server'
20
- import { getServerSeam } from '@allbluecn/kernel'
19
+ import { authContextMiddleware } from '@/server/middlewares/auth-context'
21
20
  import { getProService } from '@/server/ai-gateway/pro-services'
22
21
 
23
22
  export const listHostedModelsFn = createServerFn({ method: 'GET' })
24
- .handler(async () => {
25
- const session = await getServerSeam().requireAuth(getRequest())
26
- if (session?.user?.role !== 'SUPER_ADMIN') return { models: [], enabled: false }
23
+ .middleware([authContextMiddleware])
24
+ .handler(async ({ context }) => {
25
+ if (context.user.role !== 'SUPER_ADMIN') return { models: [], enabled: false }
27
26
  // HostedAiService 契约当前仅 chatStream(kernel pro-contract/hosted-ai.ts)。
28
27
  // 模型目录待 Pro 侧扩展 listModels 后接入;当前 OSS/Pro 均返回空列表,页面显示预留空态。
29
28
  const hosted = getProService('hostedAi')
@@ -17,7 +17,7 @@
17
17
 
18
18
  // apps/web/src/server/serverFns/design/ai/providers.ts
19
19
  import { createServerFn } from "@tanstack/react-start"
20
- import { getRequest } from "@tanstack/react-start/server"
20
+ import { authContextMiddleware } from "@/server/middlewares/auth-context"
21
21
  import { z } from "zod"
22
22
  import { getPrisma } from "@allbluecn/database/get-prisma"
23
23
  import type { Prisma } from "@allbluecn/database"
@@ -91,24 +91,22 @@ function dbRowToMeta(provider: {
91
91
  }
92
92
 
93
93
  /** 列出当前用户可见的所有服务商(平台启用 ∪ 用户已配置) */
94
- export const listAiProvidersFn = createServerFn({ method: "GET" }).handler(
95
- async () => {
94
+ export const listAiProvidersFn = createServerFn({ method: "GET" })
95
+ .middleware([authContextMiddleware]).handler(
96
+ async ({ context }) => {
96
97
  const prisma = await getPrisma()
97
- const request = getRequest()
98
- const session = await getServerSeam().requireAuth(request)
99
- const userId = session.user.id
98
+ const userId = context.user.id
100
99
  return listVisibleProvidersForUser(userId)
101
100
  },
102
101
  )
103
102
 
104
103
  /** 获取单个 provider 的元数据 + 用户配置 */
105
104
  export const getAiProviderFn = createServerFn({ method: "GET" })
105
+ .middleware([authContextMiddleware])
106
106
  .validator(z.object({ providerId: z.string() }))
107
- .handler(async ({ data }) => {
107
+ .handler(async ({ data, context }) => {
108
108
  const prisma = await getPrisma()
109
- const request = getRequest()
110
- const session = await getServerSeam().requireAuth(request)
111
- const userId = session.user.id
109
+ const userId = context.user.id
112
110
 
113
111
  const provider = await prisma.aiProvider.findUnique({
114
112
  where: { providerId: data.providerId },
@@ -179,12 +177,11 @@ const updateSchema = z.object({
179
177
  })
180
178
 
181
179
  export const updateAiProviderFn = createServerFn({ method: "POST" })
180
+ .middleware([authContextMiddleware])
182
181
  .validator(updateSchema)
183
- .handler(async ({ data }) => {
182
+ .handler(async ({ data, context }) => {
184
183
  const prisma = await getPrisma()
185
- const request = getRequest()
186
- const session = await getServerSeam().requireAuth(request)
187
- const userId = session.user.id
184
+ const userId = context.user.id
188
185
  await getServerSeam().requireUserInDb(userId)
189
186
 
190
187
  const provider = await prisma.aiProvider.findUnique({
@@ -242,12 +239,11 @@ export const updateAiProviderFn = createServerFn({ method: "POST" })
242
239
  })
243
240
 
244
241
  export const deleteAiProviderConfigFn = createServerFn({ method: "POST" })
242
+ .middleware([authContextMiddleware])
245
243
  .validator(z.object({ providerId: z.string() }))
246
- .handler(async ({ data }) => {
244
+ .handler(async ({ data, context }) => {
247
245
  const prisma = await getPrisma()
248
- const request = getRequest()
249
- const session = await getServerSeam().requireAuth(request)
250
- const userId = session.user.id
246
+ const userId = context.user.id
251
247
  await prisma.aiProviderConfig.deleteMany({
252
248
  where: { userId, providerId: data.providerId },
253
249
  })
@@ -262,12 +258,11 @@ export const deleteAiProviderConfigFn = createServerFn({ method: "POST" })
262
258
  * 不删除现有模型(自定义或 API 限制都应保留)。
263
259
  */
264
260
  export const refreshModelsFn = createServerFn({ method: "POST" })
261
+ .middleware([authContextMiddleware])
265
262
  .validator(z.object({ providerId: z.string() }))
266
- .handler(async ({ data }) => {
263
+ .handler(async ({ data, context }) => {
267
264
  const prisma = await getPrisma()
268
- const request = getRequest()
269
- const session = await getServerSeam().requireAuth(request)
270
- const userId = session.user.id
265
+ const userId = context.user.id
271
266
  await getServerSeam().requireUserInDb(userId)
272
267
  await checkAiRateLimit(userId, "refreshModels")
273
268
 
@@ -368,14 +363,13 @@ export const refreshModelsFn = createServerFn({ method: "POST" })
368
363
 
369
364
  /** 创建自定义模型,追加到用户 customModels(id 重复则报错) */
370
365
  export const createCustomModelFn = createServerFn({ method: "POST" })
366
+ .middleware([authContextMiddleware])
371
367
  .validator(
372
368
  z.object({ providerId: z.string(), model: modelMetaSchema }),
373
369
  )
374
- .handler(async ({ data }) => {
370
+ .handler(async ({ data, context }) => {
375
371
  const prisma = await getPrisma()
376
- const request = getRequest()
377
- const session = await getServerSeam().requireAuth(request)
378
- const userId = session.user.id
372
+ const userId = context.user.id
379
373
  await getServerSeam().requireUserInDb(userId)
380
374
 
381
375
  const provider = await prisma.aiProvider.findUnique({
@@ -428,11 +422,10 @@ export const createCustomModelFn = createServerFn({ method: "POST" })
428
422
  })
429
423
 
430
424
  /** 列出当前用户所有已启用 provider 的模型列表(聊天模型选择器用) */
431
- export const listEnabledModelsFn = createServerFn({ method: "GET" }).handler(
432
- async () => {
433
- const request = getRequest()
434
- const session = await getServerSeam().requireAuth(request)
435
- const userId = session.user.id
425
+ export const listEnabledModelsFn = createServerFn({ method: "GET" })
426
+ .middleware([authContextMiddleware]).handler(
427
+ async ({ context }) => {
428
+ const userId = context.user.id
436
429
  return listEnabledModelsForUser(userId)
437
430
  },
438
431
  )
@@ -445,12 +438,11 @@ const testSchema = z.object({
445
438
  })
446
439
 
447
440
  export const testAiProviderFn = createServerFn({ method: "POST" })
441
+ .middleware([authContextMiddleware])
448
442
  .validator(testSchema)
449
- .handler(async ({ data }) => {
443
+ .handler(async ({ data, context }) => {
450
444
  const prisma = await getPrisma()
451
- const request = getRequest()
452
- const session = await getServerSeam().requireAuth(request)
453
- const userId = session.user.id
445
+ const userId = context.user.id
454
446
  await checkAiRateLimit(userId, "testProvider")
455
447
 
456
448
  const provider = await prisma.aiProvider.findUnique({
@@ -497,6 +489,7 @@ const CUSTOM_PROVIDER_MAX_PER_USER = 20
497
489
 
498
490
  /** 用户创建自定义 OpenAI 兼容服务商 */
499
491
  export const createCustomProviderFn = createServerFn({ method: "POST" })
492
+ .middleware([authContextMiddleware])
500
493
  .validator(
501
494
  z.object({
502
495
  displayName: z.string().min(1).max(64),
@@ -505,11 +498,9 @@ export const createCustomProviderFn = createServerFn({ method: "POST" })
505
498
  defaultModel: z.string().min(1),
506
499
  }),
507
500
  )
508
- .handler(async ({ data }) => {
501
+ .handler(async ({ data, context }) => {
509
502
  const prisma = await getPrisma()
510
- const request = getRequest()
511
- const session = await getServerSeam().requireAuth(request)
512
- const userId = session.user.id
503
+ const userId = context.user.id
513
504
  await getServerSeam().requireUserInDb(userId)
514
505
 
515
506
  // 频控:AiProvider 是全局目录表(行被所有用户的可见性查询扫描),
@@ -16,9 +16,9 @@
16
16
  // along with this program. If not, see <https://www.gnu.org/licenses/>.
17
17
 
18
18
  import { createServerFn } from '@tanstack/react-start'
19
- import { getRequest } from '@tanstack/react-start/server'
19
+ import { authContextMiddleware } from '@/server/middlewares/auth-context'
20
20
  import { z } from 'zod'
21
- import { AI_SOURCE_MODES, getServerSeam } from '@allbluecn/kernel'
21
+ import { AI_SOURCE_MODES } from '@allbluecn/kernel'
22
22
  import { GUEST_USER_ID } from '@/server/desktop-guest'
23
23
  import { resolveSourceMode, setSourceMode } from '@/server/ai-gateway/source-mode'
24
24
  import type { AiSourceMode } from '@allbluecn/kernel'
@@ -26,12 +26,11 @@ import type { AiSourceMode } from '@allbluecn/kernel'
26
26
  const modeSchema = z.object({ mode: z.enum(AI_SOURCE_MODES) })
27
27
 
28
28
  export const setAiSourceModeFn = createServerFn({ method: 'POST' })
29
+ .middleware([authContextMiddleware])
29
30
  .validator(modeSchema)
30
- .handler(async ({ data }) => {
31
- const session = await getServerSeam().requireAuth(getRequest())
32
- const userId = session?.user?.id
33
- if (!userId) throw new Error('未登录')
34
- const role = session?.user?.role
31
+ .handler(async ({ data, context }) => {
32
+ const userId = context.user.id
33
+ const role = context.user.role
35
34
  const isGuest = userId === GUEST_USER_ID
36
35
  if (data.mode === 'hosted' && role !== 'SUPER_ADMIN') throw new Error('仅超级管理员可启用平台托管模式')
37
36
  if (data.mode === 'local-agent' && process.env.DEPLOY_TARGET !== 'desktop')
@@ -40,12 +39,11 @@ export const setAiSourceModeFn = createServerFn({ method: 'POST' })
40
39
  })
41
40
 
42
41
  export const getAiSourceModeFn = createServerFn({ method: 'GET' })
43
- .handler(async () => {
44
- const session = await getServerSeam().requireAuth(getRequest())
45
- const userId = session?.user?.id
46
- if (!userId) throw new Error('未登录')
42
+ .middleware([authContextMiddleware])
43
+ .handler(async ({ context }) => {
44
+ const userId = context.user.id
47
45
  const isGuest = userId === GUEST_USER_ID
48
46
  const mode = await resolveSourceMode({ userId, isGuest })
49
- const canHosted = session?.user?.role === 'SUPER_ADMIN'
47
+ const canHosted = context.user.role === 'SUPER_ADMIN'
50
48
  return { mode, canHosted } as { mode: AiSourceMode | null; canHosted: boolean }
51
49
  })
@@ -16,12 +16,13 @@
16
16
  // along with this program. If not, see <https://www.gnu.org/licenses/>.
17
17
 
18
18
  import { createServerFn } from '@tanstack/react-start'
19
+ import { authContextMiddleware } from '@/server/middlewares/auth-context'
19
20
  import { getRequest } from '@tanstack/react-start/server'
20
21
  import { z } from 'zod'
21
22
  import type { Prisma } from '@allbluecn/database'
22
23
  import { getPrisma } from '@allbluecn/database/get-prisma'
23
24
  import { getServerSeam } from '@allbluecn/kernel'
24
- import { assertDesignReadable, DESIGN_FORBIDDEN_MESSAGE, sessionUserId } from '@/server/design/access'
25
+ import { assertDesignReadable, DESIGN_FORBIDDEN_MESSAGE } from '@/server/design/access'
25
26
 
26
27
  const listSchema = z.object({
27
28
  designId: z.string(),
@@ -74,11 +75,11 @@ const createSchema = z.object({
74
75
  })
75
76
 
76
77
  export const createCommentFn = createServerFn({ method: 'POST' })
78
+ .middleware([authContextMiddleware])
77
79
  .validator(createSchema)
78
- .handler(async ({ data }) => {
80
+ .handler(async ({ data, context }) => {
79
81
  const prisma = await getPrisma()
80
- const request = getRequest()
81
- const userId = sessionUserId(await getServerSeam().requireAuth(request))
82
+ const userId = context.user.id
82
83
  await assertDesignReadable(data.designId, userId)
83
84
 
84
85
  if (data.pageId) {
@@ -113,10 +114,10 @@ async function setCommentResolved(id: string, userId: string, resolved: boolean)
113
114
  const ignoreSchema = z.object({ id: z.string() })
114
115
 
115
116
  export const ignoreCommentFn = createServerFn({ method: 'POST' })
117
+ .middleware([authContextMiddleware])
116
118
  .validator(ignoreSchema)
117
- .handler(async ({ data }) => {
118
- const request = getRequest()
119
- const userId = sessionUserId(await getServerSeam().requireAuth(request))
119
+ .handler(async ({ data, context }) => {
120
+ const userId = context.user.id
120
121
  await setCommentResolved(data.id, userId, true)
121
122
  return { success: true }
122
123
  })
@@ -128,11 +129,11 @@ const updateCommentSchema = z.object({
128
129
 
129
130
  // 正文只有作者本人可改
130
131
  export const updateCommentFn = createServerFn({ method: 'POST' })
132
+ .middleware([authContextMiddleware])
131
133
  .validator(updateCommentSchema)
132
- .handler(async ({ data }) => {
134
+ .handler(async ({ data, context }) => {
133
135
  const prisma = await getPrisma()
134
- const request = getRequest()
135
- const userId = sessionUserId(await getServerSeam().requireAuth(request))
136
+ const userId = context.user.id
136
137
  const owned = await prisma.comment.findFirst({
137
138
  where: { id: data.id, userId },
138
139
  select: { id: true },
@@ -144,10 +145,10 @@ export const updateCommentFn = createServerFn({ method: 'POST' })
144
145
  const resolveSchema = z.object({ id: z.string(), resolved: z.boolean() })
145
146
 
146
147
  export const resolveCommentFn = createServerFn({ method: 'POST' })
148
+ .middleware([authContextMiddleware])
147
149
  .validator(resolveSchema)
148
- .handler(async ({ data }) => {
149
- const request = getRequest()
150
- const userId = sessionUserId(await getServerSeam().requireAuth(request))
150
+ .handler(async ({ data, context }) => {
151
+ const userId = context.user.id
151
152
  await setCommentResolved(data.id, userId, data.resolved)
152
153
  return { success: true }
153
154
  })