# Vue Nuxt

> Vue 3 Composition API, Nuxt 3 routing, and state management

- Skill: `mokhtarabadi/vue-nuxt` (Agent Skill)
- Install (CLI): `npx skillmds@latest add mokhtarabadi/vue-nuxt`
- Raw SKILL.md: https://api.skillmd.com/api/skills/mokhtarabadi/vue-nuxt/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: Web & Frontend
- Author: mokhtarabadi (https://skillmd.com/u/mokhtarabadi)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/mokhtarabadi/vue-nuxt

---


# Vue 3 & Nuxt 3 — Best Practices & AI-Driven Scaffolding

## AI Context & Token Optimization

1. **Composition API & `<script setup>` Only:** Do NOT use the Options API. The Composition API is far more token-efficient and predictable for AI code generation.
2. **Auto-Imports:** Rely entirely on Nuxt's auto-imports. Explicitly importing Vue refs or components wastes tokens and causes syntax hallucinations.
3. **TypeScript Mandate:** Always use `lang="ts"`. Strongly typed props and Pinia state are required.

## Modern Nuxt 3 App Architecture

Scaffold Nuxt 3 applications using these guidelines:

1. **Composition API:** Always use `<script setup lang="ts">` with TypeScript. Banned: Options API.
2. **Auto-Imports Leverage:** Rely on Nuxt's auto-imported directory structures for `composables/`, `components/`, and core Vue APIs (`ref`, `computed`, `reactive`).
3. **State Management:** Use Pinia via `@pinia/nuxt`. Define stores using the store-factory function syntax (`defineStore('id', () => { ... })`).
4. **SSR-Safe Data Fetching:** Always use `useFetch` or `useAsyncData` to ensure data loads on the server and hydrates safely on the client. Banned: standard `axios` or bare `fetch` inside components.
5. **Form Validation:** Use Formkit or VeeValidate + Zod for robust client-side schemas.

## Project Structure

```
project/
├── assets/              # Uncompiled assets (CSS, SCSS)
├── components/          # Auto-imported Vue components
│   └── ui/              # Reusable UI elements (buttons, inputs)
├── composables/         # Auto-imported composition functions (Vue useHooks)
├── layouts/             # Shared page layouts
├── pages/               # File-based routing
├── plugins/             # Vue plugins initialized at startup
├── public/              # Static files served at root
├── server/              # Nitro API routes (Nuxt backend)
│   └── api/
├── stores/              # Pinia state management
└── nuxt.config.ts       # Main Nuxt configuration
```

## Naming Conventions

- **Components**: `PascalCase` (e.g., `UserProfile.vue`). Multi-word names are mandatory.
- **Composables**: `camelCase` starting with `use` (e.g., `useAuth.ts`).
- **Pages/Routes**: `kebab-case` (e.g., `user-settings.vue`).

## Architectural Patterns

- **Composition API**: Use `<script setup lang="ts">` exclusively. Avoid the older Options API (`data()`, `methods`).
- **Auto-imports**: Rely on Nuxt's auto-import feature for components, composables, and Vue APIs (`ref`, `computed`). Do not manually import them.
- **State Management**: Use `Pinia` for global state. Avoid Vuex.
- **Data Fetching**: Use `useFetch` or `useAsyncData` for SSR-friendly data fetching. Do not use standard `fetch` or `axios` directly in components.

## Universal DateTime Governance

- **API Boundary:** All datetimes from the backend are epoch ms or ISO-8601 UTC strings. Normalize to epoch ms in Pinia stores.
- **Client Display:** Format using `Intl.DateTimeFormat` with explicit `timeZone` in a composable (`useDateTimeFormatter`). Never rely on the browser's locale alone.
- **SSR Safety:** Use `useAsyncData` with `dayjs.utc()` for datetime parsing in server-side code. Never call `new Date()` in `setup()` without UTC normalization.
- **State:** Timestamps in Pinia stores must be epoch ms (number). Convert to localized strings only in template computed properties.

## Testing Strategies

- **Framework**: `Vitest` + `Vue Test Utils`.
- **Component Testing**: Mount components and test DOM output/emitted events.
- **E2E Testing**: Use `Playwright` or `Cypress`.

