1
[CmdletBinding()]
param (
    [Parameter(Mandatory=$true,Position=0)]
    [string]
    $subscription,

    [Parameter(Mandatory=$false)]
    [string]
    $applicationId,

    [Parameter(Mandatory=$false)]
    [string]
    $clientSecret,

    [Parameter(Mandatory=$true,Position=1)]
    [string]
    $resourceGroupName,

    [Parameter(Mandatory=$true,Position=2)]
    [string]
    $apimServiceName,

    [Parameter(Mandatory=$true,Position=3)]
    [string]
    $policyfilePath,

    [Parameter(Mandatory=$true,Position=4)]
    [ValidateSet('global','product','api','operation', IgnoreCase = $true)]
    [string]
    $scope='global',
    
    [Parameter(Mandatory=$true,Position=5)]
    [string]
    $apiIdOrProductId

    #THIS IS THE PARAMETER WHICH I WANT TO MAKE MANDATORY IF VALUE OF PREVIOUS PARAMETER $scope = "OPEARTION"
    #[Parameter(Mandatory=$false)]
    #[string]
    #$operationname
)

DynamicParam {
    if ($scope -eq "OPERATION" -or $scope -eq "operation") {
         #create a new ParameterAttribute Object
         Write-Host "Called test"
         Write-Host $scope
         $operationAttribute = New-Object System.Management.Automation.ParameterAttribute
         $operationAttribute.Mandatory = $true
         $operationAttribute.Position = 6
         
         #create an attributecollection object for the attribute we just created.
         $attributeCollection = new-object System.Collections.ObjectModel.Collection[System.Attribute]

         #add our custom attribute
         $attributeCollection.Add($operationAttribute)

         #add our paramater specifying the attribute collection
         $operationName = New-Object System.Management.Automation.RuntimeDefinedParameter('operationname', [String], $attributeCollection)

         #expose the name of our parameter
         $paramDictionary = New-Object System.Management.Automation.RuntimeDefinedParameterDictionary
         $paramDictionary.Add('operationname', $operationName)
         return $paramDictionary
   }

}

I cannot get the dynamic parameter to work which is dependent on a previous parameter "scope". It just skips over when I run the PS script. Please advice what I'm doing wrong?

3
  • 2
    As an aside: PowerShell's operators are case-insensitive by default, so -eq 'operation will do; in case you do need case-sensitivity, there are c-prefixed variants (-ceq 'operation') Commented Dec 9, 2020 at 18:08
  • 1
    Works fine for me too in 5.1 ... . "C:\Github\test.ps1" -scope operation show me operationname in the arguments and all other scope do not. (tested within vscode) Commented Dec 9, 2020 at 22:39
  • 1
    I was running the script without arguments so was allowing the command line to prompt me Commented Dec 10, 2020 at 9:57

2 Answers 2

1
  • Your code only works if you pass an argument to your -scope parameter directly on the command line.

  • If you let PowerShell prompt you for a -scope argument, based on the parameter's Mandatory property, your code cannot work, because the dynamicparam block runs before such automatic prompts.

Since you're assigning a default value to $scope, 'global' (which doesn't make sense in combination with Mandatory=$true), one option is to simply remove the Mandatory property:

  • This will default to 'global' in the absence of a (possibly positional) -scope argument, in which case you know that the additional parameter isn't required.

  • If an argument is specified, then your dynamicparam block will work as intended.

However, this also requires you to place the mandatory $apiIdOrProductId parameter declaration before $scope (swap Position values 4 and 5)

Sign up to request clarification or add additional context in comments.

Comments

0

Based on the title, there is at least one way to have a dynamic param offer a ValidateSet for that dynamic parameter based on the value of a previously entered regular parameter.

In this case the regular parameter could be a folder. But you would have to enter it without quotes.

For instance:

Function Get-SubFolderDynamically {
[CmdletBinding()]
param($path)
    
dynamicparam
{
    Write-Verbose "DynamicParam triggered. PSBoundParameters `$path is currently: $($PSBoundParameters['path'])" -Verbose
    
        #Parameter Definition
            $attributes = New-Object -Type System.Management.Automation.ParameterAttribute
            $attributes.Mandatory = $true
            $attributeCollection = New-Object -Type System.Collections.ObjectModel.Collection[System.Attribute]
            $attributeCollection.Add($attributes)

        #AcceptedValues for Parameter Definition
        #Note: Only Works if path is entered in the command line without quotes
            $subFolders = (Get-ChildItem $path).Name
            $attributeCollection.add((New-Object System.Management.Automation.ValidateSetAttribute($subFolders)))

        #ParameterDictionary
            $dynParam = New-Object -Type System.Management.Automation.RuntimeDefinedParameter("subFolder", [string], $attributeCollection)
            $paramDictionary = New-Object -TypeName System.Management.Automation.RuntimeDefinedParameterDictionary
            $paramDictionary.Add("subFolder", $dynParam)
        
        return $paramDictionary
}

}

#RUNIT - Create a Folder with subFolders to test.

Get-SubFolderDynamically -path C:\PathWithoutQuotes -subFolder [TAB|TAB|...]

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.