1

我无法思考如何解决这个问题的正确逻辑。我有一个接受两种类型开关的函数:

  • -Add
  • -Remove
Function Test-Bool {
        
    Param (
        # Input Parameters
        [Parameter(Mandatory = $false,
                   HelpMessage='Enter. Workflow. Name.')]
        [Alias('OMB','MailBox')]
        [string]$Workflow,

        [Parameter(Mandatory = $false)]
        [Alias('EDIPI','DisplayName')]
        [string[]]$UserName

    )

      DynamicParam {
        if ($Workflow -ne $null -and $UserName -ne $null) {
          $parameterAttribute = [System.Management.Automation.ParameterAttribute]@{
              ParameterSetName = "AddingMembers"
              Mandatory = $false
          }

          $attributeCollection = [System.Collections.ObjectModel.Collection[System.Attribute]]::new()
          $attributeCollection.Add($parameterAttribute)

          $dynParam1 = [System.Management.Automation.RuntimeDefinedParameter]::new(
            'Add', [switch], $attributeCollection
          )

          $paramDictionary = [System.Management.Automation.RuntimeDefinedParameterDictionary]::new()
          $paramDictionary.Add('Add', $dynParam1)
          

          $parameterAttribute1 = [System.Management.Automation.ParameterAttribute]@{
              ParameterSetName = "RemovingMembers"
              Mandatory = $false
          }

          $attributeCollection1 = [System.Collections.ObjectModel.Collection[System.Attribute]]::new()
          $attributeCollection1.Add($parameterAttribute1)

          $dynParam11 = [System.Management.Automation.RuntimeDefinedParameter]::new(
            'Remove', [switch], $attributeCollection1
          )

          $paramDictionary.Add('Remove', $dynParam11)
          return $paramDictionary

        }
      }      
    Begin {
        $ABool = {
            'Add Block'
            $Bool = Read-Host -Prompt 'Adding or Removing Member(s)'
                if ($Bool.ToLower() -like 'a*') {
                    $true
                }
                else {
                    Break;
                }
        }
        $RBool = {
            'Remove Block'
            $Bool = Read-Host -Prompt 'Adding or Removing Member(s)'
                if ($Bool.ToLower() -like 'r*') {
                    $true
                }
                else {
                    Break;
                }
        }   
        if ($PSBoundParameters['Add'].IsPresent) { [bool]$Add = $true }
        elseif ($PSBoundParameters['Remove'].IsPresent) { [bool]$Remove = $true }
        elseif (-not$PSBoundParameters['Add'].IsPresent) { $Add = & $ABool }
        elseif (-not$PSBoundParameters['Remove'].IsPresent) { $Remove = & $RBool }
    }
    Process {
        if ($Add) {       
            "Add was selected"
        }
        if ($Remove) {
            "Remove was selected"
        }
    }
}

我可以通过几种方式运行它:

  • Test-Bool -Workflow spg -UserName a -Add-作品

  • Test-Bool -Workflow spg -UserName a -Remove-作品

  • Test-Bool -Workflow spg

    • 应要求删除或添加:键入Addworks

    • 键入Remove不起作用

这是有道理的,因为elseif (-not$PSBoundParameters['Add'].IsPresent) { $Add = & $ABool }首先被评估,当被问到时,输入Remove将其扔到else块中,使其成为Break/Exit


问题:当输入(使True )时, 我可以更改什么以使$Remove被评估为 true 和反之亦然?Add$Add

老实说,我让自己非常困惑,以至于我决定在这里发帖,而不是试图自己解决这个问题。

4

1 回答 1

2

改用参数集

Function Test-Bool {
    [CmdletBinding(DefaultParameterSetName = 'Undecided')]
    Param (
        # Input Parameters
        [Parameter(Mandatory = $false,
                   HelpMessage='Enter. Workflow. Name.')]
        [Alias('OMB','MailBox')]
        [string]$Workflow,

        [Parameter(Mandatory = $false)]
        [Alias('EDIPI','DisplayName')]
        [string[]]$UserName,

        [Parameter(Mandatory = $true, ParameterSetName = 'Add')]
        [switch]$Add,

        [Parameter(Mandatory = $true, ParameterSetName = 'Remove')]
        [switch]$Remove
    )

    begin {
        $action = if($PSCmdlet.ParameterSetName -eq 'Undecided'){
            $answer = Read-Host -Prompt 'Adding or Removing Member(s)?'
            if($answer -like 'a*'){
                'Add'
            }
            elseif($answer -like 'r*') {
                'Remove'
            }
            else {
                throw 'Invalid option provided'
            }
        }
        else {
            $PSCmdlet.ParameterSetName
        }

        # $action now contains either 'Add' or 'Remove'
        $actionBlock = @{
            'Add'    = { <# code to add user to workflow #> }
            'Remove' = { <# code to remove user from workflow #> }
        }[$action]
    }

    process {
        # if/else statements no longer needed, $actionBlock contains the correct scriptblock
        . $actionBlock
    }

}

如果用户未指定任一开关,则参数集名称将为Undecided,并且将在开始块中提示用户 - 否则我们只需使用与指定开关关联的参数集名称。

由于这两个开关参数属于不同的参数集,用户不能再同时选择两者。

于 2021-09-02T15:35:39.893 回答