Avoid unauthorized midlleware cross namespace reference

Co-authored-by: Mathieu Lonjaret <mathieu.lonjaret@gmail.com>
Co-authored-by: Romain <rtribotte@users.noreply.github.com>
This commit is contained in:
Jean-Baptiste Doumenjou 2021-08-05 17:42:08 +02:00 committed by GitHub
parent 547c380961
commit 32d88a977d
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
3 changed files with 42 additions and 3 deletions

View file

@ -28,6 +28,15 @@ spec:
port: 80 port: 80
middlewares: middlewares:
- name: test-errorpage - name: test-errorpage
- match: Host(`foo.com`) && PathPrefix(`/bur`)
kind: Rule
priority: 12
services:
- name: whoami
namespace: default
port: 80
middlewares:
- name: cross-ns-stripprefix@kubernetescrd
--- ---
apiVersion: traefik.containo.us/v1alpha1 apiVersion: traefik.containo.us/v1alpha1

View file

@ -146,13 +146,23 @@ func (p *Provider) makeMiddlewareKeys(ctx context.Context, ingRouteNamespace str
var mds []string var mds []string
for _, mi := range middlewares { for _, mi := range middlewares {
if strings.Contains(mi.Name, providerNamespaceSeparator) { name := mi.Name
if !p.AllowCrossNamespace && strings.HasSuffix(mi.Name, providerNamespaceSeparator+providerName) {
// Since we are not able to know if another namespace is in the name (namespace-name@kubernetescrd),
// if the provider namespace kubernetescrd is used,
// we don't allow this format to avoid cross namespace references.
return nil, fmt.Errorf("invalid reference to middleware %s: with crossnamespace disallowed, the namespace field needs to be explicitly specified", mi.Name)
}
if strings.Contains(name, providerNamespaceSeparator) {
if len(mi.Namespace) > 0 { if len(mi.Namespace) > 0 {
log.FromContext(ctx). log.FromContext(ctx).
WithField(log.MiddlewareName, mi.Name). WithField(log.MiddlewareName, mi.Name).
Warnf("namespace %q is ignored in cross-provider context", mi.Namespace) Warnf("namespace %q is ignored in cross-provider context", mi.Namespace)
} }
mds = append(mds, mi.Name)
mds = append(mds, name)
continue continue
} }
@ -165,7 +175,7 @@ func (p *Provider) makeMiddlewareKeys(ctx context.Context, ingRouteNamespace str
ns = mi.Namespace ns = mi.Namespace
} }
mds = append(mds, makeID(ns, mi.Name)) mds = append(mds, makeID(ns, name))
} }
return mds, nil return mds, nil

View file

@ -3986,6 +3986,13 @@ func TestCrossNamespace(t *testing.T) {
Priority: 12, Priority: 12,
Middlewares: []string{"default-test-errorpage"}, Middlewares: []string{"default-test-errorpage"},
}, },
"default-test-crossnamespace-route-a1963878aac7331b7950": {
EntryPoints: []string{"foo"},
Service: "default-test-crossnamespace-route-a1963878aac7331b7950",
Rule: "Host(`foo.com`) && PathPrefix(`/bur`)",
Priority: 12,
Middlewares: []string{"cross-ns-stripprefix@kubernetescrd"},
},
}, },
Middlewares: map[string]*dynamic.Middleware{ Middlewares: map[string]*dynamic.Middleware{
"cross-ns-stripprefix": { "cross-ns-stripprefix": {
@ -4042,6 +4049,19 @@ func TestCrossNamespace(t *testing.T) {
PassHostHeader: Bool(true), PassHostHeader: Bool(true),
}, },
}, },
"default-test-crossnamespace-route-a1963878aac7331b7950": {
LoadBalancer: &dynamic.ServersLoadBalancer{
Servers: []dynamic.Server{
{
URL: "http://10.10.0.1:80",
},
{
URL: "http://10.10.0.2:80",
},
},
PassHostHeader: Bool(true),
},
},
}, },
}, },
TLS: &dynamic.TLSConfiguration{}, TLS: &dynamic.TLSConfiguration{},