nuxt-site-config
Requires Nuxt ^4.6.0 || ^5.0.0 and Node ^22.22.3 || ^24.15.0 || >=26.0.0.
The module resolves one site config per request from many sources. The Nuxt SEO modules (sitemap, robots, schema.org, OG image) read it.
Docs: https://nuxtseo.com/docs/site-config
Setup
Included in @nuxtjs/seo v6. If the app uses @nuxtjs/seo, configure the site key and do not add the module again.
Otherwise, install it with npx nuxt module add nuxt-site-config.
Set url and name under the site key. Nothing infers name from package.json.
export default defineNuxtConfig({
modules: ['nuxt-site-config'],
site: { url: 'https://example.com', name: 'Example' },
})For staging or preview deploys, set env vars instead: NUXT_SITE_URL, NUXT_SITE_NAME, NUXT_SITE_ENV.
Any NUXT_SITE_<KEY> or NUXT_PUBLIC_SITE_<KEY> var maps to a camelCase key (NUXT_SITE_TRAILING_SLASH to trailingSlash).
They work at build time and at server runtime. You do not declare them in runtimeConfig.
Automatic behaviour
Sources, from lowest to highest priority:
env: NuxtenvName, elseNODE_ENV. A production build isproduction.- CI vars:
VERCEL_URL,URL(Netlify),CF_PAGES_URL;SITE_NAMEfor the name. - The request origin (SSR only). It trusts
X-Forwarded-HostandX-Forwarded-Proto. - Modules that call
updateSiteConfig()fromnuxt-site-config/kit, then thesitekey innuxt.config.ts, then thesite-config:resolvehook. - i18n values (see below).
NUXT_SITE_*env vars at build, then at runtime.- Per request: route rules, then
multiTenancy, then thesite-config:inithook.
A build time updateSiteConfig() without _priority ranks with the site key. A runtime push without _priority (route rules, site-config:init, Nitro updateSiteConfig(event)) ranks above everything. At equal priority, the last push wins.
- Without
url, SSR uses the request origin. A prerender has no request, sourlis undefined and "absolute" URLs render as relative paths. The build warns at prerender start. indexabledefaults toenv === 'production'.getSiteConfig(event).indexableandgetSiteIndexable(event)return the same value.- A staging deploy that runs a production build is indexable. Set
NUXT_SITE_ENV=stagingorNUXT_SITE_INDEXABLE=false.
Read site config
In app code, useSiteConfig() is auto imported. In server/, use getSiteConfig(event).
Helpers are auto imported. The explicit paths are #site-config/app and #site-config/server.
// server/api/canonical.ts
export default defineEventHandler((event) => {
const { name } = getSiteConfig(event)
const toAbsolute = createSitePathResolver(event, { absolute: true, withBase: true })
return { name, about: toAbsolute('/about'), indexable: getSiteIndexable(event) }
})In app code, createSitePathResolver() returns a function that returns a computed ref. withSiteUrl(path) returns a computed ref.
Options: absolute, withBase (prefix app.baseURL, default false), and canonical. canonical: false uses the request origin instead of url.
getNitroOrigin() returns the request origin with a trailing slash, such as https://example.com/.
Set config per request
Use the site-config:init Nitro hook. It runs after every other source.
// server/plugins/site-config.ts
export default defineNitroPlugin((nitroApp) => {
nitroApp.hooks.hook('site-config:init', ({ event, siteConfig }) => {
if (new URL(getNitroOrigin(event)).hostname.startsWith('fr.'))
siteConfig.push({ _context: 'fr-host', name: 'Mon Site', url: 'https://fr.example.com' })
})
})For a fixed list of domains, use site.multiTenancy. The request host must match an entry in hosts; ports are ignored.
export default defineNuxtConfig({
site: {
url: 'https://example.com',
multiTenancy: [
{ hosts: ['foo.com', 'www.foo.com'], config: { name: 'Foo', url: 'https://foo.com' } },
],
},
})A route rule sets config for a path: routeRules: { '/fr/**': { site: { name: 'Mon Site' } } }.
In a Nuxt plugin, updateSiteConfig({ ... }) changes config for the current render. Use enforce: 'pre'.
i18n
With @nuxtjs/i18n or nuxt-i18n-micro, the module sets defaultLocale and currentLocale from the locale language, and url from i18n.baseUrl.
Per locale name and description come from the nuxtSiteConfig.name and nuxtSiteConfig.description messages.
These messages override site.name. A runtime NUXT_SITE_NAME overrides the messages.
{ "nuxtSiteConfig": { "name": "Mon Site", "description": "Ma description" } }The module order in modules does not matter.
Traps
i18n.baseUrloverridessite.url. This is intended, and a mismatch logs an error. Set one of them only, or give them the same value.NUXT_SITE_URLoverrides both.- A
urlwith a path warns and prefixes every URL with that path. Put the path inapp.baseURL, and keepurlas the origin. withSiteUrl()andcreateSitePathResolver()leave outapp.baseURLby default. PasswithBase: true.
Version limits
v5 changed these. Code written for v4 can still expect the old behaviour:
installNuxtSiteConfig()is gone fromnuxt-site-config/kit. Declarenuxt-site-configinmoduleDependencies(see references/module-authors.md).- A build time
updateSiteConfig()without_priorityno longer beats thesitekey orNUXT_SITE_*. To keep the old rank, pass_priority: SiteConfigPriority.runtime. updateSiteConfig()in thesite-config:resolvehook no longer beatsNUXT_SITE_*env vars.NUXT_SITE_TRAILING_SLASH=falsenow disables trailing slashes. In v4, the string"false"enabled them.- An unset
indexablenow resolves to a boolean fromenv. Do not check it forundefined. - The DevTools tab needs
nuxtseo-devtools-hostas a dev dependency.
v4 removed these. Code written for v3 still uses them:
- const config = useSiteConfig(event) // server
+ const config = getSiteConfig(event)
- runtimeConfig: { public: { siteUrl: 'https://example.com' } }
+ site: { url: 'https://example.com' }
- import type { SiteConfig } from 'nuxt-site-config'
+ import type { SiteConfigResolved } from 'nuxt-site-config'useNitroOrigin() is deprecated. Use getNitroOrigin(). The #internal/nuxt-site-config import path is gone.
Config
enabled(true),debug(false),multiTenancy([]). Every other key undersiteis site config.- Custom keys are allowed:
site: { twitter: '@example' }resolves assiteConfig.twitter. - Reference: https://nuxtseo.com/docs/site-config/api/config
Module authors: see references/module-authors.md.
Debug
/__site-config__/debug.jsonshows the resolved config and the full stack. It exists in dev, or in production withsite: { debug: true }.useSiteConfig({ debug: true })._contextnames the source of each key.- Nuxt DevTools has a Site Config tab. It needs
nuxtseo-devtools-hostas a dev dependency:pnpm add -D nuxtseo-devtools-host.