Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Vue-router, how to prevent the user back to the login screen pressing the back button in browser?

This code prevents the user back to the login screen by modifying the url, but if they click the back button in the browser, he can go to the login screen even when logged in.

The user data is saved in localstorage 'info' when they are authenticated, and when it exits the localstorage is updated to null

router.beforeEach((to, from, next) => {
    if(window.localStorage.getItem('info') !== null && to.path == '/login'){
        next(from.fullPath)
    }
    if(window.localStorage.getItem('info') === null && to.path != '/login'){
        next('/login')
    } 
    next()
})

Help me, please!

like image 590
Matheus Silva Avatar asked Apr 29 '18 13:04

Matheus Silva


3 Answers

It's possible using navigation guards and route meta fields, which allows to delegate route-specific rules to router file.

beforeEach code (eg in main file):

// Check the user's status, and route rules
router.beforeEach((to, from, next) => {
  // Redirect if user is disallowed to view the page
  const isLogged = !! store.getters.getUser
  if (isLogged && to.meta.disallowAuthed) {
    return router.push('/my-redirect-page')
  }

  return next()
})

Route definition (set meta flag disallowAuthed):

login: {
  path: '/login',
  name: 'login',
  component: TheLoginPage,
  meta: { disallowAuthed: true }
},

Note

Meta field does not propagate from parent route to children - in case if also the check of route's parent meta field is required, use this (checks both chosen route's meta and metas of routes at any parent level):

const isDisallowAuthed = to.matched.some((route) => route.meta.disallowAuthed)

instead of accessing it directly:

const isDisallowAuthed = to.meta.disallowAuthed

Imho, it's always better to go with this approach in case of dealing with auth logic, since checking against meta.flag directly requires mental overhead of remembering this caveat while refactoring Routes file.

Related issue: https://github.com/vuejs/vue-router/issues/704

like image 177
ego Avatar answered Oct 11 '22 18:10

ego


You can listen to back button event using popstate.

You may add this to your root component (perhaps App.vue ?). It listens to back (or forward) button event and redirects if necessary.

 mounted() {
    window.onpopstate = event => {
      if (
        window.localStorage.getItem("info") !== null &&
        this.$route.path == "/login"
      ) {
        this.$router.push("/"); // redirect to home, for example
      }
    };
  }
like image 28
Jacob Goh Avatar answered Oct 11 '22 17:10

Jacob Goh


Not sure if this is what you meant, feel free to specify the issue more. But to not go back to /login, you would need to replace the history when navigating away from /login.

next({ 
  path: from.fullPath,
  replace: true,
})

This way the browser would navigate back to the previous history entry.

You can read more about this here.

like image 35
Philipp Beck Avatar answered Oct 11 '22 18:10

Philipp Beck