Getting started with Nuxt 3 Server Routes
Table of contents
Building an API with Server Routes (Basic)
Getting Started with Nuxt 3 Server Routes
Building an API with Server Routes (Basic)
The server/
directory allows Nuxt create powerful backend APIs using the modern Nitro Engine
. Due to the power of the auto-import feature Nuxt is designed to scan files in the following api/
, routes/
, middleware/
and plugins/
- to register APIs and server handlers.
Files in these folders accept an event as their first argument which comes from the H3 Utilities. This can be defined in a function that handles the event - defineEventHandler()
or eventHandler()
.
Creating a Server Route
In this tutorial we will break our API based on the folder structure for the server/
directory.
server/
api/
routes/
middleware/
plugins/
Creating a Server Route in the api/
folder
The files in the api/
folder are prefixed with the api/
in the route path. For example, if we have a file called api/todo
it will be available at http://localhost:3000/api/todos
.
export default defineEventHandler(async (event) => {
// @ts-ignore
const _recipes: RecipeTodo = sampleData
const status = getResponseStatus(event)
return {
status,
message: "Success",
data: _recipes
}
})
With this API route in place, we can access it on our pages and components using the data-fetching method useFetch
.
<script setup lang="ts">
const _recipeTodo = await useFetch('api/todos')
</script>
Let us rework this example and make it more readable and reusable. We can create a new directory in the api/
folder called todos/
and create a file called index.ts
in it. This will allow us to create multiple routes for the todos
API.
export default defineEventHandler(async (event) => {
// @ts-ignore
const _recipes: RecipeTodo = sampleData
const status = getResponseStatus(event)
return {
status,
message: "Success",
data: _recipes
}
})
With this, we can now create a new file called createTodo.post.ts
in the todos/
folder. This will allow us to create a new route for creating a todo. (Note: This is similar to how pages are created.)
Note: The file name can be suffixed with an HTTP method.
export default defineEventHandler(async (event) => {
// Handle request with body
const body = await readBody(event);
const { title, description }: Partial<RecipeTodo> = body;
// @ts-ignore
const _recipes: RecipeTodo = {
id: uuidv4(),
title: title,
description: description,
}
const status = getResponseStatus(event)
sampleData.push(_recipes)
return {
status,
message: "Success",
data: sampleData
}
});
Note: The readBody
function is a helper function that allows us to read the body of the request. This is similar to the req.body
in Express. This function (like so many others - getResponseStatus()
) are available from the H3 utilities.
Creating a Server Route in the routes/
folder
Similar to the api/
folder, the files in the routes/
create the API route path without api/
prefix. For example, if we have a file called routes/todo
it will be available at http://localhost:3000/routes/todos
.
export default defineEventHandler(async (event) => {
// @ts-ignore
const _recipes: RecipeTodo = sampleData
const status = getResponseStatus(event)
return {
status,
message: "Success",
data: _recipes
}
})
Creating a Server Middleware
Files in the middleware/
will be automatically registered as a middleware in Nuxt. Middleware handlers will be called before the API handlers.
Note: Middleware handlers should not return a response. They should only inspect or extend the request or give an error.
export default defineEventHandler((event) => {
console.log('New request: ' + getRequestURL(event))
})
Another example:
export default defineEventHandler(async (event) => {
try {
// const data = await $fetch('https://jsonplaceholder.typicode.com/todos')
// console.log(data)
event.context.data = sampleData.length
} catch (e) {
console.error(e)
sendError(event, createError({
statusCode: 401,
statusMessage: "Unauthorized",
}))
}
});
Creating a Server Plugin
Files in the plugins/
will be automatically registered as a plugin in Nuxt. Plugins are useful for extending the functionality of the server.
export default defineEventHandler((event) => {
console.log('New request: ' + getRequestURL(event))
})
Conclusion
In this tutorial, we explored the server/
directory and how to use it to create server routes (APIs). Nuxt provides a full-stack experience that provides a backend and a frontend in one package.