auth-module: Redirect not working after login or logout

Version v4.5.1

Reproduction link https://github.com/nuxt-community/auth-module

Configuration

auth: {
    // Options
    strategies: {
      local: {
        endpoints: {
          login: { url: process.env.BASE_URL + '/auth', method: 'post', propertyName: 'token' },
          logout: false,
          user: { url: process.env.BASE_URL + '/users/auth', method: 'get', propertyName: false }
        }
      }
    },
    redirect: {
      login: '/signin',
      logout: '/signin',
      home: '/home'
    },
    watchLoggedIn: true,
    rewriteRedirects: false,
    resetOnError: true
  }

Action to login :

this.$auth.loginWith('local', {
            data: {
              username: this.username,
              password: this.password
            }
          });

Action to logout : await this.$auth.logout();

Steps to reproduce I use local strategy with a token. After the token expires if i reload the page, the user is logged out because i have resetOnError=True. I’m redirect to my signin page. Then i try to reconnect, i get new token and when i check into VueX, i got this result :

auth: {
busy:false,
loggedIn:true,
strategy:"local",
user: { ... }
 }

But i’m not redirect to home page … If i refresh, i’m connected into the home page.

Where i’m doing wrong ? Thanks for your answers.

Regards,

About this issue

  • Original URL
  • State: closed
  • Created 6 years ago
  • Reactions: 30
  • Comments: 37 (1 by maintainers)

Commits related to this issue

Most upvoted comments

This lirbary seems dead. it’s faster to create a few methods and states on vuex and manage the stuff alone…

Me too, I have spent so much time with this I could have implemented my own auth system by now… I was hoping this would be more intuitive.

I have been struggling, for days now, with redirects not working after login or logout. My setup was simple. Started a new nuxt project (SSR/Universal, with Axios, PWA), added nuxt auth-next, set auth as middleware for router in nuxt.config.js. pages/index.vue is not accessible without login. Created pages/login.vue and set auth: "guest" to allow login page to open only when not logged in.

Following is my auth config in nuxt.config.js

auth: {
    redirect: {
        login: "/login",
        logout: "/login",
        home: "/"
    },
    watchLoggedIn: true,
    strategies: {
        local: {
            token: {
                property: "jwt"
            },
            user: {
                property: false
            },
            endpoints: {
                login: {
                    url: "auth/local",
                    method: "post"
                },
                user: {
                    url: "users/me",
                    method: "get"
                },
                logout: false
            }
        }
    }
}

With this setup, when login using local strategy, after successful login redirection didn’t work and I had to refresh the page for user to redirect to /.

this.$auth
    .loginWith("local", {
        data: {
            username: this.username,
            password: this.password
        }
    })
    .then(response => {
        console.log(response);
    })
    .catch(error => {
        console.log(error.response);
    });

At this point, I am at the brink of pulling my hair out from my head in frustration. Then magic happens.

I created a store/index.js with the following code:

export const state = () => ({});

export const mutations = {};

export const getters = {};

export const actions = {};

basically, just a blank store.

Run the app again, and voila, redirection starts to work! Login, logout, everything works.

Hope this helps someone!

