From 429ecca9db91a07752b95e2363c3af10a92ad394 Mon Sep 17 00:00:00 2001 From: Benjamin Sago Date: Fri, 9 Jun 2023 01:34:27 +0100 Subject: [PATCH] mconsul supports https, cacert, and env vars --- mconsul/globals.go | 55 +++++++++++++++++++++++++++++++++++++++++++-- mconsul/kv.go | 5 ++--- mconsul/services.go | 5 ++--- 3 files changed, 57 insertions(+), 8 deletions(-) diff --git a/mconsul/globals.go b/mconsul/globals.go index 57d111a..bb20f08 100644 --- a/mconsul/globals.go +++ b/mconsul/globals.go @@ -1,10 +1,61 @@ package mconsul +import ( + "crypto/tls" + "crypto/x509" + "errors" + "fmt" + "net/http" + "os" + "strings" +) -// GlobalAddress is the address of the Consul server to communicate with. This + +// globalAddress is the address of the Consul server to communicate with. This // gets put in URLs. -var GlobalAddress string +var globalAddress string // GlobalRandomSelection holds whether to return a random address of a service, // rather than the nearest one to the Consul agent. var GlobalRandomSelection bool + +var httpClient *http.Client + +// Init sets up the HTTP client to use for Consul-related activities, using +// environment variables to configure it. +func Init() error { + envAddr := os.Getenv("CONSUL_HTTP_ADDR") + envCaCert := os.Getenv("CONSUL_CACERT") + + if envAddr == "" { + return errors.New("$CONSUL_HTTP_ADDR missing") + } + + if ! (strings.HasPrefix(envAddr, "http://") || strings.HasPrefix(envAddr, "https://")) { + return errors.New("consul address must start with ‘http://’ or ‘https://’") + } + + var cert []byte + var err error + if envCaCert != "" { + cert, err = os.ReadFile(envCaCert) + if err != nil { + return fmt.Errorf("failed to read cacert file: %w", err) + } + } + + globalAddress = envAddr + + if cert != nil { + caCertPool := x509.NewCertPool() + caCertPool.AppendCertsFromPEM(cert) + + config := &tls.Config{RootCAs: caCertPool} + tr := &http.Transport{TLSClientConfig: config} + httpClient = &http.Client{Transport: tr} + } else { + httpClient = &http.Client{} + } + + return nil +} diff --git a/mconsul/kv.go b/mconsul/kv.go index 6947221..6c0a647 100644 --- a/mconsul/kv.go +++ b/mconsul/kv.go @@ -24,7 +24,7 @@ func FetchValueFromKvStore(key string) ([]byte, error) { func fetchValueFromKvStore(key string) ([]byte, error) { // Construct the request - endpoint := fmt.Sprintf("http://%s/v1/kv/%s", GlobalAddress, key) + endpoint := fmt.Sprintf("%s/v1/kv/%s", globalAddress, key) req, err := http.NewRequest("GET", endpoint, nil) if err != nil { err = fmt.Errorf("failed to construct request: %w", err) @@ -38,8 +38,7 @@ func fetchValueFromKvStore(key string) ([]byte, error) { } // Make the request and wait for a response - client := &http.Client{} - resp, err := client.Do(req) + resp, err := httpClient.Do(req) if err != nil { err = fmt.Errorf("failed to make HTTP call: %w", err) return nil, err diff --git a/mconsul/services.go b/mconsul/services.go index 7af83e5..f7e77d5 100644 --- a/mconsul/services.go +++ b/mconsul/services.go @@ -29,7 +29,7 @@ func FetchServiceAddress(serviceName string) (*FoundService, error) { func fetchServiceAddress(serviceName string) (*FoundService, error) { // Construct the request - endpoint := fmt.Sprintf("http://%s/v1/catalog/service/%s?near=_agent", GlobalAddress, serviceName) + endpoint := fmt.Sprintf("%s/v1/catalog/service/%s?near=_agent", globalAddress, serviceName) req, err := http.NewRequest("GET", endpoint, nil) if err != nil { err = fmt.Errorf("failed to construct request: %w", err) @@ -43,8 +43,7 @@ func fetchServiceAddress(serviceName string) (*FoundService, error) { } // Make the request and wait for a response - client := &http.Client{} - resp, err := client.Do(req) + resp, err := httpClient.Do(req) if err != nil { err = fmt.Errorf("failed to make HTTP request: %w", err) return nil, err -- 2.45.2