Version 82

    Tomcat configurations

     

    JBoss-3.2.3/Tomcat-4.1.x

    • Create a test keystore in the server/default/conf directory:

        starksm@banshee9100 conf$ keytool -genkey -alias tc-ssl -keyalg RSA -keystore server.keystore -validity 3650
        Enter keystore password:  tc-ssl
        What is your first and last name?
          [Unknown]:  www.myhost.com
        What is the name of your organizational unit?
          [Unknown]:  Some dot com
        What is the name of your organization?
          [Unknown]:  Security
        What is the name of your City or Locality?
          [Unknown]:  SomeCity
        What is the name of your State or Province?
          [Unknown]:  Washington
        What is the two-letter country code for this unit?
          [Unknown]:  US
        Is CN=www.myhost.com, OU=Some dot com, O=Security, L=SomeCity, ST=Washington, C=US correct?
          [no]:  yes

        Enter key password for <tc-ssl>
                (RETURN if same as keystore password):

     

    • Please note that the answer to the "first and last name?" question is important. This answer consitutes the CN= part of your so called distinguished name. The browser will check that the CN= part matches the end of the domain it requested the web page from. If the CN= and the the web page domain do not match the browser will display an additional warning. So for local development you may want to use "localhost" as CN and later on use the domain name of the host that will serve request from the internet.

     

    • Edit jbossweb-tomcat41.sar/META-INF/jboss-service.xml and uncomment the following section and update the keystoreFile,

     <!-- SSL/TLS Connector configuration -->
    <Connector className = "org.apache.coyote.tomcat4.CoyoteConnector"
         address="${jboss.bind.address}" port = "8443" scheme = "https"
         secure = "true">

         <Factory className = "org.apache.coyote.tomcat4.CoyoteServerSocketFactory"
             keystoreFile="${jboss.server.home.dir}/conf/server.keystore"
             keystorePass="tc-ssl"
             protocol = "TLS">
    </Factory>
    </Connector>

     

    • You need to replace the value for keystorePass with the password you used while creating the key.

     

     

    On startup the log may contain this warning:

    10:31:48,952 DEBUG [SSLImplementation] [getInstance.119] Error loading SSL Implementation org.apache.tomcat.util.net.puretls.PureTLSImplementation
    java.lang.ClassNotFoundException: No ClassLoaders found for: org.apache.tomcat.util.net.puretls.PureTLSImplementation

     

    Ignore it unless you are tyring to use the PureTLS SSL implementation. Tomcat tries to find different SSL implementations and defaults to JSSE if no others are found.

     

    JBoss-3.2.4+/Tomcat-5.0.x

    In jboss-3.2.4+ the tomcat-5.0.x container has its configuration in the jbossweb-tomcat50.sar/server.xml descriptor.

     

    JBoss-4.2.1

    In jboss-4.2.1 the web container has its configuration in the deploy/jboss-web.deployer/server.xml descriptor.

     

    JBoss-5 and later

    In JBoss 5 and later, the web deployer is configured from deploy/jbossweb.sar/server.xml.

     

     

     

    Using a trusted certificate obtained from a well known CA

     

    You may get the certificate in a format not appropriate for using it directly in JBoss/Tomcat. You may use the openssl tool to convert the certifcate and key in a suitable format:

     

    openssl pkcs12 -export -out server.keystore -in certificate.pem -inkey private.key 

     

    If you get an error like this

    10300:error:0D0680A8:asn1 encoding routines:ASN1_CHECK_TLEN:wrong tag:tasn_dec.c:1002:
    10300:error:0D07803A:asn1 encoding routines:ASN1_ITEM_EX_D2I:nested asn1 error:tasn_dec.c:305:Type=PKCS12

    you might have forgotten to add the "-export" option.

     

    You can check if you have a valid keystore with the keytool (comes with the JDK):

     

    $> keytool -list -keystore ssl.keystore -storetype PKCS12

    Enter keystore password:

    Keystore type: PKCS12
    Keystore provider: SunJSSE

    Your keystore contains 1 entry

    2, Jun 14, 2006, keyEntry,
    Certificate fingerprint (MD5): CB:47:4F:56:75:23:FA:9E:9C:7B:11:D9:8C:B3:D4:1E

     

    It's important that you have a keyEntry in there.

     


     

    Authentication scenarios

     

    In this section, we'll describe four typical SSL scenarios

    • 1 - SSL enabled on the server - the common case

    • 2 - SSL enabled on the server with self-signed client certs - aka mutual authentication - standalone HTTP client

    • 3 - SSL enabled on the server with self-signed client certs - aka mutual authentication - Web Browser Client

    • 4 - SSL enabled on the server with an openssl CA issued client cert - aka mutual authentication with CA issued client cert

     

    Setup

     

    • Grab a copy of the latest JBossAS release and explode it.

    • Download the java client client-server-certs.zip from the attachment section

    • Download the http client httpclient.zip from the attachment section

    • Download openssl if you don't have it so that a pkcs12 key can be generated from the client x509 cert to import into your browser. For win32 you can download Cygwin and for nix platforms you can either build the dist from source obtained from the OpenSSL Site or search the web for an rpm or other binary package as required for your platform.

     

     

     

     

     

    Use Cases

     

    1 - SSL enabled on the server - the common case

     

      In this configuration you need three files

     

     

    1. server.keystore - contains the key pair

    2. server.cer - server certificate exported from the keystore

    3. client.truststore - contains the server certificate

     

     

    • Create the server keystore

    keytool -genkey -alias serverkeys -keyalg RSA -keystore server.keystore -storepass 123456 -keypass 123456 -dname "CN=localhost, OU=MYOU, O=MYORG, L=MYCITY, ST=MYSTATE, C=MY"

     

     

    • Create the server certificate

    keytool -export -alias serverkeys -keystore server.keystore -storepass 123456 -file server.cer

     

     

    • Configure Tomcat

    Copy server.keystore to /server/xxx/conf and update the following in server.xml

    (For JBoss AS 4.2.1 don't forget two additional attributes: protocol="HTTP/1.1" and SSLEnabled="true".)

     

          <!-- SSL/TLS Connector configuration using the admin devl guide keystore-->
          <Connector port="8443" address="${jboss.bind.address}"
               maxThreads="100" strategy="ms" maxHttpHeaderSize="8192"
               emptySessionPath="true"
               scheme="https" secure="true" clientAuth="false"           
               sslProtocol = "TLS"
               keystoreFile="${jboss.server.home.dir}/conf/server.keystore"
               keystorePass="123456" 
           >
    </Connector>

     

     

    • Start the server

     run -c default

     

     

    • Creating client.truststore (by importing server certificate)

    keytool -import -v -keystore client.truststore  -storepass 123456 -file server.cer

     

     

    • Run the client

    java -Djavax.net.ssl.trustStore=client.truststore -Djavax.net.ssl.trustStorePassword=123456 acme/ReadHttpsURL2 https://localhost:8443

     

     

     

    2 - SSL enabled on the server with self-signed client certs - aka mutual authentication - standalone HTTP client

     

    To require that a http client presents a valid client certificate you need to add a clientAuth="true" attribute to the Connector configuration. Depending on how what root CA has signed the client cert you may need to also specify the truststoreFile and truststorePass for the keystore containing the client cert signer.

     

      In this configuration you need 6 files:

     

    1. server.keystore - contains the key pair

    2. server.cer - server certificate exported from the keystore

    3. client.truststore - contains the the server certificate

    4. client.keystore - contains the key pair

    5. client.cer - client certificate exported from the keystore

    6. server.truststore - contains the client certificate

     

     

    • Create the server keystore

    keytool -genkey -alias serverkeys -keyalg RSA -keystore server.keystore -storepass 123456 -keypass 123456 -dname "CN=localhost, OU=MYOU, O=MYORG, L=MYCITY, ST=MYSTATE, C=MY"

     

     

    • Create the server certificate

    keytool -export -alias serverkeys -keystore server.keystore -storepass 123456 -file server.cer

     

     

    • Create the client keystore

    keytool -genkey -alias clientkeys  -keyalg RSA -keystore client.keystore -storepass 123456 -keypass 123456 -dname "CN=localhost, OU=MYOU, O=MYORG, L=MYCITY, S=MYSTATE, C=MY" 

     

     

    • Create the client certificate

    keytool -export -alias clientkeys -keystore client.keystore -storepass 123456 -file client.cer

     

     

    • Import server certificate into client truststore

    keytool -import -v -keystore client.truststore  -storepass 123456 -file server.cer

     

     

    • Import client certificate into server truststore

    keytool -import -v -keystore server.truststore  -storepass 123456 -file client.cer

     

     

    • Update the Tomcat configuration

       

    Copy both server.keystore and server.truststore to /server/xxx/conf and update the following in server.xml

     

    NOTE: The attribute clientAuth is set to "true".

     

         <!-- SSL/TLS Connector configuration using the admin devl guide keystore-->
         <Connector port="8443" address="${jboss.bind.address}"
               maxThreads="100" strategy="ms" maxHttpHeaderSize="8192"
               emptySessionPath="true"
               scheme="https" secure="true" clientAuth="true"
               sslProtocol = "TLS"
               keystoreFile="${jboss.server.home.dir}/conf/server.keystore"
               keystorePass="123456" 
               truststoreFile="${jboss.server.home.dir}/conf/server.truststore"
               truststorePass="123456">

         </Connector>

     

     

    • Start the server

    run -c default

     

     

     

    • Run the client

    java -Djavax.net.ssl.keyStore=client.keystore -Djavax.net.ssl.keyStorePassword=123456 
           -Djavax.net.ssl.trustStore=client.truststore -Djavax.net.ssl.trustStorePassword=123456
            acme/ReadHttpsURL2 https://localhost:8443

     

     

     

     

     

     

    3 - SSL enabled on the server with self-signed client certs - aka mutual authentication - Web Browser Client

     

    • To enable mutual authentication between the client and server, a client cert must be generated. Both the client and server certs can be generated using the java keytool utility similar to how step 1 was done. An issue with using the client cert in a browser is that the cert must be imported into the browser from a key format such as pkcs12, and keytool does not currently support this format.

    Because of this, openssl must be used to generate the required format from the keytool x509 certificate. Since there are many steps in this process, the steps have been scripted in an ant 1.6.x build.xml file that can be found in the ClientServerCerts.zip attachment. Download and unpack this zip file to create a client-server-certs directory that contains the build.xml script.

    • Cd to client-server-certs, and simply run ant to generate the client and server certs, keystores and trustores. The output will be something like:

    [starksm@banshee9100 client-server-certs]$ ant

    Buildfile: build.xml

    self-signed-certs:
         [echo] keytool -genkey -alias clientCert -keyalg RSA -validity 730 -keystore client.keystore -dname cn=ClientCert,o=SomeCA,ou=SomeCAOrg -keypass clientcert -storepass clientcert

         [exec] Keystore type: jks
         [exec] Keystore provider: SUN

         [exec] Your keystore contains 1 entry

         [exec] clientcert, Jun 17, 2005, keyEntry,
         [exec] Certificate fingerprint (MD5): A4:60:1C:44:17:F8:B4:80:BA:BC:AA:CF:5C:E9:50:32
         [echo] keytool -genkey -alias serverCert -keyalg RSA -validity 730 -keystore server.keystore -dname cn=localhost,o=SomeCA,ou=SomeCAOrg -keypass servercert -storepass servercert

         [exec] Keystore type: jks
         [exec] Keystore provider: SUN

         [exec] Your keystore contains 1 entry

         [exec] servercert, Jun 17, 2005, keyEntry,
         [exec] Certificate fingerprint (MD5): E1:46:C5:54:22:6B:D6:E5:AF:E3:11:98:55:AC:17:C9
         [echo] keytool -export -alias clientCert -keystore client.keystore -storepass clientcert -file client.cer
         [exec] Certificate stored in file <client.cer>
         [exec] Owner: CN=ClientCert, O=SomeCA, OU=SomeCAOrg
         [exec] Issuer: CN=ClientCert, O=SomeCA, OU=SomeCAOrg
         [exec] Serial number: 42b37131
         [exec] Valid from: Fri Jun 17 17:56:17 PDT 2005 until: Sun Jun 17 17:56:17 PDT 2007
         [exec] Certificate fingerprints:
         [exec]      MD5:  A4:60:1C:44:17:F8:B4:80:BA:BC:AA:CF:5C:E9:50:32
         [exec]      SHA1: 29:66:59:3B:9F:9E:2B:C4:E0:1C:37:BB:7B:58:C3:DD:19:E5:DE:D4
         [echo] keytool -export -alias serverCert -keystore server.keystore -storepass servercert -file server.cer
         [exec] Certificate stored in file <server.cer>
         [exec] Owner: CN=localhost, O=SomeCA, OU=SomeCAOrg
         [exec] Issuer: CN=localhost, O=SomeCA, OU=SomeCAOrg
         [exec] Serial number: 42b37132
         [exec] Valid from: Fri Jun 17 17:56:18 PDT 2005 until: Sun Jun 17 17:56:18PDT 2007
         [exec] Certificate fingerprints:
         [exec]      MD5:  E1:46:C5:54:22:6B:D6:E5:AF:E3:11:98:55:AC:17:C9
         [exec]      SHA1: 12:BC:6D:D5:06:B7:49:CD:DA:F4:C2:9D:5F:3F:C2:9C:5D:AF:EA:15
         [echo] keytool -import -alias serverCert -keystore client.truststore -storepass clientcert -file server.cer
         [exec] Owner: CN=localhost, O=SomeCA, OU=SomeCAOrg
         [exec] Issuer: CN=localhost, O=SomeCA, OU=SomeCAOrg
         [exec] Trust this certificate? [no]:  Certificate was added to keystore
         [exec] Serial number: 42b37132
         [exec] Valid from: Fri Jun 17 17:56:18 PDT 2005 until: Sun Jun 17 17:56:18 PDT 2007
         [exec] Certificate fingerprints:
         [exec]      MD5:  E1:46:C5:54:22:6B:D6:E5:AF:E3:11:98:55:AC:17:C9
         [exec]      SHA1: 12:BC:6D:D5:06:B7:49:CD:DA:F4:C2:9D:5F:3F:C2:9C:5D:AF:EA:15
         [echo] keytool -import -alias clientCert -keystore server.truststore -storepass servercert -file client.cer
         [exec] Owner: CN=ClientCert, O=SomeCA, OU=SomeCAOrg
         [exec] Issuer: CN=ClientCert, O=SomeCA, OU=SomeCAOrg
         [exec] Trust this certificate? [no]:  Certificate was added to keystore
         [exec] Serial number: 42b37131
         [exec] Valid from: Fri Jun 17 17:56:17 PDT 2005 until: Sun Jun 17 17:56:17 PDT 2007
         [exec] Certificate fingerprints:
         [exec]      MD5:  A4:60:1C:44:17:F8:B4:80:BA:BC:AA:CF:5C:E9:50:32
         [exec]      SHA1: 29:66:59:3B:9F:9E:2B:C4:E0:1C:37:BB:7B:58:C3:DD:19:E5:DE:D4
         [echo] client.keystore contents:

         [exec] Keystore type: jks
         [exec] Keystore provider: SUN

         [exec] Your keystore contains 1 entry

         [exec] clientcert, Jun 17, 2005, keyEntry,
         [exec] Certificate fingerprint (MD5): A4:60:1C:44:17:F8:B4:80:BA:BC:AA:CF:5C:E9:50:32
         [echo] server.keystore contents:

         [exec] Keystore type: jks
         [exec] Keystore provider: SUN

         [exec] Your keystore contains 1 entry

         [exec] servercert, Jun 17, 2005, keyEntry,
         [exec] Certificate fingerprint (MD5): E1:46:C5:54:22:6B:D6:E5:AF:E3:11:98:55:AC:17:C9

    BUILD SUCCESSFUL
    Total time: 3 seconds
    [starksm@banshee9100 client-server-certs]$ ls
    build.xml    client.keystore*    server.cer*       server.truststore*
    client.cer*  client.truststore*  server.keystore*  src/
    • Next, create a pkcs12 formatted key to import into your browser. This is done by running the cer2pkcs12 target.

    [starksm@banshee9100 client-server-certs]$ ant cer2pkcs12
    Buildfile: build.xml

    cer2pkcs12:
        [mkdir] Created dir: C:\tmp\client-server-certs\classes
        [javac] Compiling 1 source file to C:\tmp\client-server-certs\classes
         [echo] openssl x509 -out client-pem.cer -outform pem -text -in client.cer -inform der
         [echo] openssl pkcs12 -export -out client.p12 -inkey client.8 -in client-pem.cer -passout pass:clientcert

    BUILD SUCCESSFUL
    Total time: 2 seconds
    [starksm@banshee9100 client-server-certs]$ ls
    build.xml       client.cer*       client.p8*          server.keystore*
    classes/        client.keystore*  client.truststore*  server.truststore*
    client-pem.cer  client.p12        server.cer*         src/
    • The resulting client.p12 file is the pkcs12 formatted private key for the x509 client cert created in the first step. This should be imported into your browser. For Mozilla Firefox 1.0.x, this entails selecting Tools/Options menu, selecting the Advanced section of the options dialog, and selecting the Manage Certificates... button to display the import dialog. The client.p12 password to use for the import is "clientcert", without the quotes.

    • You should also import the server.cer x509 cert into the Authorities section so that the server's self signed cert is seen as trusted. Otherwise, the browser should prompt you about an untrusted server cert when you try an https connection.

    • Next, copy the server.keystore and server.truststore to the jboss server/default/conf directory, or the conf directory of whatever server configuration you are using.

    • Next, edit the deploy/jbossweb-tomcat55.sar/server.xml file to enable the SSL connector. The Connector element should look like the following, with clientAuth="true" to require that clients provide a certificate.

          <!-- SSL/TLS Connector conf using the server.{keystore,truststore}
          -->

          <Connector port="8443" address="${jboss.bind.address}"
               protocol="HTTP/1.1" SSLEnabled="true"
               maxThreads="100" strategy="ms" maxHttpHeaderSize="8192"
               emptySessionPath="true"
               scheme="https" secure="true" clientAuth="true"
               keystoreFile="${jboss.server.home.dir}/conf/server.keystore"
               keystorePass="servercert"
               truststoreFile="${jboss.server.home.dir}/conf/server.truststore"
               truststorePass="servercert"
               sslProtocol = "TLS">

          </Connector>
    • You should now be able to connect to the jboss server using https and the browser should display a dialog asking for the cert to use (unless the browser is configured to do this automatically). An example of the dialog from the Firefox 1.0.4 browser is shown here:

     

     

     

     

     

     

    4 - SSL enabled on the server with an openssl CA issued client cert - aka mutual authentication with CA issued client cert

     

    • Install openssl and configure its CA

    First, you need to configure the certificate authority application of OpenSSL. churchillobjects.com has a good overview of the required steps in the Generating a Certificate Authority article. See the ca manpage for the full details of the OpenSSL ca command.

     

    • Create server openssl CA signed cert using keytool

    [starksm@banshee9100 openssl-ca]$ keytool -genkey -alias unit-tests-server -keystore localhost.keystore
    Enter keystore password:  unit-tests-server
    What is your first and last name?
      [Unknown]:  localhost
    What is the name of your organizational unit?
      [Unknown]:  QA
    What is the name of your organization?
      [Unknown]:  JBoss Inc.
    What is the name of your City or Locality?
      [Unknown]:  Snoqualmie Pass
    What is the name of your State or Province?
      [Unknown]:  Washington
    What is the two-letter country code for this unit?
      [Unknown]:  US
    Is CN=localhost, OU=QA, O=JBoss Inc., L=Snoqualmie Pass, ST=Washington, C=US correct?
      [no]:  yes

    Enter key password for <unit-tests-server>
            (RETURN if same as keystore password):

     

    • Create a cert signing request for the server key

    [starksm@banshee9100 conf]$ keytool -keystore localhost.keystore -certreq -alias unit-tests-server -file unit-tests-server.csr
    Enter keystore password:  unit-tests-server

     

    • Sign the cert request

    [starksm@banshee9100 openssl-ca]$ openssl ca -config openssl.cnf -in unit-tests
    -server.csr -out unit-tests-server.pem
    Using configuration from openssl.cnf
    Enter pass phrase for ./private/cakey.pem: openssl-ca
    DEBUG[load_index]: unique_subject = "no"
    Check that the request matches the signature
    Signature ok
    The Subject's Distinguished Name is as follows
    countryName           PRINTABLE:'US'
    stateOrProvinceName   PRINTABLE:'Washington'
    localityName          PRINTABLE:'Snoqualmie Pass'
    organizationName      PRINTABLE:'JBoss Inc.'
    organizationalUnitName:PRINTABLE:'QA'
    commonName            PRINTABLE:'localhost'
    Certificate is to be certified until Jul 30 21:39:21 2005 GMT (365 days)
    Sign the certificate? [y/n]:y


    1 out of 1 certificate requests certified, commit? [y/n]y
    Write out database with 1 new entries
    Data Base Updated

     

    • Convert to DER

    [starksm@banshee9100 openssl-ca]$ openssl x509 -in unit-tests-server.pem -out unit-tests-server.cer

     

    • import CA root to keystore

    [starksm@banshee9100 openssl-ca]$ keytool -keystore localhost.keystore -alias openssl-ca -import -file cacert.pem
    Enter keystore password:  unit-tests-server
    Owner: CN=jboss.com, C=US, ST=Washington, L=Snoqualmie Pass, EMAILADDRESS=admin@
    jboss.com, OU=QA, O=JBoss Inc.
    Issuer: CN=jboss.com, C=US, ST=Washington, L=Snoqualmie Pass, EMAILADDRESS=admin
    @jboss.com, OU=QA, O=JBoss Inc.
    Serial number: 0
    Valid from: Wed May 26 00:53:20 PDT 2004 until: Sat May 24 00:53:20 PDT 2014
    Certificate fingerprints:
             MD5:  B3:34:05:D0:7D:7E:18:A5:E3:0B:82:0A:D9:54:41:7E
             SHA1: F0:85:B4:14:8C:4E:92:CB:68:E6:D6:08:DC:86:94:E5:BF:DC:58:32
    Trust this certificate? [no]:  yes
    Certificate was added to keystore

     

    • Import CA reply

    [starksm@banshee9100 openssl-ca]$ keytool -keystore localhost.keystore -alias unit-tests-server -import -file unit-tests-server.cer
    Enter keystore password:  unit-tests-server
    Certificate reply was installed in keystore
    [starksm@banshee9100 openssl-ca]$ ls -l localhost.keystore
    -rwxrwxrwx    1 starksm  None         3247 Jul 30 14:44 localhost.keystore*
    [starksm@banshee9100 openssl-ca]$ keytool -list -keystore localhost.keystore
    Enter keystore password:  unit-tests-server

    Keystore type: jks
    Keystore provider: SUN

    Your keystore contains 2 entries

    unit-tests-server, Jul 30, 2004, keyEntry,
    Certificate fingerprint (MD5): 34:35:A5:4A:EB:F3:3C:F8:60:C1:86:05:07:01:4B:DD
    openssl-ca, Jul 30, 2004, trustedCertEntry,
    Certificate fingerprint (MD5): B3:34:05:D0:7D:7E:18:A5:E3:0B:82:0A:D9:54:41:7E

     

    • Import the client cert

    [starksm@banshee9100 openssl-ca]$ keytool -import -keystore localhost.keystore -alias unit-tests-client -file unit-tests-client.cer
    Enter keystore password:  unit-tests-server
    Certificate was added to keystore

    [starksm@banshee9100 openssl-ca]$ keytool -list -keystore localhost.keystore
    Enter keystore password:  unit-tests-server

    Keystore type: jks
    Keystore provider: SUN

    Your keystore contains 3 entries

    unit-tests-client, Jul 30, 2004, trustedCertEntry,
    Certificate fingerprint (MD5): 4A:9C:2B:CD:1B:50:AA:85:DD:89:F6:1D:F5:AF:9E:AB
    unit-tests-server, Jul 30, 2004, keyEntry,
    Certificate fingerprint (MD5): 34:35:A5:4A:EB:F3:3C:F8:60:C1:86:05:07:01:4B:DD
    openssl-ca, Jul 30, 2004, trustedCertEntry,
    Certificate fingerprint (MD5): B3:34:05:D0:7D:7E:18:A5:E3:0B:82:0A:D9:54:41:7E
    [starksm@banshee9100 openssl-ca]$

     

    Another (untested) keystore/openssl recipe:

     

    Create Keystore certificate:

     

    1. keytool -genkey -keystore {keystore location} -keyalg RSA -alias postgresql -dname "cn=www.beyarecords.com, ou=Music, o=Urban Music, c=GB" -keystore ~/postgresql -validity 365

    2. keytool -selfcert -keystore {keystore location} -alias postgresql

    3. keytool -export -keystore {keystore location} -alias postgresql -rfc -file postgresql.cer

    4. keytool -import -keystore {keystore location} -alias postgresql -file postgresql.cer

     

    Export private key from keystore alias:

     

    1. java ExportPrivateKey <keystore> <alias> <password> > exported-pkcs8.key

    2. openssl pkcs8 -inform PEM -nocrypt -in exported-pkcs8.key -out postgresql.key

     

    Note: main keystore location on OS X is: /library/java/home/lib/security/cacerts

     

     

    The ExportPrivateKey class:

    package security;

    import java.io.File;
    import java.io.FileInputStream;
    import java.security.Key;
    import java.security.KeyPair;
    import java.security.KeyStore;
    import java.security.KeyStoreException;
    import java.security.NoSuchAlgorithmException;
    import java.security.PrivateKey;
    import java.security.PublicKey;
    import java.security.UnrecoverableKeyException;
    import java.security.cert.Certificate;

    import sun.misc.BASE64Encoder;

    public class ExportPrivateKey
    {
       public static void main(String args[]) throws Exception
       {
          for (int i = 0; i < args.length; i++)
          {
             System.out.println(i + ": " + args);
          }
          if (args.length < 2)
          {
             //Yes I know this sucks (the password is visible to other users via ps
             // but this was a quick-n-dirty fix to export from a keystore to pkcs12
             // someday I may fix, but for now it'll have to do.
             System.err.println("Usage: java ExportPriv <keystore> <alias> <password>");
             System.exit(1);
          }
          ExportPrivateKey myep = new ExportPrivateKey();
          myep.doit(args[0], args[1], args[2]);
       }

       public void doit(String fileName, String aliasName, String pass) throws Exception
       {

          KeyStore ks = KeyStore.getInstance("JKS");

          char[] passPhrase = pass.toCharArray();
          BASE64Encoder myB64 = new BASE64Encoder();

          File certificateFile = new File(fileName);
          ks.load(new FileInputStream(certificateFile), passPhrase);

          KeyPair kp = getPrivateKey(ks, aliasName, passPhrase);

          PrivateKey privKey = kp.getPrivate();


          String b64 = myB64.encode(privKey.getEncoded());

          System.out.println("-----BEGIN PRIVATE KEY-----");
          System.out.println(b64);
          System.out.println("-----END PRIVATE KEY-----");

       }

    // From http://javaalmanac.com/egs/java.security/GetKeyFromKs.html

       public KeyPair getPrivateKey(KeyStore keystore, String alias, char[] password)
       {
          try
          {
             // Get private key
             Key key = keystore.getKey(alias, password);
             if (key instanceof PrivateKey)
             {
                // Get certificate of public key
                Certificate cert = keystore.getCertificate(alias);
       
                // Get public key
                PublicKey publicKey = cert.getPublicKey();
       
                // Return a key pair
                return new KeyPair(publicKey, (PrivateKey) key);
             }
          }
          catch (UnrecoverableKeyException e)
          {
          }
          catch (NoSuchAlgorithmException e)
          {
          }
          catch (KeyStoreException e)
          {
          }
          return null;
       }

    }

     

    More Info

     

    Another guide to creating certificates using OpenSSL and JBoss Setup - Creating an SSL Keystore Using the Java Keytool

     

     

    References