foreach ($key in $MyInvocation.BoundParameters.Keys) {
if ($key -eq "ScanDurationSeconds") {
$logoutput | Where-Object ScanDurationSeconds -GT $ScanDurationSeconds
}
Okay, so if I do the above it outputs the value specified in the parameter. However, If I want to do something like:
$test = $logoutput | Where-Object ScanDurationSeconds -GT $ScanDurationSeconds
Test ends up being a blank result.
Are you unable to map a result created in a parameter to a variable for later usage? I am obviously missing something fundamental here.
Thank you very much for response.
I guess I was not super clear. I am trying to make a “search” function to search a CSV. I want to be able to search against each of the columns. Manually, I can do this fine, however I am trying to make a parameter that can replicate/standardize the process to make it easier for someone else to use the script.
So with some help this was the result (As I couldn’t figure out another way to do something with multiple parameters without a ridiculous else chain)
function Get-LogData
(
[Parameter(Mandatory=$false)][string]$Filename,
[Parameter(Mandatory=$false)][string]$Event,
[Parameter(Mandatory=$false)][string]$EventSeverityLevel,
[Parameter(Mandatory=$false)][int]$ResultID,
[Parameter(Mandatory=$false)][string]$SymantecProtectionEngineIPAddress,
[Parameter(Mandatory=$false)][string]$ClientIP,
[Parameter(Mandatory=$false)][string]$ContainerViolation,
[Parameter(Mandatory=$false)][int]$ScanDurationSeconds
)
{
$Where = @()
foreach ($key in $MyInvocation.BoundParameters.Keys) {
if ($key -ne "ScanDurationSeconds") {
$Where += "`$_.$key -like '*$(Get-Variable -Name $key -ValueOnly)*'"
}
}
if ($Where) {
$WhereFilter = [scriptblock]::Create(($Where -join " -and "))
} else {
$WhereFilter = [scriptblock]::Create($true)
}
$logoutput| ? -FilterScript $WhereFilter
}
The Best possible solution would be figuring out how to build a script block “And” run on depending on the parameters that were utilized.
So Like:
$logoutput| ? -FilterScript $WhereFilter
Would expand where filter out to something like:
$logoutput | Where-Object {$_.Filename -like *"Somefile"* -and $_.ScanDurationSeconds -gt 30}
But I am not really sure how to accomplish this.
Edit: May have found something. Looking into it now.
Okay, So here is what I have now. Problem is that it ends up loosing the variable values… not sure why.
Results:
Where-Object { $.FileName -like $Filename -and $.ScanDurationSeconds -gt $ScanDurationSeconds }
function Get-LogData
(
[Parameter(Mandatory=$false)][string]$FileName,
[Parameter(Mandatory=$false)][string]$Event,
[Parameter(Mandatory=$false)][string]$EventSeverityLevel,
[Parameter(Mandatory=$false)][int]$ResultID,
[Parameter(Mandatory=$false)][string]$ClientIP,
[Parameter(Mandatory=$false)][string]$ContainerViolation,
[Parameter(Mandatory=$false)][int]$ScanDurationSeconds
)
{
#Build Where array.
$Where = @()
#Evaluate Parameter response, If exists, add to Where array
if ($PSBoundParameters.ContainsKey("FileName")) {$Where += '$_.FileName -like $Filename'}
if ($PSBoundParameters.ContainsKey("Event")) {$Where += '$_.Event -like $Event'}
if ($PSBoundParameters.ContainsKey("EventSeverityLevel")) {$Where += '$_.EventSeverityLevel -like $Event'}
if ($PSBoundParameters.ContainsKey("ResultID")) {$where += '$_.ResultID -like $ResultID'}
if ($PSBoundParameters.ContainsKey("ClientIP")) {$Where += '$_.ClientIP -like $ClientIP'}
if ($PSBoundParameters.ContainsKey("ContainerViolation")) {$Where += '$_.ContainerViolation -like $ContainerViolation'}
if ($PSBoundParameters.ContainsKey("ScanDurationSeconds")) {$Where += '$_.ScanDurationSeconds -gt $ScanDurationSeconds'}
# Join each objects in Where array into a string seperated by -And
$WhereString = $Where -join " -and "
# Create script block with script string.
$WhereBlock = [scriptblock]::Create( $WhereString )
write-host "Where-Object { $WhereBlock }"
#$logoutput | Where-Object { $WhereBlock }
}
*** EDIT ***
Okay, fixed it. I was using ’ instead of " which prevented the variables from expanding out. Duh!
Thanks a bunch. Your layout is leading me to figuring this one out. Almost there. Still not working properly but is building the array!
With your additional explanation, I would use a for loop. However, you are severely limiting the ability to query the because there are more operators than -and (such as -or) and comparison operators such as -like, -ne and many more. It would be better to teach the other user basic query syntax than trying to modularize into a function IMHO. Here is how I would update your code above:
function Get-LogData {
param (
[Parameter(Mandatory=$false)][string]$FileName,
[Parameter(Mandatory=$false)][string]$Event,
[Parameter(Mandatory=$false)][string]$EventSeverityLevel,
[Parameter(Mandatory=$false)][int]$ResultID,
[Parameter(Mandatory=$false)][string]$ClientIP,
[Parameter(Mandatory=$false)][string]$ContainerViolation,
[Parameter(Mandatory=$false)][int]$ScanDurationSeconds
)
$Where = @()
if ($PSBoundParameters) {
foreach ($param in $PSBoundParameters.GetEnumerator()) {
$Where += '$_.{0} = ${0}' -f $param.Key
}
$where
}
}
Get-LogData -Event "Blue" -ResultID 123