Skip to content

Instantly share code, notes, and snippets.

@fkurz
Last active March 18, 2019 20:04
Show Gist options
  • Save fkurz/73a5a77093df3094efdb1f529b3a2956 to your computer and use it in GitHub Desktop.
Save fkurz/73a5a77093df3094efdb1f529b3a2956 to your computer and use it in GitHub Desktop.
Snippet: Registering an extra certificate authority in a Golang HTTP client

Registering a certificate authority in a Golang HTTP client

Problem

You want to register an extra certificate authority to be recognized by a http.Client instance when issuing requests.

I personally encountered this case while testing a HTTPS service with a key pair issued by a Kubernetes cluster.

Solution

Step-By-Step

  1. Get the system certificate pool (or fallback to a new certificate pool)
rootCAs, _ := x509.SystemCertPool()
if rootCAs == nil {
  rootCAs = x509.NewCertPool()
}
  1. Read the CA certificate file you want to add
certs, err := ioutil.ReadFile(certificateLocation)
if err != nil {
  return nil, e
}
  1. Add the CA certificate file to the system certificate pool
if ok := rootCAs.AppendCertsFromPEM(certs); !ok {
  return nil, fmt.Errorf("Failed to append Minikube CA certificate to certificate chain")
}
  1. Create a tls.Config struct using the root certificates pool
tlsConfig := &tls.Config{
  RootCAs: rootCAs,
}

You can use the tlsConfig we just created in a http.Client by passing it via the Transport property:

transport := &http.Transport{
  TLSClientConfig: tlsConfig,
}
httpClient := &http.Client{Transport: transport}

Full Code

Note: Not tested

import (
  "io/ioutil"
  "crypto/x509"
  "crypto/tls"
  "fmt"
)

func NewCaAwareTlsConfig(certificateLocation string) (*tls.Config, error) {
  rootCAs, _ := x509.SystemCertPool()
  if rootCAs == nil {
    rootCAs = x509.NewCertPool()
  }

  certs, err := ioutil.ReadFile(certificateLocation)
  if err != nil {
    return nil, e
  }

  if ok := rootCAs.AppendCertsFromPEM(certs); !ok {
    return nil, fmt.Errorf("Failed to append Minikube CA certificate to certificate chain")
  }

  return &tls.Config{
    RootCAs: rootCAs,
  }
}

Sources

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment