0

I have a node app that has Express routes. These hand off to AngularJS routes that conditionally load partials for the one-page front-page app, or to a login page if there is no session.

I explored using AngularJS $locationProvider to remove the hash character from URLs, so that I could have cleaner addresses. I looked at the module adjustments made in the answer to this question: Removing the fragment identifier from AngularJS urls (# symbol)

When doing this, this interferes with the routes set up at the Express level. The side effect is that the application no longer routes to the login page. So the following Express-side logic gets ignored:

app.get('/', function(req, res) {
    if (req.session.user) {
        res.render('index', { username : req.session.username, msg : req.session.msg });
    }
    else {
        res.redirect('/login');
    }
});

(The /login path has its own Express route.)

In other words, the application works as if a user is always logged in, because AngularJS's $routerProvider takes over and shows the (logged-in) front page:

function config($routeProvider) {
    $routeProvider
        .when('/', {
            templateUrl : '/partials/front/front.html', 
            controller : 'FrontPageController', 
            controllerAs : 'vm'
        })
        ...
        .otherwise({redirectTo: '/'});
}

If I have to keep hashed URLs, is there a way to deal with Express routes so that I can get to what is after the hash?

For instance, I have the following address that Express loads as the / GET route, and is then handled on the AngularJS side to load a viewer-specific partial into the / (front) page:

https://foo.com/#/viewer?id=1234

What I'd like to do is go to the Express routes and deal with the / GET request so that I can parse out what is after the hash and redirect after login.

Basically, I want the following kind of logic:

app.get('/', function(req, res) {
    if (req.session.user) {
        res.render('index', { username : req.session.username, msg : req.session.msg });
    }
    else {
        if (req.query.id) { 
            res.redirect('/login?t=viewer&id=' + req.query.id); 
        } else {
            res.redirect('/login');
        }
    }
});

But it looks like req.query.id gets wiped before I have a chance to extract its value for the redirect call.

Is there any way to grab the URL before it gets wiped by Express, so that I can parse it?

Failing that, is there a way to make AngularJS and Express routes play nice together if I remove the fragment identifier (hash)?

Community
  • 1
  • 1
Alex Reynolds
  • 95,983
  • 54
  • 240
  • 345
  • The express route will *only* trigger if the route cannot be processed by angular, if the link is generated from an external source, or if there is a page reload. Once the app is bootstrapped into the browser, routes that angular can match will never be sent to the server to begin with, which is part of the power of Single Page Applications. Therefore, unless your app is using a unique route like `/app/` the URLs aren't being wiped by Express, rather, they are never even seen by Express. – Claies Nov 14 '16 at 00:40
  • See: http://stackoverflow.com/questions/17777967/using-angularjs-html5mode-with-nodejs-and-express – charlietfl Nov 14 '16 at 00:41
  • Will gladly remove duplicate if it doesn't solve issue but it should. Am not an express guru – charlietfl Nov 14 '16 at 00:45
  • Note that nothing after hash in a url gets sent to server...it is maintained only by browser – charlietfl Nov 14 '16 at 00:46
  • Is there a way to pass that to the server in some way? – Alex Reynolds Nov 14 '16 at 00:56
  • I don't think this is a duplicate question. Or it is not obvious how they are the same question (other than based on the title). – Alex Reynolds Nov 14 '16 at 00:56
  • the answer shows how to configure the server side using `use()` ..note that order is important. As for passing the hash...not really, it's how browsers wrok – charlietfl Nov 14 '16 at 01:07
  • As soon as you get rid of the hash the url params will be exposed at server – charlietfl Nov 14 '16 at 01:09

0 Answers0