diff --git a/provider/consul_catalog_test.go b/provider/consul_catalog_test.go index fe9bc8d98..1c4e49763 100644 --- a/provider/consul_catalog_test.go +++ b/provider/consul_catalog_test.go @@ -236,7 +236,8 @@ func TestConsulCatalogBuildConfig(t *testing.T) { }, expectedFrontends: map[string]*types.Frontend{ "frontend-test": { - Backend: "backend-test", + Backend: "backend-test", + PassHostHeader: true, Routes: map[string]types.Route{ "route-host-test": { Rule: "Host:test.localhost", diff --git a/provider/docker.go b/provider/docker.go index 722a86a11..7169f20e1 100644 --- a/provider/docker.go +++ b/provider/docker.go @@ -279,7 +279,7 @@ func (provider *Docker) getPassHostHeader(container dockertypes.ContainerJSON) s if passHostHeader, err := getLabel(container, "traefik.frontend.passHostHeader"); err == nil { return passHostHeader } - return "false" + return "true" } func (provider *Docker) getEntryPoints(container dockertypes.ContainerJSON) []string { diff --git a/provider/docker_test.go b/provider/docker_test.go index ec0b15254..8cf5d2771 100644 --- a/provider/docker_test.go +++ b/provider/docker_test.go @@ -401,7 +401,6 @@ func TestDockerGetProtocol(t *testing.T) { func TestDockerGetPassHostHeader(t *testing.T) { provider := &Docker{} - containers := []struct { container docker.ContainerJSON expected string @@ -413,7 +412,7 @@ func TestDockerGetPassHostHeader(t *testing.T) { }, Config: &container.Config{}, }, - expected: "false", + expected: "true", }, { container: docker.ContainerJSON{ @@ -422,11 +421,11 @@ func TestDockerGetPassHostHeader(t *testing.T) { }, Config: &container.Config{ Labels: map[string]string{ - "traefik.frontend.passHostHeader": "true", + "traefik.frontend.passHostHeader": "false", }, }, }, - expected: "true", + expected: "false", }, } @@ -744,8 +743,9 @@ func TestDockerLoadDockerConfig(t *testing.T) { }, expectedFrontends: map[string]*types.Frontend{ "frontend-Host-test-docker-localhost": { - Backend: "backend-test", - EntryPoints: []string{}, + Backend: "backend-test", + PassHostHeader: true, + EntryPoints: []string{}, Routes: map[string]types.Route{ "route-frontend-Host-test-docker-localhost": { Rule: "Host:test.docker.localhost", @@ -816,8 +816,9 @@ func TestDockerLoadDockerConfig(t *testing.T) { }, expectedFrontends: map[string]*types.Frontend{ "frontend-Host-test1-docker-localhost": { - Backend: "backend-foobar", - EntryPoints: []string{"http", "https"}, + Backend: "backend-foobar", + PassHostHeader: true, + EntryPoints: []string{"http", "https"}, Routes: map[string]types.Route{ "route-frontend-Host-test1-docker-localhost": { Rule: "Host:test1.docker.localhost", @@ -825,8 +826,9 @@ func TestDockerLoadDockerConfig(t *testing.T) { }, }, "frontend-Host-test2-docker-localhost": { - Backend: "backend-foobar", - EntryPoints: []string{}, + Backend: "backend-foobar", + PassHostHeader: true, + EntryPoints: []string{}, Routes: map[string]types.Route{ "route-frontend-Host-test2-docker-localhost": { Rule: "Host:test2.docker.localhost", diff --git a/provider/kubernetes.go b/provider/kubernetes.go index 7f0758282..1235b6107 100644 --- a/provider/kubernetes.go +++ b/provider/kubernetes.go @@ -21,9 +21,10 @@ const ( // Kubernetes holds configurations of the Kubernetes provider. type Kubernetes struct { - BaseProvider `mapstructure:",squash"` - Endpoint string - Namespaces []string + BaseProvider `mapstructure:",squash"` + Endpoint string + disablePassHostHeaders bool + Namespaces []string } func (provider *Kubernetes) createClient() (k8s.Client, error) { @@ -142,6 +143,7 @@ func (provider *Kubernetes) loadIngresses(k8sClient k8s.Client) (*types.Configur map[string]*types.Backend{}, map[string]*types.Frontend{}, } + PassHostHeader := provider.getPassHostHeader() for _, i := range ingresses { for _, r := range i.Spec.Rules { for _, pa := range r.HTTP.Paths { @@ -152,8 +154,9 @@ func (provider *Kubernetes) loadIngresses(k8sClient k8s.Client) (*types.Configur } if _, exists := templateObjects.Frontends[r.Host+pa.Path]; !exists { templateObjects.Frontends[r.Host+pa.Path] = &types.Frontend{ - Backend: r.Host + pa.Path, - Routes: make(map[string]types.Route), + Backend: r.Host + pa.Path, + PassHostHeader: PassHostHeader, + Routes: make(map[string]types.Route), } } if _, exists := templateObjects.Frontends[r.Host+pa.Path].Routes[r.Host]; !exists { @@ -199,6 +202,13 @@ func (provider *Kubernetes) loadIngresses(k8sClient k8s.Client) (*types.Configur return &templateObjects, nil } +func (provider *Kubernetes) getPassHostHeader() bool { + if provider.disablePassHostHeaders { + return false + } + return true +} + func (provider *Kubernetes) loadConfig(templateObjects types.Configuration) *types.Configuration { var FuncMap = template.FuncMap{} configuration, err := provider.getConfiguration("templates/kubernetes.tmpl", FuncMap, templateObjects) diff --git a/provider/kubernetes_test.go b/provider/kubernetes_test.go index 0d110f2e1..1c1201247 100644 --- a/provider/kubernetes_test.go +++ b/provider/kubernetes_test.go @@ -139,7 +139,8 @@ func TestLoadIngresses(t *testing.T) { }, Frontends: map[string]*types.Frontend{ "foo/bar": { - Backend: "foo/bar", + Backend: "foo/bar", + PassHostHeader: true, Routes: map[string]types.Route{ "/bar": { Rule: "PathPrefixStrip:/bar", @@ -150,7 +151,8 @@ func TestLoadIngresses(t *testing.T) { }, }, "bar": { - Backend: "bar", + Backend: "bar", + PassHostHeader: true, Routes: map[string]types.Route{ "bar": { Rule: "Host:bar", @@ -167,6 +169,93 @@ func TestLoadIngresses(t *testing.T) { } } +func TestGetPassHostHeader(t *testing.T) { + ingresses := []k8s.Ingress{{ + Spec: k8s.IngressSpec{ + Rules: []k8s.IngressRule{ + { + Host: "foo", + IngressRuleValue: k8s.IngressRuleValue{ + HTTP: &k8s.HTTPIngressRuleValue{ + Paths: []k8s.HTTPIngressPath{ + { + Path: "/bar", + Backend: k8s.IngressBackend{ + ServiceName: "service1", + ServicePort: k8s.FromInt(801), + }, + }, + }, + }, + }, + }, + }, + }, + }} + services := []k8s.Service{ + { + ObjectMeta: k8s.ObjectMeta{ + Name: "service1", + UID: "1", + }, + Spec: k8s.ServiceSpec{ + ClusterIP: "10.0.0.1", + Ports: []k8s.ServicePort{ + { + Name: "http", + Port: 801, + }, + }, + }, + }, + } + watchChan := make(chan interface{}) + client := clientMock{ + ingresses: ingresses, + services: services, + watchChan: watchChan, + } + provider := Kubernetes{disablePassHostHeaders: true} + actual, err := provider.loadIngresses(client) + if err != nil { + t.Fatalf("error %+v", err) + } + + expected := &types.Configuration{ + Backends: map[string]*types.Backend{ + "foo/bar": { + Servers: map[string]types.Server{ + "1": { + URL: "http://10.0.0.1:801", + Weight: 1, + }, + }, + CircuitBreaker: nil, + LoadBalancer: nil, + }, + }, + Frontends: map[string]*types.Frontend{ + "foo/bar": { + Backend: "foo/bar", + Routes: map[string]types.Route{ + "/bar": { + Rule: "PathPrefixStrip:/bar", + }, + "foo": { + Rule: "Host:foo", + }, + }, + }, + }, + } + actualJSON, _ := json.Marshal(actual) + expectedJSON, _ := json.Marshal(expected) + + if !reflect.DeepEqual(actual, expected) { + t.Fatalf("expected %+v, got %+v", string(expectedJSON), string(actualJSON)) + } +} + func TestLoadNamespacedIngresses(t *testing.T) { ingresses := []k8s.Ingress{ { @@ -330,7 +419,8 @@ func TestLoadNamespacedIngresses(t *testing.T) { }, Frontends: map[string]*types.Frontend{ "foo/bar": { - Backend: "foo/bar", + Backend: "foo/bar", + PassHostHeader: true, Routes: map[string]types.Route{ "/bar": { Rule: "PathPrefixStrip:/bar", @@ -341,7 +431,8 @@ func TestLoadNamespacedIngresses(t *testing.T) { }, }, "bar": { - Backend: "bar", + Backend: "bar", + PassHostHeader: true, Routes: map[string]types.Route{ "bar": { Rule: "Host:bar", @@ -556,7 +647,8 @@ func TestLoadMultipleNamespacedIngresses(t *testing.T) { }, Frontends: map[string]*types.Frontend{ "foo/bar": { - Backend: "foo/bar", + Backend: "foo/bar", + PassHostHeader: true, Routes: map[string]types.Route{ "/bar": { Rule: "PathPrefixStrip:/bar", @@ -567,7 +659,8 @@ func TestLoadMultipleNamespacedIngresses(t *testing.T) { }, }, "bar": { - Backend: "bar", + Backend: "bar", + PassHostHeader: true, Routes: map[string]types.Route{ "bar": { Rule: "Host:bar", @@ -575,7 +668,8 @@ func TestLoadMultipleNamespacedIngresses(t *testing.T) { }, }, "awesome/quix": { - Backend: "awesome/quix", + Backend: "awesome/quix", + PassHostHeader: true, Routes: map[string]types.Route{ "/quix": { Rule: "PathPrefixStrip:/quix", diff --git a/provider/kv_test.go b/provider/kv_test.go index 99df7a72e..3e1502529 100644 --- a/provider/kv_test.go +++ b/provider/kv_test.go @@ -430,7 +430,7 @@ func TestKVLoadConfig(t *testing.T) { Frontends: map[string]*types.Frontend{ "frontend.with.dot": { Backend: "backend.with.dot.too", - PassHostHeader: false, + PassHostHeader: true, EntryPoints: []string{}, Routes: map[string]types.Route{ "route.with.dot": { diff --git a/provider/marathon.go b/provider/marathon.go index 64f8b2e9f..63ba9d8c0 100644 --- a/provider/marathon.go +++ b/provider/marathon.go @@ -316,7 +316,7 @@ func (provider *Marathon) getPassHostHeader(application marathon.Application) st if passHostHeader, err := provider.getLabel(application, "traefik.frontend.passHostHeader"); err == nil { return passHostHeader } - return "false" + return "true" } func (provider *Marathon) getEntryPoints(application marathon.Application) []string { diff --git a/provider/marathon_test.go b/provider/marathon_test.go index def8d5595..ff5f79f10 100644 --- a/provider/marathon_test.go +++ b/provider/marathon_test.go @@ -82,8 +82,9 @@ func TestMarathonLoadConfig(t *testing.T) { }, expectedFrontends: map[string]*types.Frontend{ `frontend-test`: { - Backend: "backend-test", - EntryPoints: []string{}, + Backend: "backend-test", + PassHostHeader: true, + EntryPoints: []string{}, Routes: map[string]types.Route{ `route-host-test`: { Rule: "Host:test.docker.localhost", @@ -780,15 +781,15 @@ func TestMarathonGetPassHostHeader(t *testing.T) { }{ { application: marathon.Application{}, - expected: "false", + expected: "true", }, { application: marathon.Application{ Labels: map[string]string{ - "traefik.frontend.passHostHeader": "true", + "traefik.frontend.passHostHeader": "false", }, }, - expected: "true", + expected: "false", }, } diff --git a/templates/consul_catalog.tmpl b/templates/consul_catalog.tmpl index 69feab01a..7724fd2b9 100644 --- a/templates/consul_catalog.tmpl +++ b/templates/consul_catalog.tmpl @@ -29,7 +29,7 @@ {{range .Services}} [frontends.frontend-{{.ServiceName}}] backend = "backend-{{.ServiceName}}" - passHostHeader = {{getAttribute "frontend.passHostHeader" .Attributes "false"}} + passHostHeader = {{getAttribute "frontend.passHostHeader" .Attributes "true"}} {{$entryPoints := getAttribute "frontend.entrypoints" .Attributes ""}} {{with $entryPoints}} entrypoints = [{{range getEntryPoints $entryPoints}} diff --git a/templates/kubernetes.tmpl b/templates/kubernetes.tmpl index 1f7dfaba1..27d0bd540 100644 --- a/templates/kubernetes.tmpl +++ b/templates/kubernetes.tmpl @@ -9,6 +9,7 @@ [frontends]{{range $frontendName, $frontend := .Frontends}} [frontends."{{$frontendName}}"] backend = "{{$frontend.Backend}}" + passHostHeader = {{$frontend.PassHostHeader}} {{range $routeName, $route := $frontend.Routes}} [frontends."{{$frontendName}}".routes."{{$routeName}}"] rule = "{{$route.Rule}}" diff --git a/templates/kv.tmpl b/templates/kv.tmpl index 70f257990..32c227af9 100644 --- a/templates/kv.tmpl +++ b/templates/kv.tmpl @@ -39,7 +39,7 @@ {{$entryPoints := SplitGet . "/entrypoints"}} [frontends."{{$frontend}}"] backend = "{{Get "" . "/backend"}}" - passHostHeader = {{Get "false" . "/passHostHeader"}} + passHostHeader = {{Get "true" . "/passHostHeader"}} entryPoints = [{{range $entryPoints}} "{{.}}", {{end}}]