Configuration
What you'll have afterwards:
- You can change what a module does by editing its options.
- You can set a secret or a per-environment value without putting it in code.
A Frigear app is configured in two places. apps/web/nuxt.config.ts holds the modules and their
options. apps/web/.env holds secrets and values that differ per environment.
Prerequisites
A project created in Installation.
1. Set module options in nuxt.config.ts
Each module has its own config key, such as account, admin, users, notify or authentication.
Every module's options are listed on its page under Modules. This is the starter's config:
// A Nuxt 4 app on the @frigear-nu modules: register/login, /account and /admin with user management.
// Every module option is documented in https://docs.frigear.dev/modules
export default defineNuxtConfig({
// Order matters only for readability: each module installs the ones it depends on (auth, notify, ui, ...).
modules: [
'@nuxt/eslint',
'@nuxthub/core',
'@nuxt/ui',
'@frigear-nu/menu',
'@frigear-nu/widget',
'@frigear-nu/users',
'@frigear-nu/authorization',
'@frigear-nu/account',
'@frigear-nu/admin',
],
devtools: { enabled: true },
css: ['~/assets/css/main.css'],
runtimeConfig: {
// NUXT_ACL_ADMINS: comma separated emails that are always admins (see server/plugins/authorization-roles.ts).
aclAdmins: '',
public: {
// NUXT_PUBLIC_SITE_URL: the public URL of the site. Emailed links (password reset, sign-in, verification) point
// here; in production they fail until it is set.
siteUrl: '',
},
},
compatibilityDate: '2026-06-30',
// Local sqlite in .data/; NuxtHub applies server/db/migrations on `nuxt dev` and `nuxt build`.
// For production, point `connection` at your database (Turso, D1, Postgres): https://hub.nuxt.com/docs/database
hub: {
db: {
dialect: 'sqlite',
driver: 'libsql',
connection: { url: 'file:./.data/db/sqlite.db' },
},
},
// @frigear-nu/account: the /account pages.
account: {
settings: {
pages: { index: true, profile: true, security: true, apiTokens: true },
},
},
// @frigear-nu/auth: sign-in with email/password (on by default) and passkeys, which users add on
// /account/security. Passkeys are bound to the domain the site runs on: choose the production domain before launch.
// `verifyEmail`: a new account signs in through the emailed link, which proves the address (NUXT_ACL_ADMINS counts
// only for verified addresses).
authentication: {
settings: {
webAuthn: true,
verifyEmail: true,
afterLogin: '/account',
pages: { login: true, register: true },
},
},
// @frigear-nu/authorization: guests on a guarded page (/account/**, /admin/**) go to the login page. A role is a
// bundle of permissions; `server/plugins/authorization-roles.ts` makes verified NUXT_ACL_ADMINS addresses admins.
authorization: {
redirectTo: '/login',
defaultRoles: ['user'],
roles: {
admin: { label: 'Admin', grant: ['*'] },
user: { label: 'User' },
},
},
eslint: {
config: {
stylistic: true,
},
},
// @frigear-nu/notify: emails (password reset, ...) are printed to the terminal until you configure a driver.
notify: {
email: { driver: 'log' },
},
// @frigear-nu/users: /admin/users; who may do what is decided by the roles' permissions (`authorization.roles`).
users: {
settings: {
admin: true,
profilePath: '/account/profile',
// A new email address takes effect once its owner confirms it from the emailed link.
verifyEmailChange: true,
},
},
})
What the options do:
| Key | Purpose |
|---|---|
modules | The modules the app uses. Order matters only for readability. |
runtimeConfig | aclAdmins (NUXT_ACL_ADMINS) and public.siteUrl (NUXT_PUBLIC_SITE_URL), set from .env. |
hub.db | The database: local SQLite in .data/. See Database. |
account.settings.pages | Which /account pages exist. |
admin.settings.permission | Optional. The permission that opens the admin area at /admin (default admin:access, granted to admin). |
authentication.settings | Sign-in: passkeys, email verification, the pages and where users land after signing in. |
authorization.roles, defaultRoles | The roles, what each grants and inherits, and the roles every user holds. |
authorization.redirectTo | Where a visitor on a guarded page (/account/**, /admin/**) is sent. |
eslint | The lint config of @nuxt/eslint, with stylistic rules. |
notify.email | Email delivery. The log driver prints emails in the terminal. |
users.settings | admin: true turns on /admin/users. profilePath is where the profile page lives. verifyEmailChange applies a new email once it is confirmed. |
modules. Each module installs the ones it depends on, such as Auth, Notify and UI. You list only the ones you use
directly.
hub.db. NuxtHub applies server/db/migrations on nuxt dev and nuxt build.
authentication.settings. Authentication explains each option.
notify.email. The log driver stays in place until you configure a real driver.
pnpm dev after you change module options, so Nuxt regenerates its types.2. Set environment variables
Nuxt maps environment variables that start with NUXT_ onto runtimeConfig. For example, NUXT_ACL_ADMINS sets
runtimeConfig.aclAdmins. Read values with useRuntimeConfig(), not process.env.
apps/web/.env.example documents the starter's three variables:
# Seals the session cookie (Nuxt's appSecret); 32+ characters in production. `pnpm prepare:env` fills in a random one.
NUXT_APP_SECRET=
# The public URL of the site: emailed links (password reset, sign-in, verification) point here. Set it to your
# domain in production, where those emails fail without it.
NUXT_PUBLIC_SITE_URL=http://localhost:3000
# Comma separated emails that are always admins, once verified. Register with one of them and open the
# verification link printed in the terminal.
NUXT_ACL_ADMINS=
Run pnpm prepare:env to copy every apps/*/.env.example to .env. It generates empty secrets. It never overwrites a
value, so it is safe to run again.
.env. It holds NUXT_APP_SECRET, which seals every session cookie. Nuxt generates one in development
when it is empty. In production set 32+ characters: with a shorter value every session request fails with a 500.Each module documents its own variables on its page:
- Stripe keys on Stripe.
- Email drivers on Notify.
- OAuth provider credentials on OAuth providers.
The Frigear website app lists the full set it uses.
pnpm dev, the app picks up the new option or variable. For example, a new
verified email in NUXT_ACL_ADMINS holds the admin role on its next request.Next steps
- Authentication – turn on sign-in methods and protect your own routes and pages.
- Database – learn when to generate a migration.