@etus/bhono-app 0.1.5 → 0.1.6

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 (269) hide show
  1. package/dist/index.js +0 -0
  2. package/package.json +5 -1
  3. package/templates/base/.husky/pre-push +26 -0
  4. package/templates/base/CLAUDE.md +5 -5
  5. package/templates/base/README.md +31 -20
  6. package/templates/base/docs/app_spec.txt +13 -10
  7. package/templates/base/docs/architecture/README.md +3 -0
  8. package/templates/base/docs/architecture/data-requirements.md +4 -3
  9. package/templates/base/docs/architecture/db-bootstrap.md +39 -0
  10. package/templates/base/docs/architecture/drizzle-migration-plan.md +125 -0
  11. package/templates/base/docs/architecture/erd.md +1 -1
  12. package/templates/base/docs/architecture/sql-standards.md +100 -0
  13. package/templates/base/docs/testing.md +36 -29
  14. package/templates/base/package.json +6 -5
  15. package/templates/base/pnpm-lock.yaml +0 -123
  16. package/templates/base/schema.sql +84 -0
  17. package/templates/base/scripts/init.sh +244 -59
  18. package/templates/base/src/client/hooks/use-auth.ts +5 -0
  19. package/templates/base/src/client/routes/_authenticated/dashboard.tsx +1 -1
  20. package/templates/base/src/client/routes/index.tsx +1 -1
  21. package/templates/base/src/server/db/client.ts +3 -5
  22. package/templates/base/src/server/db/records.ts +81 -0
  23. package/templates/base/src/server/db/seed.ts +3 -2
  24. package/templates/base/src/server/db/sql.ts +96 -0
  25. package/templates/base/src/server/index.ts +16 -2
  26. package/templates/base/src/server/lib/audit.ts +74 -26
  27. package/templates/base/src/server/lib/audited-db.ts +219 -109
  28. package/templates/base/src/server/lib/transaction.ts +10 -16
  29. package/templates/base/src/server/middleware/account.ts +8 -15
  30. package/templates/base/src/server/middleware/auth.ts +102 -38
  31. package/templates/base/src/server/middleware/rate-limit.ts +6 -1
  32. package/templates/base/src/server/routes/accounts/handlers.ts +18 -6
  33. package/templates/base/src/server/routes/audits/handlers.ts +3 -1
  34. package/templates/base/src/server/routes/auth/handlers.ts +14 -9
  35. package/templates/base/src/server/routes/auth/test-login.ts +99 -45
  36. package/templates/base/src/server/routes/health/handlers.ts +4 -4
  37. package/templates/base/src/server/routes/invitations/handlers.ts +6 -3
  38. package/templates/base/src/server/routes/users/handlers.ts +21 -14
  39. package/templates/base/src/server/services/accounts.ts +242 -217
  40. package/templates/base/src/server/services/audits.ts +114 -61
  41. package/templates/base/src/server/services/auth.ts +310 -180
  42. package/templates/base/src/server/services/invitations.ts +282 -222
  43. package/templates/base/src/server/services/users.ts +383 -293
  44. package/templates/base/src/server/types/index.ts +1 -2
  45. package/templates/base/{src/server/__tests__/fixtures.ts → tests/fixtures/server.ts} +3 -3
  46. package/templates/base/{src/client/__tests__/setup-browser.ts → tests/helpers/client-setup-browser.ts} +2 -2
  47. package/templates/base/{src/client/__tests__/setup.ts → tests/helpers/client-setup.ts} +1 -1
  48. package/templates/base/{src/client/__tests__/test-utils.tsx → tests/helpers/client-test-utils.tsx} +2 -2
  49. package/templates/base/{src/server/__tests__/setup.ts → tests/helpers/server.ts} +9 -9
  50. package/templates/base/tests/integration/accounts/crud.test.ts +2 -11
  51. package/templates/base/tests/integration/audits/list.test.ts +2 -11
  52. package/templates/base/tests/integration/auth/auth-service.test.ts +1 -10
  53. package/templates/base/tests/integration/auth/invitation-token.test.ts +2 -11
  54. package/templates/base/tests/integration/auth/logout.test.ts +2 -11
  55. package/templates/base/tests/integration/auth/oauth.test.ts +23 -42
  56. package/templates/base/tests/integration/auth/refresh-token.test.ts +1 -9
  57. package/templates/base/tests/integration/auth/session-expiry.test.ts +1 -9
  58. package/templates/base/tests/integration/auth/session.test.ts +2 -11
  59. package/templates/base/tests/integration/auth/super-admin.test.ts +1 -9
  60. package/templates/base/tests/integration/authorization/analytics-role.test.ts +2 -11
  61. package/templates/base/tests/integration/authorization/billing-role.test.ts +2 -11
  62. package/templates/base/tests/integration/authorization/guards-roles.test.ts +1 -9
  63. package/templates/base/tests/integration/authorization/multi-tenancy.test.ts +2 -11
  64. package/templates/base/tests/integration/authorization/roles.test.ts +2 -11
  65. package/templates/base/tests/integration/config/production-behavior.test.ts +2 -11
  66. package/templates/base/tests/integration/health/health.test.ts +25 -44
  67. package/templates/base/tests/integration/invitations/crud.test.ts +2 -11
  68. package/templates/base/tests/integration/invitations/email.test.ts +1 -9
  69. package/templates/base/tests/integration/middleware/auth.test.ts +3 -12
  70. package/templates/base/tests/integration/middleware/request-logger.test.ts +1 -9
  71. package/templates/base/tests/integration/performance/response-times.test.ts +1 -9
  72. package/templates/base/tests/integration/security/cookie-security.test.ts +2 -11
  73. package/templates/base/tests/integration/security/csrf-protection.test.ts +2 -11
  74. package/templates/base/tests/integration/security/log-sanitization.test.ts +1 -9
  75. package/templates/base/tests/integration/security/rate-limiting.test.ts +1 -9
  76. package/templates/base/tests/integration/security/sql-injection.test.ts +7 -18
  77. package/templates/base/tests/integration/security/xss-prevention.test.ts +2 -11
  78. package/templates/base/tests/integration/setup.ts +13 -90
  79. package/templates/base/tests/integration/smoke.test.ts +3 -2
  80. package/templates/base/tests/integration/storage/upload.test.ts +2 -11
  81. package/templates/base/tests/integration/storage/validation.test.ts +2 -11
  82. package/templates/base/tests/integration/users/crud.test.ts +2 -11
  83. package/templates/base/tests/integration/users/list.test.ts +2 -11
  84. package/templates/base/tests/integration/vitest.config.ts +2 -9
  85. package/templates/base/{src/server/__tests__ → tests}/mocks/db.ts +1 -1
  86. package/templates/base/{src/server/__tests__ → tests}/mocks/index.ts +1 -1
  87. package/templates/base/{src/server/__tests__ → tests}/mocks/kv.ts +1 -1
  88. package/templates/base/{src/server/__tests__ → tests}/mocks/r2.ts +1 -1
  89. package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/sidebar.test.tsx +1 -1
  90. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/avatar.test.tsx +1 -1
  91. package/templates/base/{src/client/__tests__ → tests/unit/client/components/ui}/button.test.tsx +1 -1
  92. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/card.test.tsx +1 -1
  93. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/dialog.test.tsx +1 -1
  94. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/input.test.tsx +1 -1
  95. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/loading-skeleton.test.tsx +1 -1
  96. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/skeleton.test.tsx +1 -1
  97. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/sonner.test.tsx +1 -1
  98. package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/tabs.test.tsx +1 -1
  99. package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/account.test.tsx +1 -1
  100. package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/integrations.test.tsx +1 -1
  101. package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/settings.test.tsx +1 -1
  102. package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/team.test.tsx +1 -1
  103. package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/authenticated-layout.test.tsx +1 -1
  104. package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/dashboard.test.tsx +1 -1
  105. package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/invite.test.tsx +1 -1
  106. package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/login.test.tsx +1 -1
  107. package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/navigation.test.tsx +1 -1
  108. package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/root-layout.test.tsx +1 -1
  109. package/templates/base/{src/server/auth/__tests__ → tests/unit/server/auth}/guards.test.ts +2 -2
  110. package/templates/base/{src → tests/unit}/server/auth/permissions.test.ts +1 -1
  111. package/templates/base/{src → tests/unit}/server/auth/roles.test.ts +1 -1
  112. package/templates/base/tests/unit/server/db/sql.test.ts +68 -0
  113. package/templates/base/{src → tests/unit}/server/env.test.ts +1 -1
  114. package/templates/base/tests/unit/server/lib/audited-db.test.ts +78 -0
  115. package/templates/base/{src → tests/unit}/server/lib/email.test.ts +1 -1
  116. package/templates/base/{src → tests/unit}/server/lib/errors.test.ts +1 -1
  117. package/templates/base/{src → tests/unit}/server/lib/oauth.test.ts +1 -1
  118. package/templates/base/{src → tests/unit}/server/lib/pagination.test.ts +1 -1
  119. package/templates/base/{src → tests/unit}/server/lib/password.test.ts +1 -1
  120. package/templates/base/{src → tests/unit}/server/lib/providers.test.ts +1 -1
  121. package/templates/base/{src → tests/unit}/server/lib/r2-storage.test.ts +2 -2
  122. package/templates/base/{src → tests/unit}/server/lib/session.test.ts +2 -2
  123. package/templates/base/{src → tests/unit}/server/lib/tokens.test.ts +1 -1
  124. package/templates/base/{src → tests/unit}/server/lib/transaction.test.ts +5 -14
  125. package/templates/base/{src → tests/unit}/server/middleware/account.test.ts +16 -24
  126. package/templates/base/{src → tests/unit}/server/middleware/auth.test.ts +71 -42
  127. package/templates/base/{src → tests/unit}/server/middleware/cors.test.ts +1 -1
  128. package/templates/base/{src → tests/unit}/server/middleware/error-handler.test.ts +2 -2
  129. package/templates/base/{src → tests/unit}/server/middleware/rate-limit.test.ts +3 -2
  130. package/templates/base/{src → tests/unit}/server/middleware/request-context.test.ts +1 -1
  131. package/templates/base/{src → tests/unit}/server/middleware/request-logger.test.ts +1 -1
  132. package/templates/base/{src/server/__tests__/mocks/__tests__ → tests/unit/server/mocks}/db.test.ts +1 -1
  133. package/templates/base/{src/server/__tests__/mocks/__tests__ → tests/unit/server/mocks}/kv.test.ts +1 -1
  134. package/templates/base/{src/server/__tests__/mocks/__tests__ → tests/unit/server/mocks}/r2.test.ts +1 -1
  135. package/templates/base/{src/server/routes/accounts/__tests__ → tests/unit/server/routes/accounts}/handlers.test.ts +12 -12
  136. package/templates/base/{src/server/routes/audits/__tests__ → tests/unit/server/routes/audits}/handlers.test.ts +11 -11
  137. package/templates/base/{src/server/routes/auth/__tests__ → tests/unit/server/routes/auth}/handlers.test.ts +13 -13
  138. package/templates/base/{src/server/routes/health/__tests__ → tests/unit/server/routes/health}/handlers.test.ts +27 -23
  139. package/templates/base/{src/server/routes/invitations/__tests__ → tests/unit/server/routes/invitations}/handlers.test.ts +14 -17
  140. package/templates/base/{src/server/routes/storage/__tests__ → tests/unit/server/routes/storage}/handlers.test.ts +6 -6
  141. package/templates/base/{src/server/routes/users/__tests__ → tests/unit/server/routes/users}/handlers.test.ts +12 -12
  142. package/templates/base/tests/unit/server/services/accounts.test.ts +258 -0
  143. package/templates/base/tests/unit/server/services/audits.test.ts +141 -0
  144. package/templates/base/tests/unit/server/services/auth.test.ts +179 -0
  145. package/templates/base/tests/unit/server/services/invitations.test.ts +165 -0
  146. package/templates/base/tests/unit/server/services/users.test.ts +351 -0
  147. package/templates/base/tsconfig.json +2 -1
  148. package/templates/base/vitest.config.browser.ts +3 -2
  149. package/templates/base/vitest.config.frontend.ts +3 -2
  150. package/templates/base/vitest.config.ts +7 -14
  151. package/templates/base/.claude/settings.local.json +0 -11
  152. package/templates/base/config/drizzle.config.ts +0 -10
  153. package/templates/base/src/server/db/schema/accounts.ts +0 -20
  154. package/templates/base/src/server/db/schema/audit-logs.ts +0 -26
  155. package/templates/base/src/server/db/schema/index.ts +0 -7
  156. package/templates/base/src/server/db/schema/invitations.ts +0 -30
  157. package/templates/base/src/server/db/schema/refresh-tokens.ts +0 -22
  158. package/templates/base/src/server/db/schema/user-accounts.ts +0 -25
  159. package/templates/base/src/server/db/schema/users.ts +0 -33
  160. package/templates/base/src/server/lib/audited-db.test.ts +0 -107
  161. package/templates/base/src/server/lib/schema-helpers.ts +0 -16
  162. package/templates/base/src/server/services/__tests__/accounts.test.ts +0 -764
  163. package/templates/base/src/server/services/__tests__/audits.test.ts +0 -235
  164. package/templates/base/src/server/services/__tests__/auth.test.ts +0 -765
  165. package/templates/base/src/server/services/__tests__/invitations.test.ts +0 -704
  166. package/templates/base/src/server/services/__tests__/users.test.ts +0 -755
  167. package/templates/base/tests/integration/lib/schema-helpers.test.ts +0 -129
  168. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-can-be-collapsed-by-default-1.png +0 -0
  169. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-expands-when-collapsed-and-expand-button-is-clicked-1.png +0 -0
  170. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-handles-logout-button-click-1.png +0 -0
  171. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-handles-navigation-clicks-1.png +0 -0
  172. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-hides-navigation-labels-when-collapsed-1.png +0 -0
  173. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-highlights-active-route-1.png +0 -0
  174. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-renders-sidebar-navigation-items-1.png +0 -0
  175. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-shows-keyboard-shortcut-hint-when-expanded-1.png +0 -0
  176. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-shows-user-info-when-authenticated-1.png +0 -0
  177. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/__screenshots__/sidebar.test.tsx/Sidebar-shows-user-initials-in-avatar-fallback-1.png +0 -0
  178. /package/templates/base/{src/client/components/__tests__ → tests/unit/client/components}/error-boundary.test.tsx +0 -0
  179. /package/templates/base/{src/client/components/ui/__tests__ → tests/unit/client/components/ui}/error-fallback.test.tsx +0 -0
  180. /package/templates/base/{src/client/hooks/__tests__ → tests/unit/client/hooks}/use-auth.test.tsx +0 -0
  181. /package/templates/base/{src/client/hooks/__tests__ → tests/unit/client/hooks}/use-theme.test.tsx +0 -0
  182. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-display-dashboard-stats-cards-1.png +0 -0
  183. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-display-quick-action-cards-1.png +0 -0
  184. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-display-recent-activity-section-1.png +0 -0
  185. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-display-user-first-name-in-welcome-message-1.png +0 -0
  186. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-display-user-information-in-sidebar-1.png +0 -0
  187. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-render-dashboard-when-authenticated-1.png +0 -0
  188. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-authenticated-should-show-navigation-sidebar-1.png +0 -0
  189. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/dashboard.test.tsx/Dashboard-Page-when-unauthenticated-should-redirect-to-login-when-not-authenticated-1.png +0 -0
  190. /package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/__screenshots__/invite.test.tsx/Invite-Token-Page-pending-invitation-state-should-display-accept-invitation-button-1.png +0 -0
  191. /package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/__screenshots__/invite.test.tsx/Invite-Token-Page-pending-invitation-state-should-display-decline-button-linking-to-homepage-1.png +0 -0
  192. /package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/__screenshots__/invite.test.tsx/Invite-Token-Page-pending-invitation-state-should-display-invitation-details--email--workspace--role--1.png +0 -0
  193. /package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/__screenshots__/invite.test.tsx/Invite-Token-Page-pending-invitation-state-should-have-a-logo-link-to-homepage-1.png +0 -0
  194. /package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/__screenshots__/invite.test.tsx/Invite-Token-Page-pending-invitation-state-should-render-invitation-page-with-inviter-name-and-workspace-1.png +0 -0
  195. /package/templates/base/{src/client/routes/__tests__ → tests/unit/client/routes}/__screenshots__/invite.test.tsx/Invite-Token-Page-pending-invitation-state-should-show-terms-of-service-and-privacy-policy-links-1.png +0 -0
  196. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/login.test.tsx/Login-Page-should-display-Google-OAuth-login-button-1.png +0 -0
  197. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/login.test.tsx/Login-Page-should-have-a-link-back-to-home-page-1.png +0 -0
  198. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/login.test.tsx/Login-Page-should-render-login-content-without-waiting-for-authentication-1.png +0 -0
  199. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/login.test.tsx/Login-Page-should-render-login-page-at--login-route-1.png +0 -0
  200. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/login.test.tsx/Login-Page-should-show-Terms-of-Service-and-Privacy-Policy-links-1.png +0 -0
  201. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/login.test.tsx/Login-Page-should-trigger-OAuth-flow-when-clicking-login-button-1.png +0 -0
  202. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-404-handling-should-display-404-text-on-not-found-page-1.png +0 -0
  203. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-404-handling-should-have-navigation-options-on-404-page-1.png +0 -0
  204. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-404-handling-should-render-404-page-for-unknown-routes-1.png +0 -0
  205. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-authenticated-navigation-should-navigate-from-dashboard-to-account-page-1.png +0 -0
  206. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-authenticated-navigation-should-navigate-from-dashboard-to-integrations-page-1.png +0 -0
  207. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-authenticated-navigation-should-navigate-from-dashboard-to-settings-page-1.png +0 -0
  208. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-authenticated-navigation-should-navigate-from-dashboard-to-team-page-1.png +0 -0
  209. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-home-page-navigation-should-display-navigation-links-on-home-page-1.png +0 -0
  210. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-home-page-navigation-should-have-correct-link-destinations-on-home-page-1.png +0 -0
  211. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-unauthenticated-navigation-should-allow-access-to-home-page-without-authentication-1.png +0 -0
  212. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-unauthenticated-navigation-should-allow-access-to-login-page-without-authentication-1.png +0 -0
  213. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-unauthenticated-navigation-should-redirect-unauthenticated-users-from-dashboard-to-login-1.png +0 -0
  214. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-unauthenticated-navigation-should-redirect-unauthenticated-users-from-settings-to-login-1.png +0 -0
  215. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/__screenshots__/navigation.test.tsx/Navigation-unauthenticated-navigation-should-redirect-unauthenticated-users-from-team-to-login-1.png +0 -0
  216. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/account.test.tsx/Account-Page-should-render-Active-Sessions-section-with-session-cards-1.png +0 -0
  217. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/account.test.tsx/Account-Page-should-render-page-with-correct-title--Account--1.png +0 -0
  218. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/account.test.tsx/Account-Page-should-show-API-Access-section-1.png +0 -0
  219. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/account.test.tsx/Account-Page-should-show-Connected-Accounts-section-with-Google-connected-1.png +0 -0
  220. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/account.test.tsx/Account-Page-should-show-Danger-Zone-section-with-delete-button-1.png +0 -0
  221. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/account.test.tsx/Account-Page-should-show-Security-section-with-Two-Factor-Authentication-1.png +0 -0
  222. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-API-documentation-section-should-display-API-documentation-link-section-1.png +0 -0
  223. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-Create-Webhook-Dialog-should-have-Add-Webhook-trigger-button-1.png +0 -0
  224. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-category-filters-should-display-all-category-buttons-1.png +0 -0
  225. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-integration-cards-should-display-all-integration-cards-with-names-1.png +0 -0
  226. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-integration-cards-should-display-category-badges-on-cards-1.png +0 -0
  227. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-integration-cards-should-show-Configure-button-for-connected-integrations-1.png +0 -0
  228. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-integration-cards-should-show-Connect-button-for-not-connected-integrations-1.png +0 -0
  229. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-integration-cards-should-show-Connected-badge-for-connected-integrations-1.png +0 -0
  230. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-page-rendering-should-display-Available-Integrations-section-1.png +0 -0
  231. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-page-rendering-should-display-Webhooks-section-1.png +0 -0
  232. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-page-rendering-should-display-connected-count-1.png +0 -0
  233. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-page-rendering-should-display-page-description-1.png +0 -0
  234. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-page-rendering-should-display-search-input-1.png +0 -0
  235. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-page-rendering-should-render-with-correct-title--Integrations--1.png +0 -0
  236. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-search-functionality-should-filter-integrations-based-on-search-query-1.png +0 -0
  237. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-search-functionality-should-search-by-description-1.png +0 -0
  238. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-search-functionality-should-show-no-results-message-when-search-has-no-matches-1.png +0 -0
  239. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-webhooks-section-should-display-existing-webhook-1.png +0 -0
  240. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-webhooks-section-should-display-webhook-events-1.png +0 -0
  241. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-webhooks-section-should-display-webhook-last-delivery-info-1.png +0 -0
  242. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-webhooks-section-should-display-webhook-success-status-1.png +0 -0
  243. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/integrations.test.tsx/Integrations-Page-webhooks-section-should-have-Add-Webhook-button-1.png +0 -0
  244. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Account-tab-should-display-connected-accounts-section-with-Google-provider-1.png +0 -0
  245. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Account-tab-should-display-sessions-and-danger-zone-sections-1.png +0 -0
  246. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Notifications-tab-should-display-all-notification-toggle-options-1.png +0 -0
  247. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Notifications-tab-should-display-email-notifications-section-1.png +0 -0
  248. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Notifications-tab-should-display-toggle-switches-for-notification-options-1.png +0 -0
  249. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Notifications-tab-should-have-toggles-checked-by-default-1.png +0 -0
  250. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Profile-tab-should-display--Save-Changes--button-1.png +0 -0
  251. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Profile-tab-should-display-personal-information-form-1.png +0 -0
  252. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Profile-tab-should-display-profile-picture-section-1.png +0 -0
  253. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Profile-tab-should-display-user-email-in-disabled-email-input-1.png +0 -0
  254. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Profile-tab-should-display-user-initials-in-avatar-1.png +0 -0
  255. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-Profile-tab-should-display-user-name-in-the-name-input-1.png +0 -0
  256. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-page-rendering-should-display-all-three-tabs-1.png +0 -0
  257. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-page-rendering-should-display-page-description-1.png +0 -0
  258. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-page-rendering-should-render-with-correct-title--Settings--1.png +0 -0
  259. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-tab-navigation-should-show-Profile-tab-as-default-active-tab-1.png +0 -0
  260. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-tab-navigation-should-switch-to-Account-tab-when-clicked-1.png +0 -0
  261. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/settings.test.tsx/Settings-Page-tab-navigation-should-switch-to-Notifications-tab-when-clicked-1.png +0 -0
  262. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/team.test.tsx/Team-Page-should-display-Active-Members-section-with-member-count-1.png +0 -0
  263. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/team.test.tsx/Team-Page-should-display-Pending-Invitations-section-with-invitation-details-1.png +0 -0
  264. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/team.test.tsx/Team-Page-should-have-invite-member-button-that-can-be-clicked-1.png +0 -0
  265. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/team.test.tsx/Team-Page-should-render-page-with-correct-title-and-description-1.png +0 -0
  266. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/team.test.tsx/Team-Page-should-render-search-input-that-filters-team-members-1.png +0 -0
  267. /package/templates/base/{src/client/routes/_authenticated/__tests__ → tests/unit/client/routes/_authenticated}/__screenshots__/team.test.tsx/Team-Page-should-show-current-user-with---you---indicator-and-role-badge-1.png +0 -0
  268. /package/templates/base/{src/client/__tests__ → tests/unit/client}/routes/error-components.test.tsx +0 -0
  269. /package/templates/base/{src/shared/schemas/__tests__ → tests/unit/shared}/schemas.test.ts +0 -0
