问题
I have a project name called 'SFO104' and I have a list of serial numbers i.e 5011849, 5011850 etc and I have to search a long list of 500+ serial numbers to see if they exist in any other documents not relating to the project name SFO104 or the PO number 114786.
I was thinking of outputting the search results to a csv for each serial number searched but the below isnt working.
$searchWords = gc C:\Users\david.craven\Documents\list.txt
$results = @()
Foreach ($sw in $searchWords)
{
$files = gci -path C:\Users\david.craven\Dropbox\ -filter "*$sw*" -recurse | select FullName
foreach ($file in $files)
{
$object = New-Object System.Object
$object | Add-Member -Type NoteProperty –Name SearchWord –Value $sw
$object | Add-Member -Type NoteProperty –Name FoundFile –Value $file
$results += $object
}
}
$results | Export-Csv C:\Users\david.craven\Documents\results.csv -NoTypeInformation
The image below shows my search of the serial number 5011849 and the results returned correspond to project SFO104 which is as expected.
回答1:
Your code works, the file is getting populated. However, what you have specified does not have the headers defined as in your screen shot. Also, what does that list.txt look like. My searchlist.txt is a single column file:
Hello
client
Using your code as is, only changing the file path and name, and a slight modification to where the filename is accessed, gives these results...
$searchWords = gc 'D:\Scripts\searchlist.txt'
$results = @()
Foreach ($sw in $searchWords)
{
$files = gci -path d:\temp -filter "*$sw*" -recurse
foreach ($file in $files)
{
$object = New-Object System.Object
$object | Add-Member -Type NoteProperty –Name SearchWord –Value $sw
$object | Add-Member -Type NoteProperty –Name FoundFile –Value $file.FullName
$results += $object
}
}
$results | Export-Csv d:\temp\searchresults.csv -NoTypeInformation
# Results
# psEdit -filenames 'd:\temp\searchresults.csv'
SearchWord FoundFile
---------- ---------
Hello D:\temp\Duplicates\PowerShellOutput.txt
Hello D:\temp\Duplicates\BeforeRename1\PowerShellOutput.txt
Hello D:\temp\Duplicates\PoSH\PowerShellOutput.txt
Hello D:\temp\Duplicates\Text\PowerShellOutput.txt
client D:\temp\Client.txt
client D:\temp\Duplicates\CertLabClients_v1.ps1
client D:\temp\Duplicates\Check Logon Server for Client.ps1
client D:\temp\Duplicates\Create Wireless Hosted Networks in Windows Clients.ps1
...
Update for OP
Since you are using a comma separate list. You need to break that into separate items. I changed my file to this
Hello,client
You cannot match on that layout unless you are trying to match the whole consecutive string. So, if I break the above this way ...
$searchWords = (gc 'D:\Scripts\searchlist.txt') -split ','
… thus the results are as shown before.
Update for the OP
Example, test with this (a different rough approach)...
Foreach ($sw in $searchWords)
{
Get-Childitem -Path "d:\temp" -Recurse -include "*.txt","*.csv" |
Select-String -Pattern "$sw" |
Select Path,LineNumber,@{n='SearchWord';e={$sw}}
}
The LineNumber was sonly added so show where the string was located. Also, note, your code, and what I provide here, will only work for text, csv files.
If you plan to hit these, doc, docx, xls, xlsx, that means way more code as you have to use the default apps Word, Excel, to open and read these files.
This means using the COM Object model for each of those file types in your code. As discussed and shown here:
How do I make powershell search a Word document for wildcards and return the word it found?
You'd need to do a similar thing for Excel or PowerPoint, and if you have PDF, that requires and addon.
Update for OP
Like I said, I put this together quickly so it is a bit rough (no error handling, etc...) by I did test it using my input file and target folder tree and it does work.
# This is what my input looks like
Hello,client
595959, 464646
LIC
Running the code should have given you the results below, using only .txt,.csv files. Using any other file type will error by design as per my comment above regarding, you cannot use this approach for non text-based files without using the native app for the non text file type.
$searchWords = ((gc 'D:\Scripts\searchlist.txt') -split ',').Trim()
Foreach ($sw in $searchWords)
{
Get-Childitem -Path "d:\temp" -Recurse -include "*.txt","*.csv" |
Select-String -Pattern "$sw" |
Select Path,LineNumber,@{n='SearchWord';e={$sw}}
}
Path LineNumber SearchWord
---- ---------- ----------
D:\temp\Duplicates\BeforeRename1\PsGet.txt 157 Hello
...
D:\temp\Duplicates\PoSH\PsGet.txt 157 Hello
...
D:\temp\Duplicates\BeforeRename1\PoSH-Get-Mo... 108 client
D:\temp\Duplicates\BeforeRename1\Powershell ... 12 client
D:\temp\Duplicates\BeforeRename1\Powershell ... 15 client
D:\temp\Duplicates\BeforeRename1\PsGet.txt 454 client
...
D:\temp\newfile.txt 4 client
D:\temp\MyFile.txt 5 595959
D:\temp\ProcessNames.csv 4 595959
D:\temp\Duplicates\Text\JSON-CSS.txt 30 464646
D:\temp\Duplicates\JSON-CSS.txt 30 464646
D:\temp\MyFile.txt 5 464646
D:\temp\ProcessNames.csv 4 464646
D:\temp\Duplicates\BeforeRename1\GetSetScree... 7 LIC
来源:https://stackoverflow.com/questions/53105844/powershell-script-to-return-search-results-from-a-list-of-keywords