不要忽略代碼執行的錯誤

2021-02-14 叻道
本文章的主題材料是《每個程式設計師應該知道的97件事》裡的第26件事

(Don't Ignore that Error!)

老規矩,先分享書裡這個章節的大意,再寫「命題作文」 不處理程序的錯誤會導致脆弱的、不安全的甚至無法維護的代碼。 https://97-things-every-x-should-know.gitbooks.io/97-things-every-programmer-should-know/content/en/thing_26/個人簡評:它講了一個非常普通的道理——小錯不改會鑄成大錯。然而,我覺得作者有些混淆了代碼錯誤和技術債務:錯誤就是錯誤,而債務並不一定是錯誤。

不要忽略代碼執行的錯誤

一般來說,代碼執行的錯誤是無法避免的,因為代碼的執行無法脫離外部依賴。再簡單的代碼至少還依賴著本地的I/O,更不用說現在的網際網路服務背後的系統架構了——每一個核心模塊都有著大量的外部依賴。 然而,即使代碼執行出錯如分布式架構中單機故障那般平常,我們還是需要正視和處理這個問題。嚴格來說,我們是無法忽略程序的錯誤的。哪怕我們寫出如下鴕鳥策略的代碼,這個錯誤始終會轉變成另一個錯誤的形式表現出來,而且很可能是一種我們難以捉摸的形式出現。 注意,忽略程序錯誤和積累技術債務並不是一回事。前者是試圖去掩蓋問題,掩耳盜鈴之舉;而後者更多是對現有局限的妥協,卻不意味著不處理已知的錯誤,只是無法系統性或者完備地解決問題。債務的問題在於積累多了還的代價太大,而不是它現在就造成問題;而錯誤已經造成問題了,個人掩蓋只是蒙蔽一部分人而言。處理代碼執行錯誤需要根據業務需求而定:要不消除它對正常業務邏輯的影響,要不將它當作業務錯誤進行處理。比如,外部服務調用出錯,如果業務需求不苛刻,我們能使用簡單的重試(re-try)方式提高業務可用性;如果業務邏輯本身是錯誤的,即有bug,修復就可以了;如果錯誤無法修正,那麼將其作為一種業務錯誤場景進行處理。有的時候我們希望能在業務整體上考慮業務錯誤場景的處理,然而在現實的工程研發中我們往往很難也沒必要做到這一點。作為研發的個體或具體小團隊,我們負責的研發工作往往只是系統架構的一部分,而不是整體。這是符合複雜系統或應用的高內聚低耦合設計的。在架構設計的時候,每個模塊的職責範圍本該明確,包括對功能錯誤的定義。如果每次考慮錯誤都需要對從整體架構進行優化,這是一種比較低效的做法。對於具體功能模塊內的錯誤,我們要不試著在保證模塊功能需求的情況下提高模塊的健壯性,要不將模塊錯誤向上層調用匯報。而將錯誤隱藏起來,向上層匯報業務正常,這對於最終用戶而言這依然會是一個業務錯誤;而對於調試業務錯誤的人來說這是一個噩夢,因為無法直接發現錯誤信息去定位原因。隱藏服務的初始化錯誤是一個常見的反例。在大多時候服務的初始化錯誤意味著服務無法正常工作。與其讓壞掉的服務繼續啟動,不如直接讓服務啟動失敗。前者往往會產生許多意想不到的奇怪錯誤,白白耽誤錯誤定位的工夫,後者則能夠讓錯誤在第一時間暴露。如果是代碼改動導致的初始化錯誤,這往往危害不是很大,只要代碼籤入前有基本的模塊功能的自動化驗證過程;這只是讓發現問題難一些些。然而,有的服務初始化錯誤只會在產品環境出現,比如產品環境的資源配置出問題了,隱藏服務的初始化錯誤的後果往往是嚴重的。分布式服務的初始化錯誤,如果單機因為本地資源問題無法初始化成功,一般會觸發架構級別的容錯機制確保用戶請求不再分發到故障的單機。然而,如果服務初始化錯誤後服務依舊正常啟動,它可能還是接受用戶請求卻無法正常服務,成為一個不易發現的壞點。如果是多輪的會話業務場景,而且負載均衡建立在簡單的無狀態輪詢策略上,少數的壞點便足以讓整個會話業務達到不可用的嚴重程度。

關於業務錯誤和異常錯誤的處理,之前的文章《理解業務錯誤才能做好異常處理》做過一些介紹。感興趣的可以看看那篇文章,在此便不複述了。

來個「分享、點讚、在看」吧👇

想了解叻道?請看此處!

感謝你的關注!

相關焦點

  • 代碼的錯誤處理(Error Handling)方式之一
    第三節 代碼的錯誤處理(Error Handling)方式之一大家好,我們今日講解代碼在遇到錯誤時的錯誤處理方式:On Error Resume Next語句的利用。這講代碼是什麼意思呢?1  On Error Resume Next 的理解On Error Resume Next語句的動作會在代碼運行錯誤發生時,控制代碼轉到緊跟在發生錯誤的語句後面的語句, 並繼續執行。On Error Resume Next導致繼續執行緊跟導致運行時錯誤的語句,或繼續執行緊跟包含 On Error Resume Next 語句的過程外部的最新調用的語句。此語句允許繼續執行,而不管運行時錯誤。
  • 【20190426】- VBA代碼中錯誤處理的小技巧
    上圖中,是因為在數組name_arr中,沒有匹配到name的項,所以發生了錯誤,可以使用On Error語句指定錯誤發生時應採取的操作:一、忽略錯誤並允許VBA繼續執行代碼 On Error我們可以利用Err對象在正常運行代碼的過程中獲得代碼中的錯誤信息。比如說,上例中,我既想讓代碼順利執行完畢,又想得到如果發生了錯誤,要告訴用戶具體是什麼錯誤。我們就利用Err對象展示錯誤信息。
  • 代碼的錯誤處理(Error Handling)方式之三
    l程序在運行過程中我們可以用On Error Resume Next語句屏蔽掉某段代碼中可能出現的預知的不要處理的錯誤,如果接下來,一切是未知的,我們需要啟動錯誤處理或者錯誤的捕獲,就可以用On Error GoTo 0 來實現。
  • 分享,HTTP協議錯誤代碼大全
    4xx(請求錯誤):這些狀態代碼表示請求可能出錯,妨礙了伺服器的處理。416  (請求範圍不符合要求) 如果頁面無法提供請求的範圍,則伺服器會返回此狀態代碼。417  (未滿足期望值) 伺服器未滿足"期望"請求標頭欄位的要求。5xx(伺服器錯誤)這些狀態代碼表示伺服器在嘗試處理請求時發生內部錯誤。這些錯誤可能是伺服器本身的錯誤,而不是請求出錯。
  • Python代碼運行報錯怎麼辦?!—常見的異常錯誤整理
    1、有錯誤才是正常的  在程式設計師的日常工作中,錯誤幾乎每次調試都在發生,例如我們會在輸入代碼時不小心漏掉或者錯誤的輸入一個標點,就會造成計算機無法準確理解代碼的含義。因此在我們大段大段的輸入代碼時,「筆誤」是不可避免的。遇到錯誤提示無需擔心,絕大多數都是可以通過仔細調試來解決的。
  • Promise裡的代碼為什麼比setTimeout先執行
    當拿到一段JavaScript代碼時,瀏覽器或者Node環境首先要做的就是;傳遞給JavaScript引擎,並且要求它去執行。然而,執行JavaScript並非一錘子買賣,宿主環境當遇到一些事件時,會繼續把一段代碼傳遞給JavaScript引擎去執行,此外,我們可能還會提供API給JavaScript引擎,比如setTimeout這樣的API,它會允許JavaScript在特定的時機執行。
  • 《使命召喚戰區》錯誤代碼3136怎麼辦 錯誤代碼3136解決方法
    導 讀 使命召喚:戰區錯誤代碼3136解決方法 使命召喚:戰區有時會遇到連不上遊戲時候,提示錯誤代碼,該怎麼解決呢
  • 代碼的錯誤處理(Error Handling)方式之二
    第四節 代碼的錯誤處理(Error Handling)方式之二在上一節,我們講解了錯誤處理語句On Error Resume Next及其應用,利用這種語句來處理錯誤,可以忽視發生的錯誤,繼續運行之後的語句。今日我們來講解錯誤處理的第二種方式:On Error GoTo line 語句,這種語句緊跟一個錯誤處理語句的行編號或者標籤。
  • .NET程序優化不要僅僅盯著代碼執行時間
    【IT168 技術】其實很多寫.NET程序的開發人員都很喜歡通過一些計時器來看來一程序或代碼的運行效率,的確這樣是可以計算出代碼執行所損耗的時間。  所以優化.net程序的時候不要忘了GC這東西,解決他的辦法只有一個就是分析那裡產生內存,想盡辦法去產生內存的地方給幹了(說得有點粗爆).前段時間了解了一個對象序列化組件,測試了一下性能發現其效率真的很出色。
  • 《steam》錯誤代碼118什麼意思 錯誤代碼118介紹
    導 讀 《steam》錯誤代碼118什麼意思?
  • ASP錯誤處理
    簡單介紹ASP是非常簡單的,以至於許多的開發者不會去思考錯誤處理。錯誤處理能夠讓你的應用程式更加合理。我看到過很多個用ASP編寫的商業網站,大多數都忽略了錯誤處理。錯誤的類型有三種主要的錯誤類型: 編譯錯誤:這種錯誤出現一般都是代碼的語法問題。因為編譯錯誤而導致辭ASP停止運行。 運行錯誤這個錯誤是發生在你準備運行ASP時的。例如:如果你試圖給一個變量賦值,但是卻超出了該變量允許的範圍。
  • 宋寶華:讓Linux的段錯誤(segmentation fault)不再是一個錯誤
    但是我們忽略了一個事實,int c = *k; 這句話,本身,是一定會引起段錯誤的,因為用戶空間做了越權訪問。其實,在熔斷漏洞的代碼中,對SIGSEGV信號,進行了特殊的處理。它截獲了SIGSEGV的信號:它實際捕獲了SIGSEGV信號,在信號發生後,修改了CPU的跳轉地址。
  • python教程之九錯誤和異常處理
    報錯信息作為新手,前面章節裡,我在敲代碼的時候,有時候敲錯了,都會報錯,Idle裡用紅色字體標識出來。Python 有兩種錯誤很容易辨認:語法錯誤和異常。語法錯誤語法分析器指出了出錯的一行,並且在最先找到的錯誤的位置標記了顏色,如下所示。
  • 寫Python代碼過程中碰到各種錯誤異常要怎麼樣去處理?
    錯誤異常即便Python程序的語法是正確的,在程序運行的過程中,也可能發生錯誤。運行期檢測到的錯誤被稱為異常。如果發生了錯誤,可以事先約定返回一個錯誤代碼,這樣,就可以知道是否有錯,以及出錯的原因。所以高級語言通常都內置了一套try...except...finally...的錯誤處理機制,Python也不例外。異常處理當我們某些代碼可能會出錯時,就可以用try來運行這段代碼。如果執行出錯,則後續代碼不會繼續執行,而是直接跳轉至錯誤處理代碼,即except語句塊。執行完except後,如果有finally語句塊,則執行finally語句塊,至此,執行完畢。
  • 代碼執行、命令執行漏洞-PHP
    代碼執行函數場景:eval()、assert()、preg_replace()、
  • 失落的龍約錯誤代碼160怎麼辦?錯誤代碼160解決辦法
    失落的龍約錯誤代碼160怎麼辦?錯誤代碼160解決辦法 失落的龍約錯誤代碼160碰到這樣的情況該怎麼辦?下面就來為大家分享一下失落的龍約錯誤代碼160的解決辦法。
  • 不要再犯SQL的這些常見錯誤了!
    但是,不要被SQL的簡單外表迷惑了,如果我們問自己:多少次我嘗試從大數據抓取數據,但是獲得了不完整或者錯誤的數據?答案是:太多次了,連自己都數不清!而正是因為SQL代碼不輕易報錯(通常只要語法正確,都會返回一些數據,但未必是你本來想要的),我們反而需要花更多的精力去校對,確保數據的準確性。
  • 致命錯誤!Python開發者的7個崩潰瞬間
    具有面向對象編程背景的開發人員容易忽略Python的慣用特性,很可能會濫用編程結構,從而產生不可預見且很難捕捉的錯誤。更糟糕的是,大多數錯誤很難發現,可能在後續工作中造成麻煩。下文匯總了程式設計師(尤其是新手)可能犯的常見錯誤,以及該如何糾正這些錯誤,編寫更好的、無錯誤的Python代碼。讓我們開始吧!
  • VBA中的錯誤轉移語句!
    有時候,在代碼運行中,會因為某些原因造成錯誤而導致程序運行中斷,而我們希望能夠忽略這些錯誤,跳轉到指定的語句繼續執行,這時候就會用到錯誤轉移語句。這種語句我們可以稱之為錯誤轉移語句,下面介紹下常用的兩種錯誤轉移語句。
  • 【Excel技巧】- VBA代碼提示運行時錯誤 '1004': 應用程式定義或對象定義錯誤
    因為按照正常的編寫VBA代碼來說,不會出現這個問題。我自從大二自學VBA以來到現在,寫了那麼多VBA代碼,也沒有遇到過一次這樣的問題。所以這個問題的出現的確讓我感到困惑,所以我從頭開始梳理代碼,按F8一條一條的調試,調試方法如下: