[英]Defer creation of controllers/services on app run angularjs
每次更改路线时,我都会检查是否使用当前登录的用户详细信息设置了变量,如果未设置此变量,我将直接重定向到登录页面。
现在,我正在尝试实现某种“记住我”功能,因此,每次路由更改时,如果不存在变量用户,而不是重定向到登录页面,我都会在本地存储中检查“ authtoken”,如果设置了if,我将调用将身份验证令牌传递到服务器的检查功能,该功能将返回用户,并且该应用程序的工作方式与手动登录后相同(返回与检查功能相同的用户)。
我敢肯定这不是最好的方法。
如果重新加载页面,则第一件事是运行检查功能,该功能将authtoken发送到服务器并等待响应(如果用户存在,则将值分配给rootscope中的变量)。
我有不同的服务,例如,使用rootscope中的变量
angular.module('myApp')
.service('AdminService', function AdminService($rootScope, $http, StorageService) {
var authtoken = StorageService.get('authtoken');
var clientId = $rootScope.loggedUser.id;
当然,当check函数运行时,它会等待响应,但是正在实例化该服务,并且$ rootScope.loggedUser.id不存在。
如何通知应用程序等待检查功能收到响应?
这是我的代码
....
}).run(function($rootScope, $location, AuthService, StorageService) {
var intended = $location.path();
AuthService.check().success(function(data) {
if(data.user) {
$rootScope.loggedUser = data.user;
$location.path(intended);
} else $location.path('login');
});
$rootScope.$on('$routeChangeStart', function() {
if($rootScope.loggedUser) {
....
例如,如果用户将页面“ myapp.com/#/admin/users”添加为书签,则我不想重定向到登录名(如果我在本地存储中拥有authtoken),但是这会导致控制器实例化,使用需要尚未填充的$ rootScope.loggedUser.id的服务。
我想仅在页面(重新)加载时运行功能检查(而不是在用户每次更改路线时都运行)。
如果您需要服务电话来检查您的身份验证令牌,我建议您重新检查您的设计。 身份验证令牌通常在其中存储了过期时间,因此您无需致电服务器就可以检查自己是否在过期期内。 您不会损害安全性,因为身份验证令牌是由服务器签名的,并且在您进行服务器调用以进行任何有用的操作时都会经过验证。 因此,在正常情况下,不需要单独的check
调用。
但是,如果您坚持认为,最好用路由的resolve
属性来处理此用例。 但是,这意味着,每个关心用户登录状态的路由都必须定义一个resolve属性。 这并不意味着您必须在每次更改路线时都调用该服务。
与其使用$rootScope.loggedUser
来存储用户, AuthService
将其由AuthService
缓存并通过resolve
参数注入。
因此,您可以执行以下操作:
$routeProvider
.when("some/secure/route", {
controller: "SecureCtrl",
resolve: {
user: AuthService.checkUser
}
});
在您的AuthService中:
...
checkUser: function(){
var deferred = $q.defer();
if (cachedUser){
deferred.resolve(cachedUser);
} else {
AuthService.check().success(
function(data){
// cachedUseris defined at AuthService's scope
cachedUser = data.user;
deferred.resolve(data.user);
});
}
return deferred.promise;
}
然后,在您的控制器中:
.controller("SecureCtrl", function(user){
$scope.userId = user.id;
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.