Configure TLS for Spinnaker Services

Spinnaker services communicate with each other and can exchange potentially sensitive data. Enabling TLS between services ensures that this data is encrypted and that a service will only communicate with another service that has a valid certificate.

Switching from plain HTTP to HTTPS will cause some short disruption to the services as they become healthy at different times.

Overview of TLS

When a client attempts to communicate with a server over SSL:

  • the server must present a certificate to the user.
  • the client must validate that certificate by checking it against its known valid certificate authorities (CA).

To properly set up TLS between services, we need to provide each service with:

  1. a certificate signed by a CA
  2. the CA certificate to verify these certificates

Note that distributing a CA public key is only needed if you sign certificates with a CA that is not bundled in most systems. In this document, we assume that you are using a self-signed CA.


Java services can present #1 as a keystore and #2 as a trust store in PKCS12 (preferred) or JKS format.


Golang services need a X509 certificate (PEM format) and a private key for #1 as well as the X509 certificate of the CA for #2.

What you need

The following table lists the Armory and Spinnaker services, their type (Java or Golang), and which certificates they need:

Service Type Server Client
Clouddriver Java Yes Yes
Deck N/A - -
Dinghy* Golang Yes Yes
Echo Java Yes Yes
Fiat Java Yes Yes
Front50 Java Yes Yes
Gate Java Maybe Yes
Kayenta Java Yes Yes
Igor Java Yes Yes
Orca Java Yes Yes
Rosco Java Yes Yes
Terraformer* Golang Yes Yes
  • Dinghy is the service for Pipelines-as-Code.
  • Terraformer is the service for the Armory Terraform Integration.

Note: Gate may be handled differently if you already terminating SSL at Gate. If not, make sure the load balancer and ingress you are using supports self-signed certificates.

In the following sections, you need to have the following information available:

  • ca.pem (all Golang servers): the CA certificate in PEM format
  • [service].crt (each Golang server): the certificate and (optionally) the private key of the Golang server in PEM format
  • [service].key (each Golang server): the private key of the Golang server if not bundled with the certificate you’re using
  • [GOSERVICE]_KEY_PASS (each Golang server): the password to the private key of the server
  • truststore.p12 (all Java clients): a PKCS12 truststore with CA certificate imported
  • TRUSTSTORE_PASS (all Java clients): the password to the truststore you’re using
  • [service].p12 (each Java server): a PKCS12 keystore containing the certificate and private key of the server
  • [SERVICE]_KEY_PASS (each Java server): the password to the keystore you’re using

The server certificate will serve as its client certificate to other services. You can generate different certificates and use them in ok-http-client.key-store* (Java) and http.key* (Golang).

To learn how to generate these files, see the Generate Certificates for Spinnaker guide.

Configuring Java services

Add the following to each Java service profile under profiles in the SpinnakerService’s profiles:

# Only needed for "server" role
    enabled: true
    key-store: <reference to [service].p12>
    key-store-type: PKCS12
    key-store-password: <[SERVICE]_KEY_PASS>

# Needed for all Java services
  key-store: <reference to truststore.p12>
  key-store-type: PKCS12
  key-store-password: <TRUSTSTORE_PASS>
  trust-store: <reference to truststore.p12>
  trust-store-type: PKCS12
  trust-store-password: <TRUSTSTORE_PASS>

Currently, ok-http-client.key-store is required even though it is not used in a simple TLS setup.

Configuring Golang services

    enabled: true
    certFile: <reference to [service].crt>
    keyFile: <reference to [service].key if not included in the certFile's PEM>
    keyPassword: <[GOSERVICE]_KEY_PASS if required>

  cacertFile: <reference to ca.pem>

Changing service endpoints

Use the Operator to change Spinnaker’s service endpoints.

Change the SpinnakerService custom resource:

kind: SpinnakerService
        baseUrl: https://spin-clouddriver.<NAMESPACE>:7002
        baseUrl: https://spin-dinghy.<NAMESPACE>:8081
        baseUrl: https://spin-echo.<NAMESPACE>:8089
        baseUrl: https://spin-fiat.<NAMESPACE>:7003
        baseUrl: https://spin-front50.<NAMESPACE>:8080
        baseUrl: https://spin-gate.<NAMESPACE>:8084
        baseUrl: https://spin-kayenta.<NAMESPACE>:8090
        baseUrl: https://spin-orca.<NAMESPACE>:8083
        baseUrl: https://spin-igor.<NAMESPACE>:8088
        baseUrl: https://spin-rosco.<NAMESPACE>:8087
        baseUrl: https://spin-terraformer.<NAMESPACE>:7088

Deploying Spinnaker

After you finish modifying the service YAML files, run kubectl -n <spinnaker namespace> apply -f <SpinnakerService manifest> to apply your changes to your Spinnaker deployment.

Switching from plain HTTP to HTTPS will cause some short disruption to the services as they become healthy at different times.

Providing certificates and passwords to services

Secret engines

You can store secrets (and non secrets) in supported secret stores as well as in Kubernetes secrets if using the Armory Operator. This is the simplest route.

For instance, assuming all the information is stored in a bucket named mybucket on s3 that all services have access to, SpinnakerService manifest might look like:

kind: SpinnakerService
  name: spinnaker
            enabled: true
            key-store: encryptedFile:s3!b:mybucket!r:us-west-2!f:echo.jks
            key-store-type: JKS
            key-alias: echo
            key-store-password: encrypted:s3!b:mybucket!r:us-west-2!f:passwords.yml!k:echo.keyPassword

          key-store: encryptedFile:s3!b:mybucket!r:us-west-2!f:truststore.jks
          key-store-type: JKS
          key-store-password: encrypted:s3!b:mybucket!r:us-west-2!f:passwords.yml!k:truststorePassword
          trust-store: encryptedFile:s3!b:mybucket!r:us-west-2!f:truststore.jks
          trust-store-type: JKS
          trust-store-password: encrypted:s3!b:mybucket!r:us-west-2!f:passwords.yml!k:truststorePassword

Run kubectl -n <spinnaker namespace> apply -f <SpinnakerService manifest> after you make your changes.

Manually providing information

An alternative if you cannot use one of the supported secret engine is to store the information in Kubernetes secrets and manually provide the information. Files are added through a volumeMount and passwords through an environment variable.

For instance, assuming mysecrets Kubernetes Secret is available in the same namespace as Spinnaker with the following keys:

  echo.jks: <base64 encoded keystore>

We’ll now provide the following in service-settings/echo.yml:

  - name: secretvol
    mountPath: /var/mysecrets

And a reference would then be:

    key-store: /var/mysecrets/echo.jks

Apply your changes.

Last modified December 9, 2022: (77a2e500)