這個項目最初我是PM,當時要求集羣達到60000tps,單服務器要能達到2000tps,這個要求說實話的確有些誇張,最終結果雖然沒這麼高,但單臺服務器主要流程的確能達到近1000tps,這不是重點。我負責的項目交付一期之後,交給另一位同事繼續後續的二期的開發,這個項目後續在甲方重視程度很高,至今仍有大量人力在支持這個項目。有一天這個項目的PM給我打電話,說最近系統出現一個奇怪的現象,很是小的機率會出現500錯誤,一旦出現錯誤之後,再訪問都是500錯誤,只有重啓才能解決,cpu和內存使用率都很是的低,沒有任何的錯誤日誌,他們已經分析了幾天了,一點兒思路也沒有,今天又出現了。tomcat
之前看這這樣一句話「全部沒有日誌的問題定位都是耍流氓」,可是現實狀況就是不耍流氓就不行,問題擺在面前。服務器
6點吃過晚飯和同事一塊兒到了客戶的辦公場所,由於這是我以前負責的項目,裏面的流程和代碼我比較熟悉,可是一時也沒有思路,惟一的思路就是這個500頁面,靈光一現,能不能在這個500頁面裏作文章,由於我知道在j2ee中會在request和session的attribute寫一些屬性,會不會這裏有一些線索。因而我在這臺出現500錯誤的jsp頁面裏面加了一堆把request和session裏全部的attribute都讀出來的代碼,這下子信息量就大了不少,發現了在attribute有一個error,一步步的推斷是底層的平臺拋出的錯誤,再進一步結合代碼反編譯發現是咱們使用的底層平臺在使用線程變量的時候在異常處理的時候沒有將ThreadLocal的值清空致使後面再進來的請求讀取的是空對象,也也致使了NPE,這樣推測下咱們找到了平臺的同事一塊兒分析,他們在Review代碼之後也認可有問題,很快他們修復了bug,至此再沒出現過。session
這個問題自己從技術來說並無太多好玩的東西,可是讓我更加堅信問題總有解決的辦法,更加全面的掌握各類知識加上實踐會讓你在遇到問題有更多的機會會靈光一現。問題自己並無太多的技術含量,可是當你去解決的時候,你會發現若是沒有經驗和知識儲備的話,解決起來步履維艱。jsp
有的人可能會問爲何NPE的日誌爲何會被吃掉了,而不是打印在tomcat的默認的日誌中,這是由於這個項目中把標準錯誤輸出和標準輸出都重定位到/dev/null這個垃圾桶中了. 線程