1

I want to be able to redirect unauthenticated users from an individual post's page to the login and then back to the post after the user has logged in.

My login route is like this:

router.get('/login', function(req, res, next){
    if (req.user){
        res.redirect('/wall');
    } else {
        res.render('login');
    }
});

My wall router looks like this:

router.get('/wall', function(req, res, next){
    res.render('wall');
});

The post URL will be something like:

http://thisisnotarealdomain.com/wall#/post/ID

My stack is: NodeJS and Angular for the SPA

How do I do that?

Thanks,

Sean
  • 1,151
  • 3
  • 15
  • 37

1 Answers1

1

First of all, I would create a middleware function to handle the redirection in case the user is not logged in, something like this:

const checkLogin = (req, res, next) => {

  // Checks if the user is logged in
  if(!userIsLoggedIn) {

    // If user is not logged in

    // Get relative path of current url
    const url = req.originalUrl;

    // And redirect to login page, passing
    // the url as a query string that Angular
    // can access later
    res.redirect(`/login/?redirect=${url}`);

  } else {

    // If user is logged in
    // go on and render the page
    next();

  }
}

router.get('/wall', checkLogin, function(req, res, next){
    res.render('wall');
});

This way, if the user is not logged in, you would get redirect to an url like /login/?redirect=/wall/post/14.

Then in your Angular code, you would wait for the login promise from Node and simply do a redirect to that query string we have: redirect. Something like this:

// Assuming you're logging from a service
angular
  .service('LoginService', function($location, $window) {

    // Generic login (could be $http, $resource, restangular)
    LOGIN_PROMISE
      .then(function(res) {

        // If login was successful
        if(res.success) {

          // $location.search() allows you
          // to access query strings
          var redirectTo = $location.search().redirect;

          // And then redirect to the page the
          // user were before being redirected
          // to the login page
          $window.location.href = redirectTo;

        }

      })
  })

Or you could do a redirect directly from your backend code:

// On your Angular code
$http({
  method: 'GET',
  params: {
    redirect: $location.search().redirect
  }
});

// On Node
router.get('/api/login', (req, res, next) => {

  if(passwordIsCorrect) {
    // And do the redirect
    res.redirect(req.body.redirect);
  }

});

This is just one of a lot of ways you can achieve this (that's the beauty of web development).

Hope this may help you!

Bruno Poeta
  • 521
  • 2
  • 9
  • Thanks for that mate. I will test it out and get back to you. Cheers – Sean Sep 18 '17 at 06:39
  • The "req.originalUrl;" doesn't have anything past the #. Remember that I need the full path for an SPA app, so something like: http://thisisnotarealdomain.com/wall#/post/ID – Sean Sep 18 '17 at 14:10
  • Is it absolutely vital that you use the hashbang (#) on the url? If not, I would recommend you to use something like on your main html in conjunction with $locationProvider.html5Mode(true); on your route configuration file. This way you can retrieve the full path. – Bruno Poeta Sep 18 '17 at 15:24
  • Not having # with defeat the purpose of SPA though, which is why I can't avoid it. Such a pain just getting a URL for redirection... And thanks so far for the help mate! – Sean Sep 19 '17 at 02:59
  • 1
    No problem, man! Having a good time trying to help you get this thing to work :) Maybe try using the hash function from the URL module from NodeJS: https://nodejs.org/api/url.html#url_url_hash. This might do the trick (hopefully) – Bruno Poeta Sep 19 '17 at 03:38
  • I only see one problem with this. You will get two hashbangs on the redirect query string. I never came across this case and I don't know how browsers would behave with that. Let me know if it works! – Bruno Poeta Sep 19 '17 at 03:43
  • I tried all sorts (to do with your URL Hash suggestion). The thing is - this will set the URL, not get it. My problem is that I can't get the full path (post # is truncated). So sadly, this doesn't work either (although would've come handy if I had the post # path). – Sean Sep 20 '17 at 14:40