我正在一个可以搜索食物的网站上工作,看看它是水果,蔬菜还是两种食物(因为我很无聊)。我决定使用Angular,尽管我对它很陌生。 我开始收到此错误:$rootScope:infdig Infinite $digest Loop
这可能是也可能不是确切的措辞或错误,因为页面滞后这么多,我无法打开Javascript控制台。
这是我的结果视图控制器:
app.controller('resultController', ['$scope', '$routeParams', '$http',
function($scope, $routeParams, $http) {
$scope.result = $routeParams.query;
$scope.whatIsIt = function() {
$http.get('json/foods.json').success(function(data) {
var lists = JSON.parse(data);
var itIsA = 'uuggghhhhh';
if (lists['fruit'].contains($scope.result)) {
itIsA = 'fruit';
} else if (lists['vegetable'].contains($scope.result)) {
itIsA = 'vegetable';
}
});
}
}]);
继承我的app模块:
var app = angular.module('fruitOrNot', [
'ngRoute'
]);
app.config(['$routeProvider' ,
function($routeProvider) {
$routeProvider.when('/', {
templateUrl: 'layouts/fruit-search.html',
controller: 'searchController'
}).when('/:query', {
templateUrl: 'layouts/result.html',
controller: 'resultController'
});
}]);
这是layouts / result.html:
<h1>{{ result }}</h1>
<p>{{ result }} is a {{ whatIsIt() }}</p>
所以我想知道可能导致$digest
循环错误的原因,或者如何查找,因为我无法使用控制台。谢谢!
整个项目也在Github上here。
答案 0 :(得分:4)
您遇到的问题是您在作用域上设置了一个字段,该字段隐式调用$digest
并再次布局模板。但是,布局模板再次发出http请求,然后更改范围,调用$ digest。这就是无限循环。
您可以通过确保在模板布局期间永远不会触发http请求来避免这种情况。
实现应用程序的更正确的方法是将您的GET请求提取到适当的服务中,然后将您的服务注入控制器。
然后在控制器中,您进行服务调用,如下所示:
app.controller('resultController', ['$scope', '$routeParams', 'whatsitService',
function($scope, $routeParams, $http) {
$scope.result = $routeParams.query;
whatsitService.doit().then(function(result) {
$scope.whatsit = result;
}
})
;
您的模板如下所示:
<h1>{{ result }}</h1>
<p>{{ result }} is a {{ whatsit }}</p>
答案 1 :(得分:3)
问题是您尝试调用函数并直接发布返回值,并且您尝试返回的值超出范围。您需要将该值放在范围内。
代码段:
app.controller('resultController', ['$scope', '$routeParams', '$http',
function($scope, $routeParams, $http) {
$scope.result = $routeParams.query;
$scope.itIsA = "";
$scope.whatIsIt = function() {
$http.get('json/foods.json').success(function(data) {
var lists = JSON.parse(data);
var itIsA = 'uuggghhhhh';
if (lists['fruit'].contains($scope.result)) {
$scope.itIsA = 'fruit';
} else if (lists['vegetable'].contains($scope.result)) {
$scope.itIsA = 'vegetable';
}
});
}
}]);
并在HTML模板中:
p>{{ result }} is a {{itIsA}}</p>
答案 2 :(得分:0)
无限$ digest循环可能发生在下面这种情况下,如果你绑定了一个表达式,如:{{events()}}
和
$scope.events = function() {
return Recording.getEvents();
}
但不是在下面的情况。即使你绑定了{{events}}
$scope.events = Recording.getEvents();
原因在于第一个角度假设每个摘要循环中的值都在变化,并且它会不断更新它。在第二个中,它只是等待承诺。
答案 3 :(得分:0)
这是因为你的角度表达式'{{ whatIsIt() }}
'正在发生
“{{ result }} is a {{ whatIsIt() }}
”您正在调用一个函数,每次调用时返回一个不同的值,从而导致一个新的摘要循环,从而调用该函数。
我认为你应该将whatIsIt()
的结果绑定到一个值,然后在模板中使用该值。检查一下https://docs.angularjs.org/error/ $ rootScope / infdig