首頁  >  文章  >  後端開發  >  應對惡劣網路環境,為php-curl設定逾時限制,防止伺服器卡死

應對惡劣網路環境,為php-curl設定逾時限制,防止伺服器卡死

WBOY
WBOY原創
2016-07-29 09:11:011280瀏覽

挖洋貨這項目,因為沒有公司的名頭,也就無法備案,所以前端機放在阿里雲香港ECS,另配一台阿里雲杭州ECS來跑crontab——執行爬蟲、保存圖片到阿里雲OSS等。最近覺得杭州ECS有點多餘了(原本還有個杭州RDS的,統一搬到香港RDS了),打算撤掉,就把杭州ECS上的crontab全部搬回香港ECS來跑,這下就引發不少問題了。
引發什麼問題了?最核心的問題是香港ECS處在國際網路環境,造訪大陸伺服器時常會出現網路抖動的現象,非常無解。具體來說,例如香港ECS向阿里雲杭州open searchopen search沒有香港節點呀親╥﹏╥...)查詢的時候,經常報錯;又例如香港ECS抓到圖片後上傳杭州OSS(OSS是有香港節點,問題是沒有圖片處理的服務啊,你們說這不是坑死人嗎),慢是其次,經常卡住一段時間後才報錯,這使得上傳的效率極度低下(我會告訴你就因為這個原因,積壓了好幾千爬回來的商品等著上傳圖片才能上架嗎)。

open search的問題還是很好解決的,SDK有提供超時的配置,我把超時限制設大了一點(5秒),基本上就不會報錯了。
而OSS的SDK根本沒有提供這方面的配置,為了解決這個問題,我決定深入到這SDK來修改源碼。
OSS的SDK是透過php-curl來請求api的,經調查後,我發現此SDK有個名為requestcore.class.php的檔案中定義了一個RequestCore類,很明顯,這個類別就是負責發送請求的。其中,prep_request()負責配置curl,send_request($parse = false)則負責執行curl(即真正發送請求)。
首先來看看prep_request(),其中包含兩個php-curl的兩個超時配置:CURLOPT_TIMEOUT以及CURLOPT_CONNECTTIMEOUTdURL. 0);curl_setopt($ curl_handle, CURLOPT_CONNECTTIMEOUT, 120);


CURLOPT_TIMEOUT

好理解,就是整個curl請求過程(http request & response)的超時限制,以秒為單位,設定為0則無限制。

CURLOPT_CONNECTTIMEOUT比較難理解,目前確認的是,這是curl請求過程中的一小部分,因此必須要設得比CURLOPT_TIMEOUT
小,不然CURLOPT_TIMEOUT無意義。網路上的資料是這麼說的:CURLOPT_CONNECTTIMEOUT 在發起連線前等待的時間,如果設定為0,則無限等待。

這個

發起連接前等待的時間

比較模糊,我傾向於這指的是完成
TCP三次握手

過程前所耗費的時間,或者換句話說,TCP三次握手的整個過程必須在CURLOPT_CONNECTTIMEOUT內完成,否則就超時。 TCP三次握手無法在指定時間內完成表示伺服器正處於繁忙/奔潰的狀態或網路異常,這正符合本文所提到的場景。 基於這個猜想下,我把CURLOPT_CONNECTTIMEOUT設成3秒:
curl_setopt($curl_handle, CURLOPT_CONNECTTIMEOUT, 3);

就在網路中抖動的時候的
CURLOPT_CONNECTTIMEOUT

是120秒)才報錯了。

PS:如果想要設定超時時間少於1秒,需要用到

CURLOPT_TIMEOUT_MS,但此配置據鳥哥說有bug,未測試,留個心眼:《Curl的毫秒超時的一個”Bug”》

以上就介紹了 應對惡劣網路環境,為php-curl設定超時限制,防止伺服器卡死,包括了crontab,保存圖片方面的內容,希望對PHP教程有興趣的朋友有所幫助。

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn