如何使用 axios 拦截器?

2022-08-30 04:16:48

我看过axios文档,但它所说的只是

// Add a request interceptor
axios.interceptors.request.use(function (config) {
    // Do something before request is sent
    return config;
  }, function (error) {
    // Do something with request error
    return Promise.reject(error);
  });

// Add a response interceptor
axios.interceptors.response.use(function (response) {
  // Do something with response data
  return response;
}, function (error) {
  // Do something with response error
  return Promise.reject(error);
});

还有很多教程只显示这个代码,但我很困惑它的用途,有人可以给我一个简单的例子来遵循。


答案 1

简单来说,它更像是每个HTTP操作的检查点。已进行的每个 API 调用都通过此侦听器传递。

那么,为什么是两个拦截器呢?

API 调用由两半、一个请求和一个响应组成。由于它的行为类似于检查点,因此请求和响应具有单独的侦听器。

一些请求拦截器用例 -

假设您要在发出请求之前检查您的凭据是否有效。因此,您可以在拦截器级别检查您的凭据是否有效,而不是实际进行 API 调用。

假设您需要将令牌附加到发出的每个请求,而不是在每次 Axios 调用时复制令牌加法逻辑,您可以创建一个侦听器,该侦听器在发出的每个请求上附加一个令牌。

一些响应拦截器用例 -

假设您收到了响应,并且根据 API 响应进行判断,您希望推断出用户已登录。因此,在响应侦听器中,可以初始化处理用户登录状态的类,并在收到的响应对象上相应地更新该类。

假设您已请求某个具有有效 API 凭证的 API,但您没有访问数据的有效角色。因此,您可以从响应侦听器触发警报,指出不允许该用户。这样,您就可以避免对每个Axios请求执行的未经授权的API错误处理。

下面是一些代码示例

请求拦截器

  • 可以通过以下操作(在这种情况下,通过检查环境变量)来打印 axios 的配置对象(如果需要):

    const DEBUG = process.env.NODE_ENV === "development";
    
    axios.interceptors.request.use((config) => {
        /** In dev, intercepts request and logs it into console for dev */
        if (DEBUG) { console.info("✉️ ", config); }
        return config;
    }, (error) => {
        if (DEBUG) { console.error("✉️ ", error); }
        return Promise.reject(error);
    });
    
  • 如果要检查正在传递的标头/添加更多的通用标头,则可以在对象中使用。例如:config.headers

    axios.interceptors.request.use((config) => {
        config.headers.genericKey = "someGenericValue";
        return config;
    }, (error) => {
        return Promise.reject(error);
    });
    
  • 如果是请求,则可以在 object 中找到正在发送的查询参数。GETconfig.params

响应拦截器

  • 您甚至可以选择在拦截器级别解析 API 响应,并将解析的响应(而不是原始响应)向下传递。它可能会节省您一次又一次地编写解析逻辑的时间,以防 API 在多个位置以相同的方式使用。一种方法是在 中传递一个额外的参数,并在响应拦截器中使用相同的参数来执行操作。例如:api-request

    //Assume we pass an extra parameter "parse: true" 
    axios.get("/city-list", { parse: true });
    

    一旦,在响应拦截器中,我们可以像这样使用它:

    axios.interceptors.response.use((response) => {
        if (response.config.parse) {
            //perform the manipulation here and change the response object
        }
        return response;
    }, (error) => {
        return Promise.reject(error.message);
    });
    

    因此,在这种情况下,每当 中有对象时,操作就会完成,对于其余情况,它将按原样工作。parseresponse.config

  • 您甚至可以查看到达的代码,然后做出决定。例如:HTTP

    axios.interceptors.response.use((response) => {
        if(response.status === 401) {
             alert("You are not authorized");
        }
        return response;
    }, (error) => {
        if (error.response && error.response.data) {
            return Promise.reject(error.response.data);
        }
        return Promise.reject(error.message);
    });
    

答案 2

例如,如果要捕获从发送请求的那一刻到收到响应所花费的时间,则可以使用此代码:

const axios = require("axios");

(async () => {
  axios.interceptors.request.use(
    function (req) {
      req.time = { startTime: new Date() };
      return req;
    },
    (err) => {
      return Promise.reject(err);
    }
  );

  axios.interceptors.response.use(
    function (res) {
      res.config.time.endTime = new Date();
      res.duration =
        res.config.time.endTime - res.config.time.startTime;
      return res;
    },
    (err) => {
      return Promise.reject(err);
    }
  );

  axios
    .get("http://localhost:3000")
    .then((res) => {
      console.log(res.duration)
    })
    .catch((err) => {
      console.log(err);
    });
})();