docs(add): database category (#1315)

* docs: sidebar updated for new category

* fix: icons to use fill version

* add: the rest of the pages for the database category

* update: MySQL done

* update: SQLite done. (and updated MySQL)

* update: PostgreSQL

* update: mssql done

* update: added callout to Kysley docs for each core dialect

* update: other relational databases page

* update: drizzle

* docs(fix): wrong words on drizzle page

* update: mongo docs

* update: prisma done

* update: community adapter page

* update: concept/database to refer to the documentation for each dialect in the docs category

* update: drizzle to mention the schema definitions

---------

Co-authored-by: Bereket Engida <86073083+Bekacru@users.noreply.github.com>
This commit is contained in:
Maxwell
2025-03-01 07:32:46 +10:00
committed by GitHub
parent 7fffd8bb90
commit b6d18ce16f
11 changed files with 958 additions and 310 deletions

File diff suppressed because one or more lines are too long

View File

@@ -0,0 +1,13 @@
---
title: Community Adapters
description: Integrate Better Auth with community made database adapters.
---
This page showcases a list of recommended community made database adapters.
We encourage you to create any missing database adapters and maybe get added to the list!
| Adapter | Database Dialect | Author |
| ------------------------------------------------------------------------- | ------------------------------------------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| [convex-better-auth](https://github.com/ping-maxwell/convex-better-auth/) | [Convex Database](https://www.convex.dev/) | <img src="https://github.com/ping-maxwell.png" className="rounded-full w-6 h-6 border opacity-70 m-0 inline mr-1" /> [ping-maxwell](https://github.com/ping-maxwell) |
| [surreal-better-auth](https://github.com/oskar-gmerek/surreal-better-auth/) | [Surreal Database](https://surrealdb.com/) | <img src="https://github.com/oskar-gmerek.png" className="rounded-full w-6 h-6 border opacity-70 m-0 inline mr-1" /> [oskar-gmerek](https://github.com/oskar-gmerek) |

View File

@@ -0,0 +1,82 @@
---
title: Drizzle ORM Adapter
description: Integrate Better Auth with Drizzle ORM.
---
Drizzle ORM is a powerful and flexible ORM for Node.js and TypeScript. It provides a simple and intuitive API for working with databases, and supports a wide range of databases including MySQL, PostgreSQL, SQLite, and more.
Read more here: [Drizzle ORM](https://orm.drizzle.team/).
## Example Usage
Make sure you have Drizzle installed and configured.
Then, you can use the Drizzle adapter to connect to your database.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { DrizzleAdapter } from "better-auth/adapters/drizzle";
import { db } from "./database.ts";
export const auth = betterAuth({
database: new DrizzleAdapter(db, {
// [!code highlight]
provider: "sqlite", // or "pg" or "mysql" // [!code highlight]
}), // [!code highlight]
//... the rest of your config
});
```
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">Drizzle Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">Drizzle Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>
❌ Not Supported - Use Drizzle [migration
command](https://orm.drizzle.team/docs/migrations)
</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
```bash title="Schema Migration"
drizzle-kit migrate
```
## Additional Information
The Drizzle adapter expects the schema you define to match the table names. For example, if your Drizzle schema maps the `user` table to `users`, you need to manually pass the schema and map it to the user table.
```ts
import { betterAuth } from "better-auth";
import { db } from "./drizzle";
import { drizzleAdapter } from "better-auth/adapters/drizzle";
import { schema } from "./schema";
export const auth = betterAuth({
database: drizzleAdapter(db, {
provider: "sqlite", // or "pg" or "mysql"
schema: {
...schema,
user: schema.users,
},
//if all of them are just using plural form, you can just pass the option below
usePlural: true,
}),
});
```
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -0,0 +1,53 @@
---
title: MongoDB Adapter
description: Integrate Better Auth with MongoDB.
---
MongoDB is a popular NoSQL database that is widely used for building scalable and flexible applications. It provides a flexible schema that allows for easy data modeling and querying.
Read more here: [MongoDB](https://www.mongodb.com/).
## Example Usage
Make sure you have MongoDB installed and configured.
Then, you can use the mongodb adapter.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { MongoClient } from "mongodb";
import { mongodbAdapter } from "better-auth/adapters/mongodb";
const client = new MongoClient("mongodb://localhost:27017/database");
const db = client.db();
export const auth = betterAuth({
database: mongodbAdapter(db),
});
```
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">MongoDB Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">MongoDB Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>❌ Not Supported</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
## Additional Information
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -0,0 +1,89 @@
---
title: MS SQL
description: Integrate Better Auth with MS SQL.
---
Microsoft SQL Server is a relational database management system developed by Microsoft, designed for enterprise-level data storage, management, and analytics with robust security and scalability features.
Read more [here](https://en.wikipedia.org/wiki/Microsoft_SQL_Server).
## Example Usage
Make sure you have MS SQL installed and configured.
Then, you can connect it straight into Better Auth.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import * as Tedious from 'tedious'
import * as Tarn from 'tarn'
const dialect = new MssqlDialect({
tarn: {
...Tarn,
options: {
min: 0,
max: 10,
},
},
tedious: {
...Tedious,
connectionFactory: () => new Tedious.Connection({
authentication: {
options: {
password: 'password',
userName: 'username',
},
type: 'default',
},
options: {
database: 'some_db',
port: 1433,
trustServerCertificate: true,
},
server: 'localhost',
}),
},
})
export const auth = betterAuth({
database: dialect
});
```
<Callout>
For more information, read Kysely's documentation to the [MssqlDialect](https://kysely-org.github.io/kysely-apidoc/classes/MssqlDialect.html).
</Callout>
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">MS SQL Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">MS SQL Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>✅ Supported</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
```bash title="Schema Migration"
npx @better-auth/cli@latest migrate
```
## Additional Information
MS SQL is supported under the hood via the [Kysely](https://kysely.dev/) adapter, any database supported by Kysely would also be supported. (<Link href="/docs/adapters/other-relational-databases">Read more here</Link>)
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -0,0 +1,65 @@
---
title: MySQL
description: Integrate Better Auth with MySQL.
---
MySQL is a popular open-source relational database management system (RDBMS) that is widely used for building web applications and other types of software. It provides a flexible and scalable database solution that allows for efficient storage and retrieval of data.
Read more here: [MySQL](https://www.mysql.com/).
## Example Usage
Make sure you have MySQL installed and configured.
Then, you can connect it straight into Better Auth.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { createPool } from "mysql2/promise";
export const auth = betterAuth({
database: createPool({
host: "localhost",
user: "root",
password: "password",
database: "database",
}),
});
```
<Callout>
For more information, read Kysely's documentation to the
[MySQLDialect](https://kysely-org.github.io/kysely-apidoc/classes/MysqlDialect.html).
</Callout>
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">MySQL Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">MySQL Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>✅ Supported</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
```bash title="Schema Migration"
npx @better-auth/cli@latest migrate
```
## Additional Information
MySQL is supported under the hood via the [Kysely](https://kysely.dev/) adapter, any database supported by Kysely would also be supported. (<Link href="/docs/adapters/other-relational-databases">Read more here</Link>)
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -0,0 +1,44 @@
---
title: Other Relational Databases
description: Integrate Better Auth with other relational databases.
---
Better Auth supports a wide range of database dialects out of the box thanks to <Link href="https://kysely.dev/">Kysely</Link>.
Any dialect supported by Kysely can be utilized with Better Auth, including capabilities for generating and migrating database schemas through the <Link href="/docs/concepts/cli">CLI</Link>.
## Core Dialects
- [MySQL](/docs/adapters/mysql)
- [SQLite](/docs/adapters/sqlite)
- [PostgreSQL](/docs/adapters/postgresql)
- [MS SQL](/docs/adapters/mssql)
## Kysely Organization Dialects
- [Postgres.js](https://github.com/kysely-org/kysely-postgres-js)
- [SingleStore Data API](https://github.com/kysely-org/kysely-singlestore)
## Kysely Community dialects
- [PlanetScale Serverless Driver](https://github.com/depot/kysely-planetscale)
- [Cloudflare D1](https://github.com/aidenwallis/kysely-d1)
- [AWS RDS Data API](https://github.com/serverless-stack/kysely-data-api)
- [SurrealDB](https://github.com/igalklebanov/kysely-surrealdb)
- [Neon](https://github.com/seveibar/kysely-neon)
- [Xata](https://github.com/xataio/client-ts/tree/main/packages/plugin-client-kysely)
- [AWS S3 Select](https://github.com/igalklebanov/kysely-s3-select)
- [libSQL/sqld](https://github.com/libsql/kysely-libsql)
- [Fetch driver](https://github.com/andersgee/kysely-fetch-driver)
- [SQLite WASM](https://github.com/DallasHoff/sqlocal)
- [Deno SQLite](https://gitlab.com/soapbox-pub/kysely-deno-sqlite)
- [TiDB Cloud Serverless Driver](https://github.com/tidbcloud/kysely)
- [Capacitor SQLite Kysely](https://github.com/DawidWetzler/capacitor-sqlite-kysely)
- [BigQuery](https://github.com/maktouch/kysely-bigquery)
- [Clickhouse](https://github.com/founderpathcom/kysely-clickhouse)
- [PGLite](https://github.com/czeidler/kysely-pglite-dialect)
<Callout>
You can see the full list of supported Kysely dialects{" "}
<Link href="https://kysely.dev/docs/dialects">here</Link>.
</Callout>

View File

@@ -0,0 +1,62 @@
---
title: PostgreSQL
description: Integrate Better Auth with PostgreSQL.
---
PostgreSQL is a powerful, open-source relational database management system known for its advanced features, extensibility, and support for complex queries and large datasets.
Read more [here](https://www.postgresql.org/).
## Example Usage
Make sure you have PostgreSQL installed and configured.
Then, you can connect it straight into Better Auth.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { Pool } from "pg";
export const auth = betterAuth({
database: new Pool({
connectionString: "postgres://user:password@localhost:5432/database",
}),
});
```
<Callout>
For more information, read Kysely's documentation to the
[PostgresDialect](https://kysely-org.github.io/kysely-apidoc/classes/PostgresDialect.html).
</Callout>
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">PostgreSQL Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">PostgreSQL Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>✅ Supported</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
```bash title="Schema Migration"
npx @better-auth/cli@latest migrate
```
## Additional Information
PostgreSQL is supported under the hood via the [Kysely](https://kysely.dev/) adapter, any database supported by Kysely would also be supported. (<Link href="/docs/adapters/other-relational-databases">Read more here</Link>)
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -0,0 +1,54 @@
---
title: Prisma
description: Integrate Better Auth with Prisma.
---
Prisma ORM is an open-source database toolkit that simplifies database access and management in applications by providing a type-safe query builder and an intuitive data modeling interface.
Read more [here](https://www.prisma.io/).
## Example Usage
Make sure you have Prisma installed and configured.
Then, you can use the Drizzle adapter to connect to your database.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { prismaAdapter } from "better-auth/adapters/prisma";
import { PrismaClient } from "@prisma/client";
const prisma = new PrismaClient();
export const auth = betterAuth({
database: prismaAdapter(prisma, {
provider: "sqlite",
}),
});
```
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">Prisma Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">Prisma Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>❌ Not Supported</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
## Additional Information
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -0,0 +1,60 @@
---
title: SQLite
description: Integrate Better Auth with SQLite.
---
SQLite is a lightweight, serverless, self-contained SQL database engine that is widely used for local data storage in applications.
Read more [here.](https://www.sqlite.org/)
## Example Usage
Make sure you have SQLite installed and configured.
Then, you can connect it straight into Better Auth.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import Database from "better-sqlite3";
export const auth = betterAuth({
database: new Database("database.sqlite"),
});
```
<Callout>
For more information, read Kysely's documentation to the
[SqliteDialect](https://kysely-org.github.io/kysely-apidoc/classes/SqliteDialect.html).
</Callout>
## Schema generaton & migration
The [Better Auth CLI](/docs/concepts/cli) allows you to generate or migrate
your database schema based on your Better Auth configuration and plugins.
<table>
<tr className="border-b">
<th>
<p className="font-bold text-[16px] mb-1">SQLite Schema Generation</p>
</th>
<th>
<p className="font-bold text-[16px] mb-1">SQLite Schema Migration</p>
</th>
</tr>
<tr className="h-10">
<td>✅ Supported</td>
<td>✅ Supported</td>
</tr>
</table>
```bash title="Schema Generation"
npx @better-auth/cli@latest generate
```
```bash title="Schema Migration"
npx @better-auth/cli@latest migrate
```
## Additional Information
SQLite is supported under the hood via the [Kysely](https://kysely.dev/) adapter, any database supported by Kysely would also be supported. (<Link href="/docs/adapters/other-relational-databases">Read more here</Link>)
If you're looking for performance improvements or tips, take a look at our guide to <Link href="/docs/guides/optimizing-for-performance">performance optimizations</Link>.

View File

@@ -3,164 +3,15 @@ title: Database
description: Learn how to use a database with Better Auth. description: Learn how to use a database with Better Auth.
--- ---
Better Auth requires a database connection to store data. It comes with a query builder called <Link href="https://kysely.dev/"> Kysely </Link> to manage and query your database. The database will be used to store data such as users, sessions, and more. Plugins can also define their own database tables to store data. ## Adapters
Better Auth requires a database connection to store data. It comes with a query builder called <Link href="https://kysely.dev/">Kysely</Link> to manage and query your database. The database will be used to store data such as users, sessions, and more. Plugins can also define their own database tables to store data.
You can pass a database connection to Better Auth by passing a supported database instance, a dialect instance or a Kysely instance in the database options. You can pass a database connection to Better Auth by passing a supported database instance, a dialect instance or a Kysely instance in the database options.
**Example: Sqlite** You can learn more about supported Kysely dialects in the [Other relational databases](/docs/adapters/other-relational-databases) documentation. Or if you're using an ORM, you can find our supported ORM adapters in that same category on the documentation sidebar.
```ts title="auth.ts"
import { betterAuth } from "better-auth"
import Database from "better-sqlite3"
export const auth = betterAuth({
database: new Database("database.sqlite")
})
```
**Example: Postgres**
```ts title="auth.ts"
import { betterAuth } from "better-auth"
import { Pool } from "pg"
export const auth = betterAuth({
database: new Pool({
connectionString: "postgres://user:password@localhost:5432/database"
})
})
```
**Example: MySQL**
```ts title="auth.ts"
import { betterAuth } from "better-auth"
import { createPool } from "mysql2/promise"
export const auth = betterAuth({
database: createPool({
host: "localhost",
user: "root",
password: "password",
database: "database"
})
})
```
**Example: Custom Dialect using libSQL**
```ts title="auth.ts"
import { betterAuth } from "better-auth"
import { LibsqlDialect } from "@libsql/kysely-libsql";
export const auth = betterAuth({
database: {
dialect: new LibsqlDialect({
url: process.env.TURSO_DATABASE_URL || "",
authToken: process.env.TURSO_AUTH_TOKEN || "",
}),
type: "sqlite"
},
})
```
<Callout>
See <Link href="https://kysely.dev/docs/dialects" target="_blank"> Kysely Dialects </Link> for more dialects supported by Kysely.
</Callout>
**Example: Custom Kysely Instance**
```ts title="auth.ts"
import { betterAuth } from "better-auth"
import { db } from "./db"
export const auth = betterAuth({
database: {
db: db,
type: "sqlite" // or "mysql", "postgres" or "mssql"
}
})
```
## Using Adapters
If your database is managed by an ORM like Prisma or Drizzle, you can use the corresponding adapter to connect to the database. Better Auth comes with built-in adapters for Prisma and Drizzle. You can pass the adapter to the `database` object in the auth options.
### Prisma Adapter
The Prisma adapter expects a prisma client instance and a provider key that specifies the database provider to use. The provider key can be `sqlite`, `postgres`, `mysql`, or any other supported by prisma.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { prismaAdapter } from "better-auth/adapters/prisma";
import { PrismaClient } from "@prisma/client";
const prisma = new PrismaClient();
export const auth = betterAuth({
database: prismaAdapter(prisma, {
provider: "sqlite"
})
})
```
### Drizzle adapter
The Drizzle adapter expects a drizzle client instance and a provider key that specifies the database provider to use. The provider key can be `sqlite`, `pg` or `mysql`.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { db } from "./drizzle";
import { drizzleAdapter } from "better-auth/adapters/drizzle";
export const auth = betterAuth({
database: drizzleAdapter(db, {
provider: "sqlite", // or "pg" or "mysql"
})
})
```
#### Mapping Schema
The Drizzle adapter expects the schema you define to match the table names. For example, if your Drizzle schema maps the `user` table to `users`, you need to manually pass the schema and map it to the user table.
```ts
import { betterAuth } from "better-auth";
import { db } from "./drizzle";
import { drizzleAdapter } from "better-auth/adapters/drizzle";
import { schema } from "./schema";
export const auth = betterAuth({
database: drizzleAdapter(db, {
provider: "sqlite", // or "pg" or "mysql"
schema: {
...schema,
user: schema.users,
},
//if all of them are just using plural form, you can just pass the option below
usePlural: true
})
})
```
### MongoDB Adapter
The MongoDB adapter expects a mongodb client instance and a database name. The adapter will create a new database with the provided name if it doesn't exist.
```ts title="auth.ts"
import { betterAuth } from "better-auth";
import { MongoClient } from "mongodb";
import { mongodbAdapter } from "better-auth/adapters/mongodb";
const client = new MongoClient("mongodb://localhost:27017/database");
const db = client.db()
export const auth = betterAuth({
database: mongodbAdapter(db)
})
```
## CLI
## CLI
Better Auth comes with a CLI tool to manage database migrations and generate schema. Better Auth comes with a CLI tool to manage database migrations and generate schema.
@@ -183,10 +34,11 @@ npx @better-auth/cli generate
See the [CLI](/docs/concepts/cli) documentation for more information on the CLI. See the [CLI](/docs/concepts/cli) documentation for more information on the CLI.
<Callout> <Callout>
If you prefer adding tables manually, you can do that as well. The core schema required by Better Auth is described below and you can find additional schema required by plugins in the plugin documentation. If you prefer adding tables manually, you can do that as well. The core schema
required by Better Auth is described below and you can find additional schema
required by plugins in the plugin documentation.
</Callout> </Callout>
## Secondary Storage ## Secondary Storage
Secondary storage in Better Auth allows you to use key-value stores for managing session data, rate limiting counters, etc. This can be useful when you want to offload the storage of this intensive records to a high performance storage or even RAM. Secondary storage in Better Auth allows you to use key-value stores for managing session data, rate limiting counters, etc. This can be useful when you want to offload the storage of this intensive records to a high performance storage or even RAM.
@@ -197,13 +49,9 @@ To use secondary storage, implement the `SecondaryStorage` interface:
```typescript ```typescript
interface SecondaryStorage { interface SecondaryStorage {
get: (key: string) => Promise<string | null> get: (key: string) => Promise<string | null>;
set: ( set: (key: string, value: string, ttl?: number) => Promise<void>;
key: string, delete: (key: string) => Promise<void>;
value: string,
ttl?: number,
) => Promise<void>;
delete: (key: string) => Promise<void>;
} }
``` ```
@@ -211,11 +59,11 @@ Then, provide your implementation to the `betterAuth` function:
```typescript ```typescript
betterAuth({ betterAuth({
// ... other options // ... other options
secondaryStorage: { secondaryStorage: {
// Your implementation here // Your implementation here
} },
}) });
``` ```
**Example: Redis Implementation** **Example: Redis Implementation**
@@ -265,38 +113,38 @@ Table Name: `user`
name: "id", name: "id",
type: "string", type: "string",
description: "Unique identifier for each user", description: "Unique identifier for each user",
isPrimaryKey: true isPrimaryKey: true,
}, },
{ {
name: "name", name: "name",
type: "string", type: "string",
description: "User's chosen display name" description: "User's chosen display name",
}, },
{ {
name: "email", name: "email",
type: "string", type: "string",
description: "User's email address for communication and login" description: "User's email address for communication and login",
}, },
{ {
name: "emailVerified", name: "emailVerified",
type: "boolean", type: "boolean",
description: "Whether the user's email is verified", description: "Whether the user's email is verified",
}, },
{ {
name: "image", name: "image",
type: "string", type: "string",
description: "User's image url", description: "User's image url",
isOptional: true isOptional: true,
}, },
{ {
name: "createdAt", name: "createdAt",
type: "Date", type: "Date",
description: "Timestamp of when the user account was created" description: "Timestamp of when the user account was created",
}, },
{ {
name: "updatedAt", name: "updatedAt",
type: "Date", type: "Date",
description: "Timestamp of the last update to the user's information" description: "Timestamp of the last update to the user's information",
}, },
]} ]}
/> />
@@ -311,49 +159,49 @@ Table Name: `session`
name: "id", name: "id",
type: "string", type: "string",
description: "Unique identifier for each session", description: "Unique identifier for each session",
isPrimaryKey: true isPrimaryKey: true,
}, },
{ {
name: "userId", name: "userId",
type: "string", type: "string",
description: "The id of the user", description: "The id of the user",
isForeignKey: true isForeignKey: true,
}, },
{ {
name:"token", name: "token",
type: "string", type: "string",
description: "The unique session token", description: "The unique session token",
isUnique: true isUnique: true,
}, },
{ {
name: "expiresAt", name: "expiresAt",
type: "Date", type: "Date",
description: "The time when the session expires" description: "The time when the session expires",
}, },
{ {
name: "ipAddress", name: "ipAddress",
type: "string", type: "string",
description: "The IP address of the device", description: "The IP address of the device",
isOptional: true isOptional: true,
}, },
{ {
name: "userAgent", name: "userAgent",
type: "string", type: "string",
description: "The user agent information of the device", description: "The user agent information of the device",
isOptional: true isOptional: true,
}, },
{ {
name: "createdAt", name: "createdAt",
type: "Date", type: "Date",
description: "Timestamp of when the verification request was created" description: "Timestamp of when the verification request was created",
}, },
{ {
name: "updatedAt", name: "updatedAt",
type: "Date", type: "Date",
description: "Timestamp of when the verification request was updated" description: "Timestamp of when the verification request was updated",
} },
]} ]}
/> />
### Account ### Account
@@ -365,18 +213,19 @@ Table Name: `account`
name: "id", name: "id",
type: "string", type: "string",
description: "Unique identifier for each account", description: "Unique identifier for each account",
isPrimaryKey: true isPrimaryKey: true,
}, },
{ {
name: "userId", name: "userId",
type: "string", type: "string",
description: "The id of the user", description: "The id of the user",
isForeignKey: true isForeignKey: true,
}, },
{ {
name: "accountId", name: "accountId",
type: "string", type: "string",
description: "The id of the account as provided by the SSO or equal to userId for credential accounts", description:
"The id of the account as provided by the SSO or equal to userId for credential accounts",
}, },
{ {
name: "providerId", name: "providerId",
@@ -422,23 +271,23 @@ Table Name: `account`
{ {
name: "password", name: "password",
type: "string", type: "string",
description: "The password of the account. Mainly used for email and password authentication", description:
"The password of the account. Mainly used for email and password authentication",
isOptional: true, isOptional: true,
}, },
{ {
name: "createdAt", name: "createdAt",
type: "Date", type: "Date",
description: "Timestamp of when the verification request was created" description: "Timestamp of when the verification request was created",
}, },
{ {
name: "updatedAt", name: "updatedAt",
type: "Date", type: "Date",
description: "Timestamp of when the verification request was updated" description: "Timestamp of when the verification request was updated",
} },
]} ]}
/> />
### Verification ### Verification
Table Name: `verification` Table Name: `verification`
@@ -449,37 +298,36 @@ Table Name: `verification`
name: "id", name: "id",
type: "string", type: "string",
description: "Unique identifier for each verification", description: "Unique identifier for each verification",
isPrimaryKey: true isPrimaryKey: true,
}, },
{ {
name: "identifier", name: "identifier",
type: "string", type: "string",
description: "The identifier for the verification request" description: "The identifier for the verification request",
}, },
{ {
name: "value", name: "value",
type: "string", type: "string",
description: "The value to be verified" description: "The value to be verified",
}, },
{ {
name: "expiresAt", name: "expiresAt",
type: "Date", type: "Date",
description: "The time when the verification request expires" description: "The time when the verification request expires",
}, },
{ {
name: "createdAt", name: "createdAt",
type: "Date", type: "Date",
description: "Timestamp of when the verification request was created" description: "Timestamp of when the verification request was created",
}, },
{ {
name: "updatedAt", name: "updatedAt",
type: "Date", type: "Date",
description: "Timestamp of when the verification request was updated" description: "Timestamp of when the verification request was updated",
} },
]} ]}
/> />
## Custom Tables ## Custom Tables
Better Auth allows you to customize the table names and column names for the core schema. You can also extend the core schema by adding additional fields to the user and session tables. Better Auth allows you to customize the table names and column names for the core schema. You can also extend the core schema by adding additional fields to the user and session tables.
@@ -490,24 +338,25 @@ You can customize the table names and column names for the core schema by using
```ts title="auth.ts" ```ts title="auth.ts"
export const auth = betterAuth({ export const auth = betterAuth({
user: { user: {
modelName: "users", modelName: "users",
fields: { fields: {
name: "full_name", name: "full_name",
email: "email_address" email: "email_address",
} },
}, },
session: { session: {
modelName: "user_sessions", modelName: "user_sessions",
fields: { fields: {
userId: "user_id" userId: "user_id",
} },
} },
}) });
``` ```
<Callout> <Callout>
Type inference in your code will still use the original field names (e.g., `user.name`, not `user.full_name`). Type inference in your code will still use the original field names (e.g.,
`user.name`, not `user.full_name`).
</Callout> </Callout>
To customize table names and column name for plugins, you can use the `schema` property in the plugin config: To customize table names and column name for plugins, you can use the `schema` property in the plugin config:
@@ -517,22 +366,21 @@ import { betterAuth } from "better-auth";
import { twoFactor } from "better-auth/plugins"; import { twoFactor } from "better-auth/plugins";
export const auth = betterAuth({ export const auth = betterAuth({
plugins: [ plugins: [
twoFactor({ twoFactor({
schema: { schema: {
user: { user: {
fields: { fields: {
twoFactorEnabled: "two_factor_enabled", twoFactorEnabled: "two_factor_enabled",
secret: "two_factor_secret", secret: "two_factor_secret",
},
}, },
}, },
}), },
], }),
],
}); });
``` ```
### Extending Core Schema ### Extending Core Schema
Better Auth provides a type-safe way to extend the `user` and `session` schemas. You can add custom fields to your auth config, and the CLI will automatically update the database schema. These additional fields will be properly inferred in functions like `useSession`, `signUp.email`, and other endpoints that work with user or session objects. Better Auth provides a type-safe way to extend the `user` and `session` schemas. You can add custom fields to your auth config, and the CLI will automatically update the database schema. These additional fields will be properly inferred in functions like `useSession`, `signUp.email`, and other endpoints that work with user or session objects.
@@ -550,42 +398,45 @@ Here's an example of how to extend the user schema with additional fields:
import { betterAuth } from "better-auth"; import { betterAuth } from "better-auth";
export const auth = betterAuth({ export const auth = betterAuth({
user: { user: {
additionalFields: { additionalFields: {
role: { role: {
type: "string", type: "string",
required: false, required: false,
defaultValue: "user", defaultValue: "user",
input: false // don't allow user to set role input: false, // don't allow user to set role
}, },
lang: { lang: {
type: "string", type: "string",
required: false, required: false,
defaultValue: "en", defaultValue: "en",
} },
} },
} },
}) });
``` ```
Now you can access the additional fields in your application logic. Now you can access the additional fields in your application logic.
```ts ```ts
//on signup //on signup
const res = await auth.api.signUpEmail({ const res = await auth.api.signUpEmail({
email: "test@example.com", email: "test@example.com",
password: "password", password: "password",
name: "John Doe", name: "John Doe",
lang: "fr" lang: "fr",
}) });
//user object //user object
res.user.role // > "admin" res.user.role; // > "admin"
res.user.lang // > "fr" res.user.lang; // > "fr"
``` ```
<Callout> <Callout>
See the [Typescript](/docs/concepts/typescript#inferring-additional-fields-on-client) documentation for more information on how to infer additional fields on the client side. See the
[Typescript](/docs/concepts/typescript#inferring-additional-fields-on-client)
documentation for more information on how to infer additional fields on the
client side.
</Callout> </Callout>
If you're using social / OAuth providers, you may want to provide `mapProfileToUser` to map the profile data to the user object. So, you can populate additional fields from the provider's profile. If you're using social / OAuth providers, you may want to provide `mapProfileToUser` to map the profile data to the user object. So, you can populate additional fields from the provider's profile.
@@ -596,29 +447,29 @@ If you're using social / OAuth providers, you may want to provide `mapProfileToU
import { betterAuth } from "better-auth"; import { betterAuth } from "better-auth";
export const auth = betterAuth({ export const auth = betterAuth({
socialProviders: { socialProviders: {
github: { github: {
clientId: "YOUR_GITHUB_CLIENT_ID", clientId: "YOUR_GITHUB_CLIENT_ID",
clientSecret: "YOUR_GITHUB_CLIENT_SECRET", clientSecret: "YOUR_GITHUB_CLIENT_SECRET",
mapProfileToUser: (profile) => { mapProfileToUser: (profile) => {
return { return {
firstName: profile.name.split(" ")[0], firstName: profile.name.split(" ")[0],
lastName: profile.name.split(" ")[1], lastName: profile.name.split(" ")[1],
} };
}
}, },
google: { },
clientId: "YOUR_GOOGLE_CLIENT_ID", google: {
clientSecret: "YOUR_GOOGLE_CLIENT_SECRET", clientId: "YOUR_GOOGLE_CLIENT_ID",
mapProfileToUser: (profile) => { clientSecret: "YOUR_GOOGLE_CLIENT_SECRET",
return { mapProfileToUser: (profile) => {
firstName: profile.given_name, return {
lastName: profile.family_name, firstName: profile.given_name,
} lastName: profile.family_name,
} };
} },
} },
}) },
});
``` ```
### ID Generation ### ID Generation
@@ -628,18 +479,19 @@ Better Auth by default will generate unique IDs for users, sessions, and other e
You can also disable ID generation by setting the `generateId` option to `false`. This will assume your database will generate the ID automatically. You can also disable ID generation by setting the `generateId` option to `false`. This will assume your database will generate the ID automatically.
**Example: Automatic Database IDs** **Example: Automatic Database IDs**
```ts title="auth.ts"
```ts title="auth.ts"
import { betterAuth } from "better-auth"; import { betterAuth } from "better-auth";
import { db } from "./db"; import { db } from "./db";
export const auth = betterAuth({ export const auth = betterAuth({
database: { database: {
db: db db: db,
}, },
advanced: { advanced: {
generateId: false, generateId: false,
}, },
}) });
``` ```
### Database Hooks ### Database Hooks
@@ -664,29 +516,30 @@ There are two types of hooks you can define:
import { betterAuth } from "better-auth"; import { betterAuth } from "better-auth";
export const auth = betterAuth({ export const auth = betterAuth({
databaseHooks: { databaseHooks: {
user: { user: {
create: { create: {
before: async (user) => { before: async (user) => {
// Modify the user object before it is created // Modify the user object before it is created
return { return {
data: { data: {
...user, ...user,
firstName: user.name.split(" ")[0], firstName: user.name.split(" ")[0],
lastName: user.name.split(" ")[1] lastName: user.name.split(" ")[1],
} },
} };
}, },
after: async (user) => { after: async (user) => {
//perform additional actions, like creating a stripe customer //perform additional actions, like creating a stripe customer
}, },
},
}, },
} },
}) },
});
``` ```
#### Throwing Errors #### Throwing Errors
If you want to stop the database hook from proceeding, you can throw errors using the `APIError` class imported from `better-auth/api`. If you want to stop the database hook from proceeding, you can throw errors using the `APIError` class imported from `better-auth/api`.
```typescript title="auth.ts" ```typescript title="auth.ts"
@@ -698,23 +551,23 @@ export const auth = betterAuth({
user: { user: {
create: { create: {
before: async (user) => { before: async (user) => {
if (user.isAgreedToTerms === false) { // Your special condition. if (user.isAgreedToTerms === false) {
// Your special condition.
// Send the API error. // Send the API error.
throw new APIError("BAD_REQUEST", { throw new APIError("BAD_REQUEST", {
message: "User must agree to the TOS before signing up.", message: "User must agree to the TOS before signing up.",
}); });
} }
return { return {
data: user data: user,
}; };
}, },
}, },
}, },
} },
}) });
``` ```
## Plugins Schema ## Plugins Schema
Plugins can define their own tables in the database to store additional data. They can also add columns to the core tables to store additional data. For example, the two factor authentication plugin adds the following columns to the `user` table: Plugins can define their own tables in the database to store additional data. They can also add columns to the core tables to store additional data. For example, the two factor authentication plugin adds the following columns to the `user` table:
@@ -729,4 +582,3 @@ To add new tables and columns to your database, you have two options:
`Manual Method`: Follow the instructions in the plugin documentation to manually add tables and columns. `Manual Method`: Follow the instructions in the plugin documentation to manually add tables and columns.
Both methods ensure your database schema stays up-to-date with your plugins' requirements. Both methods ensure your database schema stays up-to-date with your plugins' requirements.