diff --git a/transport/http/context.go b/transport/http/context.go index c101070b3..c83ce890a 100644 --- a/transport/http/context.go +++ b/transport/http/context.go @@ -16,9 +16,6 @@ import ( var _ Context = (*wrapper)(nil) -// HandlerFunc defines a function to serve HTTP requests. -type HandlerFunc func(Context) error - // Context is an HTTP Context. type Context interface { context.Context @@ -60,10 +57,10 @@ func (w *responseWriter) Write(data []byte) (int, error) { } type wrapper struct { - route *Route - req *http.Request - res http.ResponseWriter - w responseWriter + router *Router + req *http.Request + res http.ResponseWriter + w responseWriter } func (c *wrapper) Header() http.Header { @@ -90,9 +87,9 @@ func (c *wrapper) Query() url.Values { func (c *wrapper) Request() *http.Request { return c.req } func (c *wrapper) Response() http.ResponseWriter { return c.res } func (c *wrapper) Middleware(h middleware.Handler) middleware.Handler { - return middleware.Chain(c.route.srv.ms...)(h) + return middleware.Chain(c.router.srv.ms...)(h) } -func (c *wrapper) Bind(v interface{}) error { return c.route.srv.dec(c.req, v) } +func (c *wrapper) Bind(v interface{}) error { return c.router.srv.dec(c.req, v) } func (c *wrapper) BindVars(v interface{}) error { return binding.BindQuery(c.Vars(), v) } func (c *wrapper) BindQuery(v interface{}) error { return binding.BindQuery(c.Query(), v) } func (c *wrapper) BindForm(v interface{}) error { return binding.BindForm(c.req, v) } @@ -100,7 +97,7 @@ func (c *wrapper) Returns(v interface{}, err error) error { if err != nil { return err } - if err := c.route.srv.enc(&c.w, c.req, v); err != nil { + if err := c.router.srv.enc(&c.w, c.req, v); err != nil { return err } return nil @@ -108,7 +105,7 @@ func (c *wrapper) Returns(v interface{}, err error) error { func (c *wrapper) Result(code int, v interface{}) error { c.w.WriteHeader(code) - if err := c.route.srv.enc(&c.w, c.req, v); err != nil { + if err := c.router.srv.enc(&c.w, c.req, v); err != nil { return err } return nil diff --git a/transport/http/filter.go b/transport/http/filter.go new file mode 100644 index 000000000..ba7602f34 --- /dev/null +++ b/transport/http/filter.go @@ -0,0 +1,16 @@ +package http + +import "net/http" + +// FilterFunc is a function which receives an http.Handler and returns another http.Handler. +type FilterFunc func(http.Handler) http.Handler + +// FilterChain returns a FilterFunc that specifies the chained handler for HTTP Router. +func FilterChain(filters ...FilterFunc) FilterFunc { + return func(next http.Handler) http.Handler { + for i := len(filters) - 1; i >= 0; i-- { + next = filters[i](next) + } + return next + } +} diff --git a/transport/http/route.go b/transport/http/router.go similarity index 60% rename from transport/http/route.go rename to transport/http/router.go index aae84fea6..3c0550ddd 100644 --- a/transport/http/route.go +++ b/transport/http/router.go @@ -6,41 +6,31 @@ import ( "sync" ) -// FilterFunc is a function which receives an http.Handler and returns another http.Handler. -type FilterFunc func(http.Handler) http.Handler +// HandlerFunc defines a function to serve HTTP requests. +type HandlerFunc func(Context) error -// FilterChain returns a FilterFunc that specifies the chained handler for HTTP Router. -func FilterChain(filters ...FilterFunc) FilterFunc { - return func(next http.Handler) http.Handler { - for i := len(filters) - 1; i >= 0; i-- { - next = filters[i](next) - } - return next - } -} - -// Route is an HTTP route. -type Route struct { +// Router is an HTTP router. +type Router struct { prefix string pool sync.Pool srv *Server filters []FilterFunc } -func newRoute(prefix string, srv *Server, filters ...FilterFunc) *Route { - r := &Route{ +func newRouter(prefix string, srv *Server, filters ...FilterFunc) *Router { + r := &Router{ prefix: prefix, srv: srv, filters: filters, } r.pool.New = func() interface{} { - return &wrapper{route: r} + return &wrapper{router: r} } return r } // Handle registers a new route with a matcher for the URL path and method. -func (r *Route) Handle(method, relativePath string, h HandlerFunc, filters ...FilterFunc) { +func (r *Router) Handle(method, relativePath string, h HandlerFunc, filters ...FilterFunc) { next := http.Handler(http.HandlerFunc(func(res http.ResponseWriter, req *http.Request) { ctx := r.pool.Get().(Context) ctx.Reset(res, req) @@ -56,46 +46,46 @@ func (r *Route) Handle(method, relativePath string, h HandlerFunc, filters ...Fi } // GET registers a new GET route for a path with matching handler in the router. -func (r *Route) GET(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) GET(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodGet, path, h, m...) } // HEAD registers a new HEAD route for a path with matching handler in the router. -func (r *Route) HEAD(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) HEAD(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodHead, path, h, m...) } // POST registers a new POST route for a path with matching handler in the router. -func (r *Route) POST(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) POST(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodPost, path, h, m...) } // PUT registers a new PUT route for a path with matching handler in the router. -func (r *Route) PUT(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) PUT(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodPut, path, h, m...) } // PATCH registers a new PATCH route for a path with matching handler in the router. -func (r *Route) PATCH(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) PATCH(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodPatch, path, h, m...) } // DELETE registers a new DELETE route for a path with matching handler in the router. -func (r *Route) DELETE(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) DELETE(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodDelete, path, h, m...) } // CONNECT registers a new CONNECT route for a path with matching handler in the router. -func (r *Route) CONNECT(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) CONNECT(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodConnect, path, h, m...) } // OPTIONS registers a new OPTIONS route for a path with matching handler in the router. -func (r *Route) OPTIONS(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) OPTIONS(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodOptions, path, h, m...) } // TRACE registers a new TRACE route for a path with matching handler in the router. -func (r *Route) TRACE(path string, h HandlerFunc, m ...FilterFunc) { +func (r *Router) TRACE(path string, h HandlerFunc, m ...FilterFunc) { r.Handle(http.MethodTrace, path, h, m...) } diff --git a/transport/http/route_test.go b/transport/http/router_test.go similarity index 100% rename from transport/http/route_test.go rename to transport/http/router_test.go diff --git a/transport/http/server.go b/transport/http/server.go index 365ec2dd2..61e0be6d9 100644 --- a/transport/http/server.go +++ b/transport/http/server.go @@ -127,9 +127,9 @@ func NewServer(opts ...ServerOption) *Server { return srv } -// Route registers an HTTP route. -func (s *Server) Route(prefix string, filters ...FilterFunc) *Route { - return newRoute(prefix, s, filters...) +// Route registers an HTTP router. +func (s *Server) Route(prefix string, filters ...FilterFunc) *Router { + return newRouter(prefix, s, filters...) } // Handle registers a new route with a matcher for the URL path. diff --git a/transport/http/server_test.go b/transport/http/server_test.go index e0e1894c4..27ae24491 100644 --- a/transport/http/server_test.go +++ b/transport/http/server_test.go @@ -22,15 +22,9 @@ type testData struct { func TestServer(t *testing.T) { fn := func(w http.ResponseWriter, r *http.Request) { - data := &testData{Path: r.RequestURI} - json.NewEncoder(w).Encode(data) - - if r.Context().Value(testKey{}) != "test" { - w.WriteHeader(500) - } + json.NewEncoder(w).Encode(testData{Path: r.RequestURI}) } ctx := context.Background() - ctx = context.WithValue(ctx, testKey{}, "test") srv := NewServer() srv.HandleFunc("/index", fn)