package rpcclient import ( "crypto/tls" "crypto/x509" "fmt" "net/http" "os" ) // TransportHook ... type TransportHook = func(*http.Transport) func TLSClientConfig(rootCAs []string, certFile, keyFile string) (*tls.Config, error) { certificate, err := tls.LoadX509KeyPair(certFile, keyFile) if err != nil { return nil, fmt.Errorf("read client certificate: %w", err) } caCertPool := x509.NewCertPool() for _, name := range rootCAs { caCertFile, err := os.ReadFile(name) if err != nil { return nil, fmt.Errorf("read CA certificate: %w", err) } caCertPool.AppendCertsFromPEM(caCertFile) } return &tls.Config{ RootCAs: caCertPool, Certificates: []tls.Certificate{certificate}, InsecureSkipVerify: len(rootCAs) == 0, }, nil } // MTLSTransportHook enables client certificate advertising as well as retricting the set of rootCA we accept. func MTLSTransportHook(rootCAs []string, certFile, keyFile string) (func(*http.Transport), error) { cfg, err := TLSClientConfig(rootCAs, certFile, keyFile) if err != nil { return nil, err } return func(tr *http.Transport) { tr.TLSClientConfig = cfg }, nil }