日志文件分析工具


該工具可實現對日志文件的分析,可以方便地對日志文件進行類似於數據庫查詢統計一樣的操作。主要功能包括:

  • 條件篩選:包含、不包含、相等、不等、大於、大於等於、小於、小於等於、正則匹配
  • 不同條件的“或”與“並”關系可靈活控制
  • 函數:可以通過自定義AttPreProcessor對字段進行預處理,以此來實現“函數”能力
  • 分組求值:最大值、最小值、平均值、求和
  • 支持對統計結果的排序
  • 使用Limit控制輸出數量
  • 可同時處理多個文件,支持文件名通配符

按空格split

分析器認為每一行由空格分隔的每一段為一個列,例如:

120.244.106.255 - - 15/04/2019:01:38:49 +0800 "GET / HTTP/1.1" 302 -
120.244.106.255 - - 15/04/2019:01:38:49 +0800 "GET /auth.do HTTP/1.1" 302 -
120.244.106.255 - - 15/04/2019:01:38:49 +0800 "GET /loginUI.do HTTP/1.1" 302 -
120.244.106.255 - - 15/04/2019:01:39:04 +0800 "GET /loginUI.do HTTP/1.1" 200 13881
120.244.106.255 - - 15/04/2019:01:39:04 +0800 "GET /admin/filee/1ec45f5bfbd718a0e5b93a9 HTTP/1.1" 200 39735
120.244.106.255 - - 15/04/2019:01:39:05 +0800 "GET /img/favicon/favicon.ico HTTP/1.1" 404 1040
120.244.106.255 - - 15/04/2019:01:39:33 +0800 "GET /admin/filee/5f5bfbd718a0e5b93a9 HTTP/1.1" 200 39735
222.137.114.157 - - 15/04/2019:04:27:01 +0800 "GET / HTTP/1.1" 302 -
222.137.114.157 - - 15/04/2019:04:27:02 +0800 "GET / HTTP/1.1" 302 -
222.137.114.157 - - 15/04/2019:04:27:04 +0800 "GET / HTTP/1.1" 302 -
222.137.114.157 - - 15/04/2019:04:27:07 +0800 "GET / HTTP/1.1" 302 -
222.137.114.157 - - 15/04/2019:04:27:14 +0800 "GET / HTTP/1.1" 302 -
205.205.150.10 - - 15/04/2019:07:19:15 +0800 "GET / HTTP/1.1" 302 -
205.205.150.10 - - 15/04/2019:07:19:15 +0800 "GET /auth.do HTTP/1.1" 302 -
205.205.150.10 - - 15/04/2019:07:19:15 +0800 "GET /loginUI.do HTTP/1.1" 302 -
177.93.97.240 - - 15/04/2019:08:22:23 +0800 "GET / HTTP/1.1" 302 -
...

比如第一行,從0開始,各列的值為:

  • 0:120.244.106.255
  • 1:-
  • 2:-
  • 3:15/04/2019:01:38:49
  • 4:+0800
  • 5:"GET
  • 6:HTTP/1.1"
  • 7:302
  • 8:-

使用分析器進行列選的時候,給出的是行的index。如果某一行按空格split之后,長度不夠給定的index,那么這一行就會被忽略。

初始化

主要工具類FileScaner,可以同時指定由逗號分隔的多個路徑,並且支持通配符:

scaner = new FileScaner("/usr/local/tomcat/logs/localhost_access_log*.txt,/usr/local/tomcat2/logs/localhost_access_log*.txt");

字符匹配

用where查詢狀態碼為404的訪問記錄:

	@Test
	public void testWhere()throws Exception{
		scaner.select("0,3,6,8")    //選擇的列
		.where(Conditions.contains("8", "404")) //指定列的篩選條件
		.list();
		scaner.print();
	}

組合條件

多個查詢條件的情況,例如查詢狀態碼為404或者500的訪問記錄:

	@Test
	public void testMoreCondition()throws Exception{
		scaner.select("0,3,6,8")
		.where(Conditions.or(Conditions.eq("8", "404"),Conditions.eq("8", "500")))
		.list();
		scaner.print();
	}

計數統計

統計404總共出現的次數:

	@Test
	public void testWhere()throws Exception{
		scaner.select("8,count(1)")
		.where(Conditions.contains("8", "404"))
		.list();
		scaner.print();
	}

除了count,還支持sum、max、min和avg。這里不再舉例。

count中的1其實是沒意義的,既不表示列的index,並且寫成count(0)並不會少計數。其他統計函數則是有意義的,表示的是列的索引

函數:自定義AttPreProcessor預處理行為

例如,我們想將日志文件中的時間,去掉秒,只精確到分鍾,只需要實現AttPreProcessor接口即可:

	@Test
	public void testAttPreProcessor()throws Exception{
		AttPreProcessor processor = new AttPreProcessor() {
			@Override
			public String process(String att) {
				Date date = DateUtil.parse(att);
				if(date==null){
					return "";
				}
				return DateUtil.format(date, "yyyy-MM-dd HH:mm");
			}
		};
		scaner.select("0,3,6")
		.processor(3, processor)
		.where(Conditions.contains("8", "404"))
		.list();
		scaner.print();
	}

