linux?sed/awk命令檢索區(qū)間日志的問題
開發(fā)時如果需要檢索一段時間內(nèi)或者某個批量執(zhí)行期間的所有日志,也就是區(qū)間日志時,手動檢索會有一些問題:
- 如要查詢一段時間前的日志(比如歸檔日志),需要一頁一頁翻,費時且費眼睛
- 使用
grep篩選日志,但是只能搜索滿足特定字段的日志,無法檢索區(qū)間日志
為了實現(xiàn)區(qū)間日志的檢索,可以使用sed/awk命令。這兩個命令都無法直接處理壓縮文件,需要先使用zcat讀取壓縮文件再通過管道傳遞。
1 grep+sed
sed是一個流編輯器,它一次讀取一行文本,處理一行并輸出一行,要檢索日志區(qū)間時,主要使用
-- 1.行號匹配,輸出從startrow行到endrow行的內(nèi)容 sed -n 'startrow,endrowp' filename -- 2.字符匹配,輸出從匹配start的行到end的行的內(nèi)容 sed -n '/start/,/end/p' filename
行號匹配注意:
startrow,endrow為起始行號,結(jié)束行號,p為打印命令(print)sed默認(rèn)處理一行之后會輸出一行,因此需要使用-n+p來取消自動打印,只打印我們需要的行- 如果只有一個行號,則打印指定行
- 打印到末尾,則區(qū)間為
startrow,$
字符匹配注意:
sed匹配字符時,一旦匹配到start則會一直輸出內(nèi)容直到匹配到end,因此:
- 如果文件包含多個順序
start...end,則會分批輸出 - 如果只有
start,沒有end,則會從start輸出到文件末尾 - 如果文件內(nèi)容為
start...start...end...end,那么會輸出從第一個start到第一個end區(qū)間里內(nèi)容
匹配區(qū)間時候一般使用(真實使用這個最方便):
-- 1. 使用grep定位行號(如果是壓縮文件,則使用zcat filename.tar.gz|grep -n "xxx") grep -n "開始日志標(biāo)志" filename -- 2. 找到上述命令輸出行號,比如 510:xxxxx,在該行號上面+大致區(qū)間長度即可,壓縮文件同樣使用zcat+管道 sed -n '510,550p' filename
2 awk
sed一般只用于簡單的文本轉(zhuǎn)換編輯,比如查找替換,但awk命令是一個更強大的文本處理器,可以處理更復(fù)雜的命令,比如計算、分析。
awk采用“模式-動作”對執(zhí)行模型,命令基本結(jié)構(gòu)是:
pattern {action}
pattern {action}
...對于輸入流/文件里的每一行,awk會依次檢查每個pattern,如果匹配成功,則執(zhí)行對應(yīng)的action,如果某個action之后的pattern不需要繼續(xù)匹配,則需在這個action中加上next終止后續(xù)匹配。如果action缺失,則采用默認(rèn)動作{print $0},打印當(dāng)前整行。
如果要打印開始日志到結(jié)束日志中間的內(nèi)容,使用如下命令,與sed一樣,如果文件包含多組開始日志...結(jié)束日志,則會輸出所有區(qū)間:
-- 模式使用'/xxx/'表明使用正則表達(dá)式模式
-- 1.1 不包括開始日志和結(jié)束日志行
awk '/開始日志/{flag=1;next} /結(jié)束日志/{flag=0} flag' filename
-- 1.2 包括開始日志和結(jié)束日志行
awk '/開始日志/{flag=1} flag; /結(jié)束日志/{flag=0}' filename
-- 2. 語法糖,打印從開始日志行到結(jié)束日志行內(nèi)的所有內(nèi)容(包括首尾兩行)
awk '/開始日志/,/結(jié)束日志/' filename命令1.1的流程為:
- 當(dāng)匹配
開始日志行時,將開關(guān)變量flag置1,然后執(zhí)行next跳過后續(xù)模式動作處理,直接讀取下一行 - 假設(shè)下一行是中間行,那么前兩個正則匹配模式都失敗,進(jìn)行第三個
flag模式,這是一個表達(dá)式模式,檢查flag的值。當(dāng)它非0或非空時為true,然后采用默認(rèn)動作{print $0},打印當(dāng)前整行,因此中間行能被打印 - 當(dāng)匹配
結(jié)束日志行時,開關(guān)變量flag置0,繼續(xù)下一個模式,此時flag表達(dá)式判斷為false,因此不打印
這個流程完成了從開始日志行到結(jié)束日志行之間內(nèi)容的打印。1.2同樣可以按照這個流程分析,它會打印包括開始日志行和結(jié)束日志行在內(nèi)的所有區(qū)間內(nèi)容。
命令2是范圍模式,格式為pattern1,pattern2 {action},是一種特殊模式,它表示從第一次匹配pattern1的行開始,到第一次匹配pattern2的行結(jié)束,之間的所有行都執(zhí)行action動作。action缺失則打印整行。
3 sed/awk查找特定重復(fù)區(qū)間
當(dāng)某功能或任務(wù)執(zhí)行多次時,可能有多個任務(wù)開始...任務(wù)結(jié)束區(qū)間:
1: 任務(wù)開始 2: ... 10: 任務(wù)結(jié)束 11: xxxx 12: 任務(wù)開始 13: ... 22: 任務(wù)結(jié)束 ...
3.1 查找第一個區(qū)間
sed/awk查找第一個區(qū)間日志都是在輸出完后退出,sed使用q,awk使用exit:
sed -n '/任務(wù)開始/,/任務(wù)結(jié)束/p; /任務(wù)結(jié)束/q' filename
awk '/任務(wù)開始/{flag=1} flag; /任務(wù)結(jié)束/{print;exit}' filename
awk '/任務(wù)開始/,/任務(wù)結(jié)束/; /任務(wù)結(jié)束/{exit}' filename3.2 查找第n區(qū)間
如果想要找到第n組日志可以用awk定義計數(shù)器(sed不支持復(fù)雜操作):
awk '/任務(wù)開始/{cnt++} cnt==2{print} /任務(wù)結(jié)束/ && cnt==2 {exit}' filename3.3 最后一組/最新組
sed,awk都是流處理,無法回溯信息,因此無法得知當(dāng)前區(qū)間是否是最后一次,所以最新一組日志需要使用反轉(zhuǎn)命令找第一次結(jié)束日志...開始日志區(qū)間,再倒轉(zhuǎn)即可。
tac filename | sed -n '/任務(wù)結(jié)束/,/任務(wù)開始/p; /任務(wù)開始/q' filename
tac filename | awk '/任務(wù)結(jié)束/{flag=1} flag; /任務(wù)開始/{flag=0;exit}' | tac
tac filename | awk '/任務(wù)結(jié)束/,/任務(wù)開始/; 任務(wù)開始/{exit}' | tac到此這篇關(guān)于linux sed/awk命令檢索區(qū)間日志的問題的文章就介紹到這了,更多相關(guān)linux檢索區(qū)間日志內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
linux shell 腳本實現(xiàn)tcp/upd協(xié)議通訊(重定向應(yīng)用)
這篇文章主要介紹了linux shell 腳本實現(xiàn)tcp/upd協(xié)議通訊(重定向應(yīng)用),需要的朋友可以參考下2015-10-10
使用Shell 腳本實現(xiàn)每隔100行插入一條記錄且記錄第一列包含行號其他列不變
本文通過實例代碼給大家講解了使用Shell 腳本實現(xiàn)每隔100行插入一條記錄且記錄第一列包含行號其他列不變的實現(xiàn)方法,非常不錯,具有參考借鑒價值,需要的朋友參考下2016-12-12
centos 設(shè)置定時任務(wù)執(zhí)行指定腳本的方法
下面小編就為大家?guī)硪黄猚entos 設(shè)置定時任務(wù)執(zhí)行指定腳本的方法。小編覺得挺不錯的,現(xiàn)在就分享給大家,也給大家做個參考。一起跟隨小編過來看看吧2017-02-02
shell腳本實現(xiàn)的網(wǎng)站日志分析統(tǒng)計(可以統(tǒng)計9種數(shù)據(jù))
這篇文章主要介紹了shell腳本實現(xiàn)的網(wǎng)站日志分析統(tǒng)計,可以統(tǒng)計9種數(shù)據(jù),如訪問量、帶寬、訪客量、IP統(tǒng)計、搜索引擎等,需要的朋友可以參考下2014-05-05

