Reputation: 57
I have method in angular controller which call service; this method should act based on the service response.
but I don't know why the method call in the right time.
$scope.UpdateSelected = function () {
$rootScope.showConfirmModal().result.then(function () {
var selectedItems = _.filter($scope.Options, { Selected: true });
var error = 0
for (var i = 0 ; i < selectedItems.length; i++) {
InvalidOptionsFactory.UpdateOptions(selectedItems[i].Id).then(function (res) {
if (res.data.error) {
error++;
}
});
}
if (error == 0) {
toastr.success($rootScope.GetString('GENERIC_SAVE_SUCCSS_MSG'));
}
else if (error == selectedItems.length) {
$rootScope.showMessageModal($rootScope.GetString('UPDATE_STATUS_FAILED'), 'sm');
}
else {
var message = hasError + $rootScope.GetString('UPDATE_STATUS_PARTIALLY_FAILED');
toastr.success(message);
}
fetchSearchedData();
});
};
I don't now why it's directly go to if statement and execute it then call the service
Upvotes: 0
Views: 836
Reputation: 1678
It is because InvalidOptionsFactory.UpdateOptions(selectedItems[i].Id)
method is asynchronous. That's what makes the app doesn't wait for the service to call, it run the if (error == 0)
statements first instead (See below snippet for proof). Learn asynchronous method here: https://www.pluralsight.com/guides/front-end-javascript/introduction-to-asynchronous-javascript
You can make your code into something like this (p.s. I used babel as the prepocessor):
$scope.UpdateSelected = function () {
$rootScope.showConfirmModal().result.then(function () {
var selectedItems = _.filter($scope.Options, { Selected: true });
checkForError(selectedItems).then(error => {
if (error == 0) {
toastr.success($rootScope.GetString('GENERIC_SAVE_SUCCSS_MSG'));
} else if (error == selectedItems.length) {
$rootScope.showMessageModal($rootScope.GetString('UPDATE_STATUS_FAILED'), 'sm');
} else {
var message = hasError + $rootScope.GetString('UPDATE_STATUS_PARTIALLY_FAILED');
toastr.success(message);
};
fetchSearchedData();
});
});
};
function checkForError(selectedItems): Promise<number> {
return new Promise(resolve => {
var error = 0;
for (var i = 0 ; i < selectedItems.length; i++) {
InvalidOptionsFactory.UpdateOptions(selectedItems[i].Id).then(function (res) {
if (res.data.error) {
error++;
};
});
};
resolve(error);
});
}
function asyncFunc(): Promise<void> {
return new Promise(resolve => {
console.log("this is async");
resolve();
});
}
asyncFunc().then(() => {
console.log("async function ended");
});
console.log("this will be called before async function ended");
Upvotes: 1