Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix(drizzle): update schema type & fix issue with default id #10750

Merged
merged 58 commits into from May 8, 2024
Merged
Show file tree
Hide file tree
Changes from 47 commits
Commits
Show all changes
58 commits
Select commit Hold shift + click to select a range
72f28a8
update drizzle adapter
realmikesolo Apr 2, 2024
a9884a8
update adapter for drizzle: finish
realmikesolo Apr 4, 2024
3bdba8a
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 4, 2024
be9fe2b
drizzle adapter: fix table names
realmikesolo Apr 4, 2024
7b4e9fe
drizzle-adapter: fix docs
realmikesolo Apr 4, 2024
4ecfef4
drizzle adapter: edits
realmikesolo Apr 5, 2024
c57a92f
chore(examples): move Docker files to Next.js template
balazsorban44 Apr 8, 2024
67b0ebb
chore(examples): use `with-docker` dockerfile config
balazsorban44 Apr 8, 2024
ebc3c3c
chore(examples): simplify Dockerfile
balazsorban44 Apr 8, 2024
2c1f8b9
chore(express): update README.md example - .cts to .cjs (#10504)
noam-honig Apr 8, 2024
d229e29
Merge branch 'main' of github.com:nextauthjs/next-auth
balazsorban44 Apr 8, 2024
bdf7a25
chore(examples): use npm in Dockerfile
balazsorban44 Apr 8, 2024
9513f71
chore(examples): tweak
balazsorban44 Apr 8, 2024
076d5fe
chore(examples): drop `HOSTNAME`
balazsorban44 Apr 8, 2024
8a483c0
chore(examples): revert
balazsorban44 Apr 8, 2024
a4d6b14
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 8, 2024
f92c888
drizzle-adapter: edits
realmikesolo Apr 8, 2024
3216b0c
Merge branch 'main' into main
ndom91 Apr 8, 2024
b638f20
drizzle adapter: remove redundant connections in tests
realmikesolo Apr 9, 2024
f79f635
Merge branch 'main' into main
ndom91 Apr 9, 2024
f1cd1f4
drizzle adapter: fix syntax issues
realmikesolo Apr 10, 2024
36dcfa6
Merge branch 'main' into main
ndom91 Apr 10, 2024
eb9d3db
Merge branch 'main' into main
ndom91 Apr 10, 2024
b8135e8
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 12, 2024
c41a7a0
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 12, 2024
18953b9
Merge branch 'main' into main
ndom91 Apr 12, 2024
b2390f5
Merge branch 'main' into main
ndom91 Apr 13, 2024
59d5454
Merge branch 'main' into main
ndom91 Apr 13, 2024
2bdcdd5
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 21, 2024
0cf7348
fix: format errors
realmikesolo Apr 21, 2024
60b3f83
drizzle adapter: edits
realmikesolo Apr 22, 2024
9f97268
fix: format errors
realmikesolo Apr 22, 2024
d88cc82
fix(drizzle): edits
realmikesolo Apr 23, 2024
fc7bdb1
Merge branch 'main' into main
ndom91 Apr 23, 2024
b114093
Merge branch 'main' into main
ndom91 Apr 23, 2024
2a48b85
fix(drizzle): edits
realmikesolo Apr 24, 2024
f669e2b
Merge branch 'main' of https://github.com/realmikesolo/next-auth
realmikesolo Apr 24, 2024
2fee81b
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 24, 2024
d97af40
fix(drizzle): edits
realmikesolo Apr 24, 2024
53fc458
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 26, 2024
501baf7
add: function for tables creation & fix issue with id
realmikesolo Apr 27, 2024
44c0728
fix: tests
realmikesolo Apr 27, 2024
98b47b8
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 27, 2024
55cd176
fix(drizzle): update types for schema
realmikesolo Apr 28, 2024
f32f99c
Merge branch 'main' into main
ndom91 Apr 28, 2024
decf937
Merge branch 'main' into main
ndom91 Apr 28, 2024
3b61050
Merge branch 'main' into main
ndom91 Apr 28, 2024
41dbed4
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 29, 2024
bda4db4
fix(drizzle): remove redundant id generation
realmikesolo Apr 29, 2024
ded72d8
Merge remote-tracking branch 'upstream/main'
realmikesolo Apr 29, 2024
80e491f
fix: syntax error
realmikesolo Apr 29, 2024
4f11312
Merge branch 'main' into main
ndom91 Apr 30, 2024
bbc1d62
Merge branch 'main' into main
ndom91 May 3, 2024
f439bc1
Merge remote-tracking branch 'upstream/main'
realmikesolo May 6, 2024
6114327
fix(drizzle): update account type
realmikesolo May 6, 2024
6871bee
Merge remote-tracking branch 'upstream/main'
realmikesolo May 7, 2024
54966e9
fix(drizzle): update docs & schemas in tests
realmikesolo May 7, 2024
f6d30d6
Merge branch 'main' into main
ndom91 May 8, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
2 changes: 1 addition & 1 deletion docs/pages/getting-started/providers/google.mdx
Expand Up @@ -125,6 +125,6 @@ export const { handlers, auth, signIn, signOut } = NextAuth({
}
return true // Do different verification for other providers that don't have `email_verified`
},
}
},
})
```
13 changes: 6 additions & 7 deletions packages/adapter-drizzle/src/index.ts
Expand Up @@ -84,10 +84,9 @@ import type { Adapter } from "@auth/core/adapters"
* integer
* } from "drizzle-orm/pg-core"
* import type { AdapterAccount } from '@auth/core/adapters'
* import { randomUUID } from "crypto"
*
* export const users = pgTable("user", {
* id: text("id").primaryKey().$defaultFn(() => randomUUID()),
* id: text("id").primaryKey().$defaultFn(() => crypto.randomUUID()),
* name: text("name"),
* email: text("email").notNull(),
* emailVerified: timestamp("emailVerified", { mode: "date" }),
Expand All @@ -100,7 +99,7 @@ import type { Adapter } from "@auth/core/adapters"
* userId: text("userId")
* .notNull()
* .references(() => users.id, { onDelete: "cascade" }),
* type: text("type").notNull(),
* type: text("type").$type<AdapterAccount["type"]>().notNull(),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

can use the new AdapterAccountType introduced in #10832 to avoid circular refernce issues

* provider: text("provider").notNull(),
* providerAccountId: text("providerAccountId").notNull(),
* refresh_token: text("refresh_token"),
Expand Down Expand Up @@ -152,7 +151,7 @@ import type { Adapter } from "@auth/core/adapters"
* import type { AdapterAccount } from "@auth/core/adapters"
*
* export const users = mysqlTable("user", {
* id: varchar("id", { length: 255 }).primaryKey().$defaultFn(() => randomUUID()),
* id: varchar("id", { length: 255 }).primaryKey().$defaultFn(() => crypto.randomUUID()),
* name: varchar("name", { length: 255 }),
* email: varchar("email", { length: 255 }).notNull(),
* emailVerified: timestamp("emailVerified", { mode: "date", fsp: 3 }),
Expand All @@ -165,7 +164,7 @@ import type { Adapter } from "@auth/core/adapters"
* userId: varchar("userId", { length: 255 })
* .notNull()
* .references(() => users.id, { onDelete: "cascade" }),
* type: varchar("type", { length: 255 }).notNull(),
* type: varchar("type", { length: 255 }).$type<AdapterAccount["type"]>().notNull(),
* provider: varchar("provider", { length: 255 }).notNull(),
* providerAccountId: varchar("providerAccountId", { length: 255 }).notNull(),
* refresh_token: varchar("refresh_token", { length: 255 }),
Expand Down Expand Up @@ -211,7 +210,7 @@ import type { Adapter } from "@auth/core/adapters"
* import type { AdapterAccount } from "@auth/core/adapters"
*
* export const users = sqliteTable("user", {
* id: text("id").primaryKey().$defaultFn(() => randomUUID()),
* id: text("id").primaryKey().$defaultFn(() => crypto.randomUUID()),
* name: text("name"),
* email: text("email").notNull(),
* emailVerified: integer("emailVerified", { mode: "timestamp_ms" }),
Expand All @@ -224,7 +223,7 @@ import type { Adapter } from "@auth/core/adapters"
* userId: text("userId")
* .notNull()
* .references(() => users.id, { onDelete: "cascade" }),
* type: text("type").notNull(),
* type: text("type").$type<AdapterAccount["type"]>().notNull(),
* provider: text("provider").notNull(),
* providerAccountId: text("providerAccountId").notNull(),
* refresh_token: text("refresh_token"),
Expand Down
143 changes: 81 additions & 62 deletions packages/adapter-drizzle/src/lib/mysql.ts
Expand Up @@ -20,81 +20,100 @@ import type {
VerificationToken,
} from "@auth/core/adapters"

export const mysqlUsersTable = mysqlTable("user", {
id: varchar("id", { length: 255 })
.primaryKey()
.$defaultFn(() => crypto.randomUUID()),
name: varchar("name", { length: 255 }),
email: varchar("email", { length: 255 }).notNull(),
emailVerified: timestamp("emailVerified", { mode: "date", fsp: 3 }),
image: varchar("image", { length: 255 }),
}) satisfies DefaultMySqlUsersTable
export function defineTables(
schema: Partial<DefaultMySqlSchema> = {}
): Required<DefaultMySqlSchema> {
const usersTable =
schema.usersTable ??
(mysqlTable("user", {
id: varchar("id", { length: 255 })
.primaryKey()
.$defaultFn(() => crypto.randomUUID()),
name: varchar("name", { length: 255 }),
email: varchar("email", { length: 255 }).notNull(),
emailVerified: timestamp("emailVerified", { mode: "date", fsp: 3 }),
image: varchar("image", { length: 255 }),
}) satisfies DefaultMySqlUsersTable)

export const mysqlAccountsTable = mysqlTable(
"account",
{
userId: varchar("userId", { length: 255 })
.notNull()
.references(() => mysqlUsersTable.id, { onDelete: "cascade" }),
type: varchar("type", { length: 255 })
.$type<AdapterAccount["type"]>()
.notNull(),
provider: varchar("provider", { length: 255 }).notNull(),
providerAccountId: varchar("providerAccountId", { length: 255 }).notNull(),
refresh_token: varchar("refresh_token", { length: 255 }),
access_token: varchar("access_token", { length: 255 }),
expires_at: int("expires_at"),
token_type: varchar("token_type", { length: 255 }),
scope: varchar("scope", { length: 255 }),
id_token: varchar("id_token", { length: 2048 }),
session_state: varchar("session_state", { length: 255 }),
},
(account) => ({
compositePk: primaryKey({
columns: [account.provider, account.providerAccountId],
}),
})
) satisfies DefaultMySqlAccountsTable
const accountsTable =
schema.accountsTable ??
(mysqlTable(
"account",
{
userId: varchar("userId", { length: 255 })
.notNull()
.references(() => usersTable.id, { onDelete: "cascade" }),
type: varchar("type", { length: 255 })
.$type<AdapterAccount["type"]>()
.notNull(),
provider: varchar("provider", { length: 255 }).notNull(),
providerAccountId: varchar("providerAccountId", {
length: 255,
}).notNull(),
refresh_token: varchar("refresh_token", { length: 255 }),
access_token: varchar("access_token", { length: 255 }),
expires_at: int("expires_at"),
token_type: varchar("token_type", { length: 255 }),
scope: varchar("scope", { length: 255 }),
id_token: varchar("id_token", { length: 2048 }),
session_state: varchar("session_state", { length: 255 }),
},
(account) => ({
compositePk: primaryKey({
columns: [account.provider, account.providerAccountId],
}),
})
) satisfies DefaultMySqlAccountsTable)

export const mysqlSessionsTable = mysqlTable("session", {
sessionToken: varchar("sessionToken", { length: 255 }).primaryKey(),
userId: varchar("userId", { length: 255 })
.notNull()
.references(() => mysqlUsersTable.id, { onDelete: "cascade" }),
expires: timestamp("expires", { mode: "date" }).notNull(),
}) satisfies DefaultMySqlSessionsTable
const sessionsTable =
schema.sessionsTable ??
(mysqlTable("session", {
sessionToken: varchar("sessionToken", { length: 255 }).primaryKey(),
userId: varchar("userId", { length: 255 })
.notNull()
.references(() => usersTable.id, { onDelete: "cascade" }),
expires: timestamp("expires", { mode: "date" }).notNull(),
}) satisfies DefaultMySqlSessionsTable)

export const mysqlVerificationTokensTable = mysqlTable(
"verificationToken",
{
identifier: varchar("identifier", { length: 255 }).notNull(),
token: varchar("token", { length: 255 }).notNull(),
expires: timestamp("expires", { mode: "date" }).notNull(),
},
(vt) => ({
compositePk: primaryKey({ columns: [vt.identifier, vt.token] }),
})
) satisfies DefaultMySqlVerificationTokenTable
const verificationTokensTable =
schema.verificationTokensTable ??
(mysqlTable(
"verificationToken",
{
identifier: varchar("identifier", { length: 255 }).notNull(),
token: varchar("token", { length: 255 }).notNull(),
expires: timestamp("expires", { mode: "date" }).notNull(),
},
(vt) => ({
compositePk: primaryKey({ columns: [vt.identifier, vt.token] }),
})
) satisfies DefaultMySqlVerificationTokenTable)

return {
usersTable,
accountsTable,
sessionsTable,
verificationTokensTable,
}
}

export function MySqlDrizzleAdapter(
client: MySqlDatabase<QueryResultHKT, PreparedQueryHKTBase, any>,
schema: DefaultMySqlSchema = {
usersTable: mysqlUsersTable,
accountsTable: mysqlAccountsTable,
sessionsTable: mysqlSessionsTable,
verificationTokensTable: mysqlVerificationTokensTable,
}
schema?: DefaultMySqlSchema
): Adapter {
const { usersTable, accountsTable, sessionsTable, verificationTokensTable } =
schema
defineTables(schema)

return {
async createUser(data: AdapterUser) {
const { id, ...insertData } = data
const hasDefaultId = getTableColumns(usersTable)["id"]["hasDefault"]

await client
.insert(usersTable)
.values(hasDefaultId ? data : { ...data, id: crypto.randomUUID() })
.values(
hasDefaultId ? insertData : { ...insertData, id: crypto.randomUUID() }
)

return client
.select()
Expand Down Expand Up @@ -442,6 +461,6 @@ export type DefaultMySqlVerificationTokenTable = MySqlTableWithColumns<{
export type DefaultMySqlSchema = {
usersTable: DefaultMySqlUsersTable
accountsTable: DefaultMySqlAccountsTable
sessionsTable: DefaultMySqlSessionsTable
verificationTokensTable: DefaultMySqlVerificationTokenTable
sessionsTable?: DefaultMySqlSessionsTable
verificationTokensTable?: DefaultMySqlVerificationTokenTable
}