这是什么,我得到了Java从Azure密钥库证书

hgc7kmma  于 2023-02-28  发布在  Java
关注(0)|答案(1)|浏览(106)

证书是在Azure KeyVault中创建的。我需要从中下载公钥和私钥。

当内容类型是PEM时,我可以获取私钥并将其转换为RSA PrivateKey。

//when certificate is created with pem format, downloadedPK has both private and certificate sections
            //needs to extract the raw Private Key
            if ("application/x-pem-file".equalsIgnoreCase(privateKeyType)) {
                /*
                -----BEGIN PRIVATE KEY-----
                -----END PRIVATE KEY-----
                -----BEGIN CERTIFICATE-----
                -----END CERTIFICATE-----
                 */

当内容类型是PKCS12时,我不确定它是什么。

//when certificate is created with pkcs12 format, downloadedPK doesn't have any -----BEGIN * KEY-----
 //It's readable format similar to private key/certificate inside .pem file but without any "-----BEGIN *----- "

下面是我的代码:

ClientSecretCredential credential = new ClientSecretCredentialBuilder()
                .tenantId(tenantId)
                .clientId(clientId)
                .clientSecret(clientSecret)
                .build();

        CertificateClient certificateClient = new CertificateClientBuilder()
                .vaultUrl(vaultUri)
                .credential(credential)
                .buildClient();

        SecretClient secretClient = new SecretClientBuilder()
                .vaultUrl(vaultUri)
                .credential(credential)
                .buildClient();

        // Retrieving certificate
        KeyVaultCertificateWithPolicy certificateWithPolicy = certificateClient.getCertificate(alias);

        // Retrieving secrete for private key
        KeyVaultSecret secret = secretClient.getSecret(alias, certificateWithPolicy.getProperties().getVersion());
        
        String downloadedPK = secret.getValue();
        String privateKeyType = secret.getProperties().getContentType();

        byte[] rawPrivateKey = null;

            //when certificate is created with pem format, downloadedPK has both private and certificate sections
            //needs to extract the raw Private Key
            if ("application/x-pem-file".equalsIgnoreCase(privateKeyType)) {
                /*
                -----BEGIN PRIVATE KEY-----
                -----END PRIVATE KEY-----
                -----BEGIN CERTIFICATE-----
                -----END CERTIFICATE-----
                 */
                int endIndex = downloadedPK.indexOf("-----END PRIVATE KEY-----");
                String str1 = downloadedPK.substring(0, endIndex);

                privateKeyContent = str1.replaceAll("\\n", "").replace("-----BEGIN PRIVATE KEY-----", "");
            }

            //when certificate is created with pkcs12 format, downloadedPK doesn't have any -----BEGIN * KEY-----
            //It's readable format similar to private key/certificate inside .pem file but without any "-----BEGIN *----- "
            if ("application/x-pkcs12".equalsIgnoreCase(privateKeyType)) {

                //downloadedPK is "MIIKOAIBAzCCCfQGCSqGSIb3DQEHA...+1Q1jLj89b50AgIH0A==""
                privateKeyContent = downloadedPK;
            }

            rawPrivateKey = Base64.getDecoder().decode(privateKeyContent);

            KeyFactory kf = KeyFactory.getInstance("RSA");

            PKCS8EncodedKeySpec keySpecPKCS8 = new PKCS8EncodedKeySpec(Base64.getDecoder().decode(privateKeyContent));
            PrivateKey privateRsaKey = kf.generatePrivate(keySpecPKCS8);

我在这里查看了这篇关于. NET Certificate uploaded to Azure Key Vault has different content when downloading as a secret的帖子,它可以立即使用secret.value作为byte [] pfx。

// For PEM, you'll need to extract the base64-encoded message body.
// .NET 5.0 preview introduces the System.Security.Cryptography.PemEncoding class to make this easier.
if ("application/x-pkcs12".Equals(secret.Properties.ContentType, StringComparison.InvariantCultureIgnoreCase))
{
    byte[] pfx = Convert.FromBase64String(secret.Value);
    return new X509Certificate2(pfx);
}

但是我在java中下载的dPK是什么

MIIKOAIBAzCCCfQGCSqGSIb3DQEHA...+1Q1jLj89b50AgIH0A==

我得到了这个错误。这是否意味着我得到了pkcs12格式的私钥字符串?我该如何处理这个pkcs12字符串?

java.security.spec.InvalidKeySpecException: java.security.InvalidKeyException: IOException : version mismatch: (supported:     00, parsed:     03
    at java.base/sun.security.rsa.RSAKeyFactory.engineGeneratePrivate(RSAKeyFactory.java:251)
    at java.base/java.security.KeyFactory.generatePrivate(KeyFactory.java:390)
xhv8bpkk

xhv8bpkk1#

它应该是正确的P12密钥库格式(如果您从命令行生成密钥库,则可以使用JavaKeytool生成相同的格式)。
这将帮助您了解如何将其转换为证书:www.example.comhttps://github.com/nagyesta/lowkey-vault/blob/0c3fde5ad7f433d72ded05f6d3e55a3bb55aec18/lowkey-vault-docker/src/test/java/com/github/nagyesta/lowkeyvault/steps/CertificateStepDefAssertion.java#L125-L139
此外,下面几行代码也可以帮助我们了解在导入过程中如何解析相同的内容:www.example.comhttps://github.com/nagyesta/lowkey-vault/blob/0c3fde5ad7f433d72ded05f6d3e55a3bb55aec18/lowkey-vault-app/src/main/java/com/github/nagyesta/lowkeyvault/service/certificate/impl/CertContentType.java#L44-L69
当您将证书存储内容作为密码下载时,应根据以下条件使用空密码:www.example.com(我认为他们的意思是""中的空白,而不是null,因为null在Java上会有问题:https://learn.microsoft.com/en-us/azure/key-vault/certificates/how-to-export-certificate?tabs=azure-cli#export-stored-certificates (I think they mean blank as in "" and not null as null would be problematic on Java: Sun Java KeyManagerFactory and null passwords )
注:没有尝试这个代码与原来的AKV尚未,只是我的测试双,这是唯一的方式,它应该工作。

相关问题