N
Nuxt3mo ago
Omnislash

middleware in client only component

Hello Kapa If in a component named name.client.vue I have this code :
<script setup lang="ts">
definePageMeta({
middleware: [
() => {
if (import.meta.server) {
console.log('This is a server-side middleware');
return;
} else {
console.log('This is a client-side middleware');
}
},
],
});
</script>
<script setup lang="ts">
definePageMeta({
middleware: [
() => {
if (import.meta.server) {
console.log('This is a server-side middleware');
return;
} else {
console.log('This is a client-side middleware');
}
},
],
});
</script>
Will the middleware be executed only client side or both ? I would except it to be client side only but the log appears for both server and client
2 Replies
kapa.ai
kapa.ai3mo ago
Hi @Omnislash. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave: ---------------------- In Nuxt, even if you define a page as client-only by using the .client.vue suffix, the middleware specified in definePageMeta will still be executed on both the server and the client. This is because Nuxt's routing and middleware system processes middleware during both server-side rendering and client-side navigation, regardless of the .client.vue suffix on the page component. This behavior is confirmed in the documentation, which states:
If your site is server-rendered or generated, middleware for the initial page will be executed both when the page is rendered and then again on the client...
However, if you want to avoid this behaviour you can do so:
export default defineNuxtRouteMiddleware(to => {
// skip middleware on server
if (import.meta.server) return
// skip middleware on client side entirely
if (import.meta.client) return
// or only skip middleware on initial client load
const nuxtApp = useNuxtApp()
if (import.meta.client && nuxtApp.isHydrating && nuxtApp.payload.serverRendered) return
})
export default defineNuxtRouteMiddleware(to => {
// skip middleware on server
if (import.meta.server) return
// skip middleware on client side entirely
if (import.meta.client) return
// or only skip middleware on initial client load
const nuxtApp = useNuxtApp()
if (import.meta.client && nuxtApp.isHydrating && nuxtApp.payload.serverRendered) return
})
Docs > Guide > Directory-structure > middleware
Additionally, the .client.vue suffix only affects the rendering of the page/component itself, not the execution context of the middleware attached to it. Middleware is part of the Nuxt app's navigation lifecycle, not the component's rendering lifecycle. This is why you see logs from both server and client. If you want your middleware to run only on the client, you must explicitly check for import.meta.client and return early on the server, as shown above. Summary:
Middleware in a .client.vue page will still execute on both server and client unless you add logic to skip server execution. The .client.vue suffix does not restrict middleware to the client side only. ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai3mo ago
<@305772639438503936> Kapa.ai is still learning and improving, please let me know how I did by reacting below.

Did you find this page helpful?