Nuxt API Party
Nuxt API Party is a module for Nuxt that streamlines secure and type-safe interaction with multiple API endpoints. It achieves this by generating composables dynamically for each configured API, similar in feel to Nuxt's native `useFetch` and `$fetch`. The module effectively secures API credentials and circumvents common CORS issues by proxying requests through a Nuxt server route. It features robust OpenAPI specification integration for generating fully typed API clients, offering enhanced developer experience and compile-time safety. The current stable version is 3.4.2, with frequent patch and minor releases addressing bugs and introducing new features. Its key differentiators include automated composable generation, strong type-safety via OpenAPI, built-in credential protection, and smart caching.
Common errors
-
Error: Cannot find module 'openapi-typescript' from '...
cause The `openapi-typescript` package is a peer dependency and must be explicitly installed if you are leveraging OpenAPI features, but it's missing.fixInstall `openapi-typescript` in your project's dev dependencies: `pnpm add -D openapi-typescript` or `npm install -D openapi-typescript`. -
TypeError: Cannot read properties of undefined (reading 'title') in <template>
cause Data from the API might be `null` or `undefined` initially or after an error, and the template tries to access properties on it without null-checking.fixAlways add null/undefined checks in your templates, e.g., `<h1 v-if="data">{{ data.title }}</h1>` or use optional chaining `{{ data?.title }}`. -
Type 'EndpointName' is not assignable to type 'string'. (TypeScript)
cause When using auto-generated types for `$api` or `useApiData` based on OpenAPI, the endpoint name (e.g., 'jsonPlaceholder') is inferred. If you're manually trying to pass a string literal that doesn't match a configured endpoint, TypeScript will complain.fixEnsure the string literal used for the endpoint name exactly matches one of the keys defined in your `apiParty.endpoints` configuration in `nuxt.config.ts`.
Warnings
- breaking The peer dependency `openapi-typescript` is required for OpenAPI type generation features. Ensure it is installed in your project and matches the supported versions (currently ^5, ^6, or ^7).
- gotcha When using the `client: false` option, ensure that it's compatible with your intended SSR/non-SSR usage. Prior to v3.4.2, there were issues with non-SSR usage when `client: false` was set, potentially leading to hydration mismatches or unexpected behavior.
- breaking OpenAPI type helpers were significantly overhauled in v3.1.0, and further refined in subsequent patches (e.g., v3.1.2 fixed missing imports). This might require adjustments to how you import or reference generated OpenAPI types.
- gotcha Incorrect schema resolution paths, particularly on Windows environments, could lead to failed type generation or API client setup. This was addressed in v3.4.1.
Install
-
npm install nuxt-api-party -
yarn add nuxt-api-party -
pnpm add nuxt-api-party
Imports
- module configuration
import { ApiParty } from 'nuxt-api-party';// nuxt.config.ts export default defineNuxtConfig({ modules: ['nuxt-api-party'], apiParty: { /* ... */ } }); - useApiData composable
import { useJsonPlaceholderData } from 'nuxt-api-party'; // not needed, auto-imported const { data } = await useApiData('jsonPlaceholder', 'posts/1'); // incorrect usage patternconst { data, pending, error } = await useJsonPlaceholderData('posts/1'); - $api fetcher
import { $jsonPlaceholder } from 'nuxt-api-party'; // not needed, auto-imported const post = await $api('jsonPlaceholder', 'posts/1'); // incorrect usage patternconst post = await $jsonPlaceholder('posts/1'); - OpenAPI types
import { Post } from 'nuxt-api-party/types'; // generally incorrect path or approachtype Post = paths['/posts/{id}']['get']['responses']['200']['content']['application/json'];
Quickstart
// nuxt.config.ts
import { defineNuxtConfig } from 'nuxt';
export default defineNuxtConfig({
modules: ['nuxt-api-party'],
apiParty: {
endpoints: {
jsonPlaceholder: {
url: process.env.JSON_PLACEHOLDER_API_BASE_URL ?? 'https://jsonplaceholder.typicode.com',
headers: {
// In a real app, use environment variables for tokens
Authorization: `Bearer ${process.env.JSON_PLACEHOLDER_API_TOKEN ?? 'your-mock-token'}`
}
},
myCustomApi: {
url: process.env.MY_CUSTOM_API_BASE_URL ?? 'http://localhost:3001/api',
headers: {
'X-Api-Key': process.env.MY_CUSTOM_API_KEY ?? 'another-mock-key'
}
}
}
}
});
// app.vue (or any Vue component/page)
<script setup lang="ts">
interface Post {
userId: number;
id: number;
title: string;
body: string;
}
// Use the auto-generated composable for jsonPlaceholder endpoint
const { data: postData, pending, error, refresh } = await useJsonPlaceholderData<Post>('posts/1');
// Use the $api shorthand for another endpoint
const customApiResponse = await $myCustomApi('/data');
</script>
<template>
<div>
<h1>Nuxt API Party Example</h1>
<div v-if="pending">Loading post...</div>
<div v-else-if="error">Error loading post: {{ error.message }}</div>
<div v-else-if="postData">
<h2>Post Title: {{ postData.title }}</h2>
<pre>{{ JSON.stringify(postData, null, 2) }}</pre>
<button @click="refresh">Refresh Post</button>
</div>
<hr>
<h2>Custom API Response (from $myCustomApi)</h2>
<pre>{{ JSON.stringify(customApiResponse, null, 2) }}</pre>
</div>
</template>