无效的提供者类型又指定了一次 [英] Invalid provider type specified one more time

查看:53
本文介绍了无效的提供者类型又指定了一次的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我已经查看了以下问题及其答案:

I’ve already viewed these questions and their answers:

指定了无效的提供者类型"尝试加载证书的私钥时出现CryptographicException

我如何创建客户端证书以通过SSL对双向身份验证进行本地测试?

指定了无效的提供程序类型.CryptographicException

第二个问题所引用的博客.

And this blog that was referenced by the second question.

我怀疑证书颁发者有问题,但我可能是错的.

I suspect there is a problem with the certificate issuer, but I could be wrong.

前言
我是身份验证的新手(您可以看成是白痴).当前项目是将用Visual Studio 2013 .Net 4.5.1编写的现有网站和Web应用程序升级到Visual Studio 2017 2017 .Net版本4.6.1,以满足新消息代理的要求.

Preface
I’m new at authentication (you can read that as idiot). The current project is to upgrade an existing web site and web application written in Visual Studio 2013 .Net 4.5.1 to Visual Studio 2017 2017 .Net version 4.6.1 to meet requirements for a new message broker.

环境
Windows 10
Visual Studio 2017(15.8.1)
IIS 10
Microsoft SQL Server 2017

The environment
Windows 10
Visual Studio 2017 (15.8.1)
IIS 10
Microsoft SQL Server 2017

问题描述
用C#编写的Web服务器在身份验证期间抛出此错误

