2013-10-17 35 views
4

大量的JavaScript庫和框架接受一些操作完成後調用的函數。例如:javascript:如何使用抑制回調中的異常的庫?

chrome.storage.local.get('foo', function() { console.log("foo"); }); 

但我只是意識到一些API的,包括Google上面提到的捕捉本地存儲API和抑制功能的所有異常被調用。例如,如果我修改上面的代碼有錯誤(ReferenceError,我想在控制檯查看):通過捕捉和忽略所有的錯誤

chrome.storage.local.get('foo', function() { a.b(); }); 

沒有錯誤會因爲API提高壓制它。在這種情況下如何調試我的代碼?是否有任何方法來帶回錯誤或所有這些api只是不打算用於複雜的代碼,我需要手動調試通過console.log找到什麼失敗?

更新1

簡單地增加自己的try-catch到所有回調將增加複雜的代碼,是不是真的歡迎。此外,簡單console.log比異常更糟糕,因爲開發工具捕獲異常,顯示爲紅色,附有堆棧跟蹤等。當然,所有這些都可以用console.log進行模擬,但這會增加更多的複雜性。

更新2

好像它是JS代碼忽略誤差的ommon實踐,使我不得不通過添加下劃線插件,並用它來包圍每個回調來實現醜陋的解決方案:

function _safeblock(block) 
{ 
    console.assert(block); 
    return function() { 
    try { 
     block.apply(this, arguments); 
    } 
    catch(e) { 
     console.log(e.message, e.stack); 
    } 
    }; 
} 


function _safecall(block) 
{ 
    console.assert(block); 
    _safeblock(block)(); 
} 


_.mixin({ 
    safeblock: _safeblock, 
    safecall: _safecall, 
}); 
+1

你最終做了什麼來解決這個問題? –

+0

@BenjaminGruenbaum我通過將每個第三方回調包含到安全代碼中實現了一個醜陋的解決方案。但這只是暫時的黑客攻擊,而不是一個適當的架構解決方案。 – grigoryvp

回答

3

你可以嘗試自己抓住它們。

chrome.storage.local.get('foo', function() { 
    try{ 
     a.b(); 
    }catch(e){ 
     console.log(e); 
     //do whatever 
    } 
}); 

您可以通過覆蓋storage.local.get或通過創建一個通用的函數包裝自動化此。

您也可以推遲函數的setTimeout手動這將使它不可能(在瀏覽器)的庫來抑制你的錯誤

chrome.storage.local.get('foo', function() { 
    setTimeout(function(){ 
      a.b(); 
    }); 
}); 

這不會給你非常有意義的堆棧跟蹤,但(東西外該函數不會顯示),這使得它不太有用。如果你在性能敏感的情況下使用它(也可能在瀏覽器中setTimeout至少需要幾個毫秒,儘管它有一個postMessage hack),但它也可能是性能開銷。

+0

保護所有API調用中的所有回調將增加代碼的複雜性。 – grigoryvp

+1

你是對的,它會的。您將不得不代理所有API方法或嘗試/捕獲所有API調用。編寫API的包裝。抑制所有異常是API IMO中的一個糟糕的設計調用,特別是如果你沒有給出類似「調試模式」的東西。對於JS以外的其他語言也是如此。 –

2

你可以簡單地執行一個try-catch和使用console.error(在Firebug和Chrome DevTools作品,而不是別人肯定):

chrome.storage.local.get('foo', function() 
{ try { a.b(); } 
    catch (e) { console.error(e.name + ": " + e.message); } 
}); 

如果你不需要論據回調,您可以創建一個包裝功能:

function wrapTryCatch(func) 
{ return function() 
    { try { func.apply(this, arguments); } 
     catch (e) 
     { var err = e.name + ': ' + e.message; 
      console.error ? console.error(err) 
      : console.log ? console.log(err) 
      : alert(err); 
     } 
    } 
} 
+0

保護所有API調用中的所有回調將增加代碼的複雜性。 – grigoryvp

+0

@EyeofHell:這不太可能不是必要的罪惡,但我會做更多的研究。 –

+0

我不是說它是邪惡的,我會用這種方法,除非我找到更好的東西。但是我不想在沒有任何明確理由的情況下增加代碼的複雜性。也許這個問題是衆所周知的,它就像谷歌瀏覽器中的隱藏開關或全局java設置,可以將事情恢復到正常狀態。 – grigoryvp

相關問題