Repository: clusternet/clusternet
Pull request #32 (2021-07-15 14:06:57)

add tests for getExtraFromHeaders
<!--  Thanks for sending a pull request!

-->

#### What type of PR is this?
kind/tests

#### What this PR does / why we need it:
add tests for `getExtraFromHeaders`

#### Which issue(s) this PR fixes:
<!--
*Automatically closes linked issue when PR is merged.
Usage: `Fixes #<issue number>`, or `Fixes (paste link of issue)`.
-->
Fixes #

#### Special notes for your reviewer:



Patch:
diff --git a/pkg/exchanger/exchanger.go b/pkg/exchanger/exchanger.go
index 7a2d602..d77d568 100644
--- a/pkg/exchanger/exchanger.go
+++ b/pkg/exchanger/exchanger.go
@@ -139,7 +139,7 @@ func (e *Exchanger) ProxyConnect(ctx context.Context, id string, opts *proxies.S
 		// proxy and re-dial through websocket connection
 		klog.V(4).Infof("Request to %q will be redialed from cluster %q", location.String(), id)
 
-		extra := newExtra(request.Header, extraHeaderPrefixes)
+		extra := getExtraFromHeaders(request.Header, extraHeaderPrefixes)
 
 		if token, ok := extra[strings.ToLower(TokenHeaderKey)]; ok && len(token) > 0 {
 			request.Header.Set("Authorization", fmt.Sprintf("Bearer %s", token[0]))
@@ -270,6 +270,7 @@ func newThrottledUpgradeAwareProxyHandler(location *url.URL, transport http.Roun
 	return handler
 }
 
+// copied from k8s.io/apiserver/pkg/authentication/request/headerrequest/requestheader.go
 func unescapeExtraKey(encodedKey string) string {
 	key, err := url.PathUnescape(encodedKey) // Decode %-encoded bytes.
 	if err != nil {
@@ -278,7 +279,8 @@ func unescapeExtraKey(encodedKey string) string {
 	return key
 }
 
-func newExtra(h http.Header, headerPrefixes []string) map[string][]string {
+// copied from k8s.io/apiserver/pkg/authentication/request/headerrequest/requestheader.go
+func getExtraFromHeaders(h http.Header, headerPrefixes []string) map[string][]string {
 	ret := map[string][]string{}
 
 	// we have to iterate over prefixes first in order to have proper ordering inside the value slices


Test patch:
diff --git a/pkg/exchanger/exchanger_test.go b/pkg/exchanger/exchanger_test.go
index ee79127..6eea553 100644
--- a/pkg/exchanger/exchanger_test.go
+++ b/pkg/exchanger/exchanger_test.go
@@ -19,6 +19,7 @@ package exchanger
 import (
 	"net/http"
 	"net/url"
+	"reflect"
 	"testing"
 )
 
@@ -88,3 +89,94 @@ func TestAuthorizer(t *testing.T) {
 		})
 	}
 }
+
+// modified on k8s.io/apiserver/pkg/authentication/request/headerrequest/requestheader_test.go
+func TestGetExtraFromHeaders(t *testing.T) {
+	tests := []struct {
+		name           string
+		header         http.Header
+		headerPrefixes []string
+		wantedExtra    map[string][]string
+	}{
+		{
+			name:        "empty",
+			wantedExtra: map[string][]string{},
+		},
+		{
+			name:           "extra not match 1",
+			header:         http.Header{"X-Remote-User": {"Bob"}},
+			headerPrefixes: []string{"X-Remote-Extra-"},
+			wantedExtra:    map[string][]string{},
+		},
+		{
+			name: "exact not match 2",
+			header: http.Header{
+				"X-Remote-Extra":          {"", "First header, second value"},
+				"A-Second-X-Remote-Extra": {"Second header, first value", "Second header, second value"},
+				"Another-X-Remote-Extra":  {"Third header, first value"}},
+			headerPrefixes: []string{"X-Remote-Extra-"},
+			wantedExtra:    map[string][]string{},
+		},
+		{
+			name: "extra prefix matches",
+			header: http.Header{
+				"X-Remote-Extra-User": {"Bob", "Tom"},
+			},
+			headerPrefixes: []string{"X-Remote-Extra-"},
+			wantedExtra: map[string][]string{
+				"user": {"Bob", "Tom"},
+			},
+		},
+		{
+			name: "extra prefix matches case-insensitive",
+			header: http.Header{
+				"X-Remote-User":         {"Bob"},
+				"X-Remote-Group-1":      {"one-a", "one-b"},
+				"X-Remote-Group-2":      {"two-a", "two-b"},
+				"X-Remote-extra-1-key1": {"alfa", "bravo"},
+				"X-Remote-Extra-1-Key2": {"charlie", "delta"},
+				"X-Remote-Extra-1-":     {"india", "juliet"},
+				"X-Remote-extra-2-":     {"kilo", "lima"},
+				"X-Remote-extra-2-Key1": {"echo", "foxtrot"},
+				"X-Remote-Extra-2-key2": {"golf", "hotel"},
+			},
+			headerPrefixes: []string{"X-Remote-Extra-1-", "X-Remote-Extra-2-"},
+			wantedExtra: map[string][]string{
+				"key1": {"alfa", "bravo", "echo", "foxtrot"},
+				"key2": {"charlie", "delta", "golf", "hotel"},
+				"":     {"india", "juliet", "kilo", "lima"},
+			},
+		},
+		{
+			name: "escaped extra keys",
+			header: http.Header{
+				"X-Remote-User":                                            {"Bob"},
+				"X-Remote-Group":                                           {"one-a", "one-b"},
+				"X-Remote-Extra-Alpha":                                     {"alphabetical"},
+				"X-Remote-Extra-Alph4num3r1c":                              {"alphanumeric"},
+				"X-Remote-Extra-Percent%20encoded":                         {"percent encoded"},
+				"X-Remote-Extra-Almost%zzpercent%xxencoded":                {"not quite percent encoded"},
+				"X-Remote-Extra-Example.com%2fpercent%2520encoded":         {"url with double percent encoding"},
+				"X-Remote-Extra-Example.com%2F%E4%BB%8A%E6%97%A5%E3%81%AF": {"url with unicode"},
+				"X-Remote-Extra-Abc123!#$+.-_*\\^`~|'":                     {"header key legal characters"},
+			},
+			headerPrefixes: []string{"X-Remote-Extra-"},
+			wantedExtra: map[string][]string{
+				"alpha":                         {"alphabetical"},
+				"alph4num3r1c":                  {"alphanumeric"},
+				"percent encoded":               {"percent encoded"},
+				"almost%zzpercent%xxencoded":    {"not quite percent encoded"},
+				"example.com/percent%20encoded": {"url with double percent encoding"},
+				"example.com/今日は":               {"url with unicode"},
+				"abc123!#$+.-_*\\^`~|'":         {"header key legal characters"},
+			},
+		},
+	}
+	for _, tt := range tests {
+		t.Run(tt.name, func(t *testing.T) {
+			if got := getExtraFromHeaders(tt.header, tt.headerPrefixes); !reflect.DeepEqual(got, tt.wantedExtra) {
+				t.Errorf("getExtraFromHeaders() = %v, wantedExtra %v", got, tt.wantedExtra)
+			}
+		})
+	}
+}