結果類似如下,可以看到秒已經被去掉了:

[120.244.106.255, 2019-03-15 01:39, /img/favicon/favicon.ico]
[216.245.197.254, 2019-03-15 08:32, /robots.txt]
[223.72.82.114, 2019-03-15 13:52, /img/favicon/favicon.ico]
[223.72.82.114, 2019-03-15 15:03, /img/favicon/favicon.ico]
[5.8.55.40, 2019-03-15 16:32, /index.php?x=HelloThinkPHP]
...

分組

使用groupBy來進行分組統計。

注意: groupBy中的索引值是select中的列的的索引值。比如下面的代碼中,select的值是“3,count(1)",一個選擇了2列,需要以第1列排序,所以需要groupBy("0")

	@Test
	public void testGroupBy()throws Exception{
		AttPreProcessor processor = new AttPreProcessor() {
			@Override
			public String process(String att) {
				Date date = DateUtil.parse(att);
				if(date==null){
					return "";
				}
				return DateUtil.format(date, "yyyy-MM-dd HH:mm");
			}
		};
		scaner.select("3,count(1)")
		.processor(3, processor)
		.groupBy("0")
		.list();
		scaner.print();
	}

輸出效果:

[2019-03-15 01:38, 14.0]
[2019-03-15 04:27, 10.0]
[2019-03-15 07:19, 6.0]
[2019-03-15 08:22, 2.0]
[2019-03-15 08:32, 2.0]
[2019-03-15 09:28, 34342.0]
[2019-03-15 10:34, 4.0]
[2019-03-15 12:42, 2.0]
...
[2019-03-15 17:16, 20.0]
[2019-03-18 03:29, 1.0]
[2019-03-18 07:45, 1.0]
[2019-03-18 07:55, 1.0]
[2019-03-18 10:25, 47.0]
[2019-03-18 10:25, 2.0]
[2019-03-18 11:04, 1.0]
[2019-03-18 11:34, 376.0]
[2019-03-18 11:44, 6.0]
[2019-03-18 12:47, 2.0]
...
[2019-03-18 17:07, 41503.0]
[2019-03-18 19:09, 1.0]
[2019-03-18 21:08, 2.0]
[2019-03-20 13:42, 1.0]
[2019-03-20 13:42, 1.0]

排序

orderBy中可以有多個排序,排序的index和groupBy同理,是只選擇結果的列index。下面的代碼按每分鍾訪問量降序排列:

	@Test
	public void testOrderBy()throws Exception{
		AttPreProcessor processor = new AttPreProcessor() {
			@Override
			public String process(String att) {
				Date date = DateUtil.parse(att);
				if(date==null){
					return "";
				}
				return DateUtil.format(date, "yyyy-MM-dd HH:mm");
			}
		};
		scaner.select("3,count(1)")
		.processor(3, processor)
		.groupBy("0")
		.orderBy(OrderBy.desc(1))
		.list();
		scaner.print();
	}

排序結果類似:

[2019-03-18 17:07, 41503.0]
[2019-03-15 09:28, 34342.0]
[2019-03-15 13:52, 582.0]
[2019-03-18 11:34, 376.0]
[2019-03-18 13:48, 267.0]
[2019-03-18 10:25, 47.0]
[2019-03-18 14:16, 33.0]
...
[2019-03-18 14:29, 9.0]
[2019-03-18 14:29, 8.0]
[2019-03-15 07:19, 6.0]
[2019-03-18 11:44, 6.0]
[2019-03-15 10:34, 4.0]
[2019-03-15 14:00, 3.0]
...

limit:限制輸出數量

如果只關心訪問量最高的10個記錄,可以這樣寫:

	@Test
	public void testLimit()throws Exception{
		AttPreProcessor processor = new AttPreProcessor() {
			@Override
			public String process(String att) {
				Date date = DateUtil.parse(att);
				if(date==null){
					return "";
				}
				return DateUtil.format(date, "yyyy-MM-dd HH:mm");
			}
		};
		scaner.select("3,count(1)")
		.processor(3, processor)
		.groupBy("0")
		.orderBy(OrderBy.desc(1))
		.limit(10)
		.list();
		scaner.print();
	}

輸出結果類似:

[2019-03-18 17:07, 41503.0]
[2019-03-15 09:28, 34342.0]
[2019-03-15 13:52, 582.0]
[2019-03-18 11:34, 376.0]
[2019-03-18 13:48, 267.0]
[2019-03-18 10:25, 47.0]
[2019-03-18 14:16, 33.0]
[2019-03-15 17:16, 20.0]
[2019-03-15 01:38, 14.0]
[2019-03-15 16:32, 14.0]

希望對你有用,歡迎討論!


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM