nuxt-init
Nuxt Init
Scaffolds a new Nuxt 4 project with the standard config files, dev dependencies, lint-staged hooks, and bun scripts used across all Puretec Nuxt apps.
When to Use
- Starting a brand-new Nuxt 4 project.
- Auditing an existing project to ensure all standard configs are present.
- Onboarding a new repo to the same tooling baseline.
Workflow
- Create the config files listed below (skip any that already exist unless the user asks to overwrite).
- Install the dev dependencies (including
terraform-scaffold). - Add the scripts and
lint-stagedblock topackage.json. - Set up Nuxt UI: install runtime deps, create
app/assets/css/main.css, addcssconfig tonuxt.config.ts, wrap app in<UApp>, createapp.config.ts. - Create or update
CLAUDE.mdwith the standard structure: Skills table, Key Conventions, Architecture, and project-specific sections. - Run
bun installandbun run prepareto initialise husky and nuxt types. - Run
bunx terraform-scaffold initto scaffold the Terraform directory structure.
Config Files
prettier.config.js
export default {
trailingComma: 'es5',
tabWidth: 4,
semi: false,
singleQuote: true,
bracketSpacing: true,
bracketSameLine: false,
arrowParens: 'always',
vueIndentScriptAndStyle: false,
singleAttributePerLine: true,
endOfLine: 'crlf',
// Pug-specific config
plugins: ['@prettier/plugin-pug', 'prettier-plugin-terraform-formatter'],
pugFramework: 'vue',
pugSortAttributes: 'asc',
pugWrapAttributesThreshold: 1,
pugClassNotation: 'attribute', // Ensures `class="..."` inside ()
pugIdNotation: 'literal',
pugAttributeSeparator: 'always',
pugSingleQuote: false,
pugPrintWidth: 100,
}
.prettierignore
node_modules
*.log*
.nuxt
.nitro
.cache
.output
.env
.agents
.claude
.githooks
dist
jsons/**/*
public/**/*
ios
android
terraform/lambda/src/
pnpm-lock.yaml
.gitignore
# Nuxt dev/build outputs
.output
.data
.nuxt
.nitro
.cache
dist
# Node dependencies
node_modules
# Logs
logs
*.log
# Misc
.DS_Store
.fleet
.idea
# Local env files
.env
.env.*
!.env.example
# Local scratch
.tmp/
# Claude Code
.claude/worktrees/
# Terraform local artifacts
**/.terraform/*
*.tfstate
*.tfstate.*
*.tfplan
terraform/envs/*/terraform.tfvars
*.tsbuildinfo
eslint.config.ts
import withNuxt from './.nuxt/eslint.config.mjs'
// @ts-expect-error: module uses export = syntax
import prettierConfig from 'eslint-config-prettier'
export default withNuxt(
{
name: 'project/ignores',
ignores: [
'.agents/**',
'**/.agents/**',
'.claude/**',
'**/.claude/**',
'.nuxt/**',
'**/.nuxt/**',
'.output/**',
'**/.output/**',
'node_modules/**',
'**/node_modules/**',
'vendor/**',
'**/vendor/**',
'terraform/functions/**',
],
},
{
name: 'project/rules',
languageOptions: {
parserOptions: {
templateTokenizer: {
pug: 'vue-eslint-parser-template-tokenizer-pug',
},
},
},
rules: {
'@typescript-eslint/no-unused-vars': [
'error',
{
varsIgnorePattern: '^(_|on[A-Z].*|props|emit)$',
argsIgnorePattern: '^_',
},
],
'vue/max-attributes-per-line': 'off',
'vue/attributes-order': 'off',
'vue/html-quotes': 'off',
'vue/multiline-html-element-content-newline': 'off',
'vue/singleline-html-element-content-newline': 'off',
'vue/html-self-closing': 'off',
'vue/component-tags-order': [
'error',
{ order: ['script', 'template', 'style'] },
],
'func-style': ['error', 'declaration'],
},
},
prettierConfig
)
vitest.config.ts
import { resolve } from 'node:path'
import { defineConfig } from 'vitest/config'
export default defineConfig({
test: {
globals: true,
environment: 'node',
},
resolve: {
conditions: ['vitest'],
alias: {
'~~': resolve(__dirname),
'~': resolve(__dirname, 'app'),
},
},
})
tsconfig.json
{
"files": [],
"references": [
{ "path": "./.nuxt/tsconfig.app.json" },
{ "path": "./.nuxt/tsconfig.server.json" },
{ "path": "./.nuxt/tsconfig.shared.json" },
{ "path": "./.nuxt/tsconfig.node.json" }
]
}
.husky/pre-commit
bunx lint-staged
.husky/pre-push
bun run lint
bun run test
.sops.yaml
# Replace the placeholder recipients below with real age public keys (age1...)
# for your developer team and CI before encrypting secrets.
creation_rules:
- path_regex: ^(.+[\\/])?secrets[\\/].*\.sops\.json$
age: >-
age1REPLACE_WITH_YOUR_AGE_PUBLIC_KEY
- path_regex: ^(.+[\\/])?secrets[\\/]env-bundle\.sops\.json$
age: >-
age1REPLACE_WITH_YOUR_AGE_PUBLIC_KEY
package.json Additions
Scripts
{
"dev": "nuxt dev",
"build": "nuxt build",
"generate": "nuxt generate",
"preview": "nuxt preview",
"lint": "eslint . && vue-tsc --noEmit",
"lint:fix": "eslint . --fix",
"pretty": "prettier --write .",
"test": "vitest run",
"test:watch": "vitest",
"prepare": "husky",
"postinstall": "nuxt prepare"
}
lint-staged
{
"lint-staged": {
"*.{js,ts,vue}": "eslint --fix",
"*.{js,ts,vue,json,md,css,scss,yml,yaml}": "prettier --write"
}
}
Dev Dependencies
Install with:
bun add -d eslint @nuxt/eslint eslint-config-prettier prettier @prettier/plugin-pug prettier-plugin-terraform-formatter vue-eslint-parser-template-tokenizer-pug husky lint-staged vue-tsc @types/node tsx tailwindcss terraform-scaffold
Nuxt UI Setup
Nuxt UI v4 is the standard component library. Set it up after installing dependencies.
Install runtime dependencies
bun add @nuxt/ui @nuxt/image @iconify-json/lucide
app/assets/css/main.css
@import "tailwindcss";
@import "@nuxt/ui";
nuxt.config.ts additions
Add @nuxt/ui and @nuxt/image to modules and reference the CSS file:
export default defineNuxtConfig({
modules: [
'@nuxt/eslint',
'@nuxt/content',
'@nuxt/ui',
'@nuxt/image',
'@compodium/nuxt',
'@formkit/auto-animate',
],
css: ['~/assets/css/main.css'],
})
app/app.vue
Wrap the entire app in <UApp> — required for toasts, tooltips, and overlays to work:
<script setup lang="ts"></script>
<template lang="pug">
UApp
NuxtRouteAnnouncer
NuxtLayout
NuxtPage
</template>
app/app.config.ts
Set semantic color aliases:
export default defineAppConfig({
ui: {
colors: {
primary: 'blue',
neutral: 'zinc',
},
},
})
Icons
Uses Iconify with Lucide as the default collection. Format: i-{collection}-{name}.
UIcon(name="i-lucide-sun", class="size-5")
UButton(icon="i-lucide-plus", label="Add")
Browse icons at icones.js.org.
Terraform Scaffold
terraform-scaffold is a CLI tool that automates AWS infrastructure setup with Terraform, AppSync, and Lambda.
What It Provides
- Complete Terraform directory layout with environment configs (staging, production)
- GraphQL/AppSync resolver scaffolding (JS or Lambda-backed)
- Standalone Lambda function generation
- Lambda bundling with esbuild
- Terraform execution wrapper and output export scripts
Setup
After installing as a dev dependency (included in the install command above), initialise the Terraform structure:
bunx terraform-scaffold init
Key Commands
| Command | Description |
|---|---|
bunx terraform-scaffold init |
Create config file and full Terraform directory structure |
bunx terraform-scaffold graphql |
Generate a GraphQL resolver with schema, resolver, and Terraform files |
bunx terraform-scaffold lambda |
Create a standalone Lambda function |
bunx terraform-scaffold build --env=<env> |
Bundle Lambda functions with esbuild |
bunx terraform-scaffold tf <env> <action> |
Execute Terraform operations (plan, apply, etc.) |
bunx terraform-scaffold tf-output <env> |
Export Terraform outputs to environment files |
bunx terraform-scaffold sync-modules |
Copy Terraform modules into your project |
CLAUDE.md Setup
After scaffolding, create or update the project's CLAUDE.md with the standard structure. Adapt the project name, description, and AWS services to match the actual project.
Skills Table
Inject a ## Skills section with the "Load when…" format:
## Skills
| Skill | Load when… |
| ------------------------------ | --------------------------------------------------------------------------------------------------------------------------------------------------- |
| **`/nuxt-ui`** | Using or customising Nuxt UI components (`<UButton>`, `<UCard>`, `<UModal>`, etc.), app config, color theming, dark mode, form validation, icons |
| **`/tailwind-ui`** | Building new UI patterns — search templates before writing Tailwind from scratch (heroes, navbars, footers, grids, cards, responsive layouts) |
| **`/visual-development-skill`**| Developing or modifying visual elements (components, pages, layouts, styling) — Playwright screenshots, Compodium preview, responsive/dark-mode verification |
| **`/git-commit-skill`** | Committing changes, staging files, or finishing work in a git worktree — smart commit, multi-concern splitting, sensitive-file guarding. Run `bun run lint:fix` and `bun run pretty` before committing |
Key Conventions
Inject a ## Key Conventions section:
## Key Conventions
- **Vue SFC block order: `<script>` → `<template>` → `<style>`** — always place `<script setup lang="ts">` first, then `<template lang="pug">`, then `<style>` last.
- **All `.vue` files MUST use Pug templates** — use `<template lang="pug">` instead of plain `<template>`. This applies to pages, layouts, components, and `app.vue`. Never generate HTML templates in `.vue` files; always write Pug syntax. **Use `class=""` attribute syntax for classes, NOT Pug dot notation** (e.g., `div(class="flex items-center")` not `div.flex.items-center`).
- Components, composables, utils are **auto-imported** — no import statements
- Pages: `app/pages/index.vue` → `/`, `app/pages/feed.vue` → `/feed`
- Nuxt UI components are globally available
- **Reusable types go in `types/`** — always define shared TypeScript interfaces, types, and enums in the `types/` directory. When creating new types or updating existing ones, write them to `types/`. Import from `types/` across the codebase instead of defining inline or co-located types.
- Types auto-generated in `.nuxt/` — run `bun run postinstall` if stale
Full CLAUDE.md Template
The complete CLAUDE.md should follow this section order:
- Header — project name and one-line description with tech stack summary
- Commands — all bun scripts with inline comments
- Tech Stack — framework, UI, cloud, IaC, content, images, linting, dev tools
- Architecture — directory table (purpose only, no skill column)
- Skills — "Load when…" table (see above)
- Key Conventions — SFC order, pug, auto-imports, types
- AWS Services — server-side service wrappers (if applicable)
- Composables — client-side composables (if applicable)
- Terraform / Infrastructure — IaC details (if applicable)
- Ralph System — autonomous agent tooling (if applicable)
Post-Setup
After creating all files and installing dependencies:
bun install
bun run prepare # initialises husky + nuxt types
bunx terraform-scaffold init # scaffolds Terraform directory structure