log 的 debug()、 error()、 info()方法的區別

軟件中總免不了要使用諸如 Log4net, Log4j, Tracer 等東東來寫日志,不管用什么,這些東東大多是大同小異的,一般都提供了這樣5個日志級別:
??? × Debug
??? × Info
??? × Warn
??? × Error
??? × Fatal
??????? 一個等級比一個高,但是在具體開發中,關于應該如何選擇適應的等級,卻沒有找到好的文章進行說明。記錄一下自己的一些看法,以便日后使用吧。

=== Debug ===
??????? 這個級別最低的東東,一般的來說,在系統實際運行過程中,一般都是不輸出的。


??????? 因此這個級別的信息,可以隨意的使用,任何覺得有利于在調試時更詳細的了解系統運行狀態的東東,比如變量的值等等,都輸出來看看也無妨。


??????? 當然,在每一個 Debug 調用之前,一定要加上 If 判斷。

=== Info ===
??????? 這個應該用來反饋系統的當前狀態給最終用戶的,所以,在這里輸出的信息,應該對最終用戶具有實際意義,也就是最終用戶要能夠看得明白是什么意思才行。


??????? 從某種角度上說,Info 輸出的信息可以看作是軟件產品的一部分(就像那些交互界面上的文字一樣),所以需要謹慎對待,不可隨便。

=== Warn、Error、Fatal ===
??????? 警告、錯誤、嚴重錯誤,這三者應該都在系統運行時檢測到了一個不正常的狀態,他們之間的區別,要區分還真不是那么簡單的事情。我大致是這樣區分的:


??????? 所謂警告,應該是這個時候進行一些修復性的工作,應該還可以把系統恢復到正常狀態中來,系統應該可以繼續運行下去。


??????? 所謂錯誤,就是說可以進行一些修復性的工作,但無法確定系統會正常的工作下去,系統在以后的某個階段,很可能會因為當前的這個問題,導致一個無法修復的錯誤(例如宕機),但也可能一直工作到停止也不出現嚴重問題。

??????? 所謂Fatal,那就是相當嚴重的了,可以肯定這種錯誤已經無法修復,并且如果系統繼續運行下去的話,可以肯定必然會越來越亂。這時候采取的最好的措施不是試圖將系統狀態恢復到正常,而是盡可能地保留系統有效數據并停止運行。

??????? 也就是說,選擇 Warn、Error、Fatal 中的具體哪一個,是根據當前的這個問題對以后可能產生的影響而定的,如果對以后基本沒什么影響,則警告之,如果肯定是以后要出嚴重問題的了,則Fatal之,拿不準會怎么樣,則 Error 之。

示例代碼:

