mirror of
https://github.com/LukeHagar/better-auth.git
synced 2025-12-11 04:19:31 +00:00
feat: add onUpdate field on db schema generation (#4241)
Fixes: https://github.com/better-auth/better-auth/issues/4187
This commit is contained in:
@@ -201,6 +201,7 @@ exports[`init > should match config 1`] = `
|
||||
},
|
||||
"updatedAt": {
|
||||
"fieldName": "updatedAt",
|
||||
"onUpdate": [Function],
|
||||
"required": true,
|
||||
"type": "date",
|
||||
},
|
||||
@@ -243,6 +244,7 @@ exports[`init > should match config 1`] = `
|
||||
},
|
||||
"updatedAt": {
|
||||
"fieldName": "updatedAt",
|
||||
"onUpdate": [Function],
|
||||
"required": true,
|
||||
"type": "date",
|
||||
},
|
||||
@@ -300,6 +302,7 @@ exports[`init > should match config 1`] = `
|
||||
"updatedAt": {
|
||||
"defaultValue": [Function],
|
||||
"fieldName": "updatedAt",
|
||||
"onUpdate": [Function],
|
||||
"required": true,
|
||||
"type": "date",
|
||||
},
|
||||
@@ -328,6 +331,7 @@ exports[`init > should match config 1`] = `
|
||||
"updatedAt": {
|
||||
"defaultValue": [Function],
|
||||
"fieldName": "updatedAt",
|
||||
"onUpdate": [Function],
|
||||
"required": false,
|
||||
"type": "date",
|
||||
},
|
||||
|
||||
@@ -43,6 +43,13 @@ export type FieldAttributeConfig<T extends FieldType = FieldType> = {
|
||||
* be used when creating a new record.
|
||||
*/
|
||||
defaultValue?: Primitive | (() => Primitive);
|
||||
/**
|
||||
* Update value for the field
|
||||
*
|
||||
* Note: This will create an onUpdate trigger on the database level for supported adapters.
|
||||
* It will be called when updating a record.
|
||||
*/
|
||||
onUpdate?: () => Primitive;
|
||||
/**
|
||||
* transform the value before storing it.
|
||||
*/
|
||||
|
||||
@@ -96,6 +96,7 @@ export const getAuthTables = (
|
||||
type: "date",
|
||||
required: true,
|
||||
fieldName: options.session?.fields?.updatedAt || "updatedAt",
|
||||
onUpdate: () => new Date(),
|
||||
},
|
||||
ipAddress: {
|
||||
type: "string",
|
||||
@@ -161,6 +162,7 @@ export const getAuthTables = (
|
||||
updatedAt: {
|
||||
type: "date",
|
||||
defaultValue: () => new Date(),
|
||||
onUpdate: () => new Date(),
|
||||
required: true,
|
||||
fieldName: options.user?.fields?.updatedAt || "updatedAt",
|
||||
},
|
||||
@@ -244,6 +246,7 @@ export const getAuthTables = (
|
||||
type: "date",
|
||||
required: true,
|
||||
fieldName: options.account?.fields?.updatedAt || "updatedAt",
|
||||
onUpdate: () => new Date(),
|
||||
},
|
||||
...account?.fields,
|
||||
},
|
||||
@@ -277,6 +280,7 @@ export const getAuthTables = (
|
||||
type: "date",
|
||||
required: false,
|
||||
defaultValue: () => new Date(),
|
||||
onUpdate: () => new Date(),
|
||||
fieldName: options.verification?.fields?.updatedAt || "updatedAt",
|
||||
},
|
||||
},
|
||||
|
||||
@@ -160,6 +160,13 @@ export const generateDrizzleSchema: SchemaGenerator = async ({
|
||||
type += `.default(${attr.defaultValue})`;
|
||||
}
|
||||
}
|
||||
// Add .$onUpdate() for fields with onUpdate property
|
||||
// Supported for all database types: PostgreSQL, MySQL, and SQLite
|
||||
if (attr.onUpdate && attr.type === "date") {
|
||||
if (typeof attr.onUpdate === "function") {
|
||||
type += `.$onUpdate(${attr.onUpdate})`;
|
||||
}
|
||||
}
|
||||
return `${field}: ${type}${attr.required ? ".notNull()" : ""}${
|
||||
attr.unique ? ".unique()" : ""
|
||||
}${
|
||||
|
||||
@@ -0,0 +1,85 @@
|
||||
import {
|
||||
mysqlTable,
|
||||
varchar,
|
||||
text,
|
||||
timestamp,
|
||||
boolean,
|
||||
int,
|
||||
} from "drizzle-orm/mysql-core";
|
||||
|
||||
export const custom_user = mysqlTable("custom_user", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
name: text("name").notNull(),
|
||||
email: varchar("email", { length: 255 }).notNull().unique(),
|
||||
emailVerified: boolean("email_verified")
|
||||
.$defaultFn(() => false)
|
||||
.notNull(),
|
||||
image: text("image"),
|
||||
createdAt: timestamp("created_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
twoFactorEnabled: boolean("two_factor_enabled").default(false),
|
||||
username: varchar("username", { length: 255 }).unique(),
|
||||
displayUsername: text("display_username"),
|
||||
});
|
||||
|
||||
export const custom_session = mysqlTable("custom_session", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
expiresAt: timestamp("expires_at").notNull(),
|
||||
token: varchar("token", { length: 255 }).notNull().unique(),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
ipAddress: text("ip_address"),
|
||||
userAgent: text("user_agent"),
|
||||
userId: int("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
|
||||
export const custom_account = mysqlTable("custom_account", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
accountId: text("account_id").notNull(),
|
||||
providerId: text("provider_id").notNull(),
|
||||
userId: int("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
accessToken: text("access_token"),
|
||||
refreshToken: text("refresh_token"),
|
||||
idToken: text("id_token"),
|
||||
accessTokenExpiresAt: timestamp("access_token_expires_at"),
|
||||
refreshTokenExpiresAt: timestamp("refresh_token_expires_at"),
|
||||
scope: text("scope"),
|
||||
password: text("password"),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
});
|
||||
|
||||
export const custom_verification = mysqlTable("custom_verification", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
identifier: text("identifier").notNull(),
|
||||
value: text("value").notNull(),
|
||||
expiresAt: timestamp("expires_at").notNull(),
|
||||
createdAt: timestamp("created_at").$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date()),
|
||||
});
|
||||
|
||||
export const twoFactor = mysqlTable("two_factor", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
secret: text("secret").notNull(),
|
||||
backupCodes: text("backup_codes").notNull(),
|
||||
userId: int("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
84
packages/cli/test/__snapshots__/auth-schema-mysql.txt
Normal file
84
packages/cli/test/__snapshots__/auth-schema-mysql.txt
Normal file
@@ -0,0 +1,84 @@
|
||||
import {
|
||||
mysqlTable,
|
||||
varchar,
|
||||
text,
|
||||
timestamp,
|
||||
boolean,
|
||||
} from "drizzle-orm/mysql-core";
|
||||
|
||||
export const custom_user = mysqlTable("custom_user", {
|
||||
id: varchar("id", { length: 36 }).primaryKey(),
|
||||
name: text("name").notNull(),
|
||||
email: varchar("email", { length: 255 }).notNull().unique(),
|
||||
emailVerified: boolean("email_verified")
|
||||
.$defaultFn(() => false)
|
||||
.notNull(),
|
||||
image: text("image"),
|
||||
createdAt: timestamp("created_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
twoFactorEnabled: boolean("two_factor_enabled").default(false),
|
||||
username: varchar("username", { length: 255 }).unique(),
|
||||
displayUsername: text("display_username"),
|
||||
});
|
||||
|
||||
export const custom_session = mysqlTable("custom_session", {
|
||||
id: varchar("id", { length: 36 }).primaryKey(),
|
||||
expiresAt: timestamp("expires_at").notNull(),
|
||||
token: varchar("token", { length: 255 }).notNull().unique(),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
ipAddress: text("ip_address"),
|
||||
userAgent: text("user_agent"),
|
||||
userId: varchar("user_id", { length: 36 })
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
|
||||
export const custom_account = mysqlTable("custom_account", {
|
||||
id: varchar("id", { length: 36 }).primaryKey(),
|
||||
accountId: text("account_id").notNull(),
|
||||
providerId: text("provider_id").notNull(),
|
||||
userId: varchar("user_id", { length: 36 })
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
accessToken: text("access_token"),
|
||||
refreshToken: text("refresh_token"),
|
||||
idToken: text("id_token"),
|
||||
accessTokenExpiresAt: timestamp("access_token_expires_at"),
|
||||
refreshTokenExpiresAt: timestamp("refresh_token_expires_at"),
|
||||
scope: text("scope"),
|
||||
password: text("password"),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
});
|
||||
|
||||
export const custom_verification = mysqlTable("custom_verification", {
|
||||
id: varchar("id", { length: 36 }).primaryKey(),
|
||||
identifier: text("identifier").notNull(),
|
||||
value: text("value").notNull(),
|
||||
expiresAt: timestamp("expires_at").notNull(),
|
||||
createdAt: timestamp("created_at").$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date()),
|
||||
});
|
||||
|
||||
export const twoFactor = mysqlTable("two_factor", {
|
||||
id: varchar("id", { length: 36 }).primaryKey(),
|
||||
secret: text("secret").notNull(),
|
||||
backupCodes: text("backup_codes").notNull(),
|
||||
userId: varchar("user_id", { length: 36 })
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
@@ -20,6 +20,7 @@ export const custom_user = pgTable("custom_user", {
|
||||
.notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
twoFactorEnabled: boolean("two_factor_enabled").default(false),
|
||||
username: text("username").unique(),
|
||||
@@ -31,7 +32,9 @@ export const custom_session = pgTable("custom_session", {
|
||||
expiresAt: timestamp("expires_at").notNull(),
|
||||
token: text("token").notNull().unique(),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
ipAddress: text("ip_address"),
|
||||
userAgent: text("user_agent"),
|
||||
userId: integer("user_id")
|
||||
@@ -54,7 +57,9 @@ export const custom_account = pgTable("custom_account", {
|
||||
scope: text("scope"),
|
||||
password: text("password"),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
});
|
||||
|
||||
export const custom_verification = pgTable("custom_verification", {
|
||||
@@ -65,9 +70,9 @@ export const custom_verification = pgTable("custom_verification", {
|
||||
createdAt: timestamp("created_at").$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: timestamp("updated_at").$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date()),
|
||||
});
|
||||
|
||||
export const twoFactor = pgTable("two_factor", {
|
||||
|
||||
@@ -0,0 +1,84 @@
|
||||
import { sqliteTable, text, integer } from "drizzle-orm/sqlite-core";
|
||||
|
||||
export const custom_user = sqliteTable("custom_user", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
name: text("name").notNull(),
|
||||
email: text("email").notNull().unique(),
|
||||
emailVerified: integer("email_verified", { mode: "boolean" })
|
||||
.$defaultFn(() => false)
|
||||
.notNull(),
|
||||
image: text("image"),
|
||||
createdAt: integer("created_at", { mode: "timestamp" })
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
twoFactorEnabled: integer("two_factor_enabled", { mode: "boolean" }).default(
|
||||
false,
|
||||
),
|
||||
username: text("username").unique(),
|
||||
displayUsername: text("display_username"),
|
||||
});
|
||||
|
||||
export const custom_session = sqliteTable("custom_session", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
expiresAt: integer("expires_at", { mode: "timestamp" }).notNull(),
|
||||
token: text("token").notNull().unique(),
|
||||
createdAt: integer("created_at", { mode: "timestamp" }).notNull(),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
ipAddress: text("ip_address"),
|
||||
userAgent: text("user_agent"),
|
||||
userId: integer("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
|
||||
export const custom_account = sqliteTable("custom_account", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
accountId: text("account_id").notNull(),
|
||||
providerId: text("provider_id").notNull(),
|
||||
userId: integer("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
accessToken: text("access_token"),
|
||||
refreshToken: text("refresh_token"),
|
||||
idToken: text("id_token"),
|
||||
accessTokenExpiresAt: integer("access_token_expires_at", {
|
||||
mode: "timestamp",
|
||||
}),
|
||||
refreshTokenExpiresAt: integer("refresh_token_expires_at", {
|
||||
mode: "timestamp",
|
||||
}),
|
||||
scope: text("scope"),
|
||||
password: text("password"),
|
||||
createdAt: integer("created_at", { mode: "timestamp" }).notNull(),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
});
|
||||
|
||||
export const custom_verification = sqliteTable("custom_verification", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
identifier: text("identifier").notNull(),
|
||||
value: text("value").notNull(),
|
||||
expiresAt: integer("expires_at", { mode: "timestamp" }).notNull(),
|
||||
createdAt: integer("created_at", { mode: "timestamp" }).$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date()),
|
||||
});
|
||||
|
||||
export const twoFactor = sqliteTable("two_factor", {
|
||||
id: int("id").autoincrement().primaryKey(),
|
||||
secret: text("secret").notNull(),
|
||||
backupCodes: text("backup_codes").notNull(),
|
||||
userId: integer("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
84
packages/cli/test/__snapshots__/auth-schema-sqlite.txt
Normal file
84
packages/cli/test/__snapshots__/auth-schema-sqlite.txt
Normal file
@@ -0,0 +1,84 @@
|
||||
import { sqliteTable, text, integer } from "drizzle-orm/sqlite-core";
|
||||
|
||||
export const custom_user = sqliteTable("custom_user", {
|
||||
id: text("id").primaryKey(),
|
||||
name: text("name").notNull(),
|
||||
email: text("email").notNull().unique(),
|
||||
emailVerified: integer("email_verified", { mode: "boolean" })
|
||||
.$defaultFn(() => false)
|
||||
.notNull(),
|
||||
image: text("image"),
|
||||
createdAt: integer("created_at", { mode: "timestamp" })
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
twoFactorEnabled: integer("two_factor_enabled", { mode: "boolean" }).default(
|
||||
false,
|
||||
),
|
||||
username: text("username").unique(),
|
||||
displayUsername: text("display_username"),
|
||||
});
|
||||
|
||||
export const custom_session = sqliteTable("custom_session", {
|
||||
id: text("id").primaryKey(),
|
||||
expiresAt: integer("expires_at", { mode: "timestamp" }).notNull(),
|
||||
token: text("token").notNull().unique(),
|
||||
createdAt: integer("created_at", { mode: "timestamp" }).notNull(),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
ipAddress: text("ip_address"),
|
||||
userAgent: text("user_agent"),
|
||||
userId: text("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
|
||||
export const custom_account = sqliteTable("custom_account", {
|
||||
id: text("id").primaryKey(),
|
||||
accountId: text("account_id").notNull(),
|
||||
providerId: text("provider_id").notNull(),
|
||||
userId: text("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
accessToken: text("access_token"),
|
||||
refreshToken: text("refresh_token"),
|
||||
idToken: text("id_token"),
|
||||
accessTokenExpiresAt: integer("access_token_expires_at", {
|
||||
mode: "timestamp",
|
||||
}),
|
||||
refreshTokenExpiresAt: integer("refresh_token_expires_at", {
|
||||
mode: "timestamp",
|
||||
}),
|
||||
scope: text("scope"),
|
||||
password: text("password"),
|
||||
createdAt: integer("created_at", { mode: "timestamp" }).notNull(),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
});
|
||||
|
||||
export const custom_verification = sqliteTable("custom_verification", {
|
||||
id: text("id").primaryKey(),
|
||||
identifier: text("identifier").notNull(),
|
||||
value: text("value").notNull(),
|
||||
expiresAt: integer("expires_at", { mode: "timestamp" }).notNull(),
|
||||
createdAt: integer("created_at", { mode: "timestamp" }).$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: integer("updated_at", { mode: "timestamp" })
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date()),
|
||||
});
|
||||
|
||||
export const twoFactor = sqliteTable("two_factor", {
|
||||
id: text("id").primaryKey(),
|
||||
secret: text("secret").notNull(),
|
||||
backupCodes: text("backup_codes").notNull(),
|
||||
userId: text("user_id")
|
||||
.notNull()
|
||||
.references(() => custom_user.id, { onDelete: "cascade" }),
|
||||
});
|
||||
@@ -13,6 +13,7 @@ export const custom_user = pgTable("custom_user", {
|
||||
.notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
twoFactorEnabled: boolean("two_factor_enabled").default(false),
|
||||
username: text("username").unique(),
|
||||
@@ -24,7 +25,9 @@ export const custom_session = pgTable("custom_session", {
|
||||
expiresAt: timestamp("expires_at").notNull(),
|
||||
token: text("token").notNull().unique(),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
ipAddress: text("ip_address"),
|
||||
userAgent: text("user_agent"),
|
||||
userId: text("user_id")
|
||||
@@ -47,7 +50,9 @@ export const custom_account = pgTable("custom_account", {
|
||||
scope: text("scope"),
|
||||
password: text("password"),
|
||||
createdAt: timestamp("created_at").notNull(),
|
||||
updatedAt: timestamp("updated_at").notNull(),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date())
|
||||
.notNull(),
|
||||
});
|
||||
|
||||
export const custom_verification = pgTable("custom_verification", {
|
||||
@@ -58,9 +63,9 @@ export const custom_verification = pgTable("custom_verification", {
|
||||
createdAt: timestamp("created_at").$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: timestamp("updated_at").$defaultFn(
|
||||
() => /* @__PURE__ */ new Date(),
|
||||
),
|
||||
updatedAt: timestamp("updated_at")
|
||||
.$defaultFn(() => /* @__PURE__ */ new Date())
|
||||
.$onUpdate(() => /* @__PURE__ */ new Date()),
|
||||
});
|
||||
|
||||
export const twoFactor = pgTable("two_factor", {
|
||||
|
||||
169
packages/cli/test/generate-all-db.test.ts
Normal file
169
packages/cli/test/generate-all-db.test.ts
Normal file
@@ -0,0 +1,169 @@
|
||||
import { describe, expect, it } from "vitest";
|
||||
import { generateDrizzleSchema } from "../src/generators/drizzle";
|
||||
import { drizzleAdapter } from "better-auth/adapters/drizzle";
|
||||
import { twoFactor, username } from "better-auth/plugins";
|
||||
import type { BetterAuthOptions } from "better-auth";
|
||||
|
||||
describe("generate drizzle schema for all databases", async () => {
|
||||
it("should generate drizzle schema for MySQL", async () => {
|
||||
const schema = await generateDrizzleSchema({
|
||||
file: "test.drizzle",
|
||||
adapter: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "mysql",
|
||||
schema: {},
|
||||
},
|
||||
)({} as BetterAuthOptions),
|
||||
options: {
|
||||
database: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "mysql",
|
||||
schema: {},
|
||||
},
|
||||
),
|
||||
plugins: [twoFactor(), username()],
|
||||
user: {
|
||||
modelName: "custom_user",
|
||||
},
|
||||
account: {
|
||||
modelName: "custom_account",
|
||||
},
|
||||
session: {
|
||||
modelName: "custom_session",
|
||||
},
|
||||
verification: {
|
||||
modelName: "custom_verification",
|
||||
},
|
||||
},
|
||||
});
|
||||
expect(schema.code).toMatchFileSnapshot(
|
||||
"./__snapshots__/auth-schema-mysql.txt",
|
||||
);
|
||||
});
|
||||
|
||||
it("should generate drizzle schema for SQLite", async () => {
|
||||
const schema = await generateDrizzleSchema({
|
||||
file: "test.drizzle",
|
||||
adapter: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "sqlite",
|
||||
schema: {},
|
||||
},
|
||||
)({} as BetterAuthOptions),
|
||||
options: {
|
||||
database: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "sqlite",
|
||||
schema: {},
|
||||
},
|
||||
),
|
||||
plugins: [twoFactor(), username()],
|
||||
user: {
|
||||
modelName: "custom_user",
|
||||
},
|
||||
account: {
|
||||
modelName: "custom_account",
|
||||
},
|
||||
session: {
|
||||
modelName: "custom_session",
|
||||
},
|
||||
verification: {
|
||||
modelName: "custom_verification",
|
||||
},
|
||||
},
|
||||
});
|
||||
expect(schema.code).toMatchFileSnapshot(
|
||||
"./__snapshots__/auth-schema-sqlite.txt",
|
||||
);
|
||||
});
|
||||
|
||||
it("should generate drizzle schema for MySQL with number id", async () => {
|
||||
const schema = await generateDrizzleSchema({
|
||||
file: "test.drizzle",
|
||||
adapter: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "mysql",
|
||||
schema: {},
|
||||
},
|
||||
)({} as BetterAuthOptions),
|
||||
options: {
|
||||
database: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "mysql",
|
||||
schema: {},
|
||||
},
|
||||
),
|
||||
plugins: [twoFactor(), username()],
|
||||
advanced: {
|
||||
database: {
|
||||
useNumberId: true,
|
||||
},
|
||||
},
|
||||
user: {
|
||||
modelName: "custom_user",
|
||||
},
|
||||
account: {
|
||||
modelName: "custom_account",
|
||||
},
|
||||
session: {
|
||||
modelName: "custom_session",
|
||||
},
|
||||
verification: {
|
||||
modelName: "custom_verification",
|
||||
},
|
||||
},
|
||||
});
|
||||
expect(schema.code).toMatchFileSnapshot(
|
||||
"./__snapshots__/auth-schema-mysql-number-id.txt",
|
||||
);
|
||||
});
|
||||
|
||||
it("should generate drizzle schema for SQLite with number id", async () => {
|
||||
const schema = await generateDrizzleSchema({
|
||||
file: "test.drizzle",
|
||||
adapter: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "sqlite",
|
||||
schema: {},
|
||||
},
|
||||
)({} as BetterAuthOptions),
|
||||
options: {
|
||||
database: drizzleAdapter(
|
||||
{},
|
||||
{
|
||||
provider: "sqlite",
|
||||
schema: {},
|
||||
},
|
||||
),
|
||||
plugins: [twoFactor(), username()],
|
||||
advanced: {
|
||||
database: {
|
||||
useNumberId: true,
|
||||
},
|
||||
},
|
||||
user: {
|
||||
modelName: "custom_user",
|
||||
},
|
||||
account: {
|
||||
modelName: "custom_account",
|
||||
},
|
||||
session: {
|
||||
modelName: "custom_session",
|
||||
},
|
||||
verification: {
|
||||
modelName: "custom_verification",
|
||||
},
|
||||
},
|
||||
});
|
||||
expect(schema.code).toMatchFileSnapshot(
|
||||
"./__snapshots__/auth-schema-sqlite-number-id.txt",
|
||||
);
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user