1

I'm trying to find all files in a dir, modified within the last 4 hours, that contain a string. I can't have the output show files that don't contain needed content. How do I change this so it only lists the filename and content found that matches the string, but not files that don't have that string? This is run as a windows shell command. The dir has a growing list of hundreds of files, and currently output looks like this:

File1.txt
File2.txt
File3.txt
... long long list, with none containing the needed string

(powershell "Set-Location -Path "E:\SDKLogs\Logs"; Get-Item *.* | Foreach { $lastupdatetime=$_.LastWriteTime; $nowtime = get-date; if (($nowtime - $lastupdatetime).totalhours -le 4) {Select-String -Path $_.Name -Pattern "'Found = 60.'"| Write-Host "$_.Name Found = 60";  }}")

I tried changing the location of the Write-Host but it's still printing all files.

Update: I'm currently working on this fix. Hopefully it's what people were alluding to in comments.

$updateTimeRange=(get-date).addhours(-4)
$fileNames = Get-ChildItem -Path "K:\NotFound" -Recurse -Include *.* 
foreach ($file in $filenames)
{
  #$content = Get-Content $_.FullName
  Write-host "$($file.LastWriteTime)"
  if($file.LastWriteTime -ge $($updateTimeRange))
  {
    #Write-Host $file.FullName
    if(Select-String -Path $file.FullName -Pattern 'Thread = 60')
    {
        Write-Host $file.FullName
    }
  }
}
Michele
  • 3,617
  • 12
  • 47
  • 81
  • 2
    There is a bunch of missing escaping, on `$` and `"`. What's the particular need to use `powershell -Command` as opposed to the easy solution `powershell -File` with the code you need to execute in a file? – Santiago Squarzon May 31 '22 at 14:16
  • 1
    How are you calling this? Those quotes should be an issue if not escaped. That's also invalid syntax calling `$_.Name` within a string. You would need a sub-expression to expand the reference property, but also it wouldn't work; you would need to place it inside another foreach then reference it. – Abraham Zinala May 31 '22 at 14:18
  • @SantiagoSquarzon - We can't put it in a script file because we have thousands of devices we are going to be running it on remotely through our interface, which we can't store scripts on. – Michele May 31 '22 at 14:27
  • Do you guys have an example of the quote/escape thing, and foreach thing? – Michele May 31 '22 at 14:29
  • @AbrahamZinala - This is run through our interface, which runs windows shell commands, powershell included. If it runs at the windows command line, it would run there. We capture output and see it in our display for each device, and collect them through a special program. – Michele May 31 '22 at 14:39

1 Answers1

2

If I understood you correctly, you just want to display the file name and the matched content? If so, the following will work for you:

$date = (Get-Date).AddHours(-4) 
Get-ChildItem -Path 'E:\SDKLogs\Logs' | Where-Object -FilterScript { $date -lt $_.LastWriteTime } |
    Select-String -Pattern 'Found = 60.' | 
    ForEach-Object -Process {
        '{0} {1}' -f $_.FileName, $_.Matches.Value
    }

Get-Date doesn't need to be in a variable before your call but, it can become computationally expensive running a call to it again and again. Rather, just place it in a variable before your expression and call on the already created value of $date.

Typically, and for best practice, you always want to filter as far left as possible in your command. In this case we swap your if statement for a Where-Object to filter as the objects are passed down the pipeline. Luckily for us, Select-String returns the file name of a match found, and the matched content so we just reference it in our Foreach-Object loop; could also use a calculated property instead.


As for your quoting issues, you may have to double quote or escape the quotes within the PowerShell.exe call for it to run properly.

Edit: swapped the double quotes for single quotes so you can wrap the entire expression in just PowerShell.exe -Command "expression here" without the need of escaping; this works if you're pattern to find doesn't contain single quotes.

Abraham Zinala
  • 4,267
  • 3
  • 9
  • 24