/*** <p>Title: 用戶登錄處理</p>* <p>Description: </p>* @param loginId* @return  redirect page*/
@RequestMapping("/user/login.vw")
public String login(HttpServletRequest request, HttpServletResponse response, 
ModelMap model, @ModelAttribute("login") @Validated CusLogin login,
BindingResult bindingResult) throws Exception {
log.debug("用戶登錄開始......");
//1.檢查登錄信息對象:null判斷
if (null ==  login) {
log.error("用戶登錄失敗-登錄信息不存在");
bindingResult.addError(
new FieldError(
ErrorMsg.USERNOTEXIST[0], 
ErrorMsg.USERNOTEXIST[0],
ErrorMsg.USERNOTEXIST[1]));  
request.getSession().setAttribute(LOGINSTATE, "1");
login = new CusLogin();
//1:代表登錄時用戶輸入的信息有誤
login.setLoginState("1");
login.setPasswd("");
model.addAttribute("login", login);
return INDEX;
}
//2字段格式檢查
if (bindingResult.hasErrors()) {
List<ObjectError> ers = bindingResult.getAllErrors();
for (ObjectError e : ers) {
log.error(e.getDefaultMessage());
}
//has error
log.error("用戶登錄失敗-請求參數錯誤;username=" + login.getLoginNm());
//redirect index.jsp
request.getSession().setAttribute(LOGINSTATE, "1");
login.setLoginState("1");
login.setPasswd("");
model.addAttribute("login", login);
return INDEX;
}//3. 第一登錄失敗,再次登錄需輸入驗證碼,判斷驗證碼是否正確
if("1".equals(request.getSession().getAttribute(LOGINSTATE))){
if (login.getVerCode() == null || !login.getVerCode().equalsIgnoreCase(VerCodeMaker.verImgGet(session))) {
VerCodeMaker.verImgDel(request);
log.error("用戶登錄失敗-驗證碼檢查失敗;username=" + login.getLoginNm());
bindingResult.addError(
new FieldError(
ErrorMsg.VERCODEEROOR[0], 
ErrorMsg.VERCODEEROOR[0],
ErrorMsg.VERCODEEROOR[1]));  
request.getSession().setAttribute(LOGINSTATE, "1");
login.setLoginState("1");
login.setPasswd("");
model.addAttribute("login", login);
return INDEX;
}
}try {
//no error 
//4.獲取登錄用戶信息:條件為用戶名和用戶類型
LoginUsersDto dto = loginService.login(login);
if (null == dto || StringUtility.isEmpty(dto.getLoginName())) {
bindingResult.addError(
new FieldError(
ErrorMsg.USERNOTEXIST[0], 
ErrorMsg.USERNOTEXIST[0],
ErrorMsg.USERNOTEXIST[1]));  
log.error("用戶登錄-查詢用戶信息失敗,不存在或DB數據錯誤;username=" + login.getLoginNm());
request.getSession().setAttribute(LOGINSTATE, "1");
login.setLoginState("1");
login.setPasswd("");
model.addAttribute("login", login);
return INDEX;
}//4. 密碼檢查
boolean isPwdExist = loginService.passwordChk( dto.getLoginName(), login.getPasswd(), dto.getPassword());
if (!isPwdExist) {
bindingResult.addError(
new FieldError(
ErrorMsg.PWDERROR[0], 
ErrorMsg.PWDERROR[0], 
ErrorMsg.PWDERROR[1]));  
request.getSession().setAttribute(LOGINSTATE, "1");
login.setLoginState("1");
login.setPasswd("");
model.addAttribute("login", login);
log.error("用戶登錄-密碼檢查失敗;username=" + login.getLoginNm());
return INDEX;
}//3.獲取用戶認證及支付信息
PayAuthInfoDto payInfoDto = payService.getPayAuthInfoByCusCode(dto.getCusCode());
//4. 創建SESSION數據
User user = new User();
if (null != payInfoDto) {
user = UserSession.userSet(dto , payInfoDto);
} else {
user = UserSession.userSet(dto);
}
UserSession.setUser(request, user);
log.debug("用戶登錄結束");} catch (BizException e) {
log.info("用戶登錄失敗;username=" + login.getLoginNm(),e);
bindingResult.addError(
new FieldError(
ErrorMsg.UNKNOWEXPCTION[0], 
ErrorMsg.UNKNOWEXPCTION[0], 
ErrorMsg.UNKNOWEXPCTION[1])); 
login.setPasswd("");
model.addAttribute("login", login);
return INDEX;
} catch (Exception e) {
log.info("用戶登錄失敗,username=" + login.getLoginNm(),e);
bindingResult.addError(
new FieldError(
ErrorMsg.UNKNOWEXPCTION[0], 
ErrorMsg.UNKNOWEXPCTION[0], 
ErrorMsg.UNKNOWEXPCTION[1]));  
login.setPasswd("");
model.addAttribute("login", login);
return INDEX;
} finally{
request.getSession().removeAttribute(LOGINSTATE);
}return REUSERINDEX;
} 

心得:

log.error() 一般是需要if()的;

log.info()一般是在try ?catch 里面

log.debug() 做記錄一般標志著方法的開始和結束。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/451323.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/451323.shtml
英文地址,請注明出處:http://en.pswp.cn/news/451323.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

