Nuxt
app.config.ts Reference
Complete reference for the x:{} configuration object across all Nuxt layers.
app.config.ts Reference
All @xenterprises Nuxt layers are configured via app.config.ts. Each layer adds its own key under the top-level config. Layers can be combined — configs merge automatically.
Full Example
// app.config.ts
export default defineAppConfig({
// ─── Nuxt UI theme ──────────────────────────────────────────────
ui: {
colors: {
primary: 'blue',
neutral: 'zinc',
},
},
// ─── nuxt-x-app (dashboard) ─────────────────────────────────────
xDashboard: {
navigation: {
mode: 'sidebar', // 'sidebar' | 'topnav' | 'both'
sidebar: {
collapsed: false,
collapsible: true,
width: '256px',
collapsedWidth: '64px',
position: 'left',
brand: {
logo: '/logo.png',
collapsedLogo: '/icon.png',
title: 'My App',
to: '/dashboard',
},
items: [
{ label: 'Dashboard', icon: 'i-lucide-home', to: '/dashboard' },
{ label: 'Users', icon: 'i-lucide-users', to: '/users' },
{
label: 'Settings',
icon: 'i-lucide-settings',
children: [
{ label: 'Profile', to: '/settings/profile' },
{ label: 'Security', to: '/settings/security' },
],
},
{ divider: true },
{ label: 'Logout', icon: 'i-lucide-log-out', action: 'logout' },
],
footerItems: [
{ label: 'Help', icon: 'i-lucide-circle-help', to: '/help' },
],
},
},
header: {
search: {
enabled: true,
placeholder: 'Search...',
shortcut: 'meta+k',
},
userMenu: {
avatar: true,
items: [
{ label: 'Profile', icon: 'i-lucide-user', to: '/profile' },
{ type: 'divider' },
{ label: 'Sign Out', icon: 'i-lucide-log-out', action: 'logout' },
],
},
actions: [
{ icon: 'i-lucide-bell', action: 'notifications', badge: 3 },
],
},
page: {
breadcrumbs: true,
pageHeader: true,
},
},
// ─── nuxt-x-auth-better ─────────────────────────────────────────
xAuth: {
tokens: {
accessCookie: 'x_auth_access',
refreshCookie: 'x_auth_refresh',
hasRefresh: true,
},
redirects: {
login: '/auth/login',
signup: '/auth/signup',
afterLogin: '/dashboard',
afterSignup: '/dashboard',
afterLogout: '/auth/login',
forgotPassword: '/auth/forgot-password',
},
features: {
oauth: true,
magicLink: false,
otp: true,
forgotPassword: true,
signup: true,
},
oauthProviders: [
{ id: 'google', label: 'Google', icon: 'i-simple-icons-google' },
{ id: 'github', label: 'GitHub', icon: 'i-simple-icons-github' },
],
ui: {
showLogo: true,
showBrandName: true,
logoUrl: '/logo.png',
brandName: 'My App',
tagline: 'Sign in to continue',
layout: 'centered', // 'centered' | 'split'
background: {
enabled: true,
imageUrl: '/auth-bg.jpg',
overlayOpacity: 55,
blur: true,
},
card: {
glass: false,
glassIntensity: 'medium', // 'subtle' | 'medium' | 'strong'
logoUrl: '',
},
legal: {
copyright: '© 2025 My Company',
links: [
{ label: 'Privacy', to: '/privacy' },
{ label: 'Terms', to: '/terms' },
],
},
split: {
heroPosition: 'left', // 'left' | 'right'
heroImageUrl: '/split-bg.jpg',
headline: 'Build faster.',
subheadline: 'Production-ready from day one.',
features: [
'Full TypeScript support',
'Built-in dark mode',
'MCP ready',
],
},
form: {
icon: 'i-lucide-lock',
showSeparator: true,
},
},
},
// ─── nuxt-x-marketing ───────────────────────────────────────────
xMarketing: {
name: 'My Company',
url: 'https://mycompany.com',
config: {
markerProjectId: '',
emailMarketingNewsletters: {
organizationId: '',
},
},
header: {
logo: {
src: '/logo.png',
srcDark: '/logo-dark.png',
alt: 'My Company',
},
nav: {
links: [
{ label: 'Home', icon: 'i-heroicons-home', to: '/' },
{ label: 'Blog', icon: 'i-heroicons-newspaper', to: '/blog' },
{
label: 'Products',
children: [
{ label: 'Nuxt Layers', to: '/nuxt' },
{ label: 'Fastify Plugins', to: '/fastify' },
],
},
],
buttons: [
{ label: 'Sign In', to: '/auth/login', variant: 'ghost' },
{ label: 'Get Started', to: '/signup', color: 'primary' },
],
},
},
footer: {
logo: {
src: '/logo-footer.png',
alt: 'My Company',
},
bg: {
color: '#0a0a0a',
img: { src: '/footer-bg.svg', alt: '' },
},
body: 'Short description of your company for the footer.',
socials: [
{ name: 'Twitter', url: 'https://twitter.com/...', icon: 'i-simple-icons-x' },
{ name: 'GitHub', url: 'https://github.com/...', icon: 'i-simple-icons-github' },
],
columns: [
{
headerLabel: 'Product',
links: [
{ label: 'Features', to: '/features' },
{ label: 'Pricing', to: '/pricing' },
],
},
{
headerLabel: 'Company',
links: [
{ label: 'About', to: '/about' },
{ label: 'Blog', to: '/blog' },
],
},
],
},
blog: {
active: true,
title: 'Blog',
description: 'Latest news and updates.',
meta: {
title: 'Blog',
description: 'Latest news and updates.',
},
},
},
// ─── nuxt-x-cards ───────────────────────────────────────────────
x: {
cards: {
colors: {
primary: 'cream',
neutral: 'olive',
accents: {
gold: '#FFAC00',
goldHover: '#E69B00',
blue: '#8BA8BD',
green: '#1BC651',
},
},
fonts: {
sans: "'Inter', ui-sans-serif, system-ui, sans-serif",
serif: "'Playfair Display', serif",
display: "'Inter', ui-sans-serif, system-ui, sans-serif",
googleFontsUrl: 'https://fonts.googleapis.com/css2?family=Inter&family=Playfair+Display&display=swap',
},
radius: {
card: '0.75rem',
panel: '1.5rem',
pill: '9999px',
},
spacing: {
baseUnit: 4,
},
defaults: {
filter: 'cinematic', // image filter applied to all cards
overlay: 'bottom-blur', // overlay style
mediaAspectRatio: 'landscape',
productAspectRatio: 'product',
},
brand: {
appName: 'My App',
logoIcon: 'i-lucide-square-x',
},
},
},
// ─── nuxt-x-restaurants ─────────────────────────────────────────
xRestaurants: {
name: 'Restaurant Destinations',
domain: 'myrestaurantsite.com',
logo: '/logo.png',
navbar: {
links: [
{ label: 'Explore', to: '/restaurants' },
{ label: 'Popular', to: '/popular' },
],
},
homePage: {
hero: {
title: 'Find the Best Dining Near You',
description: 'Discover top-rated restaurants.',
backgroundImage: 'https://example.com/hero.jpg',
searchButtonLabel: 'Search',
cuisinePlaceholder: 'Cuisine',
locationPlaceholder: 'Neighborhood',
},
featured: {
title: 'Featured Places',
description: 'Hand-picked selections.',
viewAllLink: '/restaurants',
viewAllLabel: 'View All',
viewButtonLabel: 'View',
},
faq: {
title: 'Frequently Asked Questions',
items: [
{ label: 'How do I search?', content: 'Use the search bar...' },
],
},
},
menuCard: {
showImage: true,
showDescription: true,
showTags: true,
showSpiceLevel: false,
showCalories: false,
imageAspect: 'video', // 'square' | 'video' | 'wide'
variant: 'default', // 'default' | 'compact' | 'horizontal'
dietaryTags: [
{ id: 'vegetarian', label: 'Vegetarian', icon: 'i-heroicons-leaf', color: 'green' },
{ id: 'vegan', label: 'Vegan', icon: 'i-heroicons-sparkles', color: 'emerald' },
{ id: 'gluten-free', label: 'Gluten-Free', icon: 'i-heroicons-shield-check', color: 'amber' },
],
},
filters: {
title: 'Filters',
showClearAll: true,
mobileBreakpoint: 'lg',
groups: [
{
id: 'cuisine',
label: 'Cuisine',
type: 'checkbox',
options: [
{ label: 'Italian', value: 'italian' },
{ label: 'Japanese', value: 'japanese' },
],
},
{
id: 'price',
label: 'Price Range',
type: 'range',
min: 0,
max: 100,
step: 5,
unit: '$',
},
],
},
},
})
Key Reference
xDashboard — nuxt-x-app
| Key | Type | Description |
|---|---|---|
navigation.mode | 'sidebar' | 'topnav' | 'both' | Layout mode |
navigation.sidebar.items | NavItem[] | Main sidebar nav links |
navigation.sidebar.footerItems | NavItem[] | Bottom-pinned nav items |
navigation.sidebar.brand | BrandConfig | Logo and title |
navigation.sidebar.collapsed | boolean | Start collapsed |
navigation.sidebar.collapsible | boolean | Allow collapse toggle |
header.search.enabled | boolean | Show search bar |
header.search.shortcut | string | Keyboard shortcut e.g. 'meta+k' |
header.userMenu.items | UserMenuItem[] | User dropdown items |
header.actions | HeaderAction[] | Icon buttons in header |
page.breadcrumbs | boolean | Show breadcrumbs |
NavItem shape
interface NavItem {
label: string
icon?: string // Heroicons/Lucide name
to?: string // Internal route
href?: string // External URL
exact?: boolean
badge?: { label: string | number; color?: string }
children?: NavItem[] // Nested items
action?: string // e.g. 'logout'
disabled?: boolean
divider?: boolean // Render a divider before this item
}
xAuth — nuxt-x-auth-better / nuxt-x-neon-auth
| Key | Type | Default | Description |
|---|---|---|---|
tokens.accessCookie | string | 'x_auth_access' | Access token cookie name |
tokens.refreshCookie | string | 'x_auth_refresh' | Refresh token cookie name |
tokens.hasRefresh | boolean | true | Enable refresh token flow |
redirects.login | string | '/auth/login' | Login page route |
redirects.afterLogin | string | '/' | Redirect after successful login |
redirects.afterLogout | string | '/auth/login' | Redirect after logout |
redirects.afterSignup | string | '/' | Redirect after signup |
features.oauth | boolean | false | Show OAuth buttons |
features.magicLink | boolean | false | Enable magic link |
features.otp | boolean | false | Enable OTP/2FA |
features.signup | boolean | true | Show signup link |
oauthProviders | OAuthProvider[] | [] | OAuth provider buttons |
ui.layout | 'centered' | 'split' | 'centered' | Auth page layout |
ui.background.enabled | boolean | true | Show background image |
ui.card.glass | boolean | false | Glass morphism card |
xMarketing — nuxt-x-marketing
| Key | Type | Description |
|---|---|---|
name | string | Company/project name |
url | string | Base URL |
header.logo.src | string | Header logo image |
header.logo.srcDark | string | Dark mode logo |
header.nav.links | NavLink[] | Navigation links (supports children) |
header.nav.buttons | Button[] | CTA buttons in header |
footer.body | string | Footer description text |
footer.socials | Social[] | Social media links |
footer.columns | Column[] | Footer link columns |
blog.active | boolean | Enable blog |
blog.title | string | Blog section title |
x.cards — nuxt-x-cards
| Key | Type | Description |
|---|---|---|
colors.primary | string | Primary color name |
colors.accents.gold | string | Gold accent hex |
fonts.sans | string | Sans-serif font stack |
fonts.serif | string | Serif font stack (used in hero titles) |
fonts.googleFontsUrl | string | Google Fonts import URL |
radius.card | string | Card border radius |
defaults.filter | string | Default image filter |
defaults.overlay | string | Default image overlay |
brand.appName | string | App name |
brand.logoIcon | string | Icon name for logo |
xRestaurants — nuxt-x-restaurants
| Key | Type | Description |
|---|---|---|
name | string | Site name |
domain | string | Site domain |
logo | string | Logo URL |
navbar.links | { label, to }[] | Navbar links |
homePage.hero | HeroConfig | Hero section content |
homePage.faq.items | { label, content }[] | FAQ items |
menuCard.variant | 'default' | 'compact' | 'horizontal' | Menu card layout |
menuCard.dietaryTags | DietaryTag[] | Dietary tag definitions |
filters.groups | FilterGroup[] | Filter sidebar groups |
FilterGroup shape
interface FilterGroup {
id: string
label: string
type: 'checkbox' | 'range' | 'select' | 'search' | 'radio'
options?: { label: string; value: string | number; count?: number }[]
min?: number // for type: 'range'
max?: number
step?: number
unit?: string
collapsed?: boolean
multiple?: boolean
}
AI Context
file: app.config.ts
purpose: Configure all @xenterprises Nuxt layers via a single file
config-keys:
xDashboard: nuxt-x-app — sidebar nav, header, search, user menu
xAuth: nuxt-x-auth-better / nuxt-x-neon-auth — redirects, features, OAuth, UI layout
xMarketing: nuxt-x-marketing / nuxt-x-restaurants — site identity, header nav, footer
x.cards: nuxt-x-cards — design tokens, image filters, fonts, brand
xRestaurants: nuxt-x-restaurants — directory content, menu cards, filters
merging: configs from multiple layers merge automatically — no conflicts
type-safety: all keys are declared via AppConfigInput module augmentation
composable: useAppConfig() — reactive access to all config values at runtime
pattern: set defaults in the layer, override in the consuming app's app.config.ts
