Search code examples
javascriptangularjsangular-promiseangular-http-interceptors

Angular HTTP within a HTTP Interceptor


I need to append the necessary HMAC headers to a request. This should not be very difficult however I am starting to get frustrated. What is wrong with the following code. The actual http call I am doing works; I have run this call myself and it returns the necessary data. It does not work inside the interceptor.

I merely want to get the current implementation working before I add whitelist or blacklist and other customizable data for this interceptor. This is not a question about hmac however but with promises.

The error in this interceptor is with the entire promise line starting at $http(...). When i remove this block and use it as is (minus promise execution) it works fine. As soon as i uncomment the line it gets stuck in a loop and crashes chrome. Everywhere I have read says this is how it is done, but this clearly does not work.

function requestInterceptor(config){
  var $http = $injector.get('$http');
  var deferred = $q.defer();

  $http.get(hmacApiEndpoint, {cache: true}).then(function(data){
    console.log('HMAC - Success', data)
    deferred.resolve(config)
  }, function(config){
    console.log('HMAC - Error', config)
    deferred.resolve(config)
  })

  return deferred.promise;
}

return {
  request: requestInterceptor
};

Does this have something to do with the fact that angulars $http promise is a different implementation than that of '$q'?


Solution

  • It doesn't look like you are actually amending the config with the newly obtainted HMAC.

    Also, you'd need to protect against your requestInterceptor intercepting the call to obtain the HMAC, thus resulting in an infinite loop.

    And lastly, you don't need deferred here - just return the promise produced by $http (or $http.then()):

    function requestInterceptor(config){
      var $http = $injector.get('$http');
    
      // just return, if this is a call to get HMAC
      if (config.url === hmacApiEndpoint) return config;
    
      return $http.get(hmacApiEndpoint, {cache: true})
        .then(function(response){
          console.log('HMAC - Success', response.data)
    
          // not sure where the HMAC needs to go
          config.headers.Authorization = response.data;
          return config;
        })
        .catch(function(){
           return $q.reject("failed to obtain HMAC");
        });
    }
    
    return {
      request: requestInterceptor
    };