@@ -1,6 +1,5 @@
1
1
  import type { Role } from '../auth/roles'
2
2
  import type { Env } from '../env'
3
- import type { Database } from '../db/client'
4
3
 
5
4
  export interface User {
6
5
  id: string
@@ -106,7 +105,7 @@ export interface HonoEnv {
106
105
  userRole: Role | null
107
106
  isSystemAdminAccess: boolean
108
107
  // Set by database middleware (may be undefined before middleware runs or in health checks)
109
- db?: Database
108
+ db?: D1Database
110
109
  // Session variables (set by session middleware)
111
110
  sessionId?: string
112
111
  sessionData?: SessionData
@@ -1,6 +1,6 @@
1
- // src/server/__tests__/fixtures.ts
2
- import type { User, Account, SessionData } from '../types'
3
- import type { Role } from '../auth/roles'
1
+ // tests/fixtures/server.ts
2
+ import type { User, Account, SessionData } from '@server/types'
3
+ import type { Role } from '@server/auth/roles'
4
4
 
5
5
  /**
6
6
  * Counter for generating unique IDs
@@ -1,7 +1,7 @@
1
- // src/client/__tests__/setup-browser.ts
1
+ // tests/helpers/client-setup-browser.ts
2
2
  // Setup file for Vitest Browser Mode (real browser, no mocks needed)
3
3
  import "@testing-library/jest-dom/vitest"
4
- import "../../test/vitest-zod-matcher"
4
+ import "../../src/test/vitest-zod-matcher"
5
5
  import { cleanup } from "@testing-library/react"
6
6
  import { afterEach, vi } from "vitest"
7
7
 
@@ -1,5 +1,5 @@
1
1
  import "@testing-library/jest-dom/vitest"
2
- import "../../test/vitest-zod-matcher"
2
+ import "../../src/test/vitest-zod-matcher"
3
3
  import { cleanup } from "@testing-library/react"
4
4
  import { afterEach, vi } from "vitest"
5
5
 
@@ -6,8 +6,8 @@ import {
6
6
  createMemoryHistory,
7
7
  createRouter,
8
8
  } from "@tanstack/react-router"
9
- import { routeTree } from "../routeTree.gen"
10
- import { ThemeProvider } from "../hooks/use-theme"
9
+ import { routeTree } from "@/routeTree.gen"
10
+ import { ThemeProvider } from "@/hooks/use-theme"
11
11
  import type { ReactElement, ReactNode } from "react"
12
12
 
13
13
  // Create a fresh QueryClient for each test
@@ -1,20 +1,20 @@
1
- // src/server/__tests__/setup.ts
1
+ // tests/helpers/server.ts
2
2
  import { vi, beforeEach, afterEach } from 'vitest'
3
- import type { Env } from '../env'
4
- import type { SessionData } from '../types'
5
- import { createMockD1, createMockD1AsD1Database, type MockD1Database } from './mocks/db'
3
+ import type { Env } from '@server/env'
4
+ import type { SessionData } from '@server/types'
5
+ import { createMockD1, createMockD1AsD1Database, type MockD1Database } from '@tests/mocks/db'
6
6
  import {
7
7
  createMockKV,
8
8
  createMockKVAsKVNamespace,
9
9
  seedMockKV,
10
10
  type MockKVNamespace,
11
- } from './mocks/kv'
12
- import { createMockR2, createMockR2AsR2Bucket, type MockR2Bucket } from './mocks/r2'
11
+ } from '@tests/mocks/kv'
12
+ import { createMockR2, createMockR2AsR2Bucket, type MockR2Bucket } from '@tests/mocks/r2'
13
13
 
14
14
  // Re-export mocks for convenience
15
- export * from './mocks/db'
16
- export * from './mocks/kv'
17
- export * from './mocks/r2'
15
+ export * from '@tests/mocks/db'
16
+ export * from '@tests/mocks/kv'
17
+ export * from '@tests/mocks/r2'
18
18
 
19
19
  /**
20
20
  * Default environment configuration for tests
@@ -30,19 +30,10 @@ import { errorHandler } from '../../../src/server/middleware/error-handler'
30
30
  import { sessionMiddleware } from '../../../src/server/lib/session'
31
31
 
32
32
  /**
33
- * Creates a database wrapper that adds the `execute` method
34
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
33
+ * Creates a D1-compatible database instance for tests
35
34
  */
36
35
  function createTestDb() {
37
- const db = getDb()
38
- return new Proxy(db, {
39
- get(target, prop) {
40
- if (prop === 'execute') {
41
- return target.run.bind(target)
42
- }
43
- return (target as any)[prop]
44
- },
45
- })
36
+ return getDb()
46
37
  }
47
38
 
48
39
  describe('Accounts CRUD Integration', () => {
@@ -22,19 +22,10 @@ import { errorHandler } from '../../../src/server/middleware/error-handler'
22
22
  import { sessionMiddleware } from '../../../src/server/lib/session'
23
23
 
24
24
  /**
25
- * Creates a database wrapper that adds the `execute` method
26
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
25
+ * Creates a D1-compatible database instance for tests
27
26
  */
28
27
  function createTestDb() {
29
- const db = getDb()
30
- return new Proxy(db, {
31
- get(target, prop) {
32
- if (prop === 'execute') {
33
- return target.run.bind(target)
34
- }
35
- return (target as any)[prop]
36
- },
37
- })
28
+ return getDb()
38
29
  }
39
30
 
40
31
  /**
@@ -15,21 +15,12 @@ import { createUser } from '../fixtures'
15
15
  import { authService } from '../../../src/server/services/auth'
16
16
  import { generateRefreshToken, hashToken } from '../../../src/server/lib/tokens'
17
17
  import type { GoogleUserInfo, AuthEventContext } from '../../../src/server/types/auth'
18
- import * as schema from '../../../src/server/db/schema'
19
18
 
20
19
  /**
21
20
  * Creates a database wrapper
22
21
  */
23
22
  function createTestDb() {
24
- const db = getDb()
25
- return new Proxy(db, {
26
- get(target, prop) {
27
- if (prop === 'execute') {
28
- return target.run.bind(target)
29
- }
30
- return (target as any)[prop]
31
- },
32
- }) as any
23
+ return getDb()
33
24
  }
34
25
 
35
26
  describe('Auth Service Integration', () => {
@@ -34,19 +34,10 @@ import { sessionMiddleware } from '../../../src/server/lib/session'
34
34
  import { errorHandler } from '../../../src/server/middleware/error-handler'
35
35
 
36
36
  /**
37
- * Creates a database wrapper that adds the `execute` method
38
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
37
+ * Creates a D1-compatible database instance for tests
39
38
  */
40
39
  function createTestDb() {
41
- const db = getDb()
42
- return new Proxy(db, {
43
- get(target, prop) {
44
- if (prop === 'execute') {
45
- return target.run.bind(target)
46
- }
47
- return (target as any)[prop]
48
- },
49
- })
40
+ return getDb()
50
41
  }
51
42
 
52
43
  describe('Invitation Token Authentication Integration', () => {
@@ -24,19 +24,10 @@ import { sessionMiddleware } from '../../../src/server/lib/session'
24
24
  import { errorHandler } from '../../../src/server/middleware/error-handler'
25
25
 
26
26
  /**
27
- * Creates a database wrapper that adds the `execute` method
28
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
27
+ * Creates a D1-compatible database instance for tests
29
28
  */
30
29
  function createTestDb() {
31
- const db = getDb()
32
- return new Proxy(db, {
33
- get(target, prop) {
34
- if (prop === 'execute') {
35
- return target.run.bind(target)
36
- }
37
- return (target as any)[prop]
38
- },
39
- })
30
+ return getDb()
40
31
  }
41
32
 
42
33
  describe('Logout Integration', () => {
@@ -9,15 +9,13 @@
9
9
 
10
10
  import { describe, it, expect, beforeAll, vi, beforeEach } from 'vitest'
11
11
  import { Hono } from 'hono'
12
- import { eq } from 'drizzle-orm'
13
- import { getEnv, getDb, getKV, type TestEnv } from '../setup'
12
+ import { getEnv, getDb, getKV, getSqlite, type TestEnv } from '../setup'
14
13
  import { createUser, createUserSession } from '../fixtures'
15
14
  import type { HonoEnv } from '../../../src/server/types'
16
15
  import { auth } from '../../../src/server/routes/auth'
17
16
  import { sessionMiddleware } from '../../../src/server/lib/session'
18
17
  import { errorHandler } from '../../../src/server/middleware/error-handler'
19
18
  import { createAccount, addUserToAccount } from '../fixtures'
20
- import { users } from '../../../src/server/db/schema'
21
19
 
22
20
  // Mock ID token for testing (base64url encoded)
23
21
  function createMockIdToken(payload: Record<string, unknown>): string {
@@ -32,15 +30,7 @@ function createMockIdToken(payload: Record<string, unknown>): string {
32
30
  * Creates a database wrapper that adds the `execute` method
33
31
  */
34
32
  function createTestDb() {
35
- const db = getDb()
36
- return new Proxy(db, {
37
- get(target, prop) {
38
- if (prop === 'execute') {
39
- return target.run.bind(target)
40
- }
41
- return (target as any)[prop]
42
- },
43
- })
33
+ return getDb()
44
34
  }
45
35
 
46
36
  describe('OAuth Authentication Integration', () => {
@@ -353,16 +343,14 @@ describe('OAuth Authentication Integration', () => {
353
343
  expect(res.status).toBe(302)
354
344
 
355
345
  // Verify user was updated in database
356
- const db = createTestDb()
357
- const result = await (db as any)
358
- .select()
359
- .from(users)
360
- .where(eq(users.id, existingUser.id))
361
- .limit(1)
346
+ const sqlite = getSqlite()
347
+ const result = sqlite.prepare(
348
+ 'SELECT name, email, avatar_url as avatarUrl FROM users WHERE id = ?'
349
+ ).get(existingUser.id) as { name: string; email: string; avatarUrl: string } | undefined
362
350
 
363
- expect(result[0].name).toBe('New Updated Name')
364
- expect(result[0].email).toBe('newemail@gmail.com')
365
- expect(result[0].avatarUrl).toBe('https://new-avatar.jpg')
351
+ expect(result?.name).toBe('New Updated Name')
352
+ expect(result?.email).toBe('newemail@gmail.com')
353
+ expect(result?.avatarUrl).toBe('https://new-avatar.jpg')
366
354
 
367
355
  globalThis.fetch = originalFetch
368
356
  })
@@ -374,18 +362,16 @@ describe('OAuth Authentication Integration', () => {
374
362
  await addUserToAccount(inviter.id, account.id, 'ADMIN')
375
363
 
376
364
  // Create an invitation in the database
377
- const db = createTestDb()
365
+ const sqlite = getSqlite()
378
366
  const invitationId = crypto.randomUUID()
379
367
  const invitationToken = crypto.randomUUID()
380
368
  const expiresAt = new Date(Date.now() + 7 * 24 * 60 * 60 * 1000).toISOString()
381
369
  const inviteeEmail = `pending-invitee-${crypto.randomUUID().slice(0, 8)}@gmail.com`
382
370
 
383
- ;(db as any).run(
384
- require('drizzle-orm').sql`
385
- INSERT INTO invitations (id, account_id, email, role, token, invited_by_id, expires_at)
386
- VALUES (${invitationId}, ${account.id}, ${inviteeEmail}, ${'EDITOR'}, ${invitationToken}, ${inviter.id}, ${expiresAt})
387
- `
388
- )
371
+ sqlite.prepare(
372
+ `INSERT INTO invitations (id, account_id, email, role, token, invited_by_id, expires_at)
373
+ VALUES (?, ?, ?, ?, ?, ?, ?)`
374
+ ).run(invitationId, account.id, inviteeEmail, 'EDITOR', invitationToken, inviter.id, expiresAt)
389
375
 
390
376
  // Mock Google OAuth response
391
377
  const mockIdToken = createMockIdToken({
@@ -433,14 +419,11 @@ describe('OAuth Authentication Integration', () => {
433
419
  expect(location).toContain('/dashboard')
434
420
 
435
421
  // Verify the invitation was accepted (accepted_at should be set)
436
- const { invitations } = await import('../../../src/server/db/schema')
437
- const invitationResult = await (db as any)
438
- .select()
439
- .from(invitations)
440
- .where(eq(invitations.id, invitationId))
441
- .limit(1)
422
+ const invitationResult = sqlite.prepare(
423
+ 'SELECT accepted_at as acceptedAt FROM invitations WHERE id = ?'
424
+ ).get(invitationId) as { acceptedAt: string | null } | undefined
442
425
 
443
- expect(invitationResult[0].acceptedAt).not.toBeNull()
426
+ expect(invitationResult?.acceptedAt).not.toBeNull()
444
427
 
445
428
  globalThis.fetch = originalFetch
446
429
  })
@@ -567,17 +550,15 @@ describe('OAuth Authentication Integration', () => {
567
550
  await addUserToAccount(inviter.id, account.id, 'ADMIN')
568
551
 
569
552
  // Create invitation directly in the database
570
- const db = createTestDb()
553
+ const sqlite = getSqlite()
571
554
  const invitationId = crypto.randomUUID()
572
555
  const token = crypto.randomUUID()
573
556
  const expiresAt = new Date(Date.now() + 7 * 24 * 60 * 60 * 1000).toISOString()
574
557
 
575
- ;(db as any).run(
576
- require('drizzle-orm').sql`
577
- INSERT INTO invitations (id, account_id, email, role, token, invited_by_id, expires_at)
578
- VALUES (${invitationId}, ${account.id}, ${'invitee@example.com'}, ${'EDITOR'}, ${token}, ${inviter.id}, ${expiresAt})
579
- `
580
- )
558
+ sqlite.prepare(
559
+ `INSERT INTO invitations (id, account_id, email, role, token, invited_by_id, expires_at)
560
+ VALUES (?, ?, ?, ?, ?, ?, ?)`
561
+ ).run(invitationId, account.id, 'invitee@example.com', 'EDITOR', token, inviter.id, expiresAt)
581
562
 
582
563
  const res = await app.request(`/auth/invite/${token}`, {
583
564
  method: 'GET',
@@ -22,15 +22,7 @@ import { hashToken, generateRefreshToken, getRefreshTokenExpiry } from '../../..
22
22
  * Creates a database wrapper
23
23
  */
24
24
  function createTestDb() {
25
- const db = getDb()
26
- return new Proxy(db, {
27
- get(target, prop) {
28
- if (prop === 'execute') {
29
- return target.run.bind(target)
30
- }
31
- return (target as any)[prop]
32
- },
33
- })
25
+ return getDb()
34
26
  }
35
27
 
36
28
  describe('Refresh Token Integration', () => {
@@ -23,15 +23,7 @@ import { hashToken, generateRefreshToken } from '../../../src/server/lib/tokens'
23
23
  // ============================================================================
24
24
 
25
25
  function createTestDb() {
26
- const db = getDb()
27
- return new Proxy(db, {
28
- get(target, prop) {
29
- if (prop === 'execute') {
30
- return target.run.bind(target)
31
- }
32
- return (target as any)[prop]
33
- },
34
- })
26
+ return getDb()
35
27
  }
36
28
 
37
29
  describe('Session Expiry Integration Tests', () => {
@@ -24,19 +24,10 @@ import { sessionMiddleware } from '../../../src/server/lib/session'
24
24
  import { errorHandler } from '../../../src/server/middleware/error-handler'
25
25
 
26
26
  /**
27
- * Creates a database wrapper that adds the `execute` method
28
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
27
+ * Creates a D1-compatible database instance for tests
29
28
  */
30
29
  function createTestDb() {
31
- const db = getDb()
32
- return new Proxy(db, {
33
- get(target, prop) {
34
- if (prop === 'execute') {
35
- return target.run.bind(target)
36
- }
37
- return (target as any)[prop]
38
- },
39
- })
30
+ return getDb()
40
31
  }
41
32
 
42
33
  describe('Session Authentication Integration', () => {
@@ -30,15 +30,7 @@ import { isSuperAdminEmail } from '../../../src/server/env'
30
30
  // ============================================================================
31
31
 
32
32
  function createTestDb() {
33
- const db = getDb()
34
- return new Proxy(db, {
35
- get(target, prop) {
36
- if (prop === 'execute') {
37
- return target.run.bind(target)
38
- }
39
- return (target as any)[prop]
40
- },
41
- })
33
+ return getDb()
42
34
  }
43
35
 
44
36
  describe('Super Admin Integration Tests', () => {
@@ -38,19 +38,10 @@ import { hasMinimumRole, isHierarchicalRole, ROLE_HIERARCHY } from '../../../src
38
38
  // ============================================================================
39
39
 
40
40
  /**
41
- * Creates a database wrapper that adds the `execute` method
42
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
41
+ * Creates a D1-compatible database instance for tests
43
42
  */
44
43
  function createTestDb() {
45
- const db = getDb()
46
- return new Proxy(db, {
47
- get(target, prop) {
48
- if (prop === 'execute') {
49
- return target.run.bind(target)
50
- }
51
- return (target as any)[prop]
52
- },
53
- })
44
+ return getDb()
54
45
  }
55
46
 
56
47
  /**
@@ -38,19 +38,10 @@ import { hasMinimumRole, isHierarchicalRole, ROLE_HIERARCHY } from '../../../src
38
38
  // ============================================================================
39
39
 
40
40
  /**
41
- * Creates a database wrapper that adds the `execute` method
42
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
41
+ * Creates a D1-compatible database instance for tests
43
42
  */
44
43
  function createTestDb() {
45
- const db = getDb()
46
- return new Proxy(db, {
47
- get(target, prop) {
48
- if (prop === 'execute') {
49
- return target.run.bind(target)
50
- }
51
- return (target as any)[prop]
52
- },
53
- })
44
+ return getDb()
54
45
  }
55
46
 
56
47
  /**
@@ -40,15 +40,7 @@ import {
40
40
  * Creates a database wrapper
41
41
  */
42
42
  function createTestDb() {
43
- const db = getDb()
44
- return new Proxy(db, {
45
- get(target, prop) {
46
- if (prop === 'execute') {
47
- return target.run.bind(target)
48
- }
49
- return (target as any)[prop]
50
- },
51
- })
43
+ return getDb()
52
44
  }
53
45
 
54
46
  describe('Role Utility Functions', () => {
@@ -35,19 +35,10 @@ import { sessionMiddleware } from '../../../src/server/lib/session'
35
35
  // ============================================================================
36
36
 
37
37
  /**
38
- * Creates a database wrapper that adds the `execute` method
39
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
38
+ * Creates a D1-compatible database instance for tests
40
39
  */
41
40
  function createTestDb() {
42
- const db = getDb()
43
- return new Proxy(db, {
44
- get(target, prop) {
45
- if (prop === 'execute') {
46
- return target.run.bind(target)
47
- }
48
- return (target as any)[prop]
49
- },
50
- })
41
+ return getDb()
51
42
  }
52
43
 
53
44
  /**
@@ -49,19 +49,10 @@ import { sessionMiddleware } from '../../../src/server/lib/session'
49
49
  // ============================================================================
50
50
 
51
51
  /**
52
- * Creates a database wrapper that adds the `execute` method
53
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
52
+ * Creates a D1-compatible database instance for tests
54
53
  */
55
54
  function createTestDb() {
56
- const db = getDb()
57
- return new Proxy(db, {
58
- get(target, prop) {
59
- if (prop === 'execute') {
60
- return target.run.bind(target)
61
- }
62
- return (target as any)[prop]
63
- },
64
- })
55
+ return getDb()
65
56
  }
66
57
 
67
58
  /**
@@ -22,19 +22,10 @@ import { secureHeaders } from 'hono/secure-headers'
22
22
  import { uuidv7 } from 'uuidv7'
23
23
 
24
24
  /**
25
- * Creates a database wrapper that adds the `execute` method
26
- * The better-sqlite3 drizzle doesn't have execute, but D1 does
25
+ * Creates a D1-compatible database instance for tests
27
26
  */
28
27
  function createTestDb() {
29
- const db = getDb()
30
- return new Proxy(db, {
31
- get(target, prop) {
32
- if (prop === 'execute') {
33
- return target.run.bind(target)
34
- }
35
- return (target as any)[prop]
36
- },
37
- })
28
+ return getDb()
38
29
  }
39
30
 
40
31
  /**