# Nuxt 3

> Server route + composable for SSR + ISG.

## Server route

```ts
// server/api/blog/[...].get.ts
export default defineEventHandler(async (event) => {
  const config = useRuntimeConfig();
  const path = getRouterParam(event, "_") ?? "";
  const target = `${config.blogotoApiUrl}/api/public/${config.blogotoSiteSlug}/${path}${event.node.req.url?.includes("?") ? "?" + event.node.req.url.split("?")[1] : ""}`;
  return await $fetch(target, {
    headers: { Authorization: `Bearer ${config.blogotoApiKey}` }
  });
});
```

## Composable

```ts
// composables/useBlog.ts
export const useBlogList = () => useFetch("/api/blog/posts");
export const useBlogPost = (slug: string) => useFetch(`/api/blog/posts/${slug}`);
```

## Pages

```vue
<!-- pages/blog/index.vue -->
<script setup lang="ts">
const { data } = await useBlogList();
</script>
<template>
  <ul><li v-for="post in data?.posts" :key="post.slug">
    <NuxtLink :to="`/blog/${post.slug}`">{{ post.title }}</NuxtLink>
  </li></ul>
</template>
```

```vue
<!-- pages/blog/[slug].vue -->
<script setup lang="ts">
const route = useRoute();
const { data } = await useBlogPost(route.params.slug as string);
</script>
<template>
  <article>
    <h1>{{ data?.post.title }}</h1>
    <div v-html="data?.post.html" />
  </article>
</template>
```

## nuxt.config.ts

```ts
export default defineNuxtConfig({
  runtimeConfig: {
    blogotoApiUrl: process.env.MENTIONWELL_API_URL,
    blogotoSiteSlug: process.env.MENTIONWELL_SITE_SLUG,
    blogotoApiKey: process.env.MENTIONWELL_API_KEY
  }
});
```


---

Canonical URL: https://mentionwell.com/docs/frameworks/nuxt
Live HTML version: https://mentionwell.com/docs/frameworks/nuxt
Section: Quickstarts by stack
Site index for AI ingestion: https://mentionwell.com/llms.txt
Full reference: https://mentionwell.com/llms-full.txt
