From 52bc8bd42242f4d8f87fcbd966943fe6fa53698b Mon Sep 17 00:00:00 2001 From: Matt Bell Date: Tue, 28 Oct 2014 17:00:41 -0700 Subject: [PATCH] commands/http: Moved http request parsing into a Parse function --- commands/http/handler.go | 44 +++++++++------------------------------ commands/http/parse.go | 45 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 55 insertions(+), 34 deletions(-) create mode 100644 commands/http/parse.go diff --git a/commands/http/handler.go b/commands/http/handler.go index 682ed0078..3db13e79a 100644 --- a/commands/http/handler.go +++ b/commands/http/handler.go @@ -1,9 +1,9 @@ package http import ( + "errors" "io" "net/http" - "strings" cmds "github.com/jbenet/go-ipfs/commands" "github.com/jbenet/go-ipfs/core/commands" @@ -13,22 +13,19 @@ type Handler struct { Ctx cmds.Context } +var ErrNotFound = errors.New("404 page not found") + func (i Handler) ServeHTTP(w http.ResponseWriter, r *http.Request) { - path := strings.Split(r.URL.Path, "/")[3:] - opts := getOptions(r) - - // TODO: get args - - // ensure the requested command exists, otherwise 404 - _, err := commands.Root.Get(path) + req, err := Parse(r) if err != nil { - w.WriteHeader(http.StatusNotFound) - w.Write([]byte("404 page not found")) + if err == ErrNotFound { + w.WriteHeader(http.StatusNotFound) + } else { + w.WriteHeader(http.StatusBadRequest) + } + w.Write([]byte(err.Error())) return } - - // build the Request - req := cmds.NewRequest(path, opts, nil, nil) req.SetContext(i.Ctx) // call the command @@ -60,24 +57,3 @@ func (i Handler) ServeHTTP(w http.ResponseWriter, r *http.Request) { w.Write([]byte(err.Error())) } } - -// getOptions returns the command options in the given HTTP request -// (from the querystring and request body) -func getOptions(r *http.Request) map[string]interface{} { - opts := make(map[string]interface{}) - - query := r.URL.Query() - for k, v := range query { - opts[k] = v[0] - } - - // TODO: get more options from request body (formdata, json, etc) - - _, short := opts[cmds.EncShort] - _, long := opts[cmds.EncLong] - if !short && !long { - opts[cmds.EncShort] = cmds.JSON - } - - return opts -} diff --git a/commands/http/parse.go b/commands/http/parse.go new file mode 100644 index 000000000..24ae2f433 --- /dev/null +++ b/commands/http/parse.go @@ -0,0 +1,45 @@ +package http + +import ( + "net/http" + "strings" + + cmds "github.com/jbenet/go-ipfs/commands" + "github.com/jbenet/go-ipfs/core/commands" +) + +// Parse parses the data in a http.Request and returns a command Request object +func Parse(r *http.Request) (cmds.Request, error) { + path := strings.Split(r.URL.Path, "/")[3:] + + // 404 if there is no command at that path + if _, err := commands.Root.Get(path); err != nil { + return nil, ErrNotFound + } + + opts, args := parseOptions(r) + + // TODO: input stream (from request body) + + return cmds.NewRequest(path, opts, args, nil), nil +} + +func parseOptions(r *http.Request) (map[string]interface{}, []string) { + opts := make(map[string]interface{}) + + query := r.URL.Query() + for k, v := range query { + opts[k] = v[0] + } + + // TODO: get more options from request body (formdata, json, etc) + + // default to setting encoding to JSON + _, short := opts[cmds.EncShort] + _, long := opts[cmds.EncLong] + if !short && !long { + opts[cmds.EncShort] = cmds.JSON + } + + return opts, nil +}