2015-05-05 2 views
2

У меня есть проект с угловым проектом, когда пользователь переходит к /cloud, и они не вошли в систему (isLoggedIn() return failed), он перенаправляется на /login. И затем, если они вошли в систему и перейдут на /login, он перенаправляет их обратно на /cloud.

Однако, когда я нажимаю на кнопку выхода из системы, чтобы очистить локальное хранилище, я получаю следующее сообщение об ошибке (все еще работает):

Error: null is not an object (evaluating 'a.$current.locals[l]')

По моим бревнам, по-видимому, происходит на onEnter для мой контроллер выхода.

Я новичок в угловом, поэтому любые советы или рекомендации будут очень благодарны.

var routerApp = angular.module('myapp', ['ui.router']) 
    //config for state changes 
    .factory('Auth', function($http, $state, $q) { 

     var factory = { isLoggedIn: isLoggedIn }; 
     return factory; 

     function isLoggedIn(token) { 
      return $http.post('/auth/session', {token:token}); 
     } 

    }) 
    .config(function($stateProvider, $urlRouterProvider, $locationProvider) { 

     $locationProvider.html5Mode(true); 
     $urlRouterProvider.otherwise('/cloud'); 

     var authenticated = ['$q', 'Auth', '$rootScope', function ($q, Auth, $rootScope) { 
      var deferred = $q.defer(); 
      if (typeof window.localStorage['authtoken'] === 'undefined') { 
       var authtoken = undefined; 
      } else { 
       var authtoken = window.localStorage['authtoken']; 
      } 
      Auth.isLoggedIn(authtoken).then(function() { 
       deferred.resolve(); 
      }, function() { 
       deferred.reject(); 
      }); 
      return deferred.promise; 
     }]; 

     var authGuest = ['$q', 'Auth', '$rootScope', function ($q, Auth, $rootScope) { 
      var deferred = $q.defer(); 
      if (typeof window.localStorage['authtoken'] === 'undefined') { 
       var authtoken = undefined; 
      } else { 
       var authtoken = window.localStorage['authtoken']; 
      } 
      Auth.isLoggedIn(authtoken).then(function() { 
       deferred.reject(); 
      }, function() { 
       deferred.resolve(); 
      }); 
      return deferred.promise; 
     }]; 

     $stateProvider 

      .state('login', { 
       url: '/login', 
       templateUrl: 'pages/templates/login.html', 
       resolve: { authenticated: authGuest } 
      }) 

      .state('logout', { url: '/logout', onEnter: function($state) { localStorage.clear(); $state.go('login'); } }) 

      .state('cloud', { 
       url: '/cloud', 
       templateUrl: 'pages/templates/cloud.html', 
       resolve: { authenticated: authenticated } 
      }) 

    }) 
    .run(function ($rootScope, $state) { 
     $rootScope.$on('$stateChangeError', function (event, from, error) { 
      if(from.name == "login") { 
       $state.go('cloud'); 
      } else { 
       $state.go('login'); 
      } 
     }); 
    }); 
+1

См. Https://github.com/angular-ui/ui-router/issues/1833 и https://github.com/angular-ui/ui-router/issues/1901 – Phil

+0

Try onEnter: function ($ state, $ window) {$ window.localStorage.clear(); $ State.go ('Войти'); } – Matho

ответ

0

Проблема, кажется, здесь:

var authenticated = ['$q', 'Auth', '$rootScope', function ($q, Auth, $rootScope) { 
     var deferred = $q.defer(); 
     if (typeof window.localStorage['authtoken'] === 'undefined') { 
      var authtoken = undefined; 
     } else { 
      var authtoken = window.localStorage['authtoken']; 
     } 
     Auth.isLoggedIn(authtoken).then(function() { 
      deferred.resolve(); 
     }, function() { 
      deferred.reject(); 
     }); 
     return deferred.promise; 
    }]; 

Эта функция будет работать только один раз на Configuration. Обещание, после того, как оно разрешилось, будет продолжать решать одно и то же значение независимо от LocalStorage. Каждый раз, когда вы

resolve: { authenticated: authenticated } 

вы получите обратно значение authenticated в Configuration шаг.

вместо этого, добавить контроллер для определения функций для запроса статуса для каждого типа

.controller('AuthenticationController', function($scope, '$q', Auth, '$rootScope') { 
     $scope.authenticated = function() { 
      var deferred = $q.defer(); 
      if (typeof window.localStorage['authtoken'] === 'undefined') { 
       var authtoken = undefined; 
      } else { 
       var authtoken = window.localStorage['authtoken']; 
      } 
      Auth.isLoggedIn(authtoken).then(function() { 
       deferred.resolve(); 
      }, function() { 
       deferred.reject(); 
      }); 
      return deferred.promise; 
     }; 

     $scope.authGuest = function ($scope, '$q', Auth, '$rootScope') { 
      .... 
      return deferred.promise; 
     }; 

    }); 

Затем в вашей конфигурации маршрутизации:

 .state('login', { 
      url: '/login', 
      templateUrl: 'pages/templates/login.html', 
      controller: 'AuthenticationController' 
      resolve: { authenticated: $scope.authGuest() } 
     }) 
     .state('cloud', { 
      url: '/cloud', 
      templateUrl: 'pages/templates/cloud.html', 
      resolve: { authenticated: $scope.authenticated()} 
     }) 

Теперь, каждый раз, когда вы будете разрешение свежего обещания.

Отказ от ответственности: Без рабочей версии для использования я создал этот код для демонстрации. Его следует рассматривать как псевдокод, ведущий в правильном направлении.

Смежные вопросы