Problem Description
The web server written in C# is throwing this error during authentication

    {"IDX10614: AsymmetricSecurityKey.GetSignatureFormater( 'http://www.w3.org/2001/04/xmldsig-more#rsa-sha256' ) threw an exception.
Key:
    'System.IdentityModel.Tokens.X509AsymmetricSecurityKey'\nSignatureAlgorithm: 'http://www.w3.org/2001/04/xmldsig-more#rsa-sha256', check to make sure the     SignatureAlgorithm is supported.\nException:'System.Security.Cryptography.CryptographicException: Invalid provider type specified.
       at System.Security.Cryptography.Utils.CreateProvHandle(CspParameters parameters, Boolean randomKeyContainer)
       at System.Security.Cryptography.Utils.GetKeyPairHelper(CspAlgorithmType keyType, CspParameters parameters, Boolean randomKeyContainer, Int32 dwKeySize, SafeProvHandle& safeProvHandle, SafeKeyHandle& safeKeyHandle)\r\n   at System.Security.Cryptography.RSACryptoServiceProvider.GetKeyPair()
       at System.Security.Cryptography.RSACryptoServiceProvider..ctor(Int32 dwKeySize, CspParameters parameters, Boolean useDefaultKeySize)
       at System.Security.Cryptography.X509Certificates.X509Certificate2.get_PrivateKey()
       at System.IdentityModel.Tokens.X509AsymmetricSecurityKey.get_PrivateKey()\r\n   at System.IdentityModel.Tokens.X509AsymmetricSecurityKey.GetSignatureFormatter(String algorithm)
       at System.IdentityModel.Tokens.AsymmetricSignatureProvider..ctor(AsymmetricSecurityKey key, String algorithm, Boolean willCreateSignatures)'.
    If you only need to verify signatures the parameter 'willBeUseForSigning' should be false if the private key is not be available."}

已采取的步骤
最初没有要检查的证书,并且生成了另一个错误.
在以管理员身份运行的PowerShell中

Steps taken
Initially there was no certificate to check and that generated a different error.
In PowerShell running as Administrator

New-SelfSignedCertificate-主题"CN = XxxxxxxXXCA" -DnsName"localhost" -FriendlyName"XxxxxxxXXCA" -KeyUsage DigitalSignature -KeyUsageProperty ALL -KeyAlgorithm RSA -KeyLength 2048 -CertStoreLocation"Cert:\ CurrentUser \ My"

New-SelfSignedCertificate -Subject "CN= XxxxxxxXXCA" -DnsName "localhost" -FriendlyName "XxxxxxxXXCA" -KeyUsage DigitalSignature -KeyUsageProperty ALL -KeyAlgorithm RSA -KeyLength 2048 -CertStoreLocation "Cert:\CurrentUser\My"

启动MMC

将创建的证书复制到本地计算机个人"

Copy the certificate created to Local Machine Personal

将证书复制到本地计算机受信任的根证书颁发机构

Copy the certificate to Local Machine Trusted Root Certificate Authorities

将证书复制到本地计算机受信任的发布者

Copy the certificate to Local Machine Trusted Publishers

在IIS中启动网站

在Visual Studio 2017中运行Web服务器

Run Web Server in Visual Studio 2017

使用高级REST客户端(ARC)从客户端向服务器发送登录请求.

Use Advanced REST Client (ARC) to send a login request to the server from a client.

在下面的代码中遍历Visual Studio 2017调试器中的身份验证代码:

Walk through the authentication code in Visual Studio 2017 debugger in the code below:

在return语句中引发异常.

The exception is thrown in the return statement.

    public string GenerateToken(string email)
    {

        X509Store store = new X509Store(StoreLocation.LocalMachine);
        store.Open(OpenFlags.ReadOnly);
        var certs = store.Certificates;

        X509Certificate2 signingCert =
        certs.Cast<X509Certificate2>().FirstOrDefault(cert => cert.FriendlyName == "XxxxxxxXXCA");
        SigningCredentials signingCredentials = new X509SigningCredentials(signingCert);

        var tokenHandler = new JwtSecurityTokenHandler();
        var now = DateTime.UtcNow;

        var customer = _customerService.GetCustomerByEmail(email); 

        var emailClaim = new Claim(ClaimTypes.Email, customer.Email, ClaimValueTypes.String);
        var userIdClaim = new Claim(ClaimTypes.NameIdentifier, customer.Id.ToString(), ClaimValueTypes.Integer);
        var roleClaim = new Claim(ClaimTypes.Role, "customer", ClaimValueTypes.String);

        var claimsList = new List<Claim> { emailClaim, userIdClaim, roleClaim };

        var tokenDescriptor = new SecurityTokenDescriptor()
        {
            AppliesToAddress = "http://localhost/api",
            SigningCredentials = signingCredentials,
            TokenIssuerName = "http://localhost",
            Lifetime = new Lifetime(now, now.AddDays(30)),
            //Lifetime = new Lifetime(now, now.AddDays(1)),
            Subject = new ClaimsIdentity(claimsList)
        };

        store.Close();
        return tokenHandler.WriteToken(tokenHandler.CreateToken(tokenDescriptor));
    }

推荐答案

New-SelfSignedCertificate cmdlet默认情况下使用密钥存储提供程序.大部分.NET Framework(特别是 X509Certificate2 )不支持CNG密钥.结果,当您使用存储在CNG中的私钥从证书创建 X509Certificate2 实例时, PrivateKey 属性上的 get 访问器将引发异常:

New-SelfSignedCertificate cmdlet uses key storage provider by default. Most of .NET Framework (X509Certificate2 specifically) do not support CNG keys. As the result, when you create X509Certificate2 instance from certificate with private key stored in CNG, get accessor on PrivateKey property throws exception:

at System.Security.Cryptography.X509Certificates.X509Certificate2.get_PrivateKey()

我相信,您不拥有在 PrivateKey 上调用getter的代码,因此,您需要通过在 -Provider 参数在 New-SelfSignedCertificate cmdlet调用中.例如,您可以使用 microsoft增强的rsa和aes密码提供程序提供程序作为参数值.

I believe, you don't own the code that calls getter on PrivateKey, therefore, you need to re-create your certificate by explicitly providing legacy provider name in the -Provider parameter in New-SelfSignedCertificate cmdlet call. For example, you can use microsoft enhanced rsa and aes cryptographic provider provider as a parameter value.

这篇关于无效的提供者类型又指定了一次的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