我在我的范围内设置属性时出现问题。它确实设置但仅在第二次我点击与我的控制器绑定的按钮之后。
app.controller('ContactsController', ['$scope','$window','$http','googleService', function($scope, $window, $http, googleService) {
$scope.login = function () {
var emails =[];
var promise = googleService.login()
promise.then(function (data) {
console.log(data[0]);
gapi.client.load('gmail', 'v1', function() {
var request = gapi.client.gmail.users.messages.list({'userId' :'me',
labelIds: ['INBOX'],
});
request.execute(function(resp) {
$scope.emails = googleService.makeEmails(resp);
});
});
}
, function (err) {
console.log('Failed: ' + err);
});
};
}]);
这是我的服务方法。
this.makeEmails = function(resp){
var factory = [];
angular.forEach(resp.messages, function(message){
var newEmail = gapi.client.gmail.users.messages.get({'userId': 'me','id': message.id ,'format':'metadata', 'metadataHeaders': ['subject','from','to','date']});
newEmail.execute(function(resp) {
var emailw = resp;
factory.push(emailw);
});
});
return factory;
}
所以我单击与控制器中的click()方法绑定的按钮,在网络选项卡中,我看到所有响应都通过,当我逐步完成代码工厂时。我无法弄清楚为什么第一次点击范围没有设置但第二次点击设置它。
答案 0 :(得分:2)
你必须使用$ q
来使用promise / deferred模式https://docs.angularjs.org/api/ng/service/$q
类似这样的事情
//service
this.makeEmails = function (resp) {
//create a deferred/ promise object
var deferred = $q.defer();
var tasks = [];
//create an array of promises
angular.forEach(resp.messages, function (message) {
tasks.push(function () {
var deferred = $q.defer();
var newEmail = gapi.client.gmail.users.messages.get({
'userId': 'me',
'id': message.id,
'format': 'metadata',
'metadataHeaders': ['subject', 'from', 'to', 'date']
});
newEmail.execute(function (resp) {
deferred.resolve(resp);
});
});
});
//return the result when all the promises get executed
$q.all(tasks).then(function(result){
deferred.resolve(result);
})
return deferred;
};
//controller
googleService.makeEmails(resp).then(function(result){
$scope.emails = result;
});
答案 1 :(得分:2)
需要注意的重要事项:此处接受的答案是使用一种名为deferred antipattern的气馁做法。您应该避免这样做,因为它会导致无法正确处理错误的详细代码。
我强烈建议您使用以下方法,该方法更清晰,更强大:
//service
this.makeEmails = function (resp) {
var promises = resp.messages.map(function (message) {
return $q(function (resolve) {
gapi.client.gmail.users.messages.get({
'userId': 'me',
'id': message.id,
'format': 'metadata',
'metadataHeaders': ['subject', 'from', 'to', 'date']
}).execute(resolve);
});
});
return $q.all(promises);
};
//controller
googleService.makeEmails(resp).then(function(result){
$scope.emails = result;
});