Skip to content

Commit 37debda

Browse files
committed
README, test/e2e: add --allow-legacy-serviceaccount-tokens flag
Signed-off-by: kramaranya <[email protected]>
1 parent a9c2ea9 commit 37debda

35 files changed

+471
-8
lines changed

README.md

+2-1
Original file line numberDiff line numberDiff line change
@@ -91,11 +91,12 @@ Delegating authorization flags:
9191
9292
Proxy flags:
9393
94+
--allow-legacy-serviceaccount-tokens If true, allow legacy service account tokens (without an audience). Legacy tokens are less secure and are disabled by default.
9495
--allow-paths strings Comma-separated list of paths against which kube-rbac-proxy pattern-matches the incoming request. If the request doesn't match, kube-rbac-proxy responds with a 404 status code. If omitted, the incoming request path isn't checked. Cannot be used with --ignore-paths.
9596
--auth-header-groups-field-name string The name of the field inside a http(2) request header to tell the upstream server about the user's groups (default "x-remote-groups")
9697
--auth-header-groups-field-separator string The separator string used for concatenating multiple group names in a groups header field's value (default "|")
9798
--auth-header-user-field-name string The name of the field inside a http(2) request header to tell the upstream server about the user's name (default "x-remote-user")
98-
--auth-token-audiences strings Comma-separated list of token audiences to accept. By default a token does not have to have any specific audience. It is recommended to set a specific audience.
99+
--auth-token-audiences strings Comma-separated list of token audiences to accept. Tokens must have at least one audience from this list. Must be set unless --allow-legacy-serviceaccount-tokens is true.
99100
--config-file string Configuration file to configure static and rewrites authorization of the kube-rbac-proxy.
100101
--disable-http2-serving If true, HTTP2 serving will be disabled [default=false]
101102
--ignore-paths strings Comma-separated list of paths against which kube-rbac-proxy pattern-matches the incoming request. If the requst matches, it will proxy the request without performing an authentication or authorization check. Cannot be used with --allow-paths.

