I am having issues trying to gracefully handle $http errors. I am looping over a list of servers to make API calls to for status. The calls that complete successfully for perfectly. The ones that fail are not giving me access to the error information. It is always undefined. Here is the code snippet:
angular.forEach($scope.servers, function (server) {
// blank out results first
server.statusResults = {};
$http.jsonp(server.url + '/api/system/status?callback=JSON_CALLBACK', {headers: { 'APP-API-Key': server.apiKey }}).
success(function (data, status, headers, config) {
server.statusResults = data;
}).
error(function (data, status, headers, config) {
// data is always undefined here when there is an error
console.error('Error fetching feed:', data);
});
}
);
The console output shows the correct 401 error (which I didn't output) and my console error message (which I did output) with an undefined data object.
GET https://server_address/api/system/status?callback=angular.callbacks._1 401 (Unauthorized) angular.min.js:104
Error fetching feed: undefined
What I am trying to do is NOT have Angular display the 401 in the log, and instead I will display it in a graceful way. However since data is undefined I have no way of accessing the information.
I am new to AngularJS, but my example closely matches other examples I've found in the documentation.
I've also tried using $resource instead of the $http and got the exact same problem.
var statusResource = $resource(server.url + '/api/system/status', {alt: 'json', callback: 'JSON_CALLBACK'},
{ status: {method: 'JSONP'}, isArray: false, headers: { 'APP-API-Key': server.apiKey } });
// make status API call
statusResource.status({}, function (data) {
server.statusResults = data;
}, function (err) {
// data is always undefined here when there is an error
console.log(err);
});
I'm probably doing something obviously wrong, but I'm not sure what else to try.
Per the $http docs, body is
The response body transformed with the transform functions.
With the 401 (Unauthorized) error you are getting back, it is quite possible there is no body being returned, hence why it is undefined.
If you want to log the error code, log the status parameter instead. It contains the HTTP Status Code, which should be uniform, unlike response bodies.
Related
I want to take a specific action when an API request results in a 404 error. I've read that the appropriated way to do this would be handling the error in the application adapter like below:
handleResponse: function(status, headers, payload){
if(status === 404 && payload.errors){
//handle error
}
return this._super(...arguments);
}
The problem is, as soon as I set up the adapter, it won't finish loading the page so I can handle the error on the page itself. Instead, it automatically takes me to some error route that just says "Adapter error". How can I stop/override this behaviour?
Turns out I needed to adjust the handleResponse hook in the application adapter to pass the new requestData parameter to the super method.
handleResponse (status, headers, payload, requestData) {
return this._super(status, headers, payload, requestData);
},
Then I just changed the first line of the code in my question from
handleResponse: function(status, headers, payload) {
to
handleResponse: function(status, headers, payload, requestData) {
I was then able to catch and handle the error
Perhaps you could handle it on a request basis like below:
return this.get('store').find('user', userId).then((user) => {
this.set('user', user);
}).catch((reason) => {
var possible404 = reason.errors.filterBy('status','404');
if(possible404.length !== 0) {
// Handle 404 error
}
});
Although this is not the solution that you wanted, this alternative will allow you to customize more. By the way, the automatic behavior seems to be the application-error substates kicking in on 404, so give it a read if you want to override the behavior.
This is probably something very simple but I am having some problem making an HTTP GET request, getting the data back, and attaching it onto the javascript global window variable.
Simple HTTP Call:
$http.get("production/dashboard?dashboard_type=A").success((data) ->
$scope.pods = data;
window.pods = $scope.pods.to_json;
window.type = 'A';
alert(window.pods)
alert(window.type)
alert "success1"
return
).error (data, status, headers, config) ->
return
Upon execution, I am getting:
1. Alert("undefined")
2. Alert("A")
I thought that the promise of the http request will get resolved when the response returns?
I checked the Network tab and there is indeed JSON data being sent back as the response to the request.
I must be missing something simple...
$http.get("production/dashboard?dashboard_type=A")
.success(function(data) {
$scope.pods = data;
window.pods = $scope.pods;
window.type = 'A';
alert(window.pods);
alert(window.type);
alert("success1");
return
}).error (function(data, status, headers, config){
return;
});
This is assuming it has access to the window where your code is. Is this wrapped in a module and controller?
As we need json data to get from $http.. Trying putting .json like below.
$http.get('/products.json')
Regarding your another issue.. you might get a hint with this link AngularJS : Prevent error $digest already in progress when calling $scope.$apply()
I have the following mechanism (ignore the simplicity for the moment please) when a user clicks on a button on a dead simple login form:
$scope.login = function () {
$http.post('/rest/authenticate', {
userName: $scope.userName,
password: $scope.password
}).
success(function (data, status, headers, config) {
//handle success, etc
}).
error(function (data, status, headers, config) {
//hanlde errors, etc
});
};
The method is calling a REST service that could return a String as an answer if the proper credentials are provided or an error (400, 401) if they are not good. The success method gets executed when the good user/pass is given and the error function also executes if the REST call returns some HTTP error.
My problem is that if any kind of error happens, BEFORE the error method gets executed, angular displays the error in the browser console like this:
POST http://server.address/rest/authenticate 400 (Bad Request)
This originates from angular.js (line 8113):
xhr.send(post || null);
It even displays it before a http interceptor's 'responseError' method. Using non-compressed angular version 1.2.14
How can I turn this unnecessary logging off?
zeroflagL's comment is valid and I found no solution to this "issue"
I am new to AngularJS. I have a .net MVC WebAPI Restful app running on a IIS server. When I query the api with http://xxx.xxx.xxx.xxx/api/project I get:
[{"Id":1,"Name":"Glenn Block","Created":"0001-01-01T00:00:00"},{"Id":2,"Name":"Dan Roth","Created":"0001-01-01T00:00:00"}]
I created a ProjectCtrl (in a separate empty project) that looks like this:
angular.module('Project', ['ngResource']);
function ProjectCtrl($scope, $resource) {
$scope.project = $resource('http://192.168.1.221/api/project'
);
$scope.project.get(function (data) {
console.log('success, got data: ', data);
}, function (err) {
alert('request failed');
});
}
I always get a failure. I addressed CORS issues on the server and the request header contains
Access-Control-Request-He... x-requested-with
Access-Control-Request-Me... GET
What I find odd is that when I look in firebug it does NOT do a get but rather shows Option project with a status of 200
I am not sure what I missing.
The error mentioned in your comment, "Error: a.push is not a function", is because your response is an array. With $resource, use the query function when your response is an array.
I think the first parameter of the resource call should be resource-based params. If you have none, pass an empty object {} as the first parameter:
$scope.project.get({},function (data) {
console.log('success, got data: ', data);
}, function (err) {
alert('request failed');
});
My guess is that your err object is actually the successfully returned data. If I'm wrong, tell me and I'll delete!
I have a basic CRUD application up and running, however what I am wanting to do is wrap every response from the server with two additonal parameters namely
'error' => boolean, 'errorMessage' => string, 'data' => {whatever data}
so that I can handle when a successful request is sent and returned from the server, however the database was unable to update for some reason so I can not only keep the UI in sync with the DB, but also present the user an error message on a failed update.
As AngularJS expects an updated object the UI will be in sync if I return the same object on failure, but as there would be no notification of failure the user wouldn't realize what the problem is.
Within my old applications pre-Angular (jQuery based) I could easily decode the json data on every response and if error === true present an error message, but in Angular I cannot seem to figure out how to accomplish this.
I may very well be off base here as I am just getting into Angular so any direction would be helpful.
Make this http request from angularjs and send back a response object from server.
response object --->{'error' => boolean, 'errorMessage' => string, 'data' => {whatever data}}
which gets collected in Resdata. use Resdata to take action.
$http({method: 'POST', url:url, data:body}).success(function(Resdata, status, headers, config) {
console.log(Resdata);
if(Resdata.error == true){
// use Resdata.errorMessage
}
else if(Resdata.error == false){
// use Resdata.data
}
}).error(function(Resdata, status, headers, config) {
console.log("error:", error);
});