From 8dd0f43edf38401044631a7f16d99f48f3c6c1fc Mon Sep 17 00:00:00 2001 From: onmax Date: Tue, 30 Jun 2026 08:01:41 +0200 Subject: [PATCH] fix: support plural auth schema exports --- src/module/templates.ts | 20 ++++++++++++---- test/auth-schema-export.test.ts | 24 +++++++++++++++++-- test/cases/auth-schema-export/nuxt.config.ts | 4 ++++ .../server/api/test/schema.get.ts | 10 +++++++- test/schema-generator.test.ts | 12 ++++++++++ 5 files changed, 63 insertions(+), 7 deletions(-) diff --git a/src/module/templates.ts b/src/module/templates.ts index 44938ec8..c2f41d62 100644 --- a/src/module/templates.ts +++ b/src/module/templates.ts @@ -146,12 +146,24 @@ export const db = undefined` } export function buildSchemaExportCode(hasHubDb: boolean, hubDialect: DbDialect): string { - if (!hasHubDb) - return 'export const schema = undefined\n' + if (!hasHubDb) { + return `export const user = undefined +export const session = undefined +export const account = undefined +export const verification = undefined +export const schema = undefined +` + } return `export * from './schema.${hubDialect}.mjs' -import * as schema from './schema.${hubDialect}.mjs' -export { schema } +import * as generatedSchema from './schema.${hubDialect}.mjs' + +const getGeneratedTable = name => generatedSchema[name] ?? generatedSchema[\`\${name}s\`] +export const user = getGeneratedTable('user') +export const session = getGeneratedTable('session') +export const account = getGeneratedTable('account') +export const verification = getGeneratedTable('verification') +export const schema = { ...generatedSchema, user, session, account, verification } ` } diff --git a/test/auth-schema-export.test.ts b/test/auth-schema-export.test.ts index e4bbcd01..411e3e88 100644 --- a/test/auth-schema-export.test.ts +++ b/test/auth-schema-export.test.ts @@ -7,9 +7,29 @@ describe('#auth/schema export', async () => { rootDir: fileURLToPath(new URL('./cases/auth-schema-export', import.meta.url)), }) - it('exports stable auth tables (user + verification)', async () => { - const res = await $fetch('/api/test/schema') as { hasUser: boolean, hasVerification: boolean } + it('exports stable auth tables with plural generation enabled', async () => { + const res = await $fetch('/api/test/schema') as { + hasUser: boolean + hasNamedUser: boolean + hasUsers: boolean + hasSession: boolean + hasNamedSession: boolean + hasSessions: boolean + hasAccount: boolean + hasNamedAccount: boolean + hasAccounts: boolean + hasVerification: boolean + } + expect(res.hasUser).toBe(true) + expect(res.hasNamedUser).toBe(true) + expect(res.hasUsers).toBe(true) + expect(res.hasSession).toBe(true) + expect(res.hasNamedSession).toBe(true) + expect(res.hasSessions).toBe(true) + expect(res.hasAccount).toBe(true) + expect(res.hasNamedAccount).toBe(true) + expect(res.hasAccounts).toBe(true) expect(res.hasVerification).toBe(true) }) }) diff --git a/test/cases/auth-schema-export/nuxt.config.ts b/test/cases/auth-schema-export/nuxt.config.ts index 1dc86ae4..004a114c 100644 --- a/test/cases/auth-schema-export/nuxt.config.ts +++ b/test/cases/auth-schema-export/nuxt.config.ts @@ -1,6 +1,10 @@ export default defineNuxtConfig({ modules: ['@nuxthub/core', '../../../src/module'], + auth: { + schema: { usePlural: true }, + }, + hub: { db: 'sqlite' }, runtimeConfig: { diff --git a/test/cases/auth-schema-export/server/api/test/schema.get.ts b/test/cases/auth-schema-export/server/api/test/schema.get.ts index 439d3184..5c67ff4e 100644 --- a/test/cases/auth-schema-export/server/api/test/schema.get.ts +++ b/test/cases/auth-schema-export/server/api/test/schema.get.ts @@ -1,8 +1,16 @@ -import { schema } from '#auth/schema' +import { account, schema, session, user } from '#auth/schema' export default defineEventHandler(() => { return { hasUser: Boolean(schema?.user), + hasNamedUser: Boolean(user), + hasUsers: Boolean(schema?.users), + hasSession: Boolean(schema?.session), + hasNamedSession: Boolean(session), + hasSessions: Boolean(schema?.sessions), + hasAccount: Boolean(schema?.account), + hasNamedAccount: Boolean(account), + hasAccounts: Boolean(schema?.accounts), hasVerification: Boolean(schema?.verification), } }) diff --git a/test/schema-generator.test.ts b/test/schema-generator.test.ts index 89ef4e53..5b11059c 100644 --- a/test/schema-generator.test.ts +++ b/test/schema-generator.test.ts @@ -2,6 +2,7 @@ import { existsSync, mkdirSync, rmSync, writeFileSync } from 'node:fs' import { join } from 'node:path' import { getAuthTables } from 'better-auth/db' import { afterAll, beforeAll, describe, expect, it } from 'vitest' +import { buildSchemaExportCode } from '../src/module/templates' import { defineClientAuth, defineServerAuth } from '../src/runtime/config' import { generateDrizzleSchema, loadUserAuthConfig } from '../src/schema-generator' @@ -76,6 +77,17 @@ describe('generateDrizzleSchema', () => { }) }) +describe('buildSchemaExportCode', () => { + it('exports stable undefined auth table aliases without hub db', () => { + const code = buildSchemaExportCode(false, 'sqlite') + expect(code).toContain('export const user = undefined') + expect(code).toContain('export const session = undefined') + expect(code).toContain('export const account = undefined') + expect(code).toContain('export const verification = undefined') + expect(code).toContain('export const schema = undefined') + }) +}) + describe('getAuthTables with secondaryStorage', () => { it('excludes session table when secondaryStorage is provided', () => { const mockStorage = { get: async () => null, set: async () => {}, delete: async () => {} }