Problem
I have the command Get-Content -Path $SearchPath -Wait | Select-String -Pattern $SearchTerm which is used to search through debug file(s) for common search terms and display them live to the user.
The $SearchPath & $SearchTerm are configured from user inputs.
I would like to list out the files that will be searched to the user before starting the search.
What I have tried
Attempt #1
Get-ChildItem -Path $SearchPath | Select-Object -ExpandProperty FullName
The problem with this command is that it lists both files & directories.
However, only files will be searched in the Get-Content command.
Attempt #2
Since I know that all my files end with .log, I added in a regex check for this to eliminate the directories, like so:
Get-ChildItem -Path $SearchPath | Where-Object { $_.Name -match [regex]'([a-zA-Z0-9])*.log' } | Select-Object -ExpandProperty FullName
The problem with this command is that if $SearchPath is C:\Path\To\The\* it will list only the files in that directory, but not subdirectories.
However, the original Get-Content command will check subdirectories.
E.g. It would list C:\Path\To\The\DebugLog.log, but not C:\Path\To\The\SubDir\DebugLog.log, even though Get-Content would search it.
Attempt #3
Okay, so my next thought is that I should add -Recurse to check further directories, like so:
Get-ChildItem -Path $SearchPath -Recurse | Where-Object { $_.Name -match [regex]'([a-zA-Z0-9])*.log' } | Select-Object -ExpandProperty FullName
This solves the first problem, but now if $SearchPath is C:\Path\To\The\DebugLog.log, it will list both C:\Path\To\The\DebugLog.log & C:\Path\To\The\Subfolder\DebugLog.log. But the original Get-Content command will only search C:\Path\To\The\DebugLog.log.
Question
How can I check which files the Get-Content command will search before executing it?
Is Get-ChildItem the right command for this, or is there a better option?

Note that with
$SearchPath = 'C:\Path\To\The\*',Get-Content -Path $SearchPathwill not search subdirectories. Passing a directory path to Get-Content results in an error.To limit retrieval of file-system items to files, use the
-Fileswitch.To limit recursive retrieval to a specified depth, use the
-Depthparameter (which implies the-Recurseswitch)Therefore, in order to retrieve all
*.logfiles in the current directory and its immediate subdirectories, use the following:You can then pass these files to your
Get-Contentpipeline, using either of the following approaches:However, in neither case will
-Waitwork as you intend:Get-Content's-Waitswitch effectively only supports one input file: it reads the first one given and then indefinitely waits for it to have more data appended to it, without reading the other files; it only moves on to the next file if the file currently being monitored happens to get deleted.To monitor multiple files simultaneously, you'll need to use a form of parallelism, which PowerShell (Core) 7+ can provide via the
-Parallelparameter ofForEach-Object:-ThrottleLimit $logFilesOfInterest.Countensures that a thread is spun up for every file to be monitored right away.$using:SearchTermis required in order to refer to the$SearchTermvariable in the caller's scope.Use Ctrl-C to stop monitoring.
In Windows PowerShell, you'll have to use background jobs, which is more cumbersome:
Use Ctrl-C to stop monitoring.
After doing so, you can clean up the jobs with
$jobs | Remove-Job -Force(the$jobsvariable containing all launched jobs was created with-OutVariable jobs)Note the use of
ForEach-Object Line, which is necessary to work around a bug in Windows PowerShell, which causes directSelect-Stringoutput not to surface viaReceive-Job(PowerShell (Core) no longer has this problem.)As an aside (it won't make much difference here):
Start-ThreadJobcmdlet offers a lightweight, much faster thread-based alternative to the child-process-based regular background jobs created withStart-Job. It comes with PowerShell (Core) 7+ and in Windows PowerShell can be installed on demand with, e.g.,Install-Module ThreadJob -Scope CurrentUser. In most cases, thread jobs are the better choice, both for performance and type fidelity - see the bottom section of this answer for why.