python3 解決requests出錯(cuò)重試的問題
對(duì)python3下的requests使用并不是很熟練,今天稍微用了下,請(qǐng)求幾次下來后發(fā)現(xiàn)出現(xiàn)連接超時(shí)的異常,上網(wǎng)查了下,找到了一個(gè)還算中肯的解決方法。
retrying是python的一個(gè)自帶的重試包
導(dǎo)入方式:
from retrying import retry
簡(jiǎn)單使用
retrying 這個(gè)包的用法原理就是在你不知道那段代碼塊是否會(huì)發(fā)生異常,若發(fā)生異常,可以再次執(zhí)行該段的代碼塊,如果沒有發(fā)生異常,那么就繼續(xù)執(zhí)行往下執(zhí)行代碼塊
以前你的代碼可能是這樣寫的:
def get_html(url): pass def log_error(url): pass url = "" try: get_page(url) except: log_error(url)
也有可能是這樣子寫的:
# 請(qǐng)求超過十次就放棄 attempts = 0 success = False while attempts < 10 and not success: try: get_html(url) success = True except: attempts += 1 if attempts == 10: break
使用 retrying 的寫法:
import random from retrying import retry @retry() def do_something_unreliable(): if random.randint(0, 10) > 1: raise IOError("Broken sauce, everything is hosed!!!111one") else: return "Awesome sauce!" result = do_something_unreliable() print(result)
上面的是簡(jiǎn)單的用法,你可以試下,下面是一些可選參數(shù)的使用方式。
stop_max_attempt_number
用來設(shè)定最大的嘗試次數(shù),超過該次數(shù)就停止重試
stop_max_delay
超過時(shí)間段,函數(shù)就不會(huì)再執(zhí)行了
wait_random_min和wait_random_max
用隨機(jī)的方式產(chǎn)生兩次retrying之間的停留時(shí)間
補(bǔ)充:python中Requests的重試機(jī)制
requests原生支持
import requests from requests.adapters import HTTPAdapter s = requests.Session() # 重試次數(shù)為3 s.mount('http://', HTTPAdapter(max_retries=3)) s.mount('https://', HTTPAdapter(max_retries=3)) # 超時(shí)時(shí)間為5s s.get('http://example.com', timeout=5)
requests使用的重試算法:BackOff(指數(shù)退避算法)
什么是指數(shù)退避算法
在wiki當(dāng)中對(duì)指數(shù)退避算法的介紹是:
In a variety of computer networks, binary exponential backoff or truncated binary exponential backoff refers to an algorithm used to space out repeated retransmissions of the same block of data, often as part of network congestion avoidance.
翻譯成中文的意思大概是“在各種的計(jì)算機(jī)網(wǎng)絡(luò)中,二進(jìn)制指數(shù)后退或是截?cái)嗟亩M(jìn)制指數(shù)后退使用于一種隔離同一數(shù)據(jù)塊重復(fù)傳輸?shù)乃惴?,常常做為網(wǎng)絡(luò)避免沖突的一部分”
比如說在我們的服務(wù)調(diào)用過程中發(fā)生了調(diào)用失敗,系統(tǒng)要對(duì)失敗的資源進(jìn)行重試,那么這個(gè)重試的時(shí)間如何把握,使用指數(shù)退避算法我們可以在某一范圍內(nèi)隨機(jī)對(duì)失敗的資源發(fā)起重試,并且隨著失敗次數(shù)的增加長(zhǎng),重試時(shí)間也會(huì)隨著指數(shù)的增加而增加。
當(dāng)然,指數(shù)退避算法并沒有人上面說的那么簡(jiǎn)單,想具體了解的可以具體wiki上的介紹
當(dāng)系統(tǒng)每次調(diào)用失敗的時(shí)候,我們都會(huì)產(chǎn)生一個(gè)新的集合,集合的內(nèi)容是0~2n-1,n代表調(diào)用失敗的次數(shù)
第一次失敗 集合為 0,1
第二次失敗 集合為 0,1,2,3
第三次失敗 集合為 0,1,2,3,4,5,6,7
在集合中隨機(jī)選出一個(gè)值記為R,下次重試時(shí)間就是R*基本退避時(shí)間(對(duì)應(yīng)在指數(shù)退避算法中爭(zhēng)用期) 當(dāng)然,為了防止系統(tǒng)無限的重試下去,我們會(huì)指數(shù)重新的最大次數(shù)
為什么要使用指數(shù)退避算法
使用指數(shù)退避算法,可以防止連續(xù)的失敗,從某方面講也可以減輕失敗服務(wù)的壓力,試想一下,如果一個(gè)服務(wù)提供者的服務(wù)在某一時(shí)間發(fā)生了異常、超時(shí)或是網(wǎng)絡(luò)抖動(dòng),那么頻繁的重試所得到的結(jié)果也大致都是失敗。這樣的頻繁的重試不僅沒有效果,反而還會(huì)增服務(wù)的負(fù)擔(dān)。
應(yīng)用場(chǎng)景有哪些
接入三方支付服務(wù),在三方支付提供的接入接口規(guī)范中,服務(wù)方交易結(jié)束結(jié)果通知和商戶主動(dòng)查詢交易結(jié)果都用到重發(fā)機(jī)制
在app應(yīng)用中,很多場(chǎng)景會(huì)遇到輪詢一類的問題,輪詢對(duì)于app性能和電量的消耗都過大。
代碼示例
以上為個(gè)人經(jīng)驗(yàn),希望能給大家一個(gè)參考,也希望大家多多支持腳本之家。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教。
相關(guān)文章
基于python for in if 連著寫與分開寫的區(qū)別說明
這篇文章主要介紹了基于python for in if 連著寫與分開寫的區(qū)別說明,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2021-03-03從CentOS安裝完成到生成詞云python的實(shí)例
下面小編就為大家分享一篇從CentOS安裝完成到生成詞云python的實(shí)例,具有很好的參考價(jià)值,希望對(duì)大家有所幫助2017-12-12requests.post()方法中data和json參數(shù)的使用
這篇文章主要介紹了requests.post()方法中data和json參數(shù)的使用方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-02-02Python實(shí)現(xiàn)動(dòng)態(tài)條形圖繪制的示例代碼
這篇文章主要為大家詳細(xì)介紹了如何利用Python語言實(shí)現(xiàn)動(dòng)態(tài)條形圖的繪制,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下2022-08-08pytorch: tensor類型的構(gòu)建與相互轉(zhuǎn)換實(shí)例
今天小編就為大家分享一篇pytorch: tensor類型的構(gòu)建與相互轉(zhuǎn)換實(shí)例,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2018-07-07