Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

AngularJS How to redirect back to the next route after logging in

Tags:

angularjs

Using the $rootScope.$on('$routeChangeStart', function(event, next, current), I'm redirecting to the signin page if the route requires authentication. That works perfectly.

How do I redirect back to the intended route though after signing in?

like image 535
julie-coderiver Avatar asked Oct 31 '13 01:10

julie-coderiver


3 Answers

This is a simplified version of what's working for me:

app = angular.module('ngApp', []).config(function ($routeProvider) {
  $routeProvider
    .when('/dashboard', {
        templateUrl: 'dashboard.html',
        controller: 'dashboardController',
        loginRequired: true //
      })
    .when('/login', {
        templateUrl: 'login.html',
        controller: 'loginController'
      })
    .otherwise({redirectTo: '/login'})
});

Then in the application's run block:

app.run(function ($location, $rootScope) {
    var postLogInRoute;

    $rootScope.$on('$routeChangeStart', function (event, nextRoute, currentRoute) {

    //if login required and you're logged out, capture the current path
        if (nextRoute.loginRequired && Account.loggedOut()) {
          postLogInRoute = $location.path();
          $location.path('/login').replace();
        } else if (postLogInRoute && Account.loggedIn()) {
    //once logged in, redirect to the last route and reset it
          $location.path(postLogInRoute).replace();
          postLogInRoute = null;
        }
    });
});
like image 169
Steve Ellis Avatar answered Nov 13 '22 17:11

Steve Ellis


Here is an example of how I am doing it, hope it helps:

On the route provider, first set up the public access somehow:

// Just a demo on how the routes were set up to determine public access
angular.module('ngApp', []).config(function ($routeProvider) {

    $routeProvider

        .when('/', {
            templateUrl: 'views/main.html',
            controller : 'MainController',
        })

        .when('/login', {
            templateUrl  : 'views/login.html',
            controller   : 'LoginController',
            publicAccess : true // This is used in $routeChangeStart later
        });

    });

});

Then:

$rootScope.$on('$routeChangeStart', function(event, next, current) {

    var publicAccess = next.publicAccess || false;

    // This is just a service I made, this is how I check logged in status
    // AuthenticationService.check() returns a promise
    AuthenticationService.check().then(function() {

        // As this is a promise, this block signals that the user is logged in
        // If the page is marked as public access, then redirect to private area    
        if (publicAccess)
            $location.path('/').replace();

    }, function() {

        // Since this segment of the promise signals that the user is not
        // logged in, if the page is not publicly accessible, redirect to login
        if (!publicAccess)
            $location.path('/login').replace();

    });

});
like image 22
francisco.preller Avatar answered Nov 13 '22 15:11

francisco.preller


The following answer is from the OP.


Here's how I solved it:

I added this event broadcast into the $routeChangeStart

$rootScope.$on('$routeChangeStart', function(event, next, current) { 

  if (next.authRequired) {

    var deferred = $q.defer(),
          _token = mainConfig.csrfToken;

    security.getCurrentUser(true, _token).success(function (data, status, headers, config)     {

      if(status == 200) {
        // set the local scope variables
        next.scope.isAuthenticated = true;
        next.scope.user = security.currentUser;
        // Broadcast out to each of the listeners
        $rootScope.$broadcast('currentUserAuthenticated');

      // Any other response requires a signin.  Redirect.  
      } else {
        next.scope.isAuthenticated = false;
        next.scope.user = null;
        $rootScope.$broadcast('authenticationRequired', $location.url());
        $location.path('/signin');
      }
    });
  }
});

Then in my security factory, I listened for the event and stored the location, like so:

$rootScope.$on('authenticationRequired', function(event, callingRoute) {
redirectRoute = callingRoute;
});
like image 1
Léo Lam Avatar answered Nov 13 '22 17:11

Léo Lam