diff --git a/pkg/apiserver/apiserver_test.go b/pkg/apiserver/apiserver_test.go index fdefac6615d..3bab81bbac8 100644 --- a/pkg/apiserver/apiserver_test.go +++ b/pkg/apiserver/apiserver_test.go @@ -231,7 +231,7 @@ func handleInternal(legacy bool, storage map[string]rest.Storage, admissionContr container := restful.NewContainer() container.Router(restful.CurlyRouter{}) mux := container.ServeMux - if err := group.InstallREST(&RestContainer{container, 0}); err != nil { + if err := group.InstallREST(&RestContainer{container, 0}, nil); err != nil { panic(fmt.Sprintf("unable to install container %s: %v", group.Version, err)) } ws := new(restful.WebService) @@ -1901,7 +1901,7 @@ func TestParentResourceIsRequired(t *testing.T) { Codec: newCodec, } container := restful.NewContainer() - if err := group.InstallREST(&RestContainer{container, 0}); err == nil { + if err := group.InstallREST(&RestContainer{container, 0}, nil); err == nil { t.Fatal("expected error") } @@ -1929,7 +1929,7 @@ func TestParentResourceIsRequired(t *testing.T) { Codec: newCodec, } container = restful.NewContainer() - if err := group.InstallREST(&RestContainer{container, 0}); err != nil { + if err := group.InstallREST(&RestContainer{container, 0}, nil); err != nil { t.Fatal(err) } diff --git a/pkg/apiserver/proxy.go b/pkg/apiserver/proxy.go index 3f5bd826ac0..aa1967bceee 100644 --- a/pkg/apiserver/proxy.go +++ b/pkg/apiserver/proxy.go @@ -121,7 +121,8 @@ func (r *ProxyHandler) ServeHTTP(w http.ResponseWriter, req *http.Request) { httpCode = http.StatusNotFound return } - if r.dial != nil { + // If we have a custom dialer, and no pre-existing transport, initialize it to use the dialer. + if transport == nil && r.dial != nil { transport = &http.Transport{Dial: r.dial} } diff --git a/pkg/client/helper.go b/pkg/client/helper.go index 8f58ab722a4..8834526a834 100644 --- a/pkg/client/helper.go +++ b/pkg/client/helper.go @@ -102,6 +102,9 @@ type KubeletConfig struct { // HTTPTimeout is used by the client to timeout http requests to Kubelet. HTTPTimeout time.Duration + + // Dial is a custom dialer used for the client + Dial func(net, addr string) (net.Conn, error) } // TLSClientConfig contains settings to enable transport layer security diff --git a/pkg/client/kubelet.go b/pkg/client/kubelet.go index f456f071127..fbdeff1677f 100644 --- a/pkg/client/kubelet.go +++ b/pkg/client/kubelet.go @@ -45,14 +45,20 @@ type ConnectionInfoGetter interface { // HTTPKubeletClient is the default implementation of KubeletHealthchecker, accesses the kubelet over HTTP. type HTTPKubeletClient struct { Client *http.Client + Config *KubeletConfig Port uint EnableHttps bool } -// TODO: this structure is questionable, it should be using client.Config and overriding defaults. -func NewKubeletClient(config *KubeletConfig) (KubeletClient, error) { - transport := http.DefaultTransport - +func MakeTransport(config *KubeletConfig) (http.RoundTripper, error) { + var transport http.RoundTripper + if config.Dial == nil { + transport = http.DefaultTransport + } else { + transport = &http.Transport{ + Dial: config.Dial, + } + } cfg := &Config{TLSClientConfig: config.TLSClientConfig} if config.EnableHttps { hasCA := len(config.CAFile) > 0 || len(config.CAData) > 0 @@ -69,13 +75,22 @@ func NewKubeletClient(config *KubeletConfig) (KubeletClient, error) { TLSClientConfig: tlsConfig, } } + return transport, nil +} +// TODO: this structure is questionable, it should be using client.Config and overriding defaults. +func NewKubeletClient(config *KubeletConfig) (KubeletClient, error) { + transport, err := MakeTransport(config) + if err != nil { + return nil, err + } c := &http.Client{ Transport: transport, Timeout: config.HTTPTimeout, } return &HTTPKubeletClient{ Client: c, + Config: config, Port: config.Port, EnableHttps: config.EnableHttps, }, nil diff --git a/pkg/cloudprovider/fake/fake.go b/pkg/cloudprovider/fake/fake.go index b3a235f543d..ed81d523899 100644 --- a/pkg/cloudprovider/fake/fake.go +++ b/pkg/cloudprovider/fake/fake.go @@ -17,6 +17,7 @@ limitations under the License. package fake_cloud import ( + "errors" "fmt" "net" "regexp" diff --git a/pkg/master/master.go b/pkg/master/master.go index 9619255defa..c95af6769da 100644 --- a/pkg/master/master.go +++ b/pkg/master/master.go @@ -506,6 +506,21 @@ func (m *Master) init(c *Config) { } m.setupSecureProxy(c.SSHUser, c.SSHKeyfile) proxyDialer = m.Dial + + // This is pretty ugly. A better solution would be to pull this all the way up into the + // server.go file. + httpKubeletClient, ok := c.KubeletClient.(*client.HTTPKubeletClient) + if ok { + httpKubeletClient.Config.Dial = m.Dial + transport, err := client.MakeTransport(httpKubeletClient.Config) + if err != nil { + glog.Errorf("Error setting up transport over SSH: %v", err) + } else { + httpKubeletClient.Client.Transport = transport + } + } else { + glog.Errorf("Failed to cast %v to HTTPKubeletClient, skipping SSH tunnel.") + } } apiVersions := []string{}