From 759dd935444dc9236272d8e21af5fc77928336f0 Mon Sep 17 00:00:00 2001 From: Dao Thanh Tung Date: Thu, 27 Jan 2022 02:12:42 +0800 Subject: [PATCH] URL-encode/decode resource names for HTTP API part 3 (#12103) --- agent/event_endpoint.go | 7 +++++-- agent/federation_state_endpoint.go | 6 ++++-- agent/health_endpoint.go | 6 +++++- agent/intentions_endpoint.go | 5 ++++- agent/kvs_endpoint.go | 7 +++++-- agent/prepared_query_endpoint.go | 5 ++++- agent/session_endpoint.go | 25 ++++++++++++++++++++----- 7 files changed, 47 insertions(+), 14 deletions(-) diff --git a/agent/event_endpoint.go b/agent/event_endpoint.go index eb6561a1b7..10421d6202 100644 --- a/agent/event_endpoint.go +++ b/agent/event_endpoint.go @@ -6,7 +6,6 @@ import ( "io" "net/http" "strconv" - "strings" "time" "github.com/hashicorp/consul/acl" @@ -21,7 +20,11 @@ func (s *HTTPHandlers) EventFire(resp http.ResponseWriter, req *http.Request) (i s.parseDC(req, &dc) event := &UserEvent{} - event.Name = strings.TrimPrefix(req.URL.Path, "/v1/event/fire/") + var err error + event.Name, err = getPathSuffixUnescaped(req.URL.Path, "/v1/event/fire/") + if err != nil { + return nil, err + } if event.Name == "" { resp.WriteHeader(http.StatusBadRequest) fmt.Fprint(resp, "Missing name") diff --git a/agent/federation_state_endpoint.go b/agent/federation_state_endpoint.go index ef807adfaf..94b7a7cdd1 100644 --- a/agent/federation_state_endpoint.go +++ b/agent/federation_state_endpoint.go @@ -2,14 +2,16 @@ package agent import ( "net/http" - "strings" "github.com/hashicorp/consul/agent/structs" ) // GET /v1/internal/federation-state/ func (s *HTTPHandlers) FederationStateGet(resp http.ResponseWriter, req *http.Request) (interface{}, error) { - datacenterName := strings.TrimPrefix(req.URL.Path, "/v1/internal/federation-state/") + datacenterName, err := getPathSuffixUnescaped(req.URL.Path, "/v1/internal/federation-state/") + if err != nil { + return nil, err + } if datacenterName == "" { return nil, BadRequestError{Reason: "Missing datacenter name"} } diff --git a/agent/health_endpoint.go b/agent/health_endpoint.go index d47252626f..f6e803a3cb 100644 --- a/agent/health_endpoint.go +++ b/agent/health_endpoint.go @@ -30,7 +30,11 @@ func (s *HTTPHandlers) HealthChecksInState(resp http.ResponseWriter, req *http.R } // Pull out the service name - args.State = strings.TrimPrefix(req.URL.Path, "/v1/health/state/") + var err error + args.State, err = getPathSuffixUnescaped(req.URL.Path, "/v1/health/state/") + if err != nil { + return nil, err + } if args.State == "" { resp.WriteHeader(http.StatusBadRequest) fmt.Fprint(resp, "Missing check state") diff --git a/agent/intentions_endpoint.go b/agent/intentions_endpoint.go index 8a8456721d..2bb55b7f4b 100644 --- a/agent/intentions_endpoint.go +++ b/agent/intentions_endpoint.go @@ -486,7 +486,10 @@ func parseIntentionStringComponent(input string, entMeta *structs.EnterpriseMeta // IntentionSpecific handles the endpoint for /v1/connect/intentions/:id. // Deprecated: use IntentionExact. func (s *HTTPHandlers) IntentionSpecific(resp http.ResponseWriter, req *http.Request) (interface{}, error) { - id := strings.TrimPrefix(req.URL.Path, "/v1/connect/intentions/") + id, err := getPathSuffixUnescaped(req.URL.Path, "/v1/connect/intentions/") + if err != nil { + return nil, err + } switch req.Method { case "GET": diff --git a/agent/kvs_endpoint.go b/agent/kvs_endpoint.go index 6534718d20..b6bed301be 100644 --- a/agent/kvs_endpoint.go +++ b/agent/kvs_endpoint.go @@ -6,7 +6,6 @@ import ( "io" "net/http" "strconv" - "strings" "github.com/hashicorp/consul/agent/structs" "github.com/hashicorp/consul/api" @@ -20,7 +19,11 @@ func (s *HTTPHandlers) KVSEndpoint(resp http.ResponseWriter, req *http.Request) } // Pull out the key name, validation left to each sub-handler - args.Key = strings.TrimPrefix(req.URL.Path, "/v1/kv/") + var err error + args.Key, err = getPathSuffixUnescaped(req.URL.Path, "/v1/kv/") + if err != nil { + return nil, err + } // Check for a key list keyList := false diff --git a/agent/prepared_query_endpoint.go b/agent/prepared_query_endpoint.go index 023119e4ce..31e900288e 100644 --- a/agent/prepared_query_endpoint.go +++ b/agent/prepared_query_endpoint.go @@ -319,7 +319,10 @@ func (s *HTTPHandlers) PreparedQuerySpecific(resp http.ResponseWriter, req *http } path := req.URL.Path - id := strings.TrimPrefix(path, "/v1/query/") + id, err := getPathSuffixUnescaped(path, "/v1/query/") + if err != nil { + return nil, err + } switch { case strings.HasSuffix(path, "/execute"): diff --git a/agent/session_endpoint.go b/agent/session_endpoint.go index 97ff995b71..9371bf7418 100644 --- a/agent/session_endpoint.go +++ b/agent/session_endpoint.go @@ -3,7 +3,6 @@ package agent import ( "fmt" "net/http" - "strings" "time" "github.com/hashicorp/consul/agent/structs" @@ -72,7 +71,11 @@ func (s *HTTPHandlers) SessionDestroy(resp http.ResponseWriter, req *http.Reques } // Pull out the session id - args.Session.ID = strings.TrimPrefix(req.URL.Path, "/v1/session/destroy/") + var err error + args.Session.ID, err = getPathSuffixUnescaped(req.URL.Path, "/v1/session/destroy/") + if err != nil { + return nil, err + } if args.Session.ID == "" { resp.WriteHeader(http.StatusBadRequest) fmt.Fprint(resp, "Missing session") @@ -97,7 +100,11 @@ func (s *HTTPHandlers) SessionRenew(resp http.ResponseWriter, req *http.Request) } // Pull out the session id - args.SessionID = strings.TrimPrefix(req.URL.Path, "/v1/session/renew/") + var err error + args.SessionID, err = getPathSuffixUnescaped(req.URL.Path, "/v1/session/renew/") + if err != nil { + return nil, err + } args.Session = args.SessionID if args.SessionID == "" { resp.WriteHeader(http.StatusBadRequest) @@ -128,7 +135,11 @@ func (s *HTTPHandlers) SessionGet(resp http.ResponseWriter, req *http.Request) ( } // Pull out the session id - args.SessionID = strings.TrimPrefix(req.URL.Path, "/v1/session/info/") + var err error + args.SessionID, err = getPathSuffixUnescaped(req.URL.Path, "/v1/session/info/") + if err != nil { + return nil, err + } args.Session = args.SessionID if args.SessionID == "" { resp.WriteHeader(http.StatusBadRequest) @@ -183,7 +194,11 @@ func (s *HTTPHandlers) SessionsForNode(resp http.ResponseWriter, req *http.Reque } // Pull out the node name - args.Node = strings.TrimPrefix(req.URL.Path, "/v1/session/node/") + var err error + args.Node, err = getPathSuffixUnescaped(req.URL.Path, "/v1/session/node/") + if err != nil { + return nil, err + } if args.Node == "" { resp.WriteHeader(http.StatusBadRequest) fmt.Fprint(resp, "Missing node name")