我已经编写了一个在Azure管道中使用的PowerShell模块,该模块会将SSL证书绑定到自定义主机名。我能够使模块在本地工作,包括在管道中用于初始化模块的内联脚本。在本地运行脚本时,没有任何错误。当我在管道中使用相同的脚本时,收到以下错误:
2019-07-16T23:00:40.3007294Z ##[error]Parameter set cannot be resolved using the specified named parameters.
我没有使用参数集,所以不确定为什么会抱怨。我能够在本地而不是在发布管道中执行代码的原因是什么?参数设置错误确实是对其他问题的抱怨吗?
同样,我已经在本地测试过。我所有的参数都是必需的,所以我没有指定ParameterSet,但是我确实设置了一个以防万一,并且遇到了同样的错误。
这是我成功导入模块后在发布管道中使用Azure Powershell任务使用的脚本。我知道我的变量声明是正确的,因为我已经对其进行了测试,并且它们可以很好地输出(在本地和管道中):
当任务在脚本中单击此行时发生错误:
Enable-SslStateOnWebapp -WebappName $webappName -customWebappHostname $webAppCustomHostname -existingKeyvaultName $existingVaultName -existingKeyvaultCertName $certName
$myVars = '$(armDeploymentOutput)' | ConvertFrom-Json
Write-Host "The following variables are available: $($myVars)" -Verbose
$existingVaultName = $myVars.existingKeyVaultName.value
$webappName=$myVars.webappName.value
$webAppCustomHostname=$myVars.webAppCustomHostname.value
$certName=$myVars.existingKeyVaultCertificateName.value
if ($webappName -and $webAppCustomHostname -and $existingVaultName -and $certName) {
Write-Host "Attempting to enable SSL Binding for $($webappName) on the hostname $($webAppCustomHostname) using cert $($certName) from the existing keyvault of $($existingVaultName)." -Verbose
Enable-SslStateOnWebapp -WebappName $webappName -customWebappHostname $webAppCustomHostname -existingKeyvaultName $existingVaultName -existingKeyvaultCertName $certName
}
else {
Write-Host "Insufficient parameters have been provided to complete SSL Binding. To enable SSL binding, please provide a custom hostname, an existing keyvault where your certificate is stored, and the name of your certificate. Please visit the readme for more information." -Verbose
}
这是已初始化的PowerShell模块:
function Enable-SslStateOnWebapp {
param (
[Parameter(
Mandatory = $true,
HelpMessage = 'A webapp name is required.')]
[ValidateNotNullOrEmpty()]
[string] $WebappName,
[PARAMETER(
Mandatory = $true,
HelpMessage = 'The FQDN of the custom hostname you want to bind.')]
[ValidateNotNullOrEmpty()]
[string] $customWebappHostname,
[Parameter(
Mandatory = $true,
HelpMessage = 'A name for an existing Keyvault is required.')]
[ValidateNotNullOrEmpty()]
[string] $existingKeyvaultName,
[PARAMETER(
Mandatory = $true,
HelpMessage = 'A name of the pfx certificate stored in the pre-existing keyvault')]
[ValidateNotNullOrEmpty()]
[string] $existingKeyVaultCertName
)
#getting webapp resources
$webapp = Get-AzureRmResource -Name $webappName
#obtaining resource group resources through the use of resource group name tied to webapp
$rg = Get-AzureRmResource -ResourceGroupName $webapp.ResourceGroupName
...
}
我的预期结果是构建管道将执行脚本而不会出错。相反,我在本地传递结果(这显然使得调试起来很困难,然后在管道中获得以下调试日志记录:
2019-07-16T23:00:39.1496157Z ##[debug]Caught exception from task script.
2019-07-16T23:00:39.1536232Z ##[debug]Error record:
2019-07-16T23:00:39.1993172Z ##[debug]Enable-SslStateOnWebapp : Parameter set cannot be resolved using the specified named parameters.
2019-07-16T23:00:40.2927954Z ##[debug]At D:\agent3\_work\_temp\7be280f0-5905-4e05-99e0-972c90739a12.ps1:13 char:5
2019-07-16T23:00:40.2930113Z ##[debug]+ Enable-SslStateOnWebapp -WebappName $webappName -customWebappHost ...
2019-07-16T23:00:40.2940404Z ##[debug]+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
2019-07-16T23:00:40.2940886Z ##[debug] + CategoryInfo : InvalidArgument: (:) [Enable-SslStateOnWebapp], ParameterBindingException
2019-07-16T23:00:40.2941287Z ##[debug] + FullyQualifiedErrorId : AmbiguousParameterSet,Enable-SslStateOnWebapp
2019-07-16T23:00:40.2941647Z ##[debug]
2019-07-16T23:00:40.2941968Z ##[debug]Script stack trace:
2019-07-16T23:00:40.2942368Z ##[debug]at Enable-SslStateOnWebapp, D:\agent3\_work\r6\a\_infra-grs-referenceapp\drop\pwsh-modules\grs-arm\enable-ssl_state_on_webapp\enable-ssl_state_on_webapp.ps1: line 64
我检查是否存在隐藏的Unix字符,因为我是在Mac上本地开发的,所以没有:
答案 0 :(得分:0)
TLDR;此问题是由本地开发环境中使用的版本与AzureDevops构建代理使用的版本之间的不兼容引起的。检查构建代理版本,并确保它们与您开发的版本相同。
我从这个post的答案中得到启发。
该错误从脚本的第64行抛出(这是脚本的第一个可执行行):
2019-07-16T23:00:39.1496157Z ##[debug]Caught exception from task script.
2019-07-16T23:00:39.1536232Z ##[debug]Error record:
2019-07-16T23:00:39.1993172Z ##[debug]Enable-SslStateOnWebapp : Parameter set cannot be resolved using the specified named parameters.
2019-07-16T23:00:40.2927954Z ##[debug]At D:\agent3\_work\_temp\7be280f0-5905-4e05-99e0-972c90739a12.ps1:13 char:5
2019-07-16T23:00:40.2930113Z ##[debug]+ Enable-SslStateOnWebapp -WebappName $webappName -customWebappHost ...
2019-07-16T23:00:40.2940404Z ##[debug]+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
2019-07-16T23:00:40.2940886Z ##[debug] + CategoryInfo : InvalidArgument: (:) [Enable-SslStateOnWebapp], ParameterBindingException
2019-07-16T23:00:40.2941287Z ##[debug] + FullyQualifiedErrorId : AmbiguousParameterSet,Enable-SslStateOnWebapp
2019-07-16T23:00:40.2941647Z ##[debug]
2019-07-16T23:00:40.2941968Z ##[debug]Script stack trace:
2019-07-16T23:00:40.2942368Z ##[debug]at Enable-SslStateOnWebapp, D:\agent3\_work\r6\a\_infra-grs-referenceapp\drop\pwsh-modules\grs-arm\enable-ssl_state_on_webapp\enable-ssl_state_on_webapp.ps1: line 64
鉴于它是脚本的第一行可执行代码,因此我认为错误是由于函数上的参数绑定错误地导致的,尤其是因为第63行未写入主机。
Write-Host "Attempting to get webapp resource..." -Verbose
我发现事实并非如此。我观察到,如果下一行失败,有时可能不会调用Write-Host。
在本地开发,我正在使用AzureRM v6.13.1。如果我看我在第64行调用的函数,则此函数为:
$webapp = Get-AzureRmResource -Name $webappName
查看此cmdlet的documentation (v6.13.1):
Get-AzureRmResource
[[-Name] <String>]
[-ResourceType <String>]
[-ODataQuery <String>]
[-ResourceGroupName <String>]
[-TagName <String>]
[-TagValue <String>]
[-ExpandProperties]
[-ApiVersion <String>]
[-Pre]
[-DefaultProfile <IAzureContextContainer>]
[<CommonParameters>]
和我的构建代理(〜v4.6)上的版本的文档:
Get-AzureRmResource
[-ResourceName <String>]
[-ResourceType <String>]
[-ExtensionResourceName <String>]
[-ExtensionResourceType <String>]
[-ExpandProperties]
[-IsCollection]
[-Top <Int32>]
[-ODataQuery <String>]
[-TenantLevel]
[-ApiVersion <String>]
[-Pre]
[-DefaultProfile <IAzureContextContainer>]
[<CommonParameters>]
我们可以看到-Name
和-ResourceName
参数是不同的。这将导致AmbiguousParameterSet
错误。
解决方案: 我们特定的构建代理是本地的,不会像Microsoft托管的代理那样定期更新。
我使用标准的powershell任务强制更新了构建代理的AzureRM版本:
- task: PowerShell@2
inputs:
targetType: 'inline'
script: 'Install-PackageProvider -Name NuGet -Force -Scope CurrentUser;
Install-Module -Name AzureRM -RequiredVersion 6.13.1 -Force -Scope CurrentUser -AllowClobber;'
然后在后续任务中使用我的脚本调用Get-Module
,并在任务的preferredAzurePowerShellVersion部分中指定了版本6.13.1
(如果所需的版本在代理上不可用,则会导致错误version not available
,因此为什么要运行上一个PowerShell任务。
- task: AzurePowerShell@3
inputs:
azureSubscription: '<subscription>'
ScriptType: 'InlineScript'
Inline: 'Get-Module AzureRm;
Import-Module $(System.DefaultWorkingDirectory)\drop\pwsh-modules\grs-arm;
$myVars = '$(armDeploymentOutput)' | ConvertFrom-Json
Write-Host "The following variables are available: $($myVars)" -Verbose
$existingVaultName = $myVars.existingKeyVaultName.value
$webappName=$myVars.webappName.value
$webAppCustomHostname=$myVars.webAppCustomHostname.value
$certName=$myVars.existingKeyVaultCertificateName.value
Write-Host "Setting an access policy for the SPN to $($existingVaultName)" -Verbose
Set-AzureRmKeyVaultAccessPolicy -VaultName $existingVaultName -ServicePrincipalName <spnClientId> -PermissionsToCertificates get -PermissionsToSecrets get
if ($webappName -and $webAppCustomHostname -and $existingVaultName -and $certName)
{Write-Host "Attempting to enable SSL Binding for $($webappName) on the hostname
$($webAppCustomHostname) using cert $($certName) from the existing keyvault of
$($existingVaultName)." -Verbose
Enable-SslStateOnWebapp -WebappName $webappName -customWebappHostname
$webAppCustomHostname -existingKeyvaultName $existingVaultName -
existingKeyvaultCertName $certName -Verbose}
else {Write-Host "Insufficient parameters have been provided to complete SSL
Binding. To enable SSL binding, please provide a custom hostname, an existing
keyvault where your certificate is stored, and the name of your certificate.
Please visit the readme for more information." -Verbose}
Write-Host "Removing SPN access to $($existingVaultName)" -Verbose
Remove-AzureRmKeyVaultAccessPolicy -VaultName $existingVaultName -
ServicePrincipalName <spnClientId>
preferredAzurePowerShellVersion: '6.13.1'
这完全解决了我的问题。