Skip to content

Commit

Permalink
mux: calculate verb correctly for cases like DELETE /foo/bar:archive …
Browse files Browse the repository at this point in the history
…when user provided wrong method (grpc-ecosystem#2870)

* add failing test for DELETE /foo/bar:archive when method is wrong

The method the user meant was POST, which is supported. DELETE is not
supported, but I believe this should be NotImplemented, not NotFound.

* calculate verb in each handler
  • Loading branch information
jonathaningram authored Sep 5, 2022
1 parent 660400c commit 6efdab1
Show file tree
Hide file tree
Showing 2 changed files with 30 additions and 6 deletions.
23 changes: 17 additions & 6 deletions runtime/mux.go
Original file line number Diff line number Diff line change
Expand Up @@ -343,8 +343,7 @@ func (s *ServeMux) ServeHTTP(w http.ResponseWriter, r *http.Request) {
}
}

// Verb out here is to memoize for the fallback case below
var verb string
lastComponent := components[len(components)-1]

for _, h := range s.handlers[r.Method] {
// If the pattern has a verb, explicitly look for a suffix in the last
Expand All @@ -355,10 +354,11 @@ func (s *ServeMux) ServeHTTP(w http.ResponseWriter, r *http.Request) {
// parser because we know what verb we're looking for, however, there
// are still some cases that the parser itself cannot disambiguate. See
// the comment there if interested.

var verb string
patVerb := h.pat.Verb()
l := len(components)
lastComponent := components[l-1]
var idx int = -1

idx := -1
if patVerb != "" && strings.HasSuffix(lastComponent, ":"+patVerb) {
idx = len(lastComponent) - len(patVerb) - 1
}
Expand All @@ -368,7 +368,7 @@ func (s *ServeMux) ServeHTTP(w http.ResponseWriter, r *http.Request) {
return
}
if idx > 0 {
components[l-1], verb = lastComponent[:idx], lastComponent[idx+1:]
components[len(components)-1], verb = lastComponent[:idx], lastComponent[idx+1:]
}

pathParams, err := h.pat.MatchAndEscape(components, verb, s.unescapingMode)
Expand All @@ -394,6 +394,17 @@ func (s *ServeMux) ServeHTTP(w http.ResponseWriter, r *http.Request) {
continue
}
for _, h := range handlers {
var verb string
patVerb := h.pat.Verb()

idx := -1
if patVerb != "" && strings.HasSuffix(lastComponent, ":"+patVerb) {
idx = len(lastComponent) - len(patVerb) - 1
}
if idx > 0 {
components[len(components)-1], verb = lastComponent[:idx], lastComponent[idx+1:]
}

pathParams, err := h.pat.MatchAndEscape(components, verb, s.unescapingMode)
if err != nil {
var mse MalformedSequenceError
Expand Down
13 changes: 13 additions & 0 deletions runtime/mux_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,19 @@ func TestMuxServeHTTP(t *testing.T) {
reqPath: "/foo",
respStatus: http.StatusNotImplemented,
},
{
patterns: []stubPattern{
{
method: "POST",
ops: []int{int(utilities.OpLitPush), 0, int(utilities.OpPush), 0, int(utilities.OpConcatN), 1, int(utilities.OpCapture), 1},
pool: []string{"foo", "id"},
verb: "archive",
},
},
reqMethod: "DELETE",
reqPath: "/foo/bar:archive",
respStatus: http.StatusNotImplemented,
},
{
patterns: []stubPattern{
{
Expand Down

0 comments on commit 6efdab1

Please sign in to comment.