关于
Buy Me a Coffee
归档
友链
猫咪
RSS
后台
切换模式
返回顶部
首页
说说
日常
开发
游戏
资源
虚拟货币
首页
说说
日常
开发
游戏
资源
虚拟货币
关于
Buy Me a Coffee
归档
友链
猫咪
RSS
后台
axios较完美的超时以及重试失败解决方案
开发
·
2020-01-06
·
更新于 2020-06-26
LiesAuer
### 代码引用 1. [Retry Solution From KyleRoss@github](https://github.com/axios/axios/issues/164#issuecomment-327837467 "Retry Solution From KyleRoss@github") 2. [Timeout Solution From aarcangeli@github](https://github.com/axios/axios/issues/2143#issuecomment-495994940 "Timeout Solution From aarcangeli@github") ### axios 的 retry 解决方案 见:[Retry Solution From KyleRoss@github](https://github.com/axios/axios/issues/164#issuecomment-327837467 "Retry Solution From KyleRoss@github") ### axios 的 timeout 问题 在`0.18.0`版本中`axios`的`timeout`并没有被正确实现导致有可能在弱网环境或不稳定环境或代理环境下`timeout`无效、程序卡住的情况(见:[Axios will not timeout on idle sockets](https://github.com/axios/axios/issues/2143 "Axios will not timeout on idle sockets")),虽然这问题在`0.19.0`版本中修复了,但是`0.19.0`版本中对配置合并的规则的阻断性更新导致我们的重试失败解决方案失效(见:[Axios 0.19.0 issue](https://github.com/axios/axios/issues/2397 "Axios 0.19.0 issue")),所以我们无法升级到`0.19.0`来解决这个问题。 ### 用 CancelToken 替代 timeout 根据 [@aarcangeli](https://github.com/aarcangeli "@aarcangeli") 提供的 [CancelToken 代替方案](https://github.com/axios/axios/issues/2143#issuecomment-495994940 "CancelToken 代替方案"),我们可以很轻松的解决上面所述的 timeout 问题。 ```js const CancelToken = axios.CancelToken; const source = CancelToken.source(); let timeout = setTimeout(() => source.cancel('Timeout'), 5000); axios.get('http://localhost:3000', { timeout: 1000, cancelToken: source.token }) .then(() => { clearTimeout(timeout); console.log('hello there') }); ``` ### 最终解决方案 ```js const axios = require('axios'); timeout = 10000; // BUG: https://github.com/axios/axios/issues/2143 // axios.defaults.timeout = timeout; axios.defaults.retry = 3; axios.defaults.retryDelay = 1000; function axiosRetryInterceptor(err) { var message, config; if (axios.isCancel(err)) { message = err.message.message; config = err.message.config; } else { message = err.message; config = err.config; } config.clearCancelToken(); // If config does not exist or the retry option is not set, reject if(!config || !config.retry) return Promise.reject(new Error(message)); // Set the variable for keeping track of the retry count config.__retryCount = config.__retryCount || 0; // Check if we've maxed out the total number of retries if(config.__retryCount >= config.retry) { // Reject with the error return Promise.reject(new Error(message)); } // Increase the retry count config.__retryCount += 1; // Create new promise to handle exponential backoff var backoff = new Promise(function(resolve) { setTimeout(function() { resolve(); }, config.retryDelay || 1); }); // Return the promise in which recalls axios to retry the request return backoff.then(function() { console.log(`请求失败,重试中:${config.url}`); return axios(config); }); } axios.interceptors.request.use(function (config) { const CancelToken = axios.CancelToken; const source = CancelToken.source(); let token = setTimeout(() => source.cancel({message:'Timeout', config: config}), timeout); config.cancelToken = source.token; config.clearCancelToken = () => clearTimeout(token); return config; }); axios.interceptors.response.use(function (response){ response.config.clearCancelToken(); return response; }, axiosRetryInterceptor); axios.get("https://example.com/").then(response => { console.log(response.data); }, error => console.log(error)); ``` ### 注意事项 `npm install`时请指定`axios`版本为`0.18.0`,因为上面的代码针对的都是`0.18.0`版本的`axios`。 ```shell npm install axios@0.18.0 --save ```
如果您觉得文章或项目对您有帮助,戳我请博主喝一杯咖啡叭!
取消回复
提交评论
33
2021-06-29
回复
232
瞅一瞅叭
域名出售
uterminal.ai
服务器推荐
RackNerd 2C2G $20.98/年(美国 隐藏款)
狗云 1C0.75G ¥150/年(香港 BGP)
最新评论
tinker: 为什么运行一段时间就会停止,重启又恢复!没有报错信息,频道信息和...
pansoo: 大佬,这个只能下载文件吗?能不能保存频道消息
Miller: 最好再多加一个查漏补缺的功能(捂脸(/ω\)),因为抓取了3天才...
Miller: 大佬,好像不会爬取jpeg文件,图片和视频数量对不上,是不是图片...
cola: 大佬,可以爬取电报频道的评论内容嘛
Miller: 大佬我终于会了,用cmd命令cd /d G:\cco,感谢大佬指点!
Miller: https://img13.chkaja.com/files/2...
关于站长
广东 佛山
liesauer#liesauer.net
LiesAuer
CC BY-NC-SA 4.0
粤ICP备16094588号-1
萌ICP备20245567号
Theme
Jasmine
by
Kent Liao
232