Skip to content

Commit

Permalink
Preserve leading and trailing slashes on proxy subpaths
Browse files Browse the repository at this point in the history
Kubernetes-commit: 04eede9b2a2a24571cb084fcb952c6a2a2a2bdd1
  • Loading branch information
liggitt authored and k8s-publishing-bot committed Sep 23, 2017
1 parent be971f2 commit 06d00b1
Show file tree
Hide file tree
Showing 2 changed files with 59 additions and 0 deletions.
21 changes: 21 additions & 0 deletions pkg/util/net/http.go
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,34 @@ import (
"net/http"
"net/url"
"os"
"path"
"strconv"
"strings"

"github.com/golang/glog"
"golang.org/x/net/http2"
)

// JoinPreservingTrailingSlash does a path.Join of the specified elements,
// preserving any trailing slash on the last non-empty segment
func JoinPreservingTrailingSlash(elem ...string) string {
// do the basic path join
result := path.Join(elem...)

// find the last non-empty segment
for i := len(elem) - 1; i >= 0; i-- {
if len(elem[i]) > 0 {
// if the last segment ended in a slash, ensure our result does as well
if strings.HasSuffix(elem[i], "/") && !strings.HasSuffix(result, "/") {
result += "/"
}
break
}
}

return result
}

// IsProbableEOF returns true if the given error resembles a connection termination
// scenario that would justify assuming that the watch is empty.
// These errors are what the Go http stack returns back to us which are general
Expand Down
38 changes: 38 additions & 0 deletions pkg/util/net/http_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@ package net

import (
"crypto/tls"
"fmt"
"net"
"net/http"
"net/url"
Expand Down Expand Up @@ -218,3 +219,40 @@ func TestTLSClientConfigHolder(t *testing.T) {
t.Errorf("didn't find tls config")
}
}

func TestJoinPreservingTrailingSlash(t *testing.T) {
tests := []struct {
a string
b string
want string
}{
// All empty
{"", "", ""},

// Empty a
{"", "/", "/"},
{"", "foo", "foo"},
{"", "/foo", "/foo"},
{"", "/foo/", "/foo/"},

// Empty b
{"/", "", "/"},
{"foo", "", "foo"},
{"/foo", "", "/foo"},
{"/foo/", "", "/foo/"},

// Both populated
{"/", "/", "/"},
{"foo", "foo", "foo/foo"},
{"/foo", "/foo", "/foo/foo"},
{"/foo/", "/foo/", "/foo/foo/"},
}
for _, tt := range tests {
name := fmt.Sprintf("%q+%q=%q", tt.a, tt.b, tt.want)
t.Run(name, func(t *testing.T) {
if got := JoinPreservingTrailingSlash(tt.a, tt.b); got != tt.want {
t.Errorf("JoinPreservingTrailingSlash() = %v, want %v", got, tt.want)
}
})
}
}

0 comments on commit 06d00b1

Please sign in to comment.