-1

I'm very new to Nuxt and i'm working on a SSR app that uses Django on the backend.

I'm trying to create the login page, and before rendering it i would like to check if the user is already logged in, and if it is redirect the user to another page.

For various reasons i cannot do this from a Nuxt middleware, since i need this code to be executed from client side and not from server side, so i decided to use beforeRouteEnter. My code seems to work, but the problem is that it will load the page and then, after more or less 1-2 seconds redirect to another page. This is a bit ugly, since i don't want the user to see the login page before being redirected. I tried the same with beforeCreate but the outcome was the same

Why does that happen? Is it because the page is cached? Can i fix it?

Here is the code:

export default {
  name: 'LoginPage',

  props: {
  },

  data(){
    return {
    }
  },

  beforeRouteEnter (to, from, next) {
    return axios({
      method: 'post',
      url: 'http://127.0.0.1:8000/checkAuth',
      data: {
      },
      withCredentials: true,
      headers: {}
    }).then(function (response) {
      if (response['data']['state'] == 'True'){
        //user is logged in, redirect
        next('/')
      } else {
        //user is not logged in, don't redirect
        next()
      }
      
    }).catch(function (error) {
      next()
    });

  }
 ...
}
kissu
  • 40,416
  • 14
  • 65
  • 133
Jack022
  • 867
  • 6
  • 30
  • 91

1 Answers1

1

Try writting it in this form

beforeRouteEnter(to, from, next) {
  next(async (vm) => {
    await axios...

    if(...) {
      next()
    } else {
      next(false) // in case the navigation needs to be blocked
    }
  })
}

That way, it should wait for the result before resolving the navigation.


If you only need this check on pages, you can also use asyncData to get data before even navigating to the next page (it will block until resolved). Beware tho, because an F5 on the targetted page will not trigger this hook.

kissu
  • 40,416
  • 14
  • 65
  • 133
  • Thank you a lot! I tried this but the result is the same. The same happens with asyncData. Basically the HTML of the page is loaded and after a second all the Nuxt stuff is fired – Jack022 Apr 09 '21 at 15:06
  • If you `async/await` your axios call, it will wait before resolving the navigation. You can put a `setTimeout` of 4 seconds in your `asyncData` hook to be sure that it awaits for API call (just to be sure that you plugged it properly !). If it does not await the `setTimeout`, there is an issue somewhere. – kissu Apr 09 '21 at 15:08
  • What i mean is that whatever i try, before redirecting i will see the login page for 1 second. I mean that the HTML in my page is rendered and then the Nuxt code is executed. That happens with everything i tried, including asyncData and other methods – Jack022 Apr 09 '21 at 15:11
  • Is your page the initial one or one you navigate to (coming from a page before this, via vue-router) ? – kissu Apr 09 '21 at 15:13
  • Let me try to explain. Here is what happens in my browser (Chrome): i refresh the login page -> immediately i will see the html page in the page -> after one second or so the redirect happens, even though on the Nuxt console i see that the code is being executed immediately – Jack022 Apr 09 '21 at 15:14
  • This happens when i navigate directly from URL input, not navigation – Jack022 Apr 09 '21 at 15:15
  • 1
    If your project is generated as an universal app, it's true that you'll see the static login page before the hydration kicks in. There is no way of bypassing this but to have a static loader or alike, that you remove if it checks the JS logic. If you don't need the benefits of SSR, you can also make your app SPA only, will remove this headache. Otherwise, it's a good idea to start designing a placeholder page until the hydration kicks in. ^^ – kissu Apr 09 '21 at 15:16
  • Thank you, well i'm starting to think that what i need is the SPA mode rather than universal in this case – Jack022 Apr 09 '21 at 15:17
  • Another cool thing actually, is that you can tell Nuxt to exclude the generation of specific pages, you may write down your `login` page to it and it will be the only one to be client-side rendered. The rest of your app will stay universal. https://nuxtjs.org/docs/2.x/configuration-glossary/configuration-generate/#exclude – kissu Apr 09 '21 at 15:19
  • Thank you. Yes indeed what's weird is that i was trying this with ssr: false but i was still having this problem. Maybe i need to do something else to make it in SPA mode – Jack022 Apr 09 '21 at 15:25
  • 1
    Then, you need to `yarn build` (`target` should be `server` if I remember properly) for production build and it should work great with a basic `yarn dev`. Try disabling your JS on client side to double check if it's actually SPA only or not. May be useful: https://stackoverflow.com/a/63638062/8816585 – kissu Apr 09 '21 at 15:33