cmd/kube-rbac-proxy/app/options/proxyoptions.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ func (o *ProxyOptions) AddFlags(flagset *pflag.FlagSet) {
8181
flagset.StringVar(&o.UpstreamHeader.GroupsFieldName, "auth-header-groups-field-name", "x-remote-groups", "The name of the field inside a http(2) request header to tell the upstream server about the user's groups")
8282
flagset.StringVar(&o.UpstreamHeader.GroupSeparator, "auth-header-groups-field-separator", "|", "The separator string used for concatenating multiple group names in a groups header field's value")
8383

84-
flagset.StringSliceVar(&o.TokenAudiences, "auth-token-audiences", []string{}, "Comma-separated list of token audiences to accept. Tokens must have at least one audience from this list. If omitted, the token is considered legacy.")
84+
flagset.StringSliceVar(&o.TokenAudiences, "auth-token-audiences", []string{}, "Comma-separated list of token audiences to accept. Tokens must have at least one audience from this list. Must be set unless --allow-legacy-serviceaccount-tokens is true.")
8585

8686
// legacy tokens are disabled by default.
8787
flagset.BoolVar(&o.AllowLegacyServiceAccountTokens, "allow-legacy-serviceaccount-tokens", false, "If true, allow legacy service account tokens (without an audience). Legacy tokens are less secure and are disabled by default.")

cmd/kube-rbac-proxy/app/options/proxyoptions_test.go

+69-3
Original file line numberDiff line numberDiff line change
@@ -17,14 +17,14 @@ limitations under the License.
1717
package options
1818

1919
import (
20-
"github.com/brancz/kube-rbac-proxy/pkg/authn/identityheaders"
2120
"os"
2221
"path/filepath"
2322
"reflect"
2423
"testing"
2524

2625
"github.com/google/go-cmp/cmp"
2726

27+
"github.com/brancz/kube-rbac-proxy/pkg/authn/identityheaders"
2828
authz "github.com/brancz/kube-rbac-proxy/pkg/authorization"
2929
"github.com/brancz/kube-rbac-proxy/pkg/authorization/rewrite"
3030
"github.com/brancz/kube-rbac-proxy/pkg/authorization/static"
@@ -144,14 +144,37 @@ func TestProxyOptions_Validate(t *testing.T) {
144144
DisableHTTP2Serving bool
145145
}
146146

147-
userKey := "User"
148-
groupKey := "Group"
147+
const (
148+
userKey = "User"
149+
groupKey = "Group"
150+
)
149151

150152
tests := []struct {
151153
name string
152154
fields fields
153155
wantErr bool
154156
}{
157+
{
158+
name: "valid config with client cert, key, config, port, and token audience",
159+
fields: fields{
160+
Upstream: "http://127.0.0.1",
161+
UpstreamForceH2C: true,
162+
UpstreamCAFile: "ca.crt",
163+
UpstreamClientCertFile: "client.crt",
164+
UpstreamClientKeyFile: "client.key",
165+
AuthzConfigFileName: "authz.yaml",
166+
AllowPaths: []string{"/path1", "/path2"},
167+
ProxyEndpointsPort: 8081,
168+
TokenAudiences: []string{"kube-apiserver"},
169+
AllowLegacyServiceAccountTokens: false,
170+
DisableHTTP2Serving: true,
171+
UpstreamHeader: &identityheaders.AuthnHeaderConfig{
172+
UserFieldName: userKey,
173+
GroupsFieldName: groupKey,
174+
},
175+
},
176+
wantErr: false,
177+
},
155178
{
156179
name: "valid config with explicit token audience",
157180
fields: fields{
@@ -191,6 +214,49 @@ func TestProxyOptions_Validate(t *testing.T) {
191214
},
192215
wantErr: false,
193216
},
217+
{
218+
name: "invalid combination (both AllowPaths and IgnorePaths set)",
219+
fields: fields{
220+
Upstream: "http://127.0.0.1",
221+
AllowPaths: []string{"/path1"},
222+
IgnorePaths: []string{"/path2"},
223+
TokenAudiences: []string{"kube-apiserver"},
224+
AllowLegacyServiceAccountTokens: false,
225+
UpstreamHeader: &identityheaders.AuthnHeaderConfig{
226+
UserFieldName: userKey,
227+
GroupsFieldName: groupKey,
228+
},
229+
},
230+
wantErr: true,
231+
},
232+
{
233+
name: "invalid AllowPaths",
234+
fields: fields{
235+
Upstream: "http://127.0.0.1",
236+
AllowPaths: []string{"[path"},
237+
TokenAudiences: []string{"kube-apiserver"},
238+
AllowLegacyServiceAccountTokens: false,
239+
UpstreamHeader: &identityheaders.AuthnHeaderConfig{
240+
UserFieldName: userKey,
241+
GroupsFieldName: groupKey,
242+
},
243+
},
244+
wantErr: true,
245+
},
246+
{
247+
name: "invalid IgnorePaths",
248+
fields: fields{
249+
Upstream: "http://127.0.0.1",
250+
IgnorePaths: []string{"path\\"},
251+
TokenAudiences: []string{"kube-apiserver"},
252+
AllowLegacyServiceAccountTokens: false,
253+
UpstreamHeader: &identityheaders.AuthnHeaderConfig{
254+
UserFieldName: userKey,
255+
GroupsFieldName: groupKey,
256+
},
257+
},
258+
wantErr: true,
259+
},
194260
}
195261
for _, tt := range tests {
196262
t.Run(tt.name, func(t *testing.T) {

test/e2e/allowpaths/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ spec:
2222
- "--proxy-endpoints-port=8643"
2323
- "--upstream=http://127.0.0.1:8081/"
2424
- "--allow-paths=/metrics,/api/v1/label/*"
25+
- "--allow-legacy-serviceaccount-tokens=true"
2526
- "--authentication-skip-lookup"
2627
- "--v=10"
2728
ports:

test/e2e/basics.go

+127-1
Original file line numberDiff line numberDiff line change
@@ -110,7 +110,7 @@ func testBasics(client kubernetes.Interface) kubetest.TestSuite {
110110

111111
func testTokenAudience(client kubernetes.Interface) kubetest.TestSuite {
112112
return func(t *testing.T) {
113-
command := `curl --connect-timeout 5 -v -s -k --fail -H "Authorization: Bearer $(cat /var/run/secrets/tokens/requestedtoken)" https://kube-rbac-proxy.default.svc.cluster.local:8443/metrics`
113+
command := `curl --connect-timeout 5 -v -s -k --fail -H "Authorization: Bearer $(cat /var/run/projected/tokens/requestedtoken)" https://kube-rbac-proxy.default.svc.cluster.local:8443/metrics`
114114

115115
kubetest.Scenario{
116116
Name: "IncorrectAudience",
@@ -519,3 +519,129 @@ func testIgnorePaths(client kubernetes.Interface) kubetest.TestSuite {
519519
}.Run(t)
520520
}
521521
}
522+
523+
func testLegacyTokenFlag(client kubernetes.Interface) kubetest.TestSuite {
524+
return func(t *testing.T) {
525+
legacyCommand := `curl --connect-timeout 5 -v -s -k --fail -H "Authorization: Bearer $(cat /var/run/legacy/tokens/token)" https://kube-rbac-proxy.default.svc.cluster.local:8443/metrics`
526+
command := `curl --connect-timeout 5 -v -s -k --fail -H "Authorization: Bearer $(cat /var/run/secrets/kubernetes.io/serviceaccount/token)" https://kube-rbac-proxy.default.svc.cluster.local:8443/metrics`
527+
528+
kubetest.Scenario{
529+
Name: "LegacyAllowedAudienceSet",
530+
Description: `
531+
As a client with --allow-legacy-serviceaccount-tokens=true and a valid audience,
532+
I succeed with my request
533+
`,
534+
535+
Given: kubetest.Actions(
536+
kubetest.CreatedManifests(
537+
client,
538+
"legacy/audience/serviceAccount.yaml",
539+
"legacy/audience/secret-legacy.yaml",
540+
"legacy/audience/clusterRole.yaml",
541+
"legacy/audience/clusterRoleBinding.yaml",
542+
"legacy/audience/deployment-allowed.yaml",
543+
"legacy/audience/service.yaml",
544+
"legacy/audience/clusterRole-client.yaml",
545+
"legacy/audience/clusterRoleBinding-client.yaml",
546+
),
547+
),
548+
When: kubetest.Actions(
549+
kubetest.PodsAreReady(
550+
client,
551+
1,
552+
"app=kube-rbac-proxy",
553+
),
554+
kubetest.ServiceIsReady(
555+
client,
556+
"kube-rbac-proxy",
557+
),
558+
),
559+
Then: kubetest.Actions(
560+
kubetest.ClientSucceeds(
561+
client,
562+
legacyCommand,
563+
&kubetest.RunOptions{LegacyToken: true},
564+
),
565+
),
566+
}.Run(t)
567+
568+
kubetest.Scenario{
569+
Name: "LegacyDisallowedAudienceSet",
570+
Description: `
571+
As a client with --allow-legacy-serviceaccount-tokens=false and a valid audience,
572+
I fail with my request
573+
`,
574+
575+
Given: kubetest.Actions(
576+
kubetest.CreatedManifests(
577+
client,
578+
"legacy/audience/serviceAccount.yaml",
579+
"legacy/audience/secret-legacy.yaml",
580+
"legacy/audience/clusterRole.yaml",
581+
"legacy/audience/clusterRoleBinding.yaml",
582+
"legacy/audience/deployment-disallowed.yaml",
583+
"legacy/audience/service.yaml",
584+
"legacy/audience/clusterRole-client.yaml",
585+
"legacy/audience/clusterRoleBinding-client.yaml",
586+
),
587+
),
588+
When: kubetest.Actions(
589+
kubetest.PodsAreReady(
590+
client,
591+
1,
592+
"app=kube-rbac-proxy",
593+
),
594+
kubetest.ServiceIsReady(
595+
client,
596+
"kube-rbac-proxy",
597+
),
598+
),
599+
Then: kubetest.Actions(
600+
kubetest.ClientFails(
601+
client,
602+
legacyCommand,
603+
&kubetest.RunOptions{LegacyToken: true},
604+
),
605+
),
606+
}.Run(t)
607+
608+
kubetest.Scenario{
609+
Name: "LegacyAllowedNoAudience",
610+
Description: `
611+
As a client with --allow-legacy-serviceaccount-tokens=true and no audience set,
612+
I succeed with my request
613+
`,
614+
615+
Given: kubetest.Actions(
616+
kubetest.CreatedManifests(
617+
client,
618+
"legacy/noaud/clusterRole.yaml",
619+
"legacy/noaud/clusterRoleBinding.yaml",
620+
"legacy/noaud/deployment.yaml",
621+
"legacy/noaud/service.yaml",
622+
"legacy/noaud/serviceAccount.yaml",
623+
"legacy/noaud/clusterRole-client.yaml",
624+
"legacy/noaud/clusterRoleBinding-client.yaml",
625+
),
626+
),
627+
When: kubetest.Actions(
628+
kubetest.PodsAreReady(
629+
client,
630+
1,
631+
"app=kube-rbac-proxy",
632+
),
633+
kubetest.ServiceIsReady(
634+
client,
635+
"kube-rbac-proxy",
636+
),
637+
),
638+
Then: kubetest.Actions(
639+
kubetest.ClientSucceeds(
640+
client,
641+
command,
642+
nil,
643+
),
644+
),
645+
}.Run(t)
646+
}
647+
}

test/e2e/basics/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ spec:
2020
args:
2121
- "--secure-port=8443"
2222
- "--upstream=http://127.0.0.1:8081/"
23+
- "--allow-legacy-serviceaccount-tokens=true"
2324
- "--authentication-skip-lookup"
2425
- "--v=10"
2526
ports:

test/e2e/clientcertificates/deployment-wrongca.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ spec:
2121
- "--secure-port=8443"
2222
- "--upstream=http://127.0.0.1:8081/"
2323
- "--client-ca-file=/var/run/secrets/kubernetes.io/serviceaccount/ca.crt"
24+
- "--allow-legacy-serviceaccount-tokens=true"
2425
- "--authentication-skip-lookup"
2526
- "--v=10"
2627
ports:

test/e2e/clientcertificates/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ spec:
2121
- "--secure-port=8443"
2222
- "--upstream=http://127.0.0.1:8081/"
2323
- "--client-ca-file=/certs/ca.crt"
24+
- "--allow-legacy-serviceaccount-tokens=true"
2425
- "--authentication-skip-lookup"
2526
- "--v=10"
2627
ports:

test/e2e/h2c-upstream/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ spec:
2121
- "--secure-port=8443"
2222
- "--upstream=http://127.0.0.1:8081/"
2323
- "--authentication-skip-lookup"
24+
- "--allow-legacy-serviceaccount-tokens=true"
2425
- "--upstream-force-h2c=true"
2526
- "--v=10"
2627
ports:

test/e2e/http2/deployment-no-http2.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ spec:
2121
- "--secure-port=8443"
2222
- "--upstream=http://127.0.0.1:8081/"
2323
- "--authentication-skip-lookup"
24+
- "--allow-legacy-serviceaccount-tokens=true"
2425
- "--ignore-paths=/metrics,/api/v1/*"
2526
- "--disable-http2-serving=true"
2627
- "--v=10"

test/e2e/http2/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@ spec:
2121
- "--secure-port=8443"
2222
- "--upstream=http://127.0.0.1:8081/"
2323
- "--authentication-skip-lookup"
24+
- "--allow-legacy-serviceaccount-tokens=true"
2425
- "--ignore-paths=/metrics,/api/v1/*"
2526
- "--v=10"
2627
ports:

test/e2e/identityheaders/default/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ spec:
2424
- "--auth-header-user-field-name=x-remote-user"
2525
- "--auth-header-groups-field-name=x-remote-groups"
2626
- "--auth-header-groups-field-separator=|"
27+
- "--allow-legacy-serviceaccount-tokens=true"
2728
- "--v=10"
2829
ports:
2930
- containerPort: 8443

test/e2e/identityheaders/insecure/deployment-proxy.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ spec:
2424
- "--auth-header-user-field-name=x-remote-user"
2525
- "--auth-header-groups-field-name=x-remote-groups"
2626
- "--auth-header-groups-field-separator=|"
27+
- "--allow-legacy-serviceaccount-tokens=true"
2728
- "--v=10"
2829
ports:
2930
- containerPort: 8443

test/e2e/identityheaders/secure/deployment-proxy.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ spec:
2424
- "--auth-header-user-field-name=x-remote-user"
2525
- "--auth-header-groups-field-name=x-remote-groups"
2626
- "--auth-header-groups-field-separator=|"
27+
- "--allow-legacy-serviceaccount-tokens=true"
2728
- "--tls-cert-file=/usr/local/etc/kube-rbac-proxy/server-certs/tls.crt"
2829
- "--tls-private-key-file=/usr/local/etc/kube-rbac-proxy/server-certs/tls.key"
2930
- "--upstream-ca-file=/usr/local/etc/kube-rbac-proxy/upstream-trust/ca.crt"

test/e2e/ignorepaths/deployment.yaml

+1
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ spec:
2222
- "--upstream=http://127.0.0.1:8081/"
2323
- "--ignore-paths=/metrics,/api/v1/*"
2424
- "--authentication-skip-lookup"
25+
- "--allow-legacy-serviceaccount-tokens=true"
2526
- "--v=10"
2627
ports:
2728
- containerPort: 8443
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
apiVersion: rbac.authorization.k8s.io/v1
2+
kind: ClusterRole
3+
metadata:
4+
name: metrics
5+
rules:
6+
- nonResourceURLs: ["/metrics"]
7+
verbs: ["get"]
+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
apiVersion: rbac.authorization.k8s.io/v1
2+
kind: ClusterRole
3+
metadata:
4+
name: kube-rbac-proxy
5+
rules:
6+
- apiGroups: ["authentication.k8s.io"]
7+
resources:
8+
- tokenreviews
9+
verbs: ["create"]
10+
- apiGroups: ["authorization.k8s.io"]
11+
resources:
12+
- subjectaccessreviews
13+
verbs: ["create"]
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
apiVersion: rbac.authorization.k8s.io/v1
2+
kind: ClusterRoleBinding
3+
metadata:
4+
name: metrics
5+
roleRef:
6+
apiGroup: rbac.authorization.k8s.io
7+
kind: ClusterRole
8+
name: metrics
9+
subjects:
10+
- kind: ServiceAccount
11+
name: kube-rbac-proxy
12+
namespace: default

0 commit comments

Comments
 (0)