Creating Certificates

The following sections explain how obtain certificates from a commercial Certificate Authority and how to create self-signed test certificates.

Using Keytool

The keytool utility creates and manages certificates and cryptographic keys, and is part of the standard JDK distribution. The keytool executable usually lives in $JAVA_HOME/bin.

keytool stores certificates and keys in a file known as a keystore . While several different keystore types are supported, by default keytool uses the Java KeyStore (JKS) format.

Java-based services such as HDFS, MapReduce, and YARN use the JKS format by default. For this reason, it is convenient to use keytool for managing keys and certificates for these services. In the following topics, we assume you are using keytool.

For additional information on keytool, refer the keytool documentation.

Using OpenSSL

Hue and other Python-based services expect certificates and keys to be stored in PEM format. You can manage such services with the openssl tool.

Obtaining a Production Certificate from a Commercial CA

Once you have decided on a certificate-provisioning strategy, and have determined which hosts require certificates, you will typically purchase the necessary certificates from a commercial Certificate Authority (CA). The procedure for applying for a certificate varies from one CA to another, but typically involves providing some form of proof that you are the legitimate owner of the domain name for which you are requesting a certificate, generating a key pair, and submitting a Certificate Signing Request (CSR) to the CA.

As noted above, you may find it convenient to use the Java keytool utility to generate your key pair and CSR, and to manage your certificates. The CA you choose will provide instructions for obtaining and installing a certificate; typically, there will be separate sets of instructions for different web and application servers. The instructions for Java-based servers (Tomcat, for example), will usually describe the following process comprising three keytool commands to obtain a certificate:

  1. keytool -genkeypair to generate a public/private key pair and create the keystore.
  2. keytool -certreq to create the CSR.
  3. keytool -importcert to import the signed certificate into the keystore.
For example, to generate a public/private key pair for the domain name node1.example.com, you would use a command similar to the one shown below:
$ keytool -genkeypair -keystore node1.keystore -alias node1 \
-dname "CN=node1.example.com,O=Hadoop" -keyalg RSA \
-keysize 2048 -storepass changeme -keypass changeme

This command generates a pair of 2048-bit keys using the RSA key algorithm, one of several available. The keys are stored in a keystore file called node1.keystore, in a keystore entry identified by by the alias node1. The keystore password (which protects the keystore as a whole) and the key password (which protects the private key stored in the node1 entry) are set using the -storepass and -keypass options (respectively). -keypass must be set to the same password value as -storepass for Cloudera Manager to access the keystore.

To create a CSR, you would use a command similar to the following:

$ keytool -certreq -keystore node1.keystore -alias node1 \
-storepass changeme -keypass changeme -file node1.csr

This command generates the CSR, and stores it in a file called node1.csr. Set -keypass to the same value as -storepass (Cloudera Manager does not support separate values for -keypass and -storepass.)

Once you've submitted your CSR to the CA, and received the CA's reply (containing the signed certificate), you will use the following keytool -importcert command to import the reply into your keystore:
$ keytool -importcert -keystore node1.keystore -alias node1 \
-storepass changeme -keypass changeme -trustcacerts -file node1.crt

Here we assume that the CA's reply is stored in the file node1.crt.

Creating Self-Signed Test Certificates

It is also possible to create your own test certificates. These certificates are typically self-signed; that is, they are signed by your own private key, rather than that of an external CA. Such test certificates are useful during testing.

To generate a self-signed certificate, use keytool -genkeypair. (In addition to creating a public/private key pair, this command wraps the public key into a self-signed certificate.)

For example, the following command creates a self-signed test certificate for the host node1.example.com, and stores it in a keystore named node1.keystore:
$ keytool -genkeypair -keystore node1.keystore -keyalg RSA \
-alias node1 -dname "CN=node1.example.com,O=Hadoop" \
-storepass changeme -keypass changeme -validity <val_days>

Set -keypass to the same value as -storepass (Cloudera Manager does not support separate values for -keypass and -storepass.)

By default, self-signed certificates are only valid for 90 days. To increase this period, replace <val_days> in the previous command's -validity <val_days> parameter to specify the number of days for which the certificate should be considered valid.

Requirements for TLS/SSL Certificates

When you enable Level 3 TLS/SSL, the Cloudera Manager Agents will be required to authenticate themselves to the Cloudera Manager Server. This means the certificates used by the Agents must have flags set for Web Server Authentication, as well as Web Client Authentication. Typically, Certificate Authorities (CAs) enable only the Web Server Authentication flag by default. Therefore, to make sure the Agents can use the same certificates to authenticate themselves to the Cloudera Manager Server as clients, you must include this request when you generate a certificate-signing request (CSR) for the CA.

Use the following instructions to generate certificates with the TLS Web Client Authentication flag set.

If you are using openssl
  1. Create a local copy of the default openssl.cnf file, usually found at /etc/pki/tls/openssl.cnf (this may change according to your OS).
    cp /etc/pki/tls/openssl.cnf ./myopenssl.cnf
  2. Add the following section to the end of the file:
    cat >> ./myopenssl.cnf <<EOF
    [ cloudera_req ]
    basicConstraints = CA:FALSE
    keyUsage = nonRepudiation, digitalSignature, keyEncipherment
    extendedKeyUsage = serverAuth, clientAuth
    EOF
  3. Run the following command to generate a CSR:
    $  openssl req -subj  '/CN=hostname.sec.cloudera.com/OU=Support/O=Cloudera/L=Denver/ST=Colorado/C=US' \
    -config ./myopenssl.cnf -reqexts cloudera_req  \
    -out /opt/cloudera/security/x509/hostname.csr -new -newkey rsa:2048 \ 
    -keyout /opt/cloudera/security/x509/hostname.key -passout pass:password
  4. Examine the CSR to make sure the requested options are present under the X509v3 Extended Key Usage field.
    $ openssl req -text -noout -verify -in hostname.csr
    ...
                X509v3 Extended Key Usage: 
                    TLS Web Server Authentication, TLS Web Client Authentication
    ...
If you are using keytool
  1. Add the -ext EKU=serverAuth,clientAuth option to the keytool command you use to generate the CSR. For example:
    $ keytool -certreq -alias hostname  \
    -keystore /opt/cloudera/security/jks/hostname-keystore.jks  \ 
    -file /opt/cloudera/security/x509/hostname.csr  \
    -ext EKU=serverAuth,clientAuth  \ 
    -storepass password -keypass password
  2. Examine the CSR to make sure the requested options are present under the ExtendedKeyUsages section.
    $ keytool -printcert -v -file hostname.csr
    ...
    ObjectId: 2.5.29.37 Criticality=false
    ExtendedKeyUsages [
      serverAuth
      clientAuth
    ...