Search code examples
sslcertificatekeystorechainjks

How to add a certificate chain to a JKS


I have a certificate chain called: cert.cer with the content of:

subject= ... OU=MyCA
issuer= ... OU=MyCA
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----

subject= ... OU=Client
issuer= .. OU=MyCA
-----BEGIN CERTIFICATE-----
...
-----END CERTIFICATE-----

I tried to add this chain to JKS by calling:

keytool -import -trustcacerts -file cert.cer -keystore sample.keystore -storepass 123456 -alias chain

, which only adds the top level certificate of OU=MyCA.

How do I add this chain correctly to the JavaKeyStore (JKS)?


Solution

  • Ok, I ran your command to combine certificate in PKCS7 format:

    openssl > crl2pkcs7 -nocrl -certfile a.crt -certfile b.crt -out outfile.p7b
    

    It Worked.
    Then I tried to import the PKCS#7 file to JKS file using following command as you said:

    keytool -import -trustcacerts -file outfile.p7b -keystore keystore1.jks -storepass 123456 -alias chain
    

    It did not work.
    Then I researched a little and found that, I need to the certificate chain in a file either in Base64 format or in Der format. I had Base64 format file. So, I tried to concat the file using following windows command:

    copy /b a.crt+b.crt c.crt
    

    The linux command would be:

    cat a.crt b.crt > c.crt
    

    So the output file looked like this:

    -----BEGIN CERTIFICATE-----
    ..............................
    ..............................
    -----END CERTIFICATE----------BEGIN CERTIFICATE-----
    ...............................
    ...............................
    -----END CERTIFICATE-----
    

    Then, tried to import the certificate chain in JKS using the above command. It worked. Then, I try to see the the certificate list from the keystore. For that I ran following command:

    keytool -list -v -keystore keystore1.jks
    

    But it said, Only "1 entry is found" and one certificate was shown. As the keystore was not load with full certificate chain the experiment failed.
    So, I tried to convert the PKCS#7 file in certificate chain by using following openssl command:

    pkcs7 -print_certs -in outfile.p7b -out certificates.cer
    

    The output file looks exactly like yours, started with subject dn and issuer dn and then header and footer. Then I tried to store the certificates from the 'certificates.cer' to a jks file 'keystore1.jks'. But, Again, after import, it is showing that, the keystore has only one certificate. So, the issuer dn and subject dn were not a problem.
    Then I tried to convert the Base64 file to Der file and then tried to concat the data:

    openssl x509 -in a.crt -outform DER -out aa.crt
    openssl x509 -in b.crt -outform DER -out bb.crt
    copy /b aa.crt+bb.crt cc.crt
    

    Then, I tried to import the der concated file to JKS. But again only one certificate was imported.

    I really thought about what could really wrong I am doing. So, I looked for the source code of KeyTool and found the method where the certificate or certificate chain was being imported.

    Imports a JDK 1.1-style identity database. We can only store one certificate per identity, because we use the identity's name as the alias (which references a keystore entry), and aliases must be unique.
    

    And I am surprised that, their code convert the inputstream to List of certificate but they work with only one certificate of the certificate (first one).

    if (certs!=null && certs.length>0) {
          // we can only store one user cert per identity.
          // convert old-style to new-style cert via the encoding
             DerOutputStream dos = new DerOutputStream()
             certs[0].encode(dos);
             .............................
    

    So there is nothing we can do to add multiple certificate at once. There policy is one certificate for one entry. So, if you have multiple certificate to entry you have to make entry them individually. Or, write some java code to make our work easy (I always do this).
    Sorry for making this so long. But hopefully this will clear most of your confusion.