YES Finally just remove auth: false from your login.vue

   export default {                                                                                                   
     components: {},                                                                                                  
      data() {                                                                                                         
        return {                                                                                                       
          login: {                                                                                                     
            username: '',                                                                                              
            password: '',                                                                                              
          },                                                                                                           
        }                                                                                                              
      },                                                                                                               
      // auth: false, <========================                                                                                                  
      methods: {                                                                                                       
        async userLogin() {                                            
...
...
...

I actually found that when you set the property user on endpoints to false, it starts working as expected.

The thing is that is seems that the nuxt auth plugin waits this property to be defined to redirect to homepage. There is no need to make workarounds, but a PR may be welcome.

Here is my code:

auth: {
strategies: {
      local: {
        endpoints: {
          login: { url: '/auth/login', method: 'post', propertyName: 'token' },
          user: { url: '/auth/user', method: 'get', propertyName: false },
          logout: { url: '/auth/logout', method: 'post' }
        },
        // tokenRequired: true,
        // tokenType: 'Bearer'
      }
    },
    redirect: {
      login: '/public/login',
      home: '/',
      logout: '/public/login'
    }
  }

I came up with this which seems to work as I would have expected the redirects to work out of the box.

export default function ({ app }) {
  const oldLogout = app.$auth.logout.bind(app.$auth)
  const oldLogin = app.$auth.login.bind(app.$auth)

  app.$auth.logout = (...args) => {
    const _ = oldLogout(...args)
    _.then(() => app.$auth.redirect('logout'))
    return _
  }

  app.$auth.login = (...args) => {
    // sometimes doesn't work when the user tries to get to the admin page
    // before being logged in.

    const _ = oldLogin(...args)
    _.then(() => {
      app.$auth.redirect('home')
    })
    return _
  }
}

I can’t actually get the auth module to redirect after login. It just never emits the routeChange event after I log in it seems. I can get it to redirect on logout, or from an authed page when not logged in.

auth: {
    strategies: {
      local: {
        endpoints: {
          login: {
            url: '/login',
            method: 'get',
            propertyName: 'token'
          },
          logout: {
            url: '/logout',
            method: 'delete'
          },
          user: {
            url: '/me',
            method: 'get',
            propertyName: 'data'
          }
        }
      }
    },
    redirect: {
      login: '/auth/login',
      logout: '/',
      home: '/',
      callback: '/'
    },
    watchLoggedIn: true,
    rewriteRedirects: true
  },

I’m still not sure what callback is for in redirects, but I’ve changed it to every possible value I can think of, as well as omitting it, with no difference.

I’ve tried running as SSR and SPA, with no difference as well.

I had the same issues and fixed it the following way:

May people suggested setting propertyName: false as @AllanPinheiroDeLima suggested:

endpoints: {
    login: { url: '/api/login', method: 'post' },
    logout: { url: '/api/logout', method: 'post' },
    user: { url: '/api/me', method: 'get', propertyName: false },
},

However, seems this did nothing for me, the user was still undefined in vuex (remember to activate vuex by adding index.js in stores folder)

what worked for me was to use the user object and set property to false. This is probably the new way to do the suggestion @AllanPinheiroDeLima suggested.

local: {
    endpoints: {
        login: { url: '/api/login', method: 'post' },
        logout: { url: '/api/logout', method: 'post' },
        user: { url: '/api/me', method: 'get' },
    },
    user: {
        property: false, // <---
    },
    token: {
        property: 'access_token',
        required: true,
        type: 'Bearer',
    },
},

Hi @KunalAggarwal! Thank you for reporting 😃 From now on users will be warned that Vuex Store is not activated #1195

window.location.reload() as simple solution and it was the only one that worked for me,

based on @vencho-mdp answer I believe that my problem happened because I am using “user: false” so my user object is {} and maybe this is the reason if someone from the development team interested in fixing this issue.

My problem now is that the pwa is freezing for some reason ig because of the redirection but am gonna search for that somewhere else

Edit: I found the problem with pwa, it was the same solution that I’ve suggested, so if you’re planing to run pwa you can use plain javascript redirect with: location.href = '/ location.href = '/login in the promise of login and logout methods

Edit 2: pwa is freezing on production server even tho it worked on production on local host still debugging it

Hello, thanks a lot @KunalAggarwal for your analysis and method. As the solution seems to activate the Vuex module, placing an empty JS file in store/ folder does the trick. No code needed, and redirections work.

https://nuxtjs.org/docs/2.x/directory-structure/store#activate-the-store Nuxt.js will look for the store directory. If it contains a file, that isn’t a hidden file or a README.md file, then the store will be activated.

Thanks again !

I ended up building my own auth. As simple as fetching jwt token, writing to a localStorage and making a top-level request which decides if I am logged in or not.

They seem to be moving to nuxt 3.0 though. I think maybe we should abandon this implementation next few months, Link to the new docs: https://dev.auth.nuxtjs.org/guide

I was fighting with this error too and I solve it adding this line before redirect to the login

$auth.$storage.setUniversal('redirect', path)

Thank you @NoahCardoza, your solution worked like champ! 😃

Using the promise handler worked for me.

let data = {
  username: this.username,
  password: this.password
}

this.$auth.login({data: data})
	.then(() => {
	    this.$router.push("/dashboard")
	})
	.catch((error)=> {
	    console.log(error)
	})

I got the same issue but got it fixed by put a forward slash in front of my urls redirect: { login: '/public/login/', home: '/', logout: '/public/login/' } instead of redirect: { login: '/public/login', home: '/', logout: '/public/login' } N.B: Notice the forward slash.

@sayx I added this as an auth-module plugin.

nuxt.config.js

...
  auth: {
    plugins: ['~/plugins/auth.js'],
    strategies: {
      local: {
        endpoints: {
          login: { url: '/api/login', method: 'post' },
          logout: { url: '/api/logout', method: 'get' },
          user: { url: '/api/user', method: 'get', propertyName: 'username' }
        },
        tokenRequired: false,
        tokenType: false,
      }
    },
    redirect: {
      login: '/login',
      logout: '/login',
      home: '/admin',
      user: '/admin',
    },
  }
...

~/plugins/auth.js being what I shared earlier.

@ConsoleTVs I feel like the library is useful, it just didn’t seem to function the way I thought it would.

I came up with this which seems to work as I would have expected the redirects to work out of the box.

export default function ({ app }) {
  const oldLogout = app.$auth.logout.bind(app.$auth)
  const oldLogin = app.$auth.login.bind(app.$auth)

  app.$auth.logout = (...args) => {
    const _ = oldLogout(...args)
    _.then(() => app.$auth.redirect('logout'))
    return _
  }

  app.$auth.login = (...args) => {
    // sometimes doesn't work when the user tries to get to the admin page
    // before being logged in.

    const _ = oldLogin(...args)
    _.then(() => {
      app.$auth.redirect('home')
    })
    return _
  }
}

@NoahCardoza Where did you make these changes in the configuration?