List file names in a folder matching a pattern, excluding file content

u123 picture u123 · Jun 29, 2017 · Viewed 83.3k times · Source

I am using the below to recursively list all files in a folder that contains the $pattern

Get-ChildItem $targetDir -recurse | Select-String -pattern "$pattern" | group path | select name

But it seems it both list files having the $pattern in its name and in its content, e.g. when I run the above where $pattern="SAMPLE" I get:

C:\tmp\config.include
C:\tmp\README.md
C:\tmp\specs\SAMPLE.data.nuspec
C:\tmp\specs\SAMPLE.Connection.nuspec

Now:

C:\tmp\config.include
C:\tmp\README.md

indeed contains the SAMPLE keywords/text but I don't care about that, I only need the command to list file names not file with content matching the pattern. What am I missing?

Based on the below answers I have also tried:

$targetDir="C:\tmp\"
Get-ChildItem $targetDir -recurse | where {$_.name -like "SAMPLE"} | group path | select name

and:

$targetDir="C:\tmp\"
Get-ChildItem $targetDir -recurse | where {$_.name -like "SAMPLE"} | select name

but it does not return any results.

Answer

Matt picture Matt · Jun 29, 2017

Select-String is doing what you told it to. Emphasis mine.

The Select-String cmdlet searches for text and text patterns in input strings and files.

So if you are just looking to match with file names just use -Filter of Get-ChildItem or post process with Where-Object

Get-ChildItem -Path $path -Recurse -Filter "*sample*"

That should return all files and folders that have sample in their name. If you just wanted files or directories you would be able to use the switches -File or -Directory to return those specific object types.

If your pattern is more complicated than a simple word then you might need to use Where-Object like in Itchydon's answer with something like -match giving you access to regex.


The grouping logic in your code should be redundant since you are returning single files that all have unique paths. Therefore I have not included that here. If you just want the paths then you can pipe into Select-Object -Expand FullName or just (Get-ChildItem -Path $path -Recurse -Filter "*sample*").Fullname