[GH-ISSUE #4211] “fieldName” Mapping in additionalFields Causes “Field Does Not Exist” Error with Drizzle Adapter #18496

Closed
opened 2026-04-15 16:58:31 -05:00 by GiteaMirror · 8 comments
Owner

Originally created by @Artist-MOBAI on GitHub (Aug 24, 2025).
Original GitHub issue: https://github.com/better-auth/better-auth/issues/4211

Is this suited for github?

  • Yes, this is suited for github

To Reproduce

Description

When configuring custom fields in Better Auth’s Drizzle ORM adapter using the fieldName option inside additionalFields, user creation fails with an error claiming the specified database column does not exist, despite the field being defined in the Drizzle schema. Removing the fieldName property makes the process succeed.

Reproduction Steps

  1. Define a custom field in Drizzle schema (db/schema.ts):
export const user = pgTable("user", {
  // …other columns…
  expiryDate: timestamp("expiry_date")
    .$defaultFn(() => {
      const d = new Date();
      d.setDate(d.getDate() + 7);
      return d;
    })
    .notNull(),
});
  1. Configure Better Auth with Drizzle adapter and add expiryDate in additionalFields with fieldName:
import { betterAuth } from "better-auth";
import { drizzleAdapter } from "better-auth/adapters/drizzle";
import { db } from "@/db/drizzle";
import { schema } from "@/db/schema";

export const auth = betterAuth({
  database: drizzleAdapter(db, {
    provider: "pg",
    schema,
  }),
  user: {
    additionalFields: {
      expiryDate: {
        type: "date",
        required: true,
        fieldName: "expiry_date",  // ← Including this causes error
        defaultValue: () => {
          const d = new Date();
          d.setDate(d.getDate() + 7);
          return d;
        },
        input: false,
      },
    },
  },
  // …rest of config…
});
  1. Attempt to register a new user:
ERROR [Better Auth]: Failed to create user BetterAuthError: The field "expiry_date" does not exist in the "user" schema. Please update your drizzle schema or re-generate using "npx @better-auth/cli generate".
  1. Comment out or remove the fieldName line and restart. User creation succeeds without error.

Current vs. Expected behavior

Expected Behavior

Better Auth should respect the fieldName mapping in additionalFields and correctly find and use the database column defined in the Drizzle schema.

Actual Behavior

Better Auth ignores or misinterprets the fieldName property in additionalFields, leading to a “field does not exist” error even though the column is present in the schema.

What version of Better Auth are you using?

1.3.7

System info

System:
    OS: macOS 15.6.1
    CPU: (14) arm64 Apple M4 Max
    Memory: 152.14 MB / 36.00 GB
    Shell: 5.9 - /bin/zsh
Browsers:
    Chrome: 139.0.7258.139
    Safari: 18.6

Which area(s) are affected? (Select all that apply)

Backend

Auth config (if applicable)

import { betterAuth } from "better-auth"

export const auth = betterAuth({
  database: drizzleAdapter(db, {
    provider: "pg",
    schema,
  }),
  user: {
    additionalFields: {
      expiryDate: {
        type: "date",
        required: true,
        fieldName: "expiry_date",  // ← Including this causes error
        defaultValue: () => {
          const d = new Date();
          d.setDate(d.getDate() + 7);
          return d;
        },
        input: false,
      },
    },
  },
  // …rest of config…
});

Additional context

The error occurs consistently in both local development and CI environments; it is not isolated to a specific machine or network.

The issue manifests during server-side user registration flows and does not depend on any particular browser or client.

Removing the fieldName option in additionalFields immediately resolves the error, confirming the field exists in the Drizzle schema and database.

All other built-in and custom fields without fieldName mappings work correctly, including default Drizzle schema fields and additional fields defined without explicit column mapping.

Verified that the database table contains the expiry_date column and that Drizzle migrations are up to date.

The problem persists after clearing caches, reinstalling node_modules, and regenerating Better Auth artifacts with bunx @better-auth/cli generate.

Originally created by @Artist-MOBAI on GitHub (Aug 24, 2025). Original GitHub issue: https://github.com/better-auth/better-auth/issues/4211 ### Is this suited for github? - [x] Yes, this is suited for github ### To Reproduce ### Description When configuring custom fields in Better Auth’s Drizzle ORM adapter using the fieldName option inside additionalFields, user creation fails with an error claiming the specified database column does not exist, despite the field being defined in the Drizzle schema. Removing the fieldName property makes the process succeed. ### Reproduction Steps 1. Define a custom field in Drizzle schema (db/schema.ts): ```ts export const user = pgTable("user", { // …other columns… expiryDate: timestamp("expiry_date") .$defaultFn(() => { const d = new Date(); d.setDate(d.getDate() + 7); return d; }) .notNull(), }); ``` 2. Configure Better Auth with Drizzle adapter and add expiryDate in additionalFields with fieldName: ```ts import { betterAuth } from "better-auth"; import { drizzleAdapter } from "better-auth/adapters/drizzle"; import { db } from "@/db/drizzle"; import { schema } from "@/db/schema"; export const auth = betterAuth({ database: drizzleAdapter(db, { provider: "pg", schema, }), user: { additionalFields: { expiryDate: { type: "date", required: true, fieldName: "expiry_date", // ← Including this causes error defaultValue: () => { const d = new Date(); d.setDate(d.getDate() + 7); return d; }, input: false, }, }, }, // …rest of config… }); ``` 3. Attempt to register a new user: ```ts ERROR [Better Auth]: Failed to create user BetterAuthError: The field "expiry_date" does not exist in the "user" schema. Please update your drizzle schema or re-generate using "npx @better-auth/cli generate". ``` 4. Comment out or remove the fieldName line and restart. User creation succeeds without error. ### Current vs. Expected behavior ### Expected Behavior Better Auth should respect the fieldName mapping in additionalFields and correctly find and use the database column defined in the Drizzle schema. ### Actual Behavior Better Auth ignores or misinterprets the fieldName property in additionalFields, leading to a “field does not exist” error even though the column is present in the schema. ### What version of Better Auth are you using? 1.3.7 ### System info ```bash System: OS: macOS 15.6.1 CPU: (14) arm64 Apple M4 Max Memory: 152.14 MB / 36.00 GB Shell: 5.9 - /bin/zsh Browsers: Chrome: 139.0.7258.139 Safari: 18.6 ``` ### Which area(s) are affected? (Select all that apply) Backend ### Auth config (if applicable) ```typescript import { betterAuth } from "better-auth" export const auth = betterAuth({ database: drizzleAdapter(db, { provider: "pg", schema, }), user: { additionalFields: { expiryDate: { type: "date", required: true, fieldName: "expiry_date", // ← Including this causes error defaultValue: () => { const d = new Date(); d.setDate(d.getDate() + 7); return d; }, input: false, }, }, }, // …rest of config… }); ``` ### Additional context The error occurs consistently in both local development and CI environments; it is not isolated to a specific machine or network. The issue manifests during server-side user registration flows and does not depend on any particular browser or client. Removing the fieldName option in additionalFields immediately resolves the error, confirming the field exists in the Drizzle schema and database. All other built-in and custom fields without fieldName mappings work correctly, including default Drizzle schema fields and additional fields defined without explicit column mapping. Verified that the database table contains the expiry_date column and that Drizzle migrations are up to date. The problem persists after clearing caches, reinstalling node_modules, and regenerating Better Auth artifacts with bunx @better-auth/cli generate.
GiteaMirror added the locked label 2026-04-15 16:58:31 -05:00
Author
Owner

@dosubot[bot] commented on GitHub (Aug 24, 2025):

Hi @Artist-MOBAI! I'm Dosu and I’m helping the better-auth team.

The Drizzle adapter in Better Auth does not support the fieldName property in additionalFields. The validation logic expects the logical field name (the TypeScript property name) to match the property in your Drizzle schema object, not the physical database column name. This is why specifying fieldName: "expiry_date" causes a "Field Does Not Exist" error, even though the column exists in your database. Removing fieldName works because the logical field name matches the schema property, which is what Better Auth expects and validates against. There is no documented support or code handling for fieldName mapping in Better Auth's Drizzle adapter, and recent updates do not add this feature [docs].

For now, use logical field names in your config that match your Drizzle schema properties. If you need custom column mapping, you may want to follow future updates or request feature support for this capability.

To reply, just mention @dosu.


How did I do? Good | Irrelevant | Incorrect | Verbose | Hallucination | Report 🐛 | Other  Chat with Dosu Join Discord Share on X

<!-- gh-comment-id:3218433663 --> @dosubot[bot] commented on GitHub (Aug 24, 2025): <!-- Greeting --> Hi @Artist-MOBAI! I'm [Dosu](https://go.dosu.dev/dosubot) and I’m helping the better-auth team. <!-- Answer --> The Drizzle adapter in Better Auth does not support the `fieldName` property in `additionalFields`. The validation logic expects the logical field name (the TypeScript property name) to match the property in your Drizzle schema object, not the physical database column name. This is why specifying `fieldName: "expiry_date"` causes a "Field Does Not Exist" error, even though the column exists in your database. Removing `fieldName` works because the logical field name matches the schema property, which is what Better Auth expects and validates against. There is no documented support or code handling for `fieldName` mapping in Better Auth's Drizzle adapter, and recent updates do not add this feature [[docs](https://better-auth.com/docs/concepts/database)]. For now, use logical field names in your config that match your Drizzle schema properties. If you need custom column mapping, you may want to follow future updates or request feature support for this capability. <!-- Dosu Comment Footer --> *To reply, just mention [@dosu](https://go.dosu.dev/dosubot).* --- <sup>How did I do? [Good](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=great_response) | [Irrelevant](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=irrelevant_answer) | [Incorrect](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=incorrect_sources) | [Verbose](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=too_verbose) | [Hallucination](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=hallucination) | [Report 🐛](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=bug_report) | [Other](https://app.dosu.dev/response-feedback/600a7c04-d60c-438d-8965-ee16ccf0b7c9?feedback_type=other)</sup>&nbsp;&nbsp;[![Chat with Dosu](https://dosu.dev/dosu-chat-badge.svg)](https://app.dosu.dev/cdda13d9-dd27-4d31-b09a-5d8bec92de21/ask?utm_source=github)&nbsp;[![Join Discord](https://img.shields.io/badge/join-5865F2?logo=discord&logoColor=white&label=)](https://go.dosu.dev/discord-bot)&nbsp;[![Share on X](https://img.shields.io/badge/X-share-black)](https://twitter.com/intent/tweet?text=%40dosu_ai%20helped%20me%20solve%20this%20issue!&url=https%3A//github.com/better-auth/better-auth/issues/4211)
Author
Owner

@ping-maxwell commented on GitHub (Oct 8, 2025):

This is normal, we go off of what the drizzle schema defined field name would be, not the DB level field name.

In your case, with a schema like:

export const user = pgTable("user", {
  // …other columns…
  expiryDate: timestamp("expiry_date")
    .$defaultFn(() => {
      const d = new Date();
      d.setDate(d.getDate() + 7);
      return d;
    })
    .notNull(),
});

better-auth would be inferring to expiryDate since that's what is defined to drizzle. The string veesion in timestamp is to tell drizzle how to map that to your DB.

<!-- gh-comment-id:3381663636 --> @ping-maxwell commented on GitHub (Oct 8, 2025): This is normal, we go off of what the drizzle schema defined field name would be, not the DB level field name. In your case, with a schema like: ```ts export const user = pgTable("user", { // …other columns… expiryDate: timestamp("expiry_date") .$defaultFn(() => { const d = new Date(); d.setDate(d.getDate() + 7); return d; }) .notNull(), }); ``` better-auth would be inferring to `expiryDate` since that's what is defined to drizzle. The string veesion in `timestamp` is to tell drizzle how to map that to your DB.
Author
Owner

@vdawg-git commented on GitHub (Oct 9, 2025):

This should be documented Q_Q

<!-- gh-comment-id:3386605911 --> @vdawg-git commented on GitHub (Oct 9, 2025): This should be documented Q_Q
Author
Owner

@ping-maxwell commented on GitHub (Oct 10, 2025):

This should be documented Q_Q

Will do!

<!-- gh-comment-id:3389921766 --> @ping-maxwell commented on GitHub (Oct 10, 2025): > This should be documented Q_Q Will do!
Author
Owner

@staguer commented on GitHub (Oct 17, 2025):

I just noticed this break. It used to work. The Drizzle adapter in Better Auth used to support the fieldName property in additionalFields.

I've tried going back to previous versions of @better-auth/cli and found that it worked in 1.3.23 and broke in 1.3.24.

<!-- gh-comment-id:3413304976 --> @staguer commented on GitHub (Oct 17, 2025): I just noticed this break. It used to work. The Drizzle adapter in Better Auth used to support the `fieldName` property in `additionalFields`. I've tried going back to previous versions of @better-auth/cli and found that it worked in 1.3.23 and broke in 1.3.24.
Author
Owner

@staguer commented on GitHub (Oct 17, 2025):

In addition to setting the version of pnpm dlx @better-auth/cli@1.3.23 generate to 1.3.23 to fix the Drizzle auth-schema.ts generation, I also had to set better-auth dependency in package.json to 1.3.7 to fix the "field does not exist in the schema" run time error referred to in the title.

<!-- gh-comment-id:3413401165 --> @staguer commented on GitHub (Oct 17, 2025): In addition to setting the version of `pnpm dlx @better-auth/cli@1.3.23 generate` to 1.3.23 to fix the Drizzle auth-schema.ts generation, I also had to set better-auth dependency in package.json to 1.3.7 to fix the "field does not exist in the schema" run time error referred to in the title.
Author
Owner

@ping-maxwell commented on GitHub (Oct 17, 2025):

@staguer can you open a new issue?

<!-- gh-comment-id:3414040778 --> @ping-maxwell commented on GitHub (Oct 17, 2025): @staguer can you open a new issue?
Author
Owner

@staguer commented on GitHub (Oct 17, 2025):

Yes, opened #5386.

<!-- gh-comment-id:3416102645 --> @staguer commented on GitHub (Oct 17, 2025): Yes, opened #5386.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: github-starred/better-auth#18496