mastra-ai/mastra · error
Better Auth instance is required. Please provide the auth op
Error message
Better Auth instance is required. Please provide the auth option with your Better Auth instance created via betterAuth({ ... }), or provide `secret` so the provider can build its own instance in init() on the host database. What it means
MastraAuthBetterAuth can run in two modes: bring-your-own Better Auth instance (options.auth) or deferred mode where init() builds an instance on the host database using options.secret. The constructor throws if neither is provided, because without one of them the provider has no way to create or reach a Better Auth backend.
Source
Thrown at auth/better-auth/src/index.ts:214
this.#orgCache.delete(key);
}
this.#orgCache.delete(userId);
this.#orgCache.set(userId, { orgId, expiresAt: now + ORG_CACHE_TTL_MS });
}
/** @internal Test hook: current org-cache cardinality. */
get orgCacheSize(): number {
return this.#orgCache.size;
}
/** Set from `init()`: cross-origin SPA deploys need SameSite=None; Secure cookies. */
#crossSite = false;
protected signUpEnabledConfig: boolean;
constructor(options: MastraAuthBetterAuthOptions) {
super({ name: options?.name ?? 'better-auth' });
if (!options.auth && !options.secret) {
throw new Error(
'Better Auth instance is required. Please provide the auth option with your Better Auth instance created via betterAuth({ ... }), ' +
'or provide `secret` so the provider can build its own instance in init() on the host database.',
);
}
this.#auth = options.auth;
this.#secret = options.secret;
this.signUpEnabledConfig = options.signUpEnabled ?? true;
this.registerOptions(options);
}
/**
* The active Better Auth instance. Throws before `init()` in deferred
* instance mode (constructed with `secret` instead of `auth`).
*/
protected get auth(): Auth {
if (!this.#auth) {View on GitHub (pinned to 75dd419e61)
Solutions
- Pass your existing Better Auth instance: new MastraAuthBetterAuth({ auth: betterAuth({...}) }).
- Or pass a secret so init() builds the instance on the host database: new MastraAuthBetterAuth({ secret: process.env.BETTER_AUTH_SECRET }).
- If using env vars, verify they are loaded (e.g. dotenv/config import order) before constructing the provider.
Example fix
// before
const auth = new MastraAuthBetterAuth({ name: 'better-auth' });
// after
import { betterAuth } from 'better-auth';
const auth = new MastraAuthBetterAuth({
auth: betterAuth({ database: myDb, secret: process.env.BETTER_AUTH_SECRET }),
});
// or: new MastraAuthBetterAuth({ secret: process.env.BETTER_AUTH_SECRET }) Defensive patterns
Strategy: validation
Validate before calling
const options = { auth: maybeAuthInstance, secret: process.env.BETTER_AUTH_SECRET };
if (!options.auth && !options.secret) {
throw new Error('Provide either a betterAuth({ ... }) instance or a secret before constructing MastraAuthBetterAuth');
}
const provider = new MastraAuthBetterAuth(options); Type guard
function hasBetterAuthConfig(o: Partial<MastraAuthBetterAuthOptions>): o is MastraAuthBetterAuthOptions & ({ auth: Auth } | { secret: string }) {
return Boolean(o.auth) || typeof o.secret === 'string' && o.secret.length > 0;
} Try / catch
let provider;
try {
provider = new MastraAuthBetterAuth(options);
} catch (e) {
if (e instanceof Error && e.message.includes('Better Auth instance is required')) {
throw new Error('Misconfiguration: set BETTER_AUTH_SECRET or pass auth: betterAuth({...})', { cause: e });
}
throw e;
} Prevention
- Always pass either auth or secret explicitly rather than relying on optional chaining defaults.
- Validate env vars (BETTER_AUTH_SECRET) at startup with a schema validator (zod/envschema).
- Centralize provider construction in one config module so the requirement is enforced once.
When it happens
Trigger: new MastraAuthBetterAuth({}) or options missing both auth and secret: `if (!options.auth && !options.secret) throw` in the constructor.
Common situations: Migrating from another auth provider and forgetting to pass the betterAuth() instance; reading config from env vars that are undefined at startup (e.g. BETTER_AUTH_SECRET unset); constructing the provider before async env/config loading completes.
Related errors
- MastraAuthBetterAuth needs a database to build its own bette
- Okta domain is required. Provide it in the options or set OK
- Okta client ID is required. Provide it in the options or set
- MastraFactory: 'storage' is required. Pass a FactoryStorage
- GitHub reconcile worker requires a pull request or issue rec
AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30).
Data as JSON: /api/errors/25e41b5ad9d77b66.
Report an issue: GitHub.