我有一个文本文件。与此类似。
This is a sample data.
This is a sample data.
This is a sample data.
Sat Jun 06 08:17:01 2015
WARNING: Cannot delete file.
Error-101
Error-100
Error-102
This is a sample data.
This is a sample data.
Error-10666
This is a sample data.
Sat Jun 06 10:17:01 2015
File deleted.
This is a sample data.
This is a sample data.
Sat Jun 06 10:17:01 2015
File deleted.
Sat Jun 06 11:17:01 2015
WARNING: Cannot delete file.
Error-101
This is a sample data.
Sat Jun 06 18:17:01 2015
WARNING: Cannot delete file.
Error-101
This is a sample data.
此文件包含一个月的数据。 在目录中可能有多个这样的文件。脚本需要检查今天修改的文件。
我想获得今天日期的错误 - ??? (整行错误 - )值。 到目前为止,我已经创造了这个。
$cur_date1 = get-date -UFormat %c
$curdate = (get-date).ToString("ddMMyyyy")
ForEach ($system in (Get-Content D:\Script\system.txt)) {
$dir = "\\$system\D$\Error\"
$latest = Get-ChildItem -Path $dir -Filter error*.txt | where{$_.LastWriteTime.ToString("ddMMyyyy") -eq $date }
$files=$latest.name
Foreach($file in $files){
$path= $dir+$file
$search = Get-Content $path
$a = $search| if($_ -eq $curdate){
Where-Object{$_.Contains("Error-") }
}
}
}
我可以查看今天创建的文件。 我可以获得整个文件的内容。 我可以搜索错误字符串,但我无法搜索当前日期。
有人可以就此提出建议吗?
感谢。
如果需要在标题或描述中进行任何更改,请执行此操作。 谢谢你的时间。
更新
只是告诉你我的系统日期时间格式如下。 dd / mm / yyyy hh:mm:ss
答案 0 :(得分:2)
您可以尝试将每一行转换为日期时间。但是,这不是标准的日期格式,因此[datetime]::TryParse()
不可能正常工作。这意味着你需要使用[datetime]::TryParseExact()
,因为你必须给它一个提供者和一种风格,这会更加刺激,即使你可能也没有使用它们。
$dateString = 'Sat Jun 06 08:17:01 2015';
[System.Globalization.CultureInfo]$provider = [System.Globalization.CultureInfo]::InvariantCulture;
[System.Globalization.DateTimeStyles]$style = [System.Globalization.DateTimeStyles]::None;
$format = "ddd MMM dd HH:mm:ss yyyy";
[ref]$parsedDate = get-date;
[DateTime]::TryParseExact($dateString, $format, $provider, $style, $parsedDate);
$parsedDate.Value;
需要注意的一点是,TryParse()
和TryParseExact()
都不会返回值;解析成功时返回True,失败时返回False。为了传递结果,您通过引用传递变量,函数修改引用的变量。 $parsedDate.Value
是实际日期时间值的位置,因为$parsedDate
本身是一个引用(指针)。
如果函数失败并返回false,$parsedDate
的值将为[datetime]::MinValue
(1月1日,0001)。
答案 1 :(得分:2)
$curdate
是一个格式为ddMMyyyy
的字符串,而包含日期的日志文件中的字符串格式为ddd MMM dd HH:mm:ss yyyy
,我认为它是当前的语言环境,因此您使用Get-Date -UFormat %c
。
因此,您的if($_ -eq $curdate)
声明无法发挥作用。
if($_ -eq $cur_date1)
中包含的时间戳代表您的脚本开始运行的确切秒数,则 $_
将返回true,但随后的Where-Object
语句赢得了' t评估为$true
(因为$_
目前指的是带有日期的行,而不是错误),即使它确实如此,也不会返回任何内容(您还没有管道输入)任何Where-Object
或指定InputObject
参数参数)
作为一般规则,对于日期比较,请勿使用字符串表示形式,使用您要比较的日期时间对象的Date
属性。
错误/虚弱的做法:
Get-ChildItem |Where-Object { $_.LastWriteTime.ToString("ddMMyyyy") -eq $datestring }
安全方法:
$today = (Get-Date).Date
Get-ChildItem |Where-Object { $_.LastWriteTime.Date -eq $today }
如果要提取错误消息的上一个日期,最简单的方法是将Select-String
与Context
参数一起使用:
Select-String -Path C:\samplefile.log -Pattern "^Error" -Context 2 | Select-Object -First 1
C:\samplefile.log:4:Sat Jun 06 08:17:01 2015
C:\samplefile.log:5:WARNING: Cannot delete file.
> C:\samplefile.log:6:Error-101
C:\samplefile.log:7:This is a sample data.
C:\samplefile.log:8:This is a sample data.
然后,您可以使用Select-String
的输出数据来获取并比较日期:
$Today = (Get-Date).Date
$Format = 'ddd MMM dd HH:mm:ss yyyy'
Select-String -Path C:\samplefile.log -Pattern '^Error' -Context 2 | Where-Object {
[DateTime]::ParseExact($_.Context.PreContext[0],$Format,$null).Date -eq $Today
} | Select-Object @{Name="Error";Expression={$_.Line}},@{Name="Date";Expression={[DateTime]::ParseExact($_.Context.PreContext[0],$Format,$null).ToString("ddMMyyyy")}}
答案 2 :(得分:1)
在解析error*.txt
文件时,您可以将最后看到的日期保存在变量中。因此,当您遇到Error-*
记录时,您将知道它与之相关的日期。
$Today=[datetime]::Today
Get-Content D:\Script\system.txt|
ForEach-Object {
$System=$_
Get-ChildItem -Path "filesystem::\\$System\D$\Error" -Filter error*.txt|
# filesystem:: allows code to work, even if current provider is not a filesystem provider.
Where-Object {$_.LastWriteTime.Date-eq$Today}|
ForEach-Object {
Get-Content -LiteralPath $_.PSPath|
ForEach-Object {
$ParseDate=New-Object datetime
$LastSeenDate=$null
} {
if([datetime]::TryParseExact($_,'ddd MMM dd HH:mm:ss yyyy',[cultureinfo]::InvariantCulture,'None',[ref]$ParseDate)){
$LastSeenDate=$ParseDate
}
if($_.StartsWith('Error-')){
[PSCustomObject]@{
Error=$_
Date=$LastSeenDate
System=$System
}
}
}
}
}|
Where-Object {$_.Date.Date-eq$Today}
答案 3 :(得分:1)
我得到了这个问题,所以这是我对解决方案的看法:
#Create test file from posted data:
(@'
This is a sample data.
This is a sample data.
This is a sample data.
Sat Jun 06 08:17:01 2015
WARNING: Cannot delete file.
Error-101
Error-100
Error-102
This is a sample data.
This is a sample data.
Error-10666
This is a sample data.
Sat Jun 06 10:17:01 2015
File deleted.
This is a sample data.
This is a sample data.
Sat Jun 06 10:17:01 2015
File deleted.
Sat Jun 06 11:17:01 2015
WARNING: Cannot delete file.
Error-101
This is a sample data.
Sat Jun 06 18:17:01 2015
WARNING: Cannot delete file.
Error-101
This is a sample data.
'@).split("`n") |
#where { -notmatch '^#'} |
foreach {$_.trim()} |sc testfile.txt
#Proxy function for testing
function get-date {[datetime]'06/06/2015 18:17:01'}
#Actual solution code follows:
$DateSearch = (get-date).ToString('MMM dd [0-9:]+ yyyy(.+)')
$DateSearch = '(?ms)' + $DateSearch
if ((Get-Content testfile.txt -Raw) -match $DateSearch)
{ $Matches[1].Split("`n") -like 'Error*' }
#remove the proxy function:
remove-item function:get-date
Error-101
Error-100
Error-102
Error-10666
Error-101
Error-101
这使用[datetime] tostring()
方法来帮助创建正则表达式以在文件中搜索今天的日期。然后它捕获从该点到文件末尾的所有内容,将其拆分为换行符并过滤除错误记录之外的所有内容。
忽略get-date的代理函数。这就是让脚本使用测试数据。