代码:
@echo off
for /f "delims=" %%a in ('wmic OS Get localdatetime ^| find "."') do set "dt=%%a"
set "YY=%dt:~2,2%"
set "MM=%dt:~4,2%"
set "DD=%dt:~6,2%"
set "today=%YY%%MM%%DD%"
findstr /i /c:"The_database_has_been_locked." "C:\admin\logs\*%today%.log" >> "C:\records\Error.txt"
问题描述:
我在路径C:\ admin \ logs \下有一些日志文件,这些日志文件每天都会以名字命名。
我想在今天创建的所有文件中搜索特定的错误消息。一旦发现错误消息,立即将包含错误消息的完整行附加到名为Error.txt的文本文件中。
我已安排此脚本每隔10分钟运行一次。
我在这里面临的问题是,它在特定时间实例上多次出现附加的指定错误消息。我的意思是在每次运行时它都附加了先前解析的错误消息,这是我不想要的。
我想在Error.txt中只将错误消息一次附加到当前日期错误发生的特定时间实例。
你能帮帮我吗?
编辑:日志摘要
日志片段:
2013-12-06 16:29:31 10.35.44.195 GET /perform/all/per_cubes.asp - 80 - 172.23.45.72 Mozilla/4.0+(compatible;+MSIE+7.0;+Windows+NT+6.1;+Trident/4.0;+NGD_build;+SLCC2;+.NET+CLR+2.0.50727;+.NET+CLR+3.5.30729;+.NET+CLR+3.0.30729;+Media+Center+PC+6.0;+.NET4.0C;+.NET4.0E;+InfoPath.3;+MS-RTC+LM+8) 200 0 0 328
2013-12-06 16:29:33 10.35.44.195 GET /perform/all/per_cubes.asp |62|80004005|[Microsoft][ODBC_Microsoft_Access_Driver]_The_database_has_been_locked. 80 - 62.239.225.222 Mozilla/4.0+(compatible;+MSIE+7.0;+Windows+NT+6.1;+WOW64;+Trident/5.0;+.NET+CLR+2.0.50727;+.NET+CLR+3.0.30729;+.NET+CLR+3.5.30729;+.NET4.0C;+.NET4.0E;+SLCC2) 500 0 0 468
2013-12-06 16:29:44 10.35.44.195 GET /perform/all/per_cubes.asp |62|80004005|Unspecified_error 80 - 10.225.206.76 Mozilla/4.0+(compatible;+MSIE+7.0;+Windows+NT+6.1;+Trident/4.0;+NGD_build;+SLCC2;+.NET+CLR+2.0.50727;+.NET+CLR+3.5.30729;+.NET+CLR+3.0.30729;+Media+Center+PC+6.0;+.NET4.0C;+.NET4.0E;+InfoPath.3;+MS-RTC+LM+8) 500 0 0 93
将错误消息附加到Error.txt,如下所示(在当前日期的特定时间内只有一次):
2013-12-06 16:29:33 10.35.44.195 GET /perform/all/per_cubes.asp |62|80004005|[Microsoft][ODBC_Microsoft_Access_Driver]_The_database_has_been_locked. 80 - 62.239.225.222 Mozilla/4.0+(compatible;+MSIE+7.0;+Windows+NT+6.1;+WOW64;+Trident/5.0;+.NET+CLR+2.0.50727;+.NET+CLR+3.0.30729;+.NET+CLR+3.5.30729;+.NET4.0C;+.NET4.0E;+SLCC2) 500 0 0 468
答案 0 :(得分:1)
据推测,日志条目在某种程度上都是唯一的。
setLocal enableDelayedExpansion
set searchString=The_database_has_been_locked.
set sourceFile=C:\admin\logs\*%today%.log
for /f "delims=~!" %%a in ('findstr /i /c:"%searchString%" "%sourceFile%"') do (
set skip=0
for /f "delims=~!" %%b in ('findstr /i /c:"%%a" "Error.txt"') do set skip=1
if !skip!==0 echo %%a & echo %%a >> Error.txt
)
内部for循环只有在skip
中找到%%a
时才能设置变量Error.txt
。因此,如果未定义skip,则不会有重复的条目,您可以将错误附加到Error.txt
。
答案 1 :(得分:1)
@ECHO OFF
SETLOCAL
SET "sourcedir=c:\sourcedir"
SET "destdir=c:\destdir"
:: Need to put YOUR setting of %TODAY% in here - I'm using constants for testing
SET today=20140109
FOR %%a IN ("%sourcedir%"\beenprocessed*.txt) DO IF /i NOT "%%a"=="%sourcedir%\beenprocessed%today%.txt" DEL "%%a"
IF NOT EXIST "%sourcedir%\*%today%.log" GOTO :eof
ECHO dummy>>"%sourcedir%\beenprocessed%today%.txt"
findstr /i /c:"The_database_has_been_locked." "%sourcedir%\*%today%.log" >"%sourcedir%\beINGprocessednow.txt"
FINDSTR /i /v /b /e /g:"%sourcedir%\beenprocessed%today%.txt" "%sourcedir%\beINGprocessednow.txt" >>"%destdir%\Error.txt"
type "%sourcedir%\beINGprocessednow.txt" >> "%sourcedir%\beenprocessed%today%.txt"
GOTO :EOF
您需要插入%today%
的设置 - 我只是使用常量。另外,我将源目录和目标目录设置为变量。只是做出改变。
我并不感兴趣...beenprocessed...
和...beingprocessednow...
文件是%sourcedir%
,%destdir%
,%temp%
还是%someotherdir%
。由程序员选择。
原则是:
将一个虚拟字符串附加到beenprocessed...
。这可以创建一个文件或附加到它,一个根本不感兴趣的字符串(它没有'... database_has_been ...`过滤器)。
查找日志中的所有目标记录,并将它们放在文件beingprocessednow
中。
查找beingprocessednow
中未出现在beenprocessed
中的所有行 - 即。新行,并将它们附加到error.txt
文件。
将beingprocessednow
的全部内容附加到beenprocessed
,其中包含新数据
启动时,将删除除今天之外的任何一天的beenprocessed
个文件。
dummy
需要添加到“要排除的字词”中,因为findstr ../g
要求文件中至少包含一个字符串。 dummy
不能是一个有效的单词,它占据一行(/b /e
),因为所有感兴趣的行都包含目标字符串。