Quick Start
Quick Start
This guide will walk you through creating your first API and admin panel with Nuxt Auto in under 10 minutes.
Project Setup
1. Create a New Nuxt Project
npx nuxi@latest init my-app
cd my-app
2. Install Nuxt Auto
npm install @websideproject/nuxt-auto-api @websideproject/nuxt-auto-admin @nuxt/ui tailwindcss
npm install drizzle-orm better-sqlite3
npm install -D drizzle-kit @types/better-sqlite3
3. Configure Nuxt
Update nuxt.config.ts:
export default defineNuxtConfig({
modules: [
'@nuxt/ui',
'@websideproject/nuxt-auto-api',
'@websideproject/nuxt-auto-admin',
],
autoApi: {
prefix: '/api',
},
autoAdmin: {
prefix: '/admin',
branding: {
title: 'Blog Admin',
},
},
css: ['~/assets/css/main.css'],
compatibilityDate: '2024-01-01',
})
Create app/assets/css/main.css (Nuxt UI and the admin are styled with Tailwind CSS v4):
@import "tailwindcss";
@import "@nuxt/ui";
The admin pages render inside <NuxtLayout> — make app/app.vue:
<template>
<UApp>
<NuxtLayout>
<NuxtPage />
</NuxtLayout>
</UApp>
</template>
Create Your Schema
1. Define Database Schema
Create server/database/schema.ts:
import { sqliteTable, text, integer } from 'drizzle-orm/sqlite-core'
export const posts = sqliteTable('posts', {
id: integer('id').primaryKey({ autoIncrement: true }),
title: text('title').notNull(),
slug: text('slug').notNull().unique(),
content: text('content'),
published: integer('published', { mode: 'boolean' }).default(false),
createdAt: integer('created_at', { mode: 'timestamp' }).$defaultFn(() => new Date()),
updatedAt: integer('updated_at', { mode: 'timestamp' }).$defaultFn(() => new Date()),
})
export const authors = sqliteTable('authors', {
id: integer('id').primaryKey({ autoIncrement: true }),
name: text('name').notNull(),
email: text('email').notNull().unique(),
bio: text('bio'),
})
2. Initialize Database
Create server/plugins/database.ts:
import { drizzle } from 'drizzle-orm/better-sqlite3'
import Database from 'better-sqlite3'
import { initializeDatabase } from '@websideproject/nuxt-auto-api/database'
import * as schema from '../database/schema'
export default defineNitroPlugin(() => {
const sqlite = new Database('sqlite.db')
const db = drizzle(sqlite, { schema })
initializeDatabase(db, 'better-sqlite3')
})
3. Configure Drizzle Kit
Create drizzle.config.ts:
import { defineConfig } from 'drizzle-kit'
export default defineConfig({
schema: './server/database/schema.ts',
out: './drizzle',
dialect: 'sqlite',
dbCredentials: {
url: 'sqlite.db',
},
})
4. Generate Database
npx drizzle-kit push
Register Resources
1. Create a Module
Create modules/base/index.ts:
import { defineNuxtModule, createResolver } from '@nuxt/kit'
import { createModuleImport } from '@websideproject/nuxt-auto-api'
export default defineNuxtModule({
meta: {
name: 'base',
},
setup(_options, nuxt) {
const resolver = createResolver(import.meta.url)
nuxt.hook('autoApi:registerSchema', (registry) => {
registry.register('posts', {
schema: createModuleImport(
resolver.resolve('../../server/database/schema'),
'posts'
),
authorization: createModuleImport(resolver.resolve('./auth'), 'openAuth'),
})
registry.register('authors', {
schema: createModuleImport(
resolver.resolve('../../server/database/schema'),
'authors'
),
authorization: createModuleImport(resolver.resolve('./auth'), 'openAuth'),
})
})
},
})
Create modules/base/auth.ts. Every operation must be allowed explicitly — a resource without
authorization refuses every request:
import type { ResourceAuthConfig } from '@websideproject/nuxt-auto-api'
// Open to everyone — fine for this local walkthrough, never for production.
// See /auto-api/authentication-authorization for users, roles and ownership rules.
export const openAuth: ResourceAuthConfig = {
permissions: { read: true, create: true, update: true, delete: true },
}
2. Load the Module
Update nuxt.config.ts to include your module:
export default defineNuxtConfig({
modules: [
'@nuxt/ui',
'@websideproject/nuxt-auto-api',
'@websideproject/nuxt-auto-admin',
'./modules/base', // Add this
],
// ... rest of config
})
Test Your API
Start the development server:
npm run dev
API Endpoints
Your API is now available at:
GET /api/posts # List all posts
GET /api/posts/:id # Get single post
POST /api/posts # Create post
PATCH /api/posts/:id # Update post
DELETE /api/posts/:id # Delete post
GET /api/authors # List all authors
GET /api/authors/:id # Get single author
POST /api/authors # Create author
PATCH /api/authors/:id # Update author
DELETE /api/authors/:id # Delete author
Test with cURL
# Create an author
curl -X POST http://localhost:3000/api/authors \
-H "Content-Type: application/json" \
-d '{"name":"John Doe","email":"john@example.com"}'
# Create a post
curl -X POST http://localhost:3000/api/posts \
-H "Content-Type: application/json" \
-d '{"title":"Hello World","slug":"hello-world","content":"My first post"}'
# List posts
curl http://localhost:3000/api/posts
Access Admin Panel
Navigate to http://localhost:3000/admin
You'll see:
- Posts resource with list, create, edit, and delete pages
- Authors resource with full CRUD operations
- Auto-generated forms based on your schema
Use in Frontend
1. List Posts
<template>
<div>
<h1>Blog Posts</h1>
<div v-if="isLoading">Loading...</div>
<ul v-else>
<li v-for="post in posts?.data" :key="post.id">
<h2>{{ post.title }}</h2>
<p>{{ post.content }}</p>
</li>
</ul>
</div>
</template>
<script setup lang="ts">
const { data: posts, isLoading } = useAutoApiList('posts', {
filter: { published: true },
sort: '-createdAt',
limit: 10,
})
</script>
2. Create Post
<template>
<form @submit.prevent="handleSubmit">
<input v-model="form.title" placeholder="Title" required>
<textarea v-model="form.content" placeholder="Content"></textarea>
<button type="submit" :disabled="isPending">
{{ isPending ? 'Creating...' : 'Create Post' }}
</button>
</form>
</template>
<script setup lang="ts">
const form = reactive({
title: '',
slug: '',
content: '',
})
const { mutateAsync: createPost, isPending } = useAutoApiMutation('posts', 'create', {
toast: { enabled: true, showSuccess: true, showErrors: true },
})
const handleSubmit = async () => {
form.slug = form.title.toLowerCase().replace(/\s+/g, '-')
await createPost(form)
Object.assign(form, { title: '', slug: '', content: '' })
}
</script>
Customize Admin Panel
Configure Resources
Update nuxt.config.ts:
export default defineNuxtConfig({
// ... modules
autoAdmin: {
prefix: '/admin',
branding: {
title: 'Blog Admin',
logo: '/logo.svg',
},
resources: {
posts: {
displayName: 'Blog Posts',
icon: 'i-heroicons-document-text',
group: 'Content',
listFields: ['id', 'title', 'published', 'createdAt'],
// `formFields` replaces the generated forms: give both `create` and `edit`
formFields: {
create: [
{ name: 'title', widget: 'TextInput', required: true },
{ name: 'slug', widget: 'TextInput', required: true },
{ name: 'content', widget: 'TextareaInput', options: { rows: 10 } },
{ name: 'published', widget: 'CheckboxInput' },
],
edit: [
{ name: 'title', widget: 'TextInput', required: true },
{ name: 'slug', widget: 'TextInput', required: true },
{ name: 'content', widget: 'TextareaInput', options: { rows: 10 } },
{ name: 'published', widget: 'CheckboxInput' },
],
},
},
authors: {
displayName: 'Authors',
icon: 'i-heroicons-user-group',
group: 'Content',
listFields: ['id', 'name', 'email'],
},
},
},
})
Next Steps
Now that you have a working setup:
Learn More About Auto API
- Validation - Add custom validation rules
- Authorization - Secure your endpoints
- Custom Endpoints - Add custom logic
- Pagination - Configure cursor or offset pagination
- Multi-Tenancy - Build SaaS applications
Learn More About Auto Admin
- Configuration & Theming - Customize appearance
- Form Fields & Widgets - Rich form controls
- Permissions - Access control
- Custom Pages - Add custom functionality
Example Project
Clone the example project for a complete working setup:
git clone https://github.com/websideproject/nuxt-auto
cd nuxt-auto
bun install
bun run dev:prepare # build the module stubs
cd apps/playground
mkdir -p .data
bun run db:migrate && bun run db:seed # create and fill .data/db.sqlite
cd ../..
bun run dev # starts the playground
Visit http://localhost:3000 to see the example in action.
Installation
This guide will help you install and set up Nuxt Auto in your Nuxt project.
Getting Started
Nuxt Auto API automatically generates type-safe REST APIs from your Drizzle ORM schemas with built-in authorization, validation, and multi-tenancy support.