mirror of
https://github.com/traefik/traefik.git
synced 2026-10-28 08:36:10 +08:00
Bump to go1.27
This commit is contained in:
1 parent
ef51566a5f
commit
84d9df3ce1
30 files changed
+568
-601
No files matched your search
@@ -6,7 +6,7 @@ on:
|
||||
- '*'
|
||||
|
||||
env:
|
||||
GOLANGCI_LINT_VERSION: v2.13.2
|
||||
GOLANGCI_LINT_VERSION: v2.14.0
|
||||
MISSPELL_VERSION: v0.7.0
|
||||
|
||||
jobs:
|
||||
|
||||
+1
-1
@@ -1 +1 @@
|
||||
1.26
|
||||
1.27
|
||||
+9
-11
@@ -18,17 +18,15 @@ type TraefikCmdConfiguration struct {
|
||||
// NewTraefikConfiguration creates a TraefikCmdConfiguration with default values.
|
||||
func NewTraefikConfiguration() *TraefikCmdConfiguration {
|
||||
return &TraefikCmdConfiguration{
|
||||
Configuration: static.Configuration{
|
||||
Global: &static.Global{
|
||||
CheckNewVersion: true,
|
||||
},
|
||||
EntryPoints: make(static.EntryPoints),
|
||||
Providers: &static.Providers{
|
||||
ProvidersThrottleDuration: ptypes.Duration(2 * time.Second),
|
||||
},
|
||||
ServersTransport: &static.ServersTransport{
|
||||
MaxIdleConnsPerHost: 200,
|
||||
},
|
||||
Global: &static.Global{
|
||||
CheckNewVersion: true,
|
||||
},
|
||||
EntryPoints: make(static.EntryPoints),
|
||||
Providers: &static.Providers{
|
||||
ProvidersThrottleDuration: ptypes.Duration(2 * time.Second),
|
||||
},
|
||||
ServersTransport: &static.ServersTransport{
|
||||
MaxIdleConnsPerHost: 200,
|
||||
},
|
||||
ConfigFile: "",
|
||||
}
|
||||
|
||||
@@ -1196,3 +1196,34 @@ As the rejection happens before the routing, the rejected requests are not repor
|
||||
They are only visible at the `DEBUG` log level.
|
||||
|
||||
To tunnel traffic through a forward proxy exposed by Traefik, route it with a [TCP router](../routing/routers/index.md#configuring-tcp-routers) instead.
|
||||
|
||||
## v2.11.61
|
||||
|
||||
Starting with `v2.11.61`, Traefik is built with Go 1.27.
|
||||
|
||||
### GODEBUG TLS Settings
|
||||
|
||||
Go 1.27 removed the `tlsrsakex`, `tls10server` and `tls3des` `GODEBUG` settings.
|
||||
Setting them in the `GODEBUG` environment variable has no effect anymore.
|
||||
|
||||
For the incoming connections, the RSA key exchange and 3DES cipher suites, as well as TLS 1.0 and 1.1,
|
||||
can still be enabled with the `cipherSuites` and `minVersion` fields of the [TLS options](../https/tls.md#tls-options),
|
||||
referenced in the TLS configuration of a [router](../routing/routers/index.md#tls) or of an [entrypoint](../routing/entrypoints.md#tls).
|
||||
|
||||
For the connections to the backends, Traefik does not offer to configure the cipher suites,
|
||||
so the RSA key exchange and 3DES cipher suites are not available anymore.
|
||||
A backend supporting only these cipher suites cannot be reached.
|
||||
|
||||
Please check out the [go documentation](https://go.dev/doc/go1.27#cryptotlspkgcryptotls) for more details.
|
||||
|
||||
### Maximum Number of Request Header Values
|
||||
|
||||
Go 1.27 limits the number of header values a request can carry to 500.
|
||||
|
||||
A request exceeding this limit is rejected with a `431 Request Header Fields Too Large` response,
|
||||
for HTTP/1 and HTTP/2.
|
||||
This limit is not configurable.
|
||||
|
||||
As the rejection happens before the routing, the rejected requests are not reported in the access logs.
|
||||
|
||||
Please check out the [go documentation](https://go.dev/doc/go1.27#nethttppkgnethttp) for more details.
|
||||
@@ -1,6 +1,6 @@
|
||||
module github.com/traefik/traefik/v2
|
||||
|
||||
go 1.26.0
|
||||
go 1.27.0
|
||||
|
||||
require (
|
||||
github.com/BurntSushi/toml v1.6.0
|
||||
@@ -60,10 +60,12 @@ require (
|
||||
github.com/prometheus/client_model v0.6.2
|
||||
github.com/quic-go/quic-go v0.59.1
|
||||
github.com/rancher/go-rancher-metadata v0.0.0-20200311180630-7f4c936a06ac // No tag on the repo.
|
||||
github.com/samber/slog-logrus/v2 v2.5.4
|
||||
github.com/sirupsen/logrus v1.10.2
|
||||
github.com/stretchr/testify v1.12.1
|
||||
github.com/stvp/go-udp-testing v0.0.0-20191102171040-06b61409b154 // No tag on the repo.
|
||||
github.com/testcontainers/testcontainers-go v0.42.0
|
||||
github.com/testcontainers/testcontainers-go/modules/k3s v0.42.0
|
||||
github.com/traefik/paerser v0.2.2
|
||||
github.com/traefik/yaegi v0.16.1
|
||||
github.com/uber/jaeger-client-go v2.30.0+incompatible
|
||||
@@ -89,6 +91,7 @@ require (
|
||||
k8s.io/utils v0.0.0-20251002143259-bc988d571ff4 // No tag on the repo.
|
||||
mvdan.cc/xurls/v2 v2.5.0
|
||||
sigs.k8s.io/gateway-api v0.4.0
|
||||
sigs.k8s.io/structured-merge-diff/v6 v6.3.0
|
||||
)
|
||||
|
||||
require (
|
||||
@@ -330,7 +333,6 @@ require (
|
||||
github.com/sagikazarmark/slog-shim v0.1.0 // indirect
|
||||
github.com/samber/lo v1.53.0 // indirect
|
||||
github.com/samber/slog-common v0.21.0 // indirect
|
||||
github.com/samber/slog-logrus/v2 v2.5.4
|
||||
github.com/scaleway/scaleway-sdk-go v1.0.0-beta.36 // indirect
|
||||
github.com/secure-systems-lab/go-securesystemslib v0.10.0 // indirect
|
||||
github.com/segmentio/fasthash v1.0.3 // indirect
|
||||
@@ -349,7 +351,6 @@ require (
|
||||
github.com/stretchr/objx v0.5.3 // indirect
|
||||
github.com/subosito/gotenv v1.6.0 // indirect
|
||||
github.com/tencentcloud/tencentcloud-sdk-go/tencentcloud/common v1.3.106 // indirect
|
||||
github.com/testcontainers/testcontainers-go/modules/k3s v0.42.0
|
||||
github.com/tinylib/msgp v1.6.3 // indirect
|
||||
github.com/tjfoc/gmsm v1.4.1 // indirect
|
||||
github.com/tklauser/go-sysconf v0.3.16 // indirect
|
||||
@@ -410,7 +411,6 @@ require (
|
||||
k8s.io/kube-openapi v0.0.0-20250910181357-589584f1c912 // indirect
|
||||
sigs.k8s.io/json v0.0.0-20250730193827-2d320260d730 // indirect
|
||||
sigs.k8s.io/randfill v1.0.0 // indirect
|
||||
sigs.k8s.io/structured-merge-diff/v6 v6.3.0
|
||||
sigs.k8s.io/yaml v1.6.0 // indirect
|
||||
software.sslmate.com/src/go-pkcs12 v0.7.3 // indirect
|
||||
)
|
||||
|
||||
@@ -1378,10 +1378,8 @@ func (s *HTTPSSuite) modifyCertificateConfFileContent(certFileName, confFileName
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*traefiktls.CertAndStores{
|
||||
{
|
||||
Certificate: traefiktls.Certificate{
|
||||
CertFile: traefiktls.FileOrContent("fixtures/https/" + certFileName + ".cert"),
|
||||
KeyFile: traefiktls.FileOrContent("fixtures/https/" + certFileName + ".key"),
|
||||
},
|
||||
CertFile: traefiktls.FileOrContent("fixtures/https/" + certFileName + ".cert"),
|
||||
KeyFile: traefiktls.FileOrContent("fixtures/https/" + certFileName + ".key"),
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
@@ -12,17 +12,12 @@ import (
|
||||
// Middleware tests based on https://github.com/unrolled/secure
|
||||
|
||||
func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
type expected struct {
|
||||
statusCode int
|
||||
location string
|
||||
}
|
||||
|
||||
testCases := []struct {
|
||||
expected
|
||||
|
||||
desc string
|
||||
host string
|
||||
cfg dynamic.Headers
|
||||
desc string
|
||||
host string
|
||||
cfg dynamic.Headers
|
||||
expectedStatusCode int
|
||||
expectedLocation string
|
||||
}{
|
||||
{
|
||||
desc: "http should return a 301",
|
||||
@@ -32,10 +27,8 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
SSLForceHost: true,
|
||||
SSLHost: "powpow.example.com",
|
||||
},
|
||||
expected: expected{
|
||||
statusCode: http.StatusMovedPermanently,
|
||||
location: "https://powpow.example.com",
|
||||
},
|
||||
expectedStatusCode: http.StatusMovedPermanently,
|
||||
expectedLocation: "https://powpow.example.com",
|
||||
},
|
||||
{
|
||||
desc: "http sub domain should return a 301",
|
||||
@@ -45,10 +38,8 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
SSLForceHost: true,
|
||||
SSLHost: "powpow.example.com",
|
||||
},
|
||||
expected: expected{
|
||||
statusCode: http.StatusMovedPermanently,
|
||||
location: "https://powpow.example.com",
|
||||
},
|
||||
expectedStatusCode: http.StatusMovedPermanently,
|
||||
expectedLocation: "https://powpow.example.com",
|
||||
},
|
||||
{
|
||||
desc: "https should return a 200",
|
||||
@@ -58,7 +49,7 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
SSLForceHost: true,
|
||||
SSLHost: "powpow.example.com",
|
||||
},
|
||||
expected: expected{statusCode: http.StatusOK},
|
||||
expectedStatusCode: http.StatusOK,
|
||||
},
|
||||
{
|
||||
desc: "https sub domain should return a 301",
|
||||
@@ -68,10 +59,8 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
SSLForceHost: true,
|
||||
SSLHost: "powpow.example.com",
|
||||
},
|
||||
expected: expected{
|
||||
statusCode: http.StatusMovedPermanently,
|
||||
location: "https://powpow.example.com",
|
||||
},
|
||||
expectedStatusCode: http.StatusMovedPermanently,
|
||||
expectedLocation: "https://powpow.example.com",
|
||||
},
|
||||
{
|
||||
desc: "http without force host and sub domain should return a 301",
|
||||
@@ -81,10 +70,8 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
SSLForceHost: false,
|
||||
SSLHost: "powpow.example.com",
|
||||
},
|
||||
expected: expected{
|
||||
statusCode: http.StatusMovedPermanently,
|
||||
location: "https://powpow.example.com",
|
||||
},
|
||||
expectedStatusCode: http.StatusMovedPermanently,
|
||||
expectedLocation: "https://powpow.example.com",
|
||||
},
|
||||
{
|
||||
desc: "https without force host and sub domain should return a 301",
|
||||
@@ -94,7 +81,7 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
SSLForceHost: false,
|
||||
SSLHost: "powpow.example.com",
|
||||
},
|
||||
expected: expected{statusCode: http.StatusOK},
|
||||
expectedStatusCode: http.StatusOK,
|
||||
},
|
||||
}
|
||||
|
||||
@@ -112,8 +99,8 @@ func Test_newSecure_sslForceHost(t *testing.T) {
|
||||
|
||||
mid.ServeHTTP(rw, req)
|
||||
|
||||
assert.Equal(t, test.expected.statusCode, rw.Result().StatusCode)
|
||||
assert.Equal(t, test.expected.location, rw.Header().Get("Location"))
|
||||
assert.Equal(t, test.expectedStatusCode, rw.Result().StatusCode)
|
||||
assert.Equal(t, test.expectedLocation, rw.Header().Get("Location"))
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
@@ -152,11 +152,9 @@ func createMessage(certs map[string]*Certificate) dynamic.Message {
|
||||
|
||||
for _, cert := range certs {
|
||||
certConf := &traefiktls.CertAndStores{
|
||||
Certificate: traefiktls.Certificate{
|
||||
CertFile: traefiktls.FileOrContent(cert.Certificate),
|
||||
KeyFile: traefiktls.FileOrContent(cert.Key),
|
||||
},
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
CertFile: traefiktls.FileOrContent(cert.Certificate),
|
||||
KeyFile: traefiktls.FileOrContent(cert.Key),
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
}
|
||||
conf.Configuration.TLS.Certificates = append(conf.Configuration.TLS.Certificates, certConf)
|
||||
}
|
||||
|
||||
@@ -775,11 +775,9 @@ func (p *Provider) buildMessage() dynamic.Message {
|
||||
|
||||
for _, cert := range p.certificates {
|
||||
certConf := &traefiktls.CertAndStores{
|
||||
Certificate: traefiktls.Certificate{
|
||||
CertFile: traefiktls.FileOrContent(cert.Certificate.Certificate),
|
||||
KeyFile: traefiktls.FileOrContent(cert.Key),
|
||||
},
|
||||
Stores: []string{cert.Store},
|
||||
CertFile: traefiktls.FileOrContent(cert.Certificate.Certificate),
|
||||
KeyFile: traefiktls.FileOrContent(cert.Key),
|
||||
Stores: []string{cert.Store},
|
||||
}
|
||||
conf.Configuration.TLS.Certificates = append(conf.Configuration.TLS.Certificates, certConf)
|
||||
}
|
||||
|
||||
@@ -49,9 +49,7 @@ func TestGetUncheckedCertificates(t *testing.T) {
|
||||
domains: []string{"*.traefik.wtf"},
|
||||
acmeCertificates: []*CertAndStore{
|
||||
{
|
||||
Certificate: Certificate{
|
||||
Domain: types.Domain{Main: "*.traefik.wtf"},
|
||||
},
|
||||
Domain: types.Domain{Main: "*.traefik.wtf"},
|
||||
},
|
||||
},
|
||||
expectedDomains: nil,
|
||||
@@ -72,9 +70,7 @@ func TestGetUncheckedCertificates(t *testing.T) {
|
||||
domains: []string{"traefik.wtf", "foo.traefik.wtf"},
|
||||
acmeCertificates: []*CertAndStore{
|
||||
{
|
||||
Certificate: Certificate{
|
||||
Domain: types.Domain{Main: "traefik.wtf"},
|
||||
},
|
||||
Domain: types.Domain{Main: "traefik.wtf"},
|
||||
},
|
||||
},
|
||||
expectedDomains: []string{"foo.traefik.wtf"},
|
||||
@@ -90,9 +86,7 @@ func TestGetUncheckedCertificates(t *testing.T) {
|
||||
domains: []string{"traefik.wtf"},
|
||||
acmeCertificates: []*CertAndStore{
|
||||
{
|
||||
Certificate: Certificate{
|
||||
Domain: types.Domain{Main: "traefik.wtf"},
|
||||
},
|
||||
Domain: types.Domain{Main: "traefik.wtf"},
|
||||
},
|
||||
},
|
||||
expectedDomains: nil,
|
||||
@@ -108,9 +102,7 @@ func TestGetUncheckedCertificates(t *testing.T) {
|
||||
domains: []string{"who.traefik.wtf", "foo.traefik.wtf"},
|
||||
acmeCertificates: []*CertAndStore{
|
||||
{
|
||||
Certificate: Certificate{
|
||||
Domain: types.Domain{Main: "*.traefik.wtf"},
|
||||
},
|
||||
Domain: types.Domain{Main: "*.traefik.wtf"},
|
||||
},
|
||||
},
|
||||
expectedDomains: nil,
|
||||
@@ -120,9 +112,7 @@ func TestGetUncheckedCertificates(t *testing.T) {
|
||||
domains: []string{"traefik.wtf", "foo.traefik.wtf"},
|
||||
acmeCertificates: []*CertAndStore{
|
||||
{
|
||||
Certificate: Certificate{
|
||||
Domain: types.Domain{Main: "*.traefik.wtf"},
|
||||
},
|
||||
Domain: types.Domain{Main: "*.traefik.wtf"},
|
||||
},
|
||||
},
|
||||
expectedDomains: []string{"traefik.wtf"},
|
||||
|
||||
@@ -276,10 +276,8 @@ func TestDefaultRule(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
p := Provider{
|
||||
Configuration: Configuration{
|
||||
ExposedByDefault: true,
|
||||
DefaultRule: test.defaultRule,
|
||||
},
|
||||
ExposedByDefault: true,
|
||||
DefaultRule: test.defaultRule,
|
||||
}
|
||||
|
||||
err := p.Init()
|
||||
@@ -3160,12 +3158,10 @@ func Test_buildConfiguration(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
p := Provider{
|
||||
Configuration: Configuration{
|
||||
ExposedByDefault: true,
|
||||
DefaultRule: "Host(`{{ normalize .Name }}.traefik.wtf`)",
|
||||
ConnectAware: test.ConnectAware,
|
||||
Constraints: test.constraints,
|
||||
},
|
||||
ExposedByDefault: true,
|
||||
DefaultRule: "Host(`{{ normalize .Name }}.traefik.wtf`)",
|
||||
ConnectAware: test.ConnectAware,
|
||||
Constraints: test.constraints,
|
||||
}
|
||||
|
||||
err := p.Init()
|
||||
|
||||
@@ -199,23 +199,21 @@ func TestListServices(t *testing.T) {
|
||||
dockerVersion: "1.30",
|
||||
networks: []networktypes.Summary{
|
||||
{
|
||||
Network: networktypes.Network{
|
||||
Name: "network_name",
|
||||
ID: "yk6l57rfwizjzxxzftn4amaot",
|
||||
Created: time.Now(),
|
||||
Scope: "swarm",
|
||||
Driver: "overlay",
|
||||
EnableIPv6: false,
|
||||
Internal: true,
|
||||
Ingress: false,
|
||||
ConfigOnly: false,
|
||||
Options: map[string]string{
|
||||
"com.docker.networktypes.driver.overlay.vxlanid_list": "4098",
|
||||
"com.docker.networktypes.enable_ipv6": "false",
|
||||
},
|
||||
Labels: map[string]string{
|
||||
"com.docker.stack.namespace": "test",
|
||||
},
|
||||
Name: "network_name",
|
||||
ID: "yk6l57rfwizjzxxzftn4amaot",
|
||||
Created: time.Now(),
|
||||
Scope: "swarm",
|
||||
Driver: "overlay",
|
||||
EnableIPv6: false,
|
||||
Internal: true,
|
||||
Ingress: false,
|
||||
ConfigOnly: false,
|
||||
Options: map[string]string{
|
||||
"com.docker.networktypes.driver.overlay.vxlanid_list": "4098",
|
||||
"com.docker.networktypes.enable_ipv6": "false",
|
||||
},
|
||||
Labels: map[string]string{
|
||||
"com.docker.stack.namespace": "test",
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -256,23 +254,21 @@ func TestListServices(t *testing.T) {
|
||||
dockerVersion: "1.30",
|
||||
networks: []networktypes.Summary{
|
||||
{
|
||||
Network: networktypes.Network{
|
||||
Name: "network_name",
|
||||
ID: "yk6l57rfwizjzxxzftn4amaot",
|
||||
Created: time.Now(),
|
||||
Scope: "swarm",
|
||||
Driver: "overlay",
|
||||
EnableIPv6: false,
|
||||
Internal: true,
|
||||
Ingress: false,
|
||||
ConfigOnly: false,
|
||||
Options: map[string]string{
|
||||
"com.docker.networktypes.driver.overlay.vxlanid_list": "4098",
|
||||
"com.docker.networktypes.enable_ipv6": "false",
|
||||
},
|
||||
Labels: map[string]string{
|
||||
"com.docker.stack.namespace": "test",
|
||||
},
|
||||
Name: "network_name",
|
||||
ID: "yk6l57rfwizjzxxzftn4amaot",
|
||||
Created: time.Now(),
|
||||
Scope: "swarm",
|
||||
Driver: "overlay",
|
||||
EnableIPv6: false,
|
||||
Internal: true,
|
||||
Ingress: false,
|
||||
ConfigOnly: false,
|
||||
Options: map[string]string{
|
||||
"com.docker.networktypes.driver.overlay.vxlanid_list": "4098",
|
||||
"com.docker.networktypes.enable_ipv6": "false",
|
||||
},
|
||||
Labels: map[string]string{
|
||||
"com.docker.stack.namespace": "test",
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
@@ -8,24 +8,19 @@ import (
|
||||
"github.com/stretchr/testify/require"
|
||||
traefikcrdfake "github.com/traefik/traefik/v2/pkg/provider/kubernetes/crd/generated/clientset/versioned/fake"
|
||||
corev1 "k8s.io/api/core/v1"
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
kubefake "k8s.io/client-go/kubernetes/fake"
|
||||
)
|
||||
|
||||
func TestClientIgnoresHelmOwnedSecrets(t *testing.T) {
|
||||
secret := &corev1.Secret{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Namespace: "default",
|
||||
Name: "secret",
|
||||
},
|
||||
Namespace: "default",
|
||||
Name: "secret",
|
||||
}
|
||||
helmSecret := &corev1.Secret{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Namespace: "default",
|
||||
Name: "helm-secret",
|
||||
Labels: map[string]string{
|
||||
"owner": "helm",
|
||||
},
|
||||
Namespace: "default",
|
||||
Name: "helm-secret",
|
||||
Labels: map[string]string{
|
||||
"owner": "helm",
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
@@ -1127,10 +1127,8 @@ func getTLS(k8sClient Client, secretName, namespace string) (*tls.CertAndStores,
|
||||
}
|
||||
|
||||
return &tls.CertAndStores{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent(cert),
|
||||
KeyFile: tls.FileOrContent(key),
|
||||
},
|
||||
CertFile: tls.FileOrContent(cert),
|
||||
KeyFile: tls.FileOrContent(key),
|
||||
}, nil
|
||||
}
|
||||
|
||||
|
||||
@@ -720,10 +720,8 @@ func TestLoadIngressRouteTCPs(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -3647,10 +3645,8 @@ func TestLoadIngressRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -5070,11 +5066,9 @@ func TestLoadIngressRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
Stores: []string{"default"},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
Stores: []string{"default"},
|
||||
},
|
||||
},
|
||||
Stores: map[string]tls.Store{
|
||||
|
||||
@@ -1387,10 +1387,8 @@ func getTLS(k8sClient Client, secretName gatev1alpha2.ObjectName, namespace stri
|
||||
}
|
||||
|
||||
return &tls.CertAndStores{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent(cert),
|
||||
KeyFile: tls.FileOrContent(key),
|
||||
},
|
||||
CertFile: tls.FileOrContent(cert),
|
||||
KeyFile: tls.FileOrContent(key),
|
||||
}, nil
|
||||
}
|
||||
|
||||
|
||||
@@ -8,7 +8,6 @@ import (
|
||||
"github.com/traefik/traefik/v2/pkg/config/dynamic"
|
||||
"github.com/traefik/traefik/v2/pkg/provider"
|
||||
"github.com/traefik/traefik/v2/pkg/tls"
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
"k8s.io/utils/ptr"
|
||||
gatev1alpha2 "sigs.k8s.io/gateway-api/apis/v1alpha2"
|
||||
)
|
||||
@@ -470,10 +469,8 @@ func TestLoadHTTPRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -705,10 +702,8 @@ func TestLoadHTTPRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -1110,10 +1105,8 @@ func TestLoadHTTPRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -1195,10 +1188,8 @@ func TestLoadHTTPRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -2003,10 +1994,8 @@ func TestLoadTCPRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -2485,10 +2474,8 @@ func TestLoadTLSRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -2694,10 +2681,8 @@ func TestLoadTLSRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -2762,10 +2747,8 @@ func TestLoadTLSRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -3552,10 +3535,8 @@ func TestLoadMixedRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -3726,10 +3707,8 @@ func TestLoadMixedRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -3960,10 +3939,8 @@ func TestLoadMixedRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -4107,10 +4084,8 @@ func TestLoadMixedRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -4235,10 +4210,8 @@ func TestLoadMixedRoutes(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -4708,10 +4681,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "No ParentRefs",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4725,10 +4696,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Unsupported Kind",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4750,10 +4719,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Unsupported Group",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4775,10 +4742,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Kind is nil",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4799,10 +4764,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Group is nil",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4823,10 +4786,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "SectionName does not match a listener desc",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4848,10 +4809,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Namespace does not match the Gateway namespace",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4873,10 +4832,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Route namespace does not match the Gateway namespace",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4897,10 +4854,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Unsupported Kind",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4922,10 +4877,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Route namespace matches the Gateway namespace",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4946,10 +4899,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Namespace matches the Gateway namespace",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
@@ -4971,10 +4922,8 @@ func Test_shouldAttach(t *testing.T) {
|
||||
{
|
||||
desc: "Only one ParentRef matches the Gateway",
|
||||
gateway: &gatev1alpha2.Gateway{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
Name: "gateway",
|
||||
Namespace: "default",
|
||||
},
|
||||
listener: gatev1alpha2.Listener{
|
||||
Name: "foo",
|
||||
|
||||
@@ -134,18 +134,14 @@ func TestIsLoadBalancerIngressEquals(t *testing.T) {
|
||||
|
||||
func TestClientIgnoresHelmOwnedSecrets(t *testing.T) {
|
||||
secret := &corev1.Secret{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Namespace: "default",
|
||||
Name: "secret",
|
||||
},
|
||||
Namespace: "default",
|
||||
Name: "secret",
|
||||
}
|
||||
helmSecret := &corev1.Secret{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Namespace: "default",
|
||||
Name: "helm-secret",
|
||||
Labels: map[string]string{
|
||||
"owner": "helm",
|
||||
},
|
||||
Namespace: "default",
|
||||
Name: "helm-secret",
|
||||
Labels: map[string]string{
|
||||
"owner": "helm",
|
||||
},
|
||||
}
|
||||
|
||||
@@ -190,22 +186,18 @@ func TestClientIgnoresHelmOwnedSecrets(t *testing.T) {
|
||||
|
||||
func TestClientIgnoresEmptyEndpointUpdates(t *testing.T) {
|
||||
emptyEndpoint := &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "empty-endpoint",
|
||||
Namespace: "test",
|
||||
ResourceVersion: "1244",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "_",
|
||||
},
|
||||
Name: "empty-endpoint",
|
||||
Namespace: "test",
|
||||
ResourceVersion: "1244",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "_",
|
||||
},
|
||||
}
|
||||
|
||||
filledEndpoint := &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "filled-endpoint",
|
||||
Namespace: "test",
|
||||
ResourceVersion: "1234",
|
||||
},
|
||||
Name: "filled-endpoint",
|
||||
Namespace: "test",
|
||||
ResourceVersion: "1234",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.13.37.1",
|
||||
@@ -289,17 +281,13 @@ func TestClientIgnoresEmptyEndpointUpdates(t *testing.T) {
|
||||
|
||||
func TestClientUsesCorrectServerVersion(t *testing.T) {
|
||||
ingressV1Beta := &netv1beta1.Ingress{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Namespace: "default",
|
||||
Name: "ingress-v1beta",
|
||||
},
|
||||
Namespace: "default",
|
||||
Name: "ingress-v1beta",
|
||||
}
|
||||
|
||||
ingressV1 := &netv1.Ingress{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Namespace: "default",
|
||||
Name: "ingress-v1",
|
||||
},
|
||||
Namespace: "default",
|
||||
Name: "ingress-v1",
|
||||
}
|
||||
|
||||
kubeClient := kubefake.NewClientset(ingressV1Beta, ingressV1)
|
||||
|
||||
@@ -483,10 +483,8 @@ func getCertificates(ctx context.Context, ingress *netv1.Ingress, k8sClient Clie
|
||||
}
|
||||
|
||||
tlsConfigs[configKey] = &tls.CertAndStores{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent(cert),
|
||||
KeyFile: tls.FileOrContent(key),
|
||||
},
|
||||
CertFile: tls.FileOrContent(cert),
|
||||
KeyFile: tls.FileOrContent(key),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -15,7 +15,6 @@ import (
|
||||
"github.com/traefik/traefik/v2/pkg/types"
|
||||
corev1 "k8s.io/api/core/v1"
|
||||
netv1 "k8s.io/api/networking/v1"
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
)
|
||||
|
||||
var _ provider.Provider = (*Provider)(nil)
|
||||
@@ -824,10 +823,8 @@ func TestLoadConfigurationFromIngresses(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("-----BEGIN CERTIFICATE-----\n-----END CERTIFICATE-----"),
|
||||
KeyFile: tls.FileOrContent("-----BEGIN PRIVATE KEY-----\n-----END PRIVATE KEY-----"),
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -2135,10 +2132,8 @@ func TestGetCertificates(t *testing.T) {
|
||||
client: clientMock{
|
||||
secrets: []*corev1.Secret{
|
||||
{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
},
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
Data: map[string][]byte{
|
||||
"tls.key": []byte("tls-key"),
|
||||
},
|
||||
@@ -2153,10 +2148,8 @@ func TestGetCertificates(t *testing.T) {
|
||||
client: clientMock{
|
||||
secrets: []*corev1.Secret{
|
||||
{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
},
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
Data: map[string][]byte{
|
||||
"tls.crt": []byte("tls-crt"),
|
||||
},
|
||||
@@ -2171,11 +2164,9 @@ func TestGetCertificates(t *testing.T) {
|
||||
client: clientMock{
|
||||
secrets: []*corev1.Secret{
|
||||
{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
},
|
||||
Data: map[string][]byte{},
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
Data: map[string][]byte{},
|
||||
},
|
||||
},
|
||||
},
|
||||
@@ -2198,20 +2189,16 @@ func TestGetCertificates(t *testing.T) {
|
||||
client: clientMock{
|
||||
secrets: []*corev1.Secret{
|
||||
{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "test-secret2",
|
||||
Namespace: "testing",
|
||||
},
|
||||
Name: "test-secret2",
|
||||
Namespace: "testing",
|
||||
Data: map[string][]byte{
|
||||
"tls.crt": []byte("tls-crt"),
|
||||
"tls.key": []byte("tls-key"),
|
||||
},
|
||||
},
|
||||
{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
},
|
||||
Name: "test-secret",
|
||||
Namespace: "testing",
|
||||
Data: map[string][]byte{
|
||||
"tls.crt": []byte("tls-crt"),
|
||||
"tls.key": []byte("tls-key"),
|
||||
|
||||
@@ -6,7 +6,6 @@ import (
|
||||
"github.com/stretchr/testify/assert"
|
||||
corev1 "k8s.io/api/core/v1"
|
||||
netv1 "k8s.io/api/networking/v1"
|
||||
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
|
||||
)
|
||||
|
||||
func Test_detectChanges(t *testing.T) {
|
||||
@@ -38,139 +37,103 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same version",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "With different version",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "Ingress With same version",
|
||||
oldObj: &netv1.Ingress{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
newObj: &netv1.Ingress{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "Ingress With different version",
|
||||
oldObj: &netv1.Ingress{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
newObj: &netv1.Ingress{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
want: true,
|
||||
},
|
||||
{
|
||||
name: "With same annotations",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "_",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "_",
|
||||
},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "_",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "_",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "With different annotations",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "V",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "V",
|
||||
},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "X",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Annotations: map[string]string{
|
||||
"test-annotation": "X",
|
||||
},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "With same subsets",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
Subsets: []corev1.EndpointSubset{},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
Subsets: []corev1.EndpointSubset{},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{},
|
||||
},
|
||||
},
|
||||
{
|
||||
name: "With different len of subsets",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
Subsets: []corev1.EndpointSubset{},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
Subsets: []corev1.EndpointSubset{{}},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{}},
|
||||
},
|
||||
want: true,
|
||||
},
|
||||
{
|
||||
name: "With same subsets with same len of addresses",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{},
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{},
|
||||
}},
|
||||
@@ -179,17 +142,13 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with different len of addresses",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{},
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{}},
|
||||
}},
|
||||
@@ -199,17 +158,13 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of ports",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{},
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{},
|
||||
}},
|
||||
@@ -218,17 +173,13 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with different len of ports",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{},
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{}},
|
||||
}},
|
||||
@@ -238,9 +189,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of addresses with same ip",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.10.10.10",
|
||||
@@ -248,9 +197,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.10.10.10",
|
||||
@@ -261,9 +208,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of addresses with different ip",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.10.10.10",
|
||||
@@ -271,9 +216,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.10.10.42",
|
||||
@@ -285,9 +228,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of addresses with same hostname",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
Hostname: "foo",
|
||||
@@ -295,9 +236,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
Hostname: "foo",
|
||||
@@ -308,9 +247,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of addresses with same hostname",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
Hostname: "foo",
|
||||
@@ -318,9 +255,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
Hostname: "bar",
|
||||
@@ -332,9 +267,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of port with same name",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Name: "foo",
|
||||
@@ -342,9 +275,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Name: "foo",
|
||||
@@ -355,9 +286,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of port with different name",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Name: "foo",
|
||||
@@ -365,9 +294,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Name: "bar",
|
||||
@@ -379,9 +306,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of port with same port",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Port: 4242,
|
||||
@@ -389,9 +314,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Port: 4242,
|
||||
@@ -402,9 +325,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of port with different port",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Port: 4242,
|
||||
@@ -412,9 +333,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Port: 6969,
|
||||
@@ -426,9 +345,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of port with same protocol",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Protocol: "HTTP",
|
||||
@@ -436,9 +353,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Protocol: "HTTP",
|
||||
@@ -449,9 +364,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same len of port with different protocol",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Protocol: "HTTP",
|
||||
@@ -459,9 +372,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Ports: []corev1.EndpointPort{{
|
||||
Protocol: "TCP",
|
||||
@@ -473,9 +384,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
{
|
||||
name: "With same subsets with same subset",
|
||||
oldObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "1",
|
||||
},
|
||||
ResourceVersion: "1",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.10.10.10",
|
||||
@@ -489,9 +398,7 @@ func Test_detectChanges(t *testing.T) {
|
||||
}},
|
||||
},
|
||||
newObj: &corev1.Endpoints{
|
||||
ObjectMeta: metav1.ObjectMeta{
|
||||
ResourceVersion: "2",
|
||||
},
|
||||
ResourceVersion: "2",
|
||||
Subsets: []corev1.EndpointSubset{{
|
||||
Addresses: []corev1.EndpointAddress{{
|
||||
IP: "10.10.10.10",
|
||||
|
||||
@@ -825,20 +825,16 @@ func Test_buildConfiguration(t *testing.T) {
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("foobar"),
|
||||
KeyFile: tls.FileOrContent("foobar"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("foobar"),
|
||||
KeyFile: tls.FileOrContent("foobar"),
|
||||
Stores: []string{
|
||||
"foobar",
|
||||
"foobar",
|
||||
},
|
||||
},
|
||||
{
|
||||
Certificate: tls.Certificate{
|
||||
CertFile: tls.FileOrContent("foobar"),
|
||||
KeyFile: tls.FileOrContent("foobar"),
|
||||
},
|
||||
CertFile: tls.FileOrContent("foobar"),
|
||||
KeyFile: tls.FileOrContent("foobar"),
|
||||
Stores: []string{
|
||||
"foobar",
|
||||
"foobar",
|
||||
|
||||
@@ -66,10 +66,8 @@ func Test_globalConfig(t *testing.T) {
|
||||
for _, test := range cases {
|
||||
t.Run(test.Name, func(t *testing.T) {
|
||||
p := Provider{
|
||||
Configuration: Configuration{
|
||||
ExposedByDefault: test.ExposedByDefault,
|
||||
Prefix: test.Prefix,
|
||||
},
|
||||
ExposedByDefault: test.ExposedByDefault,
|
||||
Prefix: test.Prefix,
|
||||
}
|
||||
result := p.getExtraConf(test.Tags)
|
||||
require.Equal(t, test.exp, result)
|
||||
|
||||
@@ -23,7 +23,6 @@ import (
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kubernetes/crd"
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kubernetes/gateway"
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kubernetes/ingress"
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kv"
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kv/consul"
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kv/etcd"
|
||||
"github.com/traefik/traefik/v2/pkg/provider/kv/redis"
|
||||
@@ -448,11 +447,9 @@ func init() {
|
||||
},
|
||||
Certificates: []*traefiktls.CertAndStores{
|
||||
{
|
||||
Certificate: traefiktls.Certificate{
|
||||
CertFile: "cert.pem",
|
||||
KeyFile: "key.pem",
|
||||
},
|
||||
Stores: []string{"foo"},
|
||||
CertFile: "cert.pem",
|
||||
KeyFile: "key.pem",
|
||||
Stores: []string{"foo"},
|
||||
},
|
||||
},
|
||||
Stores: map[string]traefiktls.Store{
|
||||
@@ -683,36 +680,34 @@ func TestDo_staticConfiguration(t *testing.T) {
|
||||
}
|
||||
|
||||
config.Providers.ConsulCatalog = &consulcatalog.ProviderBuilder{
|
||||
Configuration: consulcatalog.Configuration{
|
||||
Constraints: `Label("foo", "bar")`,
|
||||
Endpoint: &consulcatalog.EndpointConfig{
|
||||
Address: "MyAddress",
|
||||
Scheme: "MyScheme",
|
||||
DataCenter: "MyDatacenter",
|
||||
Token: "MyToken",
|
||||
TLS: &types.ClientTLS{
|
||||
CA: "myCa",
|
||||
CAOptional: true,
|
||||
Cert: "mycert.pem",
|
||||
Key: "mycert.key",
|
||||
InsecureSkipVerify: true,
|
||||
},
|
||||
HTTPAuth: &consulcatalog.EndpointHTTPAuthConfig{
|
||||
Username: "MyUsername",
|
||||
Password: "MyPassword",
|
||||
},
|
||||
EndpointWaitTime: 42,
|
||||
Constraints: `Label("foo", "bar")`,
|
||||
Endpoint: &consulcatalog.EndpointConfig{
|
||||
Address: "MyAddress",
|
||||
Scheme: "MyScheme",
|
||||
DataCenter: "MyDatacenter",
|
||||
Token: "MyToken",
|
||||
TLS: &types.ClientTLS{
|
||||
CA: "myCa",
|
||||
CAOptional: true,
|
||||
Cert: "mycert.pem",
|
||||
Key: "mycert.key",
|
||||
InsecureSkipVerify: true,
|
||||
},
|
||||
Prefix: "MyPrefix",
|
||||
RefreshInterval: 42,
|
||||
RequireConsistent: true,
|
||||
Stale: true,
|
||||
Cache: true,
|
||||
ExposedByDefault: true,
|
||||
DefaultRule: "PathPrefix(`/`)",
|
||||
HTTPAuth: &consulcatalog.EndpointHTTPAuthConfig{
|
||||
Username: "MyUsername",
|
||||
Password: "MyPassword",
|
||||
},
|
||||
EndpointWaitTime: 42,
|
||||
},
|
||||
Namespace: "ns",
|
||||
Namespaces: []string{"ns1", "ns2"},
|
||||
Prefix: "MyPrefix",
|
||||
RefreshInterval: 42,
|
||||
RequireConsistent: true,
|
||||
Stale: true,
|
||||
Cache: true,
|
||||
ExposedByDefault: true,
|
||||
DefaultRule: "PathPrefix(`/`)",
|
||||
Namespace: "ns",
|
||||
Namespaces: []string{"ns1", "ns2"},
|
||||
}
|
||||
|
||||
config.Providers.Ecs = &ecs.Provider{
|
||||
@@ -729,11 +724,9 @@ func TestDo_staticConfiguration(t *testing.T) {
|
||||
}
|
||||
|
||||
config.Providers.Consul = &consul.ProviderBuilder{
|
||||
Provider: kv.Provider{
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
},
|
||||
Token: "secret",
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
Token: "secret",
|
||||
TLS: &types.ClientTLS{
|
||||
CA: "myCa",
|
||||
CAOptional: true,
|
||||
@@ -746,12 +739,10 @@ func TestDo_staticConfiguration(t *testing.T) {
|
||||
}
|
||||
|
||||
config.Providers.Etcd = &etcd.Provider{
|
||||
Provider: kv.Provider{
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
},
|
||||
Username: "username",
|
||||
Password: "password",
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
Username: "username",
|
||||
Password: "password",
|
||||
TLS: &types.ClientTLS{
|
||||
CA: "myCa",
|
||||
CAOptional: true,
|
||||
@@ -762,21 +753,17 @@ func TestDo_staticConfiguration(t *testing.T) {
|
||||
}
|
||||
|
||||
config.Providers.ZooKeeper = &zk.Provider{
|
||||
Provider: kv.Provider{
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
},
|
||||
Username: "username",
|
||||
Password: "password",
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
Username: "username",
|
||||
Password: "password",
|
||||
}
|
||||
|
||||
config.Providers.Redis = &redis.Provider{
|
||||
Provider: kv.Provider{
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
},
|
||||
Username: "username",
|
||||
Password: "password",
|
||||
RootKey: "RootKey",
|
||||
Endpoints: nil,
|
||||
Username: "username",
|
||||
Password: "password",
|
||||
TLS: &types.ClientTLS{
|
||||
CA: "myCa",
|
||||
CAOptional: true,
|
||||
|
||||
@@ -149,15 +149,17 @@ func Test_mergeConfiguration_tlsCertificates(t *testing.T) {
|
||||
"tlsalpn.acme": &dynamic.Configuration{
|
||||
TLS: &dynamic.TLSConfiguration{
|
||||
Certificates: []*tls.CertAndStores{{
|
||||
Certificate: tls.Certificate{CertFile: "foo", KeyFile: "bar"},
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
CertFile: "foo",
|
||||
KeyFile: "bar",
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
}},
|
||||
},
|
||||
},
|
||||
},
|
||||
expected: []*tls.CertAndStores{{
|
||||
Certificate: tls.Certificate{CertFile: "foo", KeyFile: "bar"},
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
CertFile: "foo",
|
||||
KeyFile: "bar",
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
}},
|
||||
},
|
||||
}
|
||||
|
||||
@@ -192,8 +192,8 @@ func Test_Routing(t *testing.T) {
|
||||
},
|
||||
},
|
||||
[]*traefiktls.CertAndStores{{
|
||||
Certificate: traefiktls.Certificate{CertFile: traefiktls.FileOrContent(certPEM), KeyFile: traefiktls.FileOrContent(keyPEM)},
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
CertFile: traefiktls.FileOrContent(certPEM), KeyFile: traefiktls.FileOrContent(keyPEM),
|
||||
Stores: []string{tlsalpn01.ACMETLS1Protocol},
|
||||
}})
|
||||
|
||||
middlewaresBuilder := tcpmiddleware.NewBuilder(conf.TCPMiddlewares)
|
||||
|
||||
@@ -17,18 +17,8 @@ import (
|
||||
"github.com/traefik/traefik/v2/pkg/config/dynamic"
|
||||
"github.com/traefik/traefik/v2/pkg/log"
|
||||
traefiktls "github.com/traefik/traefik/v2/pkg/tls"
|
||||
"golang.org/x/net/http2"
|
||||
)
|
||||
|
||||
type h2cTransportWrapper struct {
|
||||
*http2.Transport
|
||||
}
|
||||
|
||||
func (t *h2cTransportWrapper) RoundTrip(req *http.Request) (*http.Response, error) {
|
||||
req.URL.Scheme = "http"
|
||||
return t.Transport.RoundTrip(req)
|
||||
}
|
||||
|
||||
// RoundTripperManager handles roundtripper for the reverse proxy.
|
||||
type RoundTripperManager struct {
|
||||
rtLock sync.RWMutex
|
||||
@@ -133,6 +123,16 @@ func createRoundTripper(cfg *dynamic.ServersTransport) (http.RoundTripper, error
|
||||
if cfg.ForwardingTimeouts != nil {
|
||||
transport.ResponseHeaderTimeout = time.Duration(cfg.ForwardingTimeouts.ResponseHeaderTimeout)
|
||||
transport.IdleConnTimeout = time.Duration(cfg.ForwardingTimeouts.IdleConnTimeout)
|
||||
// The forwarding timeout names come from the x/net/http2.Transport fields (ReadIdleTimeout/PingTimeout),
|
||||
// which were used to configure the HTTP/2 health checks before the net/http native support (Go 1.24).
|
||||
// HTTP2Config.SendPingTimeout carries the same semantics as ReadIdleTimeout:
|
||||
// the delay without any frame received on a connection after which a ping health check is sent.
|
||||
// The field was renamed when the HTTP/2 configuration moved to net/http, see https://go.dev/issue/67813.
|
||||
// The HTTP2 config does not enable HTTP2 protocol.
|
||||
transport.HTTP2 = &http.HTTP2Config{
|
||||
SendPingTimeout: time.Duration(cfg.ForwardingTimeouts.ReadIdleTimeout),
|
||||
PingTimeout: time.Duration(cfg.ForwardingTimeouts.PingTimeout),
|
||||
}
|
||||
}
|
||||
|
||||
if cfg.InsecureSkipVerify || len(cfg.RootCAs) > 0 || len(cfg.ServerName) > 0 || len(cfg.Certificates) > 0 || cfg.PeerCertURI != "" {
|
||||
@@ -160,10 +160,8 @@ func createRoundTripper(cfg *dynamic.ServersTransport) (http.RoundTripper, error
|
||||
}, nil
|
||||
}
|
||||
|
||||
rt, err := newSmartRoundTripper(transport, cfg.ForwardingTimeouts)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
rt := newSmartRoundTripper(transport)
|
||||
|
||||
return &KerberosRoundTripper{
|
||||
OriginalRoundTripper: rt,
|
||||
new: func() http.RoundTripper {
|
||||
|
||||
@@ -1,19 +1,26 @@
|
||||
package service
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"crypto/tls"
|
||||
"crypto/x509"
|
||||
"io"
|
||||
"net"
|
||||
"net/http"
|
||||
"net/http/httptest"
|
||||
"net/url"
|
||||
"sync"
|
||||
"sync/atomic"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
"github.com/stretchr/testify/assert"
|
||||
"github.com/stretchr/testify/require"
|
||||
ptypes "github.com/traefik/paerser/types"
|
||||
"github.com/traefik/traefik/v2/pkg/config/dynamic"
|
||||
traefiktls "github.com/traefik/traefik/v2/pkg/tls"
|
||||
"golang.org/x/net/http2"
|
||||
"golang.org/x/net/http2/hpack"
|
||||
)
|
||||
|
||||
// LocalhostCert is a PEM-encoded TLS cert
|
||||
@@ -261,6 +268,7 @@ func TestDisableHTTP2(t *testing.T) {
|
||||
srv := httptest.NewUnstartedServer(http.HandlerFunc(func(rw http.ResponseWriter, req *http.Request) {
|
||||
rw.WriteHeader(http.StatusOK)
|
||||
}))
|
||||
defer srv.Close()
|
||||
|
||||
srv.EnableHTTP2 = test.serverHTTP2
|
||||
srv.StartTLS()
|
||||
@@ -290,6 +298,188 @@ func TestDisableHTTP2(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestHTTP2HealthCheckTimeouts(t *testing.T) {
|
||||
rt, err := createRoundTripper(&dynamic.ServersTransport{
|
||||
ForwardingTimeouts: &dynamic.ForwardingTimeouts{
|
||||
ReadIdleTimeout: ptypes.Duration(10 * time.Second),
|
||||
PingTimeout: ptypes.Duration(15 * time.Second),
|
||||
},
|
||||
})
|
||||
require.NoError(t, err)
|
||||
|
||||
krt, ok := rt.(*KerberosRoundTripper)
|
||||
require.True(t, ok)
|
||||
|
||||
srt, ok := krt.OriginalRoundTripper.(*smartRoundTripper)
|
||||
require.True(t, ok)
|
||||
|
||||
expected := &http.HTTP2Config{
|
||||
SendPingTimeout: 10 * time.Second,
|
||||
PingTimeout: 15 * time.Second,
|
||||
}
|
||||
assert.Equal(t, expected, srt.http.HTTP2)
|
||||
assert.Equal(t, expected, srt.http2.HTTP2)
|
||||
assert.Equal(t, expected, srt.h2c.HTTP2)
|
||||
}
|
||||
|
||||
func TestProxyHTTP2BackendScheme(t *testing.T) {
|
||||
testCases := []struct {
|
||||
desc string
|
||||
tls bool
|
||||
expectedScheme string
|
||||
}{
|
||||
{
|
||||
desc: "h2c backend",
|
||||
expectedScheme: "http",
|
||||
},
|
||||
{
|
||||
desc: "https backend",
|
||||
tls: true,
|
||||
expectedScheme: "https",
|
||||
},
|
||||
}
|
||||
|
||||
for _, test := range testCases {
|
||||
t.Run(test.desc, func(t *testing.T) {
|
||||
t.Parallel()
|
||||
|
||||
backendURL, schemes := startHTTP2FramerBackend(t, test.tls)
|
||||
|
||||
rtManager := NewRoundTripperManager()
|
||||
rtManager.Update(map[string]*dynamic.ServersTransport{
|
||||
"test": {
|
||||
InsecureSkipVerify: true,
|
||||
},
|
||||
})
|
||||
|
||||
rt, err := rtManager.Get("test")
|
||||
require.NoError(t, err)
|
||||
|
||||
proxy, err := buildProxy(new(true), nil, rt, newBufferPool())
|
||||
require.NoError(t, err)
|
||||
|
||||
// The load balancer sets the backend server on the request URL before the proxy runs.
|
||||
handler := http.HandlerFunc(func(rw http.ResponseWriter, req *http.Request) {
|
||||
req.URL.Scheme = backendURL.Scheme
|
||||
req.URL.Host = backendURL.Host
|
||||
proxy.ServeHTTP(rw, req)
|
||||
})
|
||||
|
||||
srv := httptest.NewServer(handler)
|
||||
t.Cleanup(srv.Close)
|
||||
|
||||
req, err := http.NewRequestWithContext(t.Context(), http.MethodGet, srv.URL, nil)
|
||||
require.NoError(t, err)
|
||||
|
||||
res, err := http.DefaultClient.Do(req)
|
||||
require.NoError(t, err)
|
||||
t.Cleanup(func() { _ = res.Body.Close() })
|
||||
|
||||
assert.Equal(t, http.StatusOK, res.StatusCode)
|
||||
|
||||
select {
|
||||
case scheme := <-schemes:
|
||||
assert.Equal(t, test.expectedScheme, scheme)
|
||||
default:
|
||||
t.Error("backend did not receive an HTTP/2 request")
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
// startHTTP2FramerBackend starts a backend speaking raw HTTP/2 frames,
|
||||
// as the standard library server does not expose the :scheme pseudo-header.
|
||||
func startHTTP2FramerBackend(t *testing.T, useTLS bool) (*url.URL, <-chan string) {
|
||||
t.Helper()
|
||||
|
||||
ln, err := net.Listen("tcp", "127.0.0.1:0")
|
||||
require.NoError(t, err)
|
||||
|
||||
scheme := "h2c"
|
||||
if useTLS {
|
||||
cert, err := tls.X509KeyPair(LocalhostCert, LocalhostKey)
|
||||
require.NoError(t, err)
|
||||
|
||||
ln = tls.NewListener(ln, &tls.Config{
|
||||
Certificates: []tls.Certificate{cert},
|
||||
NextProtos: []string{"h2"},
|
||||
})
|
||||
scheme = "https"
|
||||
}
|
||||
t.Cleanup(func() { _ = ln.Close() })
|
||||
|
||||
schemes := make(chan string, 1)
|
||||
go func() {
|
||||
for {
|
||||
conn, err := ln.Accept()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
go serveHTTP2Frames(conn, schemes)
|
||||
}
|
||||
}()
|
||||
|
||||
return &url.URL{Scheme: scheme, Host: ln.Addr().String()}, schemes
|
||||
}
|
||||
|
||||
func serveHTTP2Frames(conn net.Conn, schemes chan<- string) {
|
||||
defer func() { _ = conn.Close() }()
|
||||
|
||||
_ = conn.SetDeadline(time.Now().Add(5 * time.Second))
|
||||
|
||||
preface := make([]byte, len(http2.ClientPreface))
|
||||
if _, err := io.ReadFull(conn, preface); err != nil || string(preface) != http2.ClientPreface {
|
||||
return
|
||||
}
|
||||
|
||||
framer := http2.NewFramer(conn, conn)
|
||||
framer.ReadMetaHeaders = hpack.NewDecoder(4096, nil)
|
||||
|
||||
if err := framer.WriteSettings(); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
for {
|
||||
frame, err := framer.ReadFrame()
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
switch f := frame.(type) {
|
||||
case *http2.SettingsFrame:
|
||||
if f.IsAck() {
|
||||
continue
|
||||
}
|
||||
|
||||
if err := framer.WriteSettingsAck(); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
case *http2.MetaHeadersFrame:
|
||||
select {
|
||||
case schemes <- f.PseudoValue("scheme"):
|
||||
default:
|
||||
}
|
||||
|
||||
var headers bytes.Buffer
|
||||
if err := hpack.NewEncoder(&headers).WriteField(hpack.HeaderField{Name: ":status", Value: "200"}); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
err := framer.WriteHeaders(http2.HeadersFrameParam{
|
||||
StreamID: f.StreamID,
|
||||
BlockFragment: headers.Bytes(),
|
||||
EndHeaders: true,
|
||||
EndStream: true,
|
||||
})
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
type roundTripperFn func(req *http.Request) (*http.Response, error)
|
||||
|
||||
func (r roundTripperFn) RoundTrip(request *http.Request) (*http.Response, error) {
|
||||
|
||||
@@ -1,49 +1,33 @@
|
||||
package service
|
||||
|
||||
import (
|
||||
"crypto/tls"
|
||||
"net"
|
||||
"net/http"
|
||||
"time"
|
||||
|
||||
"github.com/traefik/traefik/v2/pkg/config/dynamic"
|
||||
"golang.org/x/net/http/httpguts"
|
||||
"golang.org/x/net/http2"
|
||||
)
|
||||
|
||||
func newSmartRoundTripper(transport *http.Transport, forwardingTimeouts *dynamic.ForwardingTimeouts) (*smartRoundTripper, error) {
|
||||
func newSmartRoundTripper(transport *http.Transport) *smartRoundTripper {
|
||||
// HTTP/1 only transport for requests with a Connection: Upgrade header.
|
||||
transportHTTP1 := transport.Clone()
|
||||
transportHTTP1.Protocols = new(http.Protocols)
|
||||
transportHTTP1.Protocols.SetHTTP1(true)
|
||||
|
||||
transportHTTP2, err := http2.ConfigureTransports(transport)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
// Transport switching automatically to HTTP/2 with TLS ALPN.
|
||||
transportHTTP2 := transport.Clone()
|
||||
transportHTTP2.Protocols = new(http.Protocols)
|
||||
transportHTTP2.Protocols.SetHTTP1(true)
|
||||
transportHTTP2.Protocols.SetHTTP2(true)
|
||||
|
||||
if forwardingTimeouts != nil {
|
||||
transportHTTP2.ReadIdleTimeout = time.Duration(forwardingTimeouts.ReadIdleTimeout)
|
||||
transportHTTP2.PingTimeout = time.Duration(forwardingTimeouts.PingTimeout)
|
||||
}
|
||||
|
||||
transportH2C := &h2cTransportWrapper{
|
||||
Transport: &http2.Transport{
|
||||
DialTLS: func(network, addr string, cfg *tls.Config) (net.Conn, error) {
|
||||
return net.Dial(network, addr)
|
||||
},
|
||||
AllowHTTP: true,
|
||||
},
|
||||
}
|
||||
|
||||
if forwardingTimeouts != nil {
|
||||
transportH2C.ReadIdleTimeout = time.Duration(forwardingTimeouts.ReadIdleTimeout)
|
||||
transportH2C.PingTimeout = time.Duration(forwardingTimeouts.PingTimeout)
|
||||
}
|
||||
|
||||
transport.RegisterProtocol("h2c", transportH2C)
|
||||
// Transport speaking HTTP/2 with prior knowledge on unencrypted connections.
|
||||
transportH2C := transport.Clone()
|
||||
transportH2C.Protocols = new(http.Protocols)
|
||||
transportH2C.Protocols.SetUnencryptedHTTP2(true)
|
||||
|
||||
return &smartRoundTripper{
|
||||
http2: transport,
|
||||
http2: transportHTTP2,
|
||||
http: transportHTTP1,
|
||||
}, nil
|
||||
h2c: transportH2C,
|
||||
}
|
||||
}
|
||||
|
||||
// smartRoundTripper implements RoundTrip while making sure that HTTP/2 is not used
|
||||
@@ -51,19 +35,31 @@ func newSmartRoundTripper(transport *http.Transport, forwardingTimeouts *dynamic
|
||||
type smartRoundTripper struct {
|
||||
http2 *http.Transport
|
||||
http *http.Transport
|
||||
h2c *http.Transport
|
||||
}
|
||||
|
||||
func (m *smartRoundTripper) Clone() http.RoundTripper {
|
||||
h := m.http.Clone()
|
||||
h2 := m.http2.Clone()
|
||||
return &smartRoundTripper{http: h, http2: h2}
|
||||
return &smartRoundTripper{
|
||||
http2: m.http2.Clone(),
|
||||
http: m.http.Clone(),
|
||||
h2c: m.h2c.Clone(),
|
||||
}
|
||||
}
|
||||
|
||||
func (m *smartRoundTripper) RoundTrip(req *http.Request) (*http.Response, error) {
|
||||
// If we have a connection upgrade, we don't use HTTP/2
|
||||
h2c := req.URL.Scheme == "h2c"
|
||||
if h2c {
|
||||
req.URL.Scheme = "http"
|
||||
}
|
||||
|
||||
// Connection upgrades cannot be carried over HTTP/2, they always use HTTP/1.
|
||||
if httpguts.HeaderValuesContainsToken(req.Header["Connection"], "Upgrade") {
|
||||
return m.http.RoundTrip(req)
|
||||
}
|
||||
|
||||
if h2c {
|
||||
return m.h2c.RoundTrip(req)
|
||||
}
|
||||
|
||||
return m.http2.RoundTrip(req)
|
||||
}
|
||||
@@ -69,10 +69,8 @@ ZboOWVe3icTy64BT3OQhmg==
|
||||
|
||||
func TestTLSInStore(t *testing.T) {
|
||||
dynamicConfigs := []*CertAndStores{{
|
||||
Certificate: Certificate{
|
||||
CertFile: localhostCert,
|
||||
KeyFile: localhostKey,
|
||||
},
|
||||
CertFile: localhostCert,
|
||||
KeyFile: localhostKey,
|
||||
}}
|
||||
|
||||
tlsManager := NewManager()
|
||||
@@ -86,10 +84,8 @@ func TestTLSInStore(t *testing.T) {
|
||||
|
||||
func TestTLSInvalidStore(t *testing.T) {
|
||||
dynamicConfigs := []*CertAndStores{{
|
||||
Certificate: Certificate{
|
||||
CertFile: localhostCert,
|
||||
KeyFile: localhostKey,
|
||||
},
|
||||
CertFile: localhostCert,
|
||||
KeyFile: localhostKey,
|
||||
}}
|
||||
|
||||
tlsManager := NewManager()
|
||||
@@ -111,10 +107,8 @@ func TestTLSInvalidStore(t *testing.T) {
|
||||
|
||||
func TestManager_Get(t *testing.T) {
|
||||
dynamicConfigs := []*CertAndStores{{
|
||||
Certificate: Certificate{
|
||||
CertFile: localhostCert,
|
||||
KeyFile: localhostKey,
|
||||
},
|
||||
CertFile: localhostCert,
|
||||
KeyFile: localhostKey,
|
||||
}}
|
||||
|
||||
tlsConfigs := map[string]Options{
|
||||
|
||||
Reference in new issue
Block a user