Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/344.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
如何从pfx证书读取java中的私钥_Java_Security_Openssl_Private Key_Pem - Fatal编程技术网

如何从pfx证书读取java中的私钥

如何从pfx证书读取java中的私钥,java,security,openssl,private-key,pem,Java,Security,Openssl,Private Key,Pem,我正在尝试读取java中的私钥。为了做到这一点,我必须以pfx格式从完整证书中提取私钥。 我曾尝试使用下面的openssl命令将pfx转换为pem,然后再转换为pk8,但当我尝试用java读取密钥时,它显示密钥格式无效 将pfx转换为pem openssl pkcs12 -in C:\Documents\xbox-token\conversion\xbox token-FullCert.pfx -nocerts -out C:\Documents\xbox-token\conve

我正在尝试读取java中的私钥。为了做到这一点,我必须以pfx格式从完整证书中提取私钥。 我曾尝试使用下面的openssl命令将pfx转换为pem,然后再转换为pk8,但当我尝试用java读取密钥时,它显示密钥格式无效

将pfx转换为pem

      openssl pkcs12 -in C:\Documents\xbox-token\conversion\xbox
  token-FullCert.pfx -nocerts -out C:\Documents\xbox-token\conversion\xboxkey.pem
删除密码保护

openssl rsa -in C:\Documents\xbox-token\conversion\xboxkey.pem  -out C:\Documents\xbox-token\conversion\xboxkey.pem
将pem转换为pk8

openssl pkcs8 -topk8 -in C:\Documents\xbox-token\conversion\xboxkey.pem -out C:\Documents\xbox-token\conversion\xboxprv.pk8
在java代码中

  byte[] encodedPrivateKey=null;
    File privateKeyFile = new File("C:/Documents/xbox-token/conversion/xboxprv.pk8");
    FileInputStream inputStreamPrivateKey = null;
    try {
        inputStreamPrivateKey = new FileInputStream(privateKeyFile);
          encodedPrivateKey = new byte[(int)privateKeyFile.length()];
            inputStreamPrivateKey.read(encodedPrivateKey);
            inputStreamPrivateKey.close();
    } catch (FileNotFoundException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (IOException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }


    // Create the private key.
    PKCS8EncodedKeySpec privateKeySpec = new PKCS8EncodedKeySpec(encodedPrivateKey);
    System.out.println(encodedPrivateKey);
    System.out.println(privateKeySpec);
    RSAPrivateKey privateKey = null;
    try {
        privateKey = (RSAPrivateKey)KeyFactory.getInstance("RSA").generatePrivate(privateKeySpec);
    } catch (InvalidKeySpecException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    } catch (NoSuchAlgorithmException e) {
        // TODO Auto-generated catch block
        e.printStackTrace();
    }
我得到一个java.security.spec.InvalidKeySpecException:java.security.InvalidKeyException:无效密钥格式


有人能帮忙吗?

我认为关键在于使用openssl做一点工作,然后让keytool来做所有真正的工作。因此,使用openssl将现有证书和密钥转换为PKCS12文件。使用openssl,您将获得类似的功能

openssl pkcs12 \
  -export -in cert.crt \
  -inkey cert.key \
  -certfile ica.crt \
  -name "yourKey" \
  -out cert.p12
然后神奇的是将.p12导入密钥库,就像它是另一个密钥库一样

$JAVA_HOME/bin/keytool \
  -importkeystore -deststorepass secret \
  -destkeypass secret -destkeystore $KEYSTORE \
  -srckeystore cert.p12 \
  -srcstoretype PKCS12 \
  -srcstorepass secret \
  -alias "yourKey"
您可以在java中使用它,但我希望完整的答案包括以下内容

import java.security.KeyStore;
KeyStore trustStore  = KeyStore.getInstance(KeyStore.getDefaultType());
FileInputStream instream = new FileInputStream(new File("/your/keystore"));
trustStore.load(instream, "secret".toCharArray());

希望它能起作用

如果您没有为OpenSSL命令指定输出格式,您将得到一个PEM编码的文件。Java需要DER编码。请尝试以下操作,而不是上次的openssl调用:

openssl pkcs8 -topk8 -inform=PEM -outform=DER
              -in C:\Documents\xbox-token\conversion\xboxkey.pem 
              -out C:\Documents\xbox-token\conversion\xboxprv.pk8
'-inform'参数不应该是必需的(似乎是默认值),但'-outform'可能是必需的


如果您想检查您的格式:PEM文件是ASCII(Base64编码),DER文件是二进制文件。如果您的文本编辑器喜欢它,Java可能不会。但我确实需要它作为p8而不是p12。我添加的程序只是其中的一部分。我需要p8格式的,因为我需要使用密钥进行saml解密。我从下面的帖子中找到了答案,用“-”行读取pem内容并进行Base64解码。java.util.Base64.getDecoder().decode(不带连字符线)