重定向时的 AngularJS 无限循环

AngularJS infinite loop when redirecting

本文关键字:无限循环 AngularJS 重定向      更新时间:2023-09-26

我有一个登录的应用程序,并且必须决定用户是否可以访问某些页面,如果他们已登录。我遇到的问题是,在到达某个路线时,我不需要模板,但我调用服务来处理将它们发送到登录页面或让他们继续。该服务会检查它们是否已登录,如果没有,则使用 window.location.href 将它们发送到登录路由。

当它到达 window.location.href 行时,登录控制器被无限初始化(达到 10 次 $digest(( 迭代(,之后没有任何工作。就哈希重定向而言,我是否缺少一些东西?

这只发生在IE9中。循环问题不会发生在 chrome 或 safari 中。

路由代码:

angular.module('myApp', []).config(['$routeProvider', function($routeProvider) { 
$routeProvider
  .when('/login', {templateUrl: 'partials/login.html', controller: 'LoginCtrl', title:'Login'})
  .when('/register', {template  : " ", controller:  'RegisterCtrl', title:'Register'})
  .when('/eBooks', {resolve: {redirect: 'LoginRouter'}});
}]);

用于处理登录路由的服务:

.service('LoginRouter', ['RouteService', '$rootScope', '$window',  function(RouteService, $rootScope, $window) {        
if (!$rootScope.isLoggedIn) {
    RouteService.setModule("eBooks");
    $window.location.href = "#/login"; // Causing infinite loop
}
else {
    var config = $rootScope.config; 
    $rootScope.startLoading();
    $window.location.href = config.EBOOK_URL+ "&bookId=" + config.bookId.replace("-","");
}
}]);

登录控制器:

.controller('LoginCtrl',['$scope' ,'LoginService', function ($scope, LoginService) {
    $scope.user = {mtn: ""};
    $scope.checkUser = function() {
        LoginService.validateUser($scope);
    };
}]); 

注意:我更改了代码以指向带有锚标记和 href 指向"登录"的 html 模板,它工作得很好。只有当我直接通过窗口触发位置更改时,它才会卡在循环中。

更新:我从登录.html模板中删除了所有内容,以查看 html 中的某些内容是否导致了问题,删除了控制器范围和 rootScope 上的所有指令以及任何功能/模型,但问题仍然发生。

更新 2 我尝试使用 angular 强制单击锚点以尝试绕过问题,但它仍然发生。我注意到的一件有趣的事情是,如果我在IE中打开控制台窗口,那么问题甚至不会首先发生。这是怎么回事????

我建议使用绝对路径,以确保一些不太聪明的浏览器(IE!(理解你的代码。尝试添加原点:

 window.location.href = $window.location.origin + "#/login"; 

附带说明一下,我认为您使用$window.location.href而不是$location做对

这就是官方 AngularJS 文档推荐的内容 - 请参阅此处:

页面重新加载导航

$location服务只允许您更改 URL;它不允许您重新加载页面。当您需要更改 URL 并重新加载页面或导航到其他页面时,请使用较低级别的 API $window.location.href。

事实证明,问题实际上是我在整个应用程序中的控制台日志语句。我最终将它们全部注释掉,一切开始正常。我想这可以解释为什么当我打开控制台时一切正常。不得不爱上IE。

如果其他人像我一样遇到这种情况,要考虑的另一件事是在服务器上建立一个基本 URL。

例如,我的服务器将根重定向到 '/home' 。因此,'www.mydomain.com'将通过我的 Web 服务器路由约束重定向到 'www.mydomain.com/home'。这完全搞砸了IE9(同时使用角度(,并导致它在'/home'之后而不是之前尝试进行哈希爆炸,这将导致URL继续构建'/home#!/home#!/home#!/...'等等。

一旦我放宽了服务器端重定向规则,允许主页'/''/home',IE9 再次开始工作,将哈希爆炸放在站点的根目录 (www.mydomain.com/#!/home( 而不是在'/home'之后。

另外,不要忘记添加一个角度路由来处理根 URL。例如:

$routeProvider.when('/', {templateUrl: '/templates/home.html', controller: 'homeCtrl'})

希望这对其他人有所帮助。