我有一个提交给第三方服务的表单,以便接收"令牌"。我可以指定一个回调函数来处理来自第三方服务的响应。理想情况下,此响应将是令牌,但它也可能是错误消息。回调函数在我的控制器中。在该函数中,我设置了一些其他$ scope变量,这些变量是在应用程序流程中向前推进的。
由于我没有更新的$ scope变量值而无法向前移动并且它们正在我的回调函数中设置,我认为我在使用$ watch来更新$ scope变量时触发更多事件或者我可以将其余功能放在回调函数中。
选项1(简化示例):
使用$ watch on $ scope变量在其值更新时向前移动
var myApp = angular.module('myApp',[]);
myApp.controller('GreetingController', ['$scope', function($scope) {
$scope.token = false;
$scope.$watch('token', function () {
doThis();
for(var i=0; i<len; i++) {
myFnction("Do Some", MORE_STUFF);
}
someObj.fetchGoodStuff($scope.token);
});
$scope.myCallback = function(status, response) {
if(!response.error) {
$scope.token = response.token;
}
})
}]);
选项2(简化示例):
从回调函数
var myApp = angular.module('myApp',[]);
myApp.controller('GreetingController', ['$scope', function($scope) {
$scope.token = false;
$scope.$watch('token', function () {
doThis();
for(var i=0; i<len; i++) {
myFnction("Do Some", MORE_STUFF);
}
someObj.fetchGoodStuff($scope.token);
});
$scope.myCallback = function(status, response) {
if(!response.error) {
$scope.token = response.token;
doThis();
for(var i=0; i<len; i++) {
myFnction("Do Some", MORE_STUFF);
}
someObj.fetchGoodStuff($scope.token);
}
})
}]);
对我而言,似乎更多&#34;正确&#34;隔离基本功能,在这种情况下是从第三方服务接收响应函数的响应,并将进行中的功能放在其他地方。
但是我能看到的另一个地方就是在$ watch调用的函数中...因为$ scope变量的值每页访问只更改一次,$手表似乎不合适。
有人对收到回复后采取行动的最佳方式有任何见解吗?
答案 0 :(得分:1)
您需要多少次拨打第三方服务?你需要每次都打电话还是需要打电话一次?常见的方法是使用返回promise的服务包装第三方代码。
myApp.factory('My3rdParty', ['$q', '$rootScope', function ($q, $rootScope) {
return {
getToken: function () {
var deferred = $q.defer();
doSome3rdPartyStuff(function success(token) {
// we need to trigger a digest because 3rd party lib runs out of
// angular's digest cycle
$rootScope.$apply(function (){
deferred.resolve(token);
});
}, function error(err){
$rootScope.$apply(function (){
deferred.reject(err);
});
});
return deferred.promise;
}
}
}]);
在您的控制器中,注入服务并拨打电话并使用承诺继续
myApp.controller('SomeController', ['$scope', 'My3rdParty', function ($scope, My3rdParty) {
$scope.doSomeAction = function () {
My3rdParty.getToken().then(function (token) {
alert("I got the token!");
}, function (err) {
alert("I got an error");
});
};
}]);
如果您需要向用户显示令牌,可以将其放在$ scope下, 如果您希望在控制器之外更改令牌(用户更改它,其他一些服务更改它),您可能需要$ watch,否则上面的代码就足够了。
答案 1 :(得分:0)
不要使用手表。它会在以后产生大量的开销和麻烦。仅在绝对必要时使用。您应该尝试使用承诺,并尽可能让您的服务返回承诺。如果必须向您的外发服务提供回调(无法返回承诺),请执行以下操作:
myApp.controller('GreetingController', ['$scope', '$timeout', function($scope, $timeout) {
$scope.token = false;
// Use this promise to simulate various events related to token fetching
var tokenFetched = $q.defer();
$scope.callbackYouMustHave = function(status, response) {
if (!response.error) {
tokenFetched.resolve(response.token); // or any other data you need
} else {
tokenFetched.reject(status, response); // Error handling
}
}
tokenFetched.then(function(token) {
// Triggering a digest with $timeout, a little awkward but better than watch trust me
$timeout(function() {
$scope.token = token; // This triggers a digest and changes your view / whatever
});
doThis();
for(var i=0; i<len; i++) {
myFnction("Do Some", MORE_STUFF);
}
someObj.fetchGoodStuff($scope.token);
});
tokenFetched.catch(function(status, response) {
// error handling
console.log('error fetching token:', response);
});
有。完全干净,完全可读。除非你绝对必须
,否则不要使用手表作为对此的补充,我意识到如果你使用promises,你可能需要手动触发摘要。我做了另一个编辑