使用拦截器处理200 HTTP响应的错误

时间:2015-11-30 10:21:32

标签: angularjs ngresource

我有与外部API集成的服务。此API不一致,不太可能更改。

内部API有两种报告错误的方法,一种是使用HTTP 500代码的响应,另一种是正常的200 HTTP响应,但JSON中的status设置为“错误”。

处理500错误工作正常,我刚刚用responseError方法创建了拦截器(ngResource拦截器,而不是$ http),当API有任何500响应时,它将向用户显示错误消息:

.factory('ApiErrorHandling', ['ngDialog', function(ngDialog) {
    return {
        responseError: function(response) {
            console.log(response);
            var error_dialog = ngDialog.open({
                template: '/api/error.html',
                className: 'error',
                preCloseCallback: function() {
                    if (response.data.status == 'fatal') {
                        window.location.href = '/';
                    } else if (response.data.status == 'error') {
                        var dialogs = ngDialog.getOpenDialogs();
                        for (var i in dialogs) {
                            var dialog = dialogs[i];
                            if (dialog != error_dialog.id) {
                                ngDialog.close(dialog);
                            }
                        }
                    }
                },
                data: {
                    code: response.data.code,
                    status: response.data.status,
                    message: response.data.message,
                    httpCode: response.status,
                }
            });
        },
    }
}])
.factory('ApiMethod', ['$resource', 'ApiErrorHandling', function($resource, ApiErrorHandling) {
    return $resource('/api/method/', {}, {
            query: {method:'POST', interceptor: ApiErrorHandling},
    });
}])

但我在使用status处理错误回复时遇到问题。我不希望在发生错误时调用正常的成功回调(从资源实例传入方法),我想要一个全局错误处理程序,但到目前为止我还没有尝试过。每次响应都传递回调。到目前为止我已经尝试过了:

  • 从拦截器
  • 返回response方法中的$ q.reject
  • 更改状态代码以响应拦截器中的500 response方法
  • 从拦截器
  • 更改或删除response方法中的response.resource

理想的解决方案是在不调用普通回调时,而是调用拦截器中的responseError方法。

2 个答案:

答案 0 :(得分:3)

  

但我在处理状态错误响应时遇到问题。我不希望在发生错误时调用正常的成功回调(从资源实例传入方法),我想要一个全局错误处理程序,但到目前为止我还没有尝试过。每次响应都传递回调。到目前为止我已经尝试过了:

     

从拦截器

返回响应方法中的$ q.reject

要拒绝您不喜欢的回复,请使用throw

function inteceptor(httpPromise) {
    var newPromise = (httpPromise
        .then(function(response) {
                  if (dontLike) {
                      throw response;
                  } else {
                      return response;
              },
              function (eResponse) {
                  if (iLike) {
                      return eResponse;
                  } else {
                      throw eResponse;
                  };
              })
     );
     return newPromise;
};

从拦截器

var chainedPromise = (interceptor(httpPromise)
    .then (function (response) {
         //render data
         return response;
    }).catch (function (error) {
         console.log(error);
         throw error;
    })
);

答案 1 :(得分:1)

我找到了解决方案。我认为是ngResource模块中的一些错误。

注册回拨时:

ApiMethod.query({'get_parameter': 1}, {'post_json': 2}, function(result) {
    something...
});

只有防止调用回调的解决方案才会从ngResource拦截器抛出错误。但是在承诺中注册回调时:

ApiMethod.query({'get_parameter': 1}, {'post_json': 2}).$promise.then(function(result) {
    something...
});

只需从拦截器返回$q.reject即可阻止调用回调。

重写所有回调注册可以解决问题。