存儲容量(空間)換算公式(B、KB、MB、GB、TB、PB、EB)

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 <strong>存儲容量&#xff1a;是該存儲設備上可以存儲數據的最大數量&#xff0c;通常使用千字節&#xff08;kb kilobyte&#x…

如何防止表單的重復提交

表單重復提交是在多用戶Web應用中最常見、帶來很多麻煩的一個問題。有很多的應用場景都會遇到重復提交問題&#xff0c;比如&#xff1a; (1)點擊提交按鈕兩次。 (2)點擊刷新按鈕。 (3)使用瀏覽器后退按鈕重復之前的操作&#xff0c;導致重復提交表單。 (4)使用瀏覽器歷史記錄重…

GDB調試精粹及使用實例

一&#xff1a;列文件清單 1&#xff0e; List (gdb) list line1,line2 二&#xff1a;執行程序 要想運行準備調試的程序&#xff0c;可使用run命令&#xff0c;在它后面可以跟隨發給該程序的任何參數&#xff0c;包括標準輸入和標準輸出說明符(<和>)和外殼通配符&a…

如何使用log.debug()

log4j是一個開源的日志&#xff0c;共分為六個等級&#xff1a;LOG、DEBUG、INFO、WARN、ERROR、和FATAL。 DEBUG是其中的一種日志級別。一般我們用這個方法的時候都是這樣的&#xff1a; if(log.isDebugEnabled()){log.debug("debug&#xff01;"); } 意思是&am…

寫給大數據開發初學者的話

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 導讀&#xff1a; 第一章&#xff1a;初識Hadoop 第二章&#xff1a;更高效的WordCount第三章&#xff1a;把別處的數據搞到Hadoop上第…

2018年7月份,python上傳自己的包庫到pypi官網的方法

最近pypi官網進行了更新&#xff0c;老的上傳網址作廢了。記錄下上傳到pypi的方法 0、去pypi官網注冊賬號&#xff0c;沒賬號是不可能上傳的&#xff0c;想想也是那不亂套了嗎&#xff0c;注冊后會收到一個郵件需要點擊然后重新登錄 1、目錄就是這樣 &#xff0c;我要上傳muli…

linux系統C語言學習總結

引言   盡管 C 語言問世已近 30 年&#xff0c;但它的魅力仍未減退。C 語言繼續吸引著眾多的開發者&#xff0c;他們為了編寫、移植或維護應用程序而必須學習新技能。   本文是為了滿足對C語言初學者或想提高自身C語言修為的開發人員的需要而寫的。希望對您的學習和工作有…

redis 刪除操作

Redis 鍵(key) Redis 鍵命令用于管理 redis 的鍵。 語法 Redis 鍵命令的基本語法如下&#xff1a; redis 127.0.0.1:6379> COMMAND KEY_NAME 實例 redis 127.0.0.1:6379> SET runoobkey redis OK redis 127.0.0.1:6379> DEL runoobkey (integer) 1 在以上實例中 DEL 是…

寫給大數據開發初學者的話2

見 : http://lxw1234.com/archives/2016/11/782.htm 如果你已經按照《寫給大數據開發初學者的話》中第一章和第二章的流程認真完整的走了一遍&#xff0c;那么你應該已經具備以下技能和知識點&#xff1a; 0和Hadoop2.0的區別&#xff1b;MapReduce的原理&#xff08;還是那個…

Pandas的結構和應用

Pandas處理以下三個數據結構 - 系列(Series)----一維ndarray   特點&#xff1a;帶有標簽&#xff0c;可以使用標簽作為索引&#xff0c;大小不能改變&#xff0c;內部數據可以改變。 屬性&#xff1a;與NumPy類似&#xff0c;多了一個軸標簽axis lables 數據…

JZOJ5857 【NOIP提高組模擬A組2018.9.8】沒有上司的舞會

題目 Description “那么真的有果爾德施坦因這樣一個人?”他問道。 “是啊&#xff0c;有這樣一個人&#xff0c;他還活著。至于在哪里&#xff0c;我就不知道了。” “那么那個密謀——那個組織?這是真的嗎?不是秘密警察的捏造吧?” “不是&#xff0c;這是真的。我們管…

python 中如何判斷list中是否包含某個元素

在python中可以通過in和not in關鍵字來判讀一個list中是否包含一個元素 theList [‘a’,’b’,’c’] if ‘a’ in theList: print ‘a in the list’ if ‘d’ not in theList: print ‘d is not in the list’

時間即財富:創業者浪費精力的八個錯誤

導讀&#xff1a;本文作者Jeff Miller是美食網頁應用Punchfork的創始人&#xff0c;同時也是DuckDuckGo、Ginzametrics、Art.sy、DataMinr以及Forkly的投資人。作者通過對自己創業初期一些錯誤選擇進行盤點&#xff0c;告訴讀者在創業初期應該學會選擇&#xff0c;因為在創業初…

寫給大數據開發初學者的話3

前些天發現了一個巨牛的人工智能學習網站&#xff0c;通俗易懂&#xff0c;風趣幽默&#xff0c;忍不住分享一下給大家。點擊跳轉到教程。 如果你已經按照《寫給大數據開發初學者的話2》中第三章和第四章的流程認真完整的走了一遍&#xff0c;那么你應該已經具備以下技能和知識…

十五周二次課

18.6 負載均衡集群介紹 主流開源軟件LVS、keepalived、haproxy、nginx等其中LVS屬于4層&#xff08;網絡OSI 7層模型&#xff09;&#xff0c;nginx屬于7層&#xff0c;haproxy既可以認為是4層&#xff0c;也可以當做7層使用keepalived的負載均衡功能其實就是lvslvs這種4層的負…

LeetCode--171--Excel表列序號

問題描述&#xff1a; 給定一個Excel表格中的列名稱&#xff0c;返回其相應的列序號。 例如&#xff0c; A -> 1B -> 2C -> 3...Z -> 26AA -> 27AB -> 28 ...示例 1: 輸入: "A" 輸出: 1示例 2: 輸入: "AB" 輸出: 28示例 3: 輸入: "…

中國歷代王朝大排名

中國自秦以降&#xff0c;一共出過九個大王朝&#xff0c;它們是&#xff1a;秦、漢、晉、隋、唐、宋、元、明、清。另外&#xff0c;還出過五十幾個小王朝&#xff0c;它們是&#xff1a; 三國時的魏、蜀、吳&#xff0c;共三個&#xff1b; [ 轉自鐵血社區 http://bbs.tiexue…

寫給大數據開發初學者的話4

見&#xff1a;http://lxw1234.com/archives/2016/11/795.htm 如果你已經按照《寫給大數據開發初學者的話3》中第五章和第六章的流程認真完整的走了一遍&#xff0c;那么你應該已經具備以下技能和知識點&#xff1a; 為什么Spark比MapReduce快。使用SparkSQL代替Hive&#xff…

TPS及計算方法

TPS (transaction per second)代表每秒執行的事務數量&#xff0c;可基于測試周期內完成的事務數量計算得出。例如&#xff0c;用戶每分鐘執行6個事務&#xff0c;TPS為6 / 60s 0.10 TPS。同時我們會知道事務的響應時間(或節拍)&#xff0c;以此例&#xff0c;60秒完成6個事務…

域名解析服務之DNS查詢類型

在實際應用中DNS查詢主要分為兩種方式查詢&#xff1a;1.遞歸查詢&#xff1b;2.迭代查詢 一般情況下&#xff1a;為了減少資源的消耗&#xff0c;網絡中客戶端與所屬的本地DNS服務器查詢方式通常為遞歸查詢&#xff0c;本地DNS服務器與外部的公共DNS服務器間的查詢方式為迭代查…