X509Store.Open() 抛出异常
X509Store.Open() throwing an Exception
为什么 $store.Open($openFlags)
抛出异常,有没有比我的 "work around" 更好的方法让它工作?
<#
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store("Cert:\CurrentUser\My")
$openFlags = [System.Security.Cryptography.X509Certificates.OpenFlags]::MaxAllowed
$store.Open($openFlags) #Exception calling "Open" with "1" argument(s): "The parameter is incorrect.
#>
#Work Around:
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store("Cert:\CurrentUser\My")
$openFlags = [System.Security.Cryptography.X509Certificates.OpenFlags]::MaxAllowed
$startIndexOfStoreName = $store.Name.LastIndexOf("\") + 1
$lengthOfStoreName = $store.Name.Length - $startIndexOfStoreName
$storeNameString = $store.Name.Substring($startIndexOfStoreName, $lengthOfStoreName)
$storeName = [System.Security.Cryptography.X509Certificates.StoreName]$storeNameString
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store($storeName, $store.Location)
$store.Open($openFlags) #No Exception thrown!
更新: 似乎在使用 X509Store(String) 构造函数时,不允许使用任何斜杠(如果我错了请纠正我)。所以 $store = New-Object System.Security.Cryptography.X509Certificates.X509Store("My")
有效。
使用
定义您的证书存储
$store = Get-Item "Cert:\CurrentUser\My"
而不是
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store("Cert:\CurrentUser\My")
老实说,我仍在努力弄清楚它为何起作用或如何起作用。
第一种方法 returns 一个名为 "My" 的 $store,所以我假设它专门针对商店,您可以使用
打开它
$store.Open($openFlags)
第二种方法 returns 一个名为 "Cert:\CurrentUser\My" 的 $store。对此的打开方法将失败。
其实你是在混方法。一种是通过提供商 (Cert:),另一种是 .Net 类型 (X509Store)。附加到证书商店和提取证书详细信息的过程非常不同。
将 "Cert:" 想象成 PSDrive(它基本上就是)。所以你可以get-childitem等,不需要"open"商店。在这种思维方式下,证书存储位置是文件夹,证书是单个对象:
# List the store locations
gci Cert:\
# List store names in CurrentUser store location
gci Cert:\CurrentUser
# List certs in the My store of CurrentUser store location
gci Cert:\CurrentUser\My | format-list
使用 Cert: 提供程序的要点是,如果您想在远程系统上使用证书,则需要启用远程处理 (WinRM),这样您就可以 "Invoke-Command"。并非每个环境都允许这样做。这就是 .Net X509Store 的用武之地。不确定它与 "CurrentUser" 的配合情况如何,但我从来没有担心过这一点 - 我对 "LocalMachine" 商店中的内容更感兴趣(特别是"My" 因为那是系统保存 web 和 auth 证书的地方)。修改后的代码段以列出这些证书(从我为询问 SharePoint 场中的所有服务器而构建的脚本中提取)。
# Change as necessary
$strTarget = $env:computername
$strCertStoreLocation = 'LocalMachine'
$strCertStoreName = 'My'
# Set up store parameters, connect and open store
[System.Security.Cryptography.X509Certificates.StoreLocation]$strStoreLoc = [String]$strCertStoreLocation
[System.Security.Cryptography.X509Certificates.StoreName]$strStoreName = [String]$strCertStoreName
$objCertStore = New-Object System.Security.Cryptography.X509Certificates.X509Store -ArgumentList "\$($strTarget)$($strStoreName)", $strStoreLoc
$objCertStore.Open('ReadOnly')
# List cert details in bulk
$objCertStore.Certificates | Format-List
# List specific props
foreach ($Cert in $objCertStore.Certificates) {
"Subject: $($Cert.Subject)"
"Issuer: $($Cert.Issuer)"
"Issued: $($Cert.NotBefore)"
"Expires: $($Cert.NotAfter)"
""
}
有关每个的更多详细信息,请访问您最喜欢的技术存储库(MSDN、PowerShell.org、嘿脚本专家等):)
我想对此发表评论,因为正如前面的示例中已经指出的那样,"the mixing of .NET Framework and the use of PowerShell Providers"。对我来说,我需要它作为一种纯 .NET 的方式来获取证书来测试一些 C# 等效代码,而无需用户计算机上的完整开发环境。
这是我想出的方法:
$Location = [Security.Cryptography.X509Certificates.StoreLocation]::CurrentUser
$StoreName = [Security.Cryptography.X509Certificates.StoreName]::My
$Store = New-Object System.Security.Cryptography.X509Certificates.X509Store -ArgumentList $StoreName, $Location
$OpenFlags = [System.Security.Cryptography.X509Certificates.OpenFlags]::ReadOnly
$Store.Open($OpenFlags)
$Store.Certificates
为什么 $store.Open($openFlags)
抛出异常,有没有比我的 "work around" 更好的方法让它工作?
<#
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store("Cert:\CurrentUser\My")
$openFlags = [System.Security.Cryptography.X509Certificates.OpenFlags]::MaxAllowed
$store.Open($openFlags) #Exception calling "Open" with "1" argument(s): "The parameter is incorrect.
#>
#Work Around:
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store("Cert:\CurrentUser\My")
$openFlags = [System.Security.Cryptography.X509Certificates.OpenFlags]::MaxAllowed
$startIndexOfStoreName = $store.Name.LastIndexOf("\") + 1
$lengthOfStoreName = $store.Name.Length - $startIndexOfStoreName
$storeNameString = $store.Name.Substring($startIndexOfStoreName, $lengthOfStoreName)
$storeName = [System.Security.Cryptography.X509Certificates.StoreName]$storeNameString
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store($storeName, $store.Location)
$store.Open($openFlags) #No Exception thrown!
更新: 似乎在使用 X509Store(String) 构造函数时,不允许使用任何斜杠(如果我错了请纠正我)。所以 $store = New-Object System.Security.Cryptography.X509Certificates.X509Store("My")
有效。
使用
定义您的证书存储$store = Get-Item "Cert:\CurrentUser\My"
而不是
$store = New-Object System.Security.Cryptography.X509Certificates.X509Store("Cert:\CurrentUser\My")
老实说,我仍在努力弄清楚它为何起作用或如何起作用。
第一种方法 returns 一个名为 "My" 的 $store,所以我假设它专门针对商店,您可以使用
打开它$store.Open($openFlags)
第二种方法 returns 一个名为 "Cert:\CurrentUser\My" 的 $store。对此的打开方法将失败。
其实你是在混方法。一种是通过提供商 (Cert:),另一种是 .Net 类型 (X509Store)。附加到证书商店和提取证书详细信息的过程非常不同。
将 "Cert:" 想象成 PSDrive(它基本上就是)。所以你可以get-childitem等,不需要"open"商店。在这种思维方式下,证书存储位置是文件夹,证书是单个对象:
# List the store locations
gci Cert:\
# List store names in CurrentUser store location
gci Cert:\CurrentUser
# List certs in the My store of CurrentUser store location
gci Cert:\CurrentUser\My | format-list
使用 Cert: 提供程序的要点是,如果您想在远程系统上使用证书,则需要启用远程处理 (WinRM),这样您就可以 "Invoke-Command"。并非每个环境都允许这样做。这就是 .Net X509Store 的用武之地。不确定它与 "CurrentUser" 的配合情况如何,但我从来没有担心过这一点 - 我对 "LocalMachine" 商店中的内容更感兴趣(特别是"My" 因为那是系统保存 web 和 auth 证书的地方)。修改后的代码段以列出这些证书(从我为询问 SharePoint 场中的所有服务器而构建的脚本中提取)。
# Change as necessary
$strTarget = $env:computername
$strCertStoreLocation = 'LocalMachine'
$strCertStoreName = 'My'
# Set up store parameters, connect and open store
[System.Security.Cryptography.X509Certificates.StoreLocation]$strStoreLoc = [String]$strCertStoreLocation
[System.Security.Cryptography.X509Certificates.StoreName]$strStoreName = [String]$strCertStoreName
$objCertStore = New-Object System.Security.Cryptography.X509Certificates.X509Store -ArgumentList "\$($strTarget)$($strStoreName)", $strStoreLoc
$objCertStore.Open('ReadOnly')
# List cert details in bulk
$objCertStore.Certificates | Format-List
# List specific props
foreach ($Cert in $objCertStore.Certificates) {
"Subject: $($Cert.Subject)"
"Issuer: $($Cert.Issuer)"
"Issued: $($Cert.NotBefore)"
"Expires: $($Cert.NotAfter)"
""
}
有关每个的更多详细信息,请访问您最喜欢的技术存储库(MSDN、PowerShell.org、嘿脚本专家等):)
我想对此发表评论,因为正如前面的示例中已经指出的那样,"the mixing of .NET Framework and the use of PowerShell Providers"。对我来说,我需要它作为一种纯 .NET 的方式来获取证书来测试一些 C# 等效代码,而无需用户计算机上的完整开发环境。
这是我想出的方法:
$Location = [Security.Cryptography.X509Certificates.StoreLocation]::CurrentUser
$StoreName = [Security.Cryptography.X509Certificates.StoreName]::My
$Store = New-Object System.Security.Cryptography.X509Certificates.X509Store -ArgumentList $StoreName, $Location
$OpenFlags = [System.Security.Cryptography.X509Certificates.OpenFlags]::ReadOnly
$Store.Open($OpenFlags)
$Store.Certificates