在寫JavaScript代碼的時候,異步回調是一個很是常見的特徵。完善的回調會有和超時相關的設置,例如Ajax的timeout選項。那若是SDK提供的異步調用函數中沒有提供超時設置,在出現異常的時候就只能乾等了嗎?這固然是不能忍的。
app
咱們先構造一個沒有提供超時設置的回調函數:異步
function myTimeout(options) { options = options || {}; setTimeout(function () { options.callback("called!"); }, 5000); }
上面的代碼很簡單,5秒後回調送進去的回調函數。若是咱們要爲這個異步回調提供超時設置,例如3秒鐘超時,那麼該怎麼弄呢?函數
(function () { var oldMyTimeout = myTimeout; myTimeout = function (options) { var timeoutFlag = false; var timeoutHandle = -1; var timeout = options.timeout; var callback = options.callback; var hookCallback = function () { if(timeoutFlag == true) return; // 檢測到超時,再也不執行後面的實際回調函數 clearTimeout(timeoutHandle); // 清空超時控制器 return callback.apply(this, Array.prototype.slice.call(arguments)); //調用原始的回調函數 } options.callback = hookCallback; if(timeout > 0) { // 超時設置小於0時,不進行超時檢測 timeoutHandle = setTimeout(function() { timeoutFlag = true; callback("已經超時(" + timeout + "ms)"); }, timeout); } oldMyTimeout(options); } })();
能夠用下面代碼進行測試:測試
// called! myTimeout({ callback: function (data) {console.log(data);}, timeout: 6000 }); // 已經超時(4000ms) myTimeout({ callback: function (data) {console.log(data);}, timeout: 4000 });