2015-08-03 151 views
0

我有一個文本文件。與此類似。今天的日期從PowerShell的txt文件中的具體文本

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

回答

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} 
+0

感謝您的回答。已投票。 – Ironic

+0

您的回答對我有用,我將測試一個答案,之後我會將其中一個標記爲答案,我非常感謝您的幫助。 – Ironic

+0

是否可以從system.txt中打印系統名稱(您已使用$ _)? – Ironic

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(Jan 1,0001)。

+0

您能否爲我們提供一些有關此的工作代碼。我沒有得到它。 – Ironic

2

$curdate與格式ddMMyyyy一個字符串,而在包含日期的日誌文件中的字符串格式爲ddd MMM dd HH:mm:ss yyyy,我以爲是當前語言環境,因此,您所使用的Get-Date -UFormat %c

因此,您的if($_ -eq $curdate)聲明不起作用。

if($_ -eq $cur_date1)如果包含在$_的時間戳表示腳本開始運行的確切第二,但隨後Where-Object聲明將不計算$true(因爲$_目前是指符合日期將返回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-StringContext參數:

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")}} 
+0

感謝您的詳細解答。我會試一試 – Ironic

+0

我測試了你的腳本,它正在解析這個值,但是我有一個問題,它只給我一個單一的錯誤。如果有多個錯誤,那麼它不會給我所有錯誤的輸出。 – Ironic

+0

請務必不要使用'Select-Object -First 1'語句,它只是向您顯示** 1 **匹配的輸出與上下文 –

1

我被ping通的問題,所以這裏是我採取的一個解決方案:

#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的代理函數。這只是爲了讓腳本與測試數據一起工作。

+0

感謝您的幫助。我會試一試。 – Ironic