Search code examples
nuxt.jsvue-routervuejs3middlewarenuxt3.js

Nuxt 3 use composable in middleware


I want to guard a route by checking if the user is logged in, but:

  1. I can't read the composable value,
  2. I am unsure if my middleware got the right body.

My composable:

// composable/useAuth.js
const useAuth = () => {

  // user login, sign out, sign up logic

  const isLoggedIn = () => {
    return !!user.value
  }

  return {
    isLoggedIn
  }
}

export default useAuth

My middleware:

// middleware/check-admin.js
export default defineNuxtRouteMiddleware((to, from) => {
  const { isLoggedIn } = useAuth()

  console.log(isLoggedIn); // <- Screenshot

  if (isLoggedIn) {
    return navigateTo(`/albums/${to.params.id}/edit`)
  } else {
    return navigateTo('/')
  }
})

My console logs a method body. But I expected a falsy or truthy value: enter image description here


Problems:

  • How can I read a boolean value from my composables to pass the test inside the middleware?
  • It is okay to use navigateTo to abort the routing, if the user got no credentials? The docs says, I can use abortNavigation()

Solution

  • You returning function, but never invoke it by using () at the end.

    Try like this:

    export default defineNuxtRouteMiddleware((to, from) => {
      const { isLoggedIn } = useAuth()
    
      console.log(isLoggedIn()); // <- Screenshot
      // `from.name === login` will trigger rediraction for example if user want to login but he is already logged in.
      // form.name will be necesery if you use suffix `.global` in file name.
      if (isLoggedIn() && to.params.id && !from.params.id && from.name === `login`) {
        return navigateTo(`/albums/${to.params.id}/edit`)
      }
      if (!isLoggedIn() && form.params.id) {
        return abortNavigation()
      }
    })
    

    Use to value to know where user want to navigate.

    You can choose where to use middleware in component if you're not using .global suffix in middleware file.

    <script setup>
    definePageMeta({
      middleware: ["auth"]
      // or middleware: 'auth'
    })
    </script>