Documentation ¶
Index ¶
- Constants
- Variables
- func Bearer(r *http.Request) (string, bool)
- func BodyClose(next http.Handler) http.Handler
- func Chain(handlers ...interface{}) http.Handler
- func ClaimsFromContextTo(ctx context.Context, recv interface{}) (err error)
- func ContextHandler(next http.Handler) http.Handler
- func Go(ctx context.Context, handler func(stop <-chan struct{}) error) error
- func RequestCodecFromContext(ctx context.Context) codec.Codec
- func RequestID(next http.Handler) http.Handler
- func RequestIDFromContext(ctx context.Context) string
- func ResponseCodecFromContext(ctx context.Context) codec.Codec
- type BaseController
- type Claims
- type ClaimsFactory
- type Codecs
- type Controller
- type HandlerTask
- type JWTParser
- type JobStatus
- type Middleware
- func AsyncRequest(reqTimeout, asyncTimeout, keepResult time.Duration) Middleware
- func Codec(fn errors.HandlerFunc, codecs Codecs) Middleware
- func ContextDeadline(timeout time.Duration) Middleware
- func JWT(parser JWTParser, cf ClaimsFactory) Middleware
- func New(middlewares ...Middleware) Middleware
- func PanicRecover(onPanic OnPanic) Middleware
- func RequestLimiter(fn errors.HandlerFunc, maxConcurrentRequests int) Middleware
- func SetHeaders(headers map[string]string) Middleware
- func Throttle(count int64, duration time.Duration) Middleware
- type MiddlewareFunc
- type OnPanic
Constants ¶
const StatusNoResponse = 444
StatusNoResponse is returned when request is canceled
Variables ¶
var ( // ErrNotCompleted - current job was not completed. ErrNotCompleted = errors.New("task has not been completed") // ErrNotStarted - current job was not started. ErrNotStarted = errors.New("job has not been started") // ErrAlreadyDone - current job has been already done. ErrAlreadyDone = errors.New("job already completed") )
var DefaultTimeFormat = time.RFC1123
DefaultTimeFormat contains default date/time layout to be used across middlewares of the package.
Functions ¶
func Chain ¶
Chain builds a http.Handler from passed arguments. It accepts different kinds of argument types:
- MiddlewareFunc
- func(http.ResponseWriter, *http.Request, http.Handler)
- Middleware
- func(http.Handler) http.Handler
- http.Handler
- func(w http.ResponseWriter, r *http.Request)
Keep in mind:
- by passing http.Handler/http.HandlerFunc instead of Middleware you lose control over the next Middleware (no way to cancel it), but if you only need to put something to the context (and do not have any logic after calling "next") there is no sense to build Middleware func around
- even if you do not pass any handlers blobHandler will be executed.
func ClaimsFromContextTo ¶
ClaimsFromContextTo retrieves claims from context and assigns to the provided receiver.
func ContextHandler ¶
ContextHandler reads from context.Done channel to handle deadline/timeout
func Go ¶
Go function runs the handler and processes its execuion in a new goroutine. It also passes Done channel to the handler. Once channel is closed handler should be able to stop its goroutine to avoid resource leaks.
func RequestCodecFromContext ¶
RequestCodecFromContext pulls the Codec from a request context or returns nil.
func RequestID ¶ added in v1.1.0
RequestID is a middleware that injects a request ID into the context of each request. A request ID is a string (randomly generated UUID).
func RequestIDFromContext ¶ added in v1.1.0
RequestIDFromContext pulls request ID from the context or empty string.
Types ¶
type BaseController ¶
type BaseController struct {
// contains filtered or unexported fields
}
BaseController provides ability to register/unregister middleware for HTTP methods. This is a basic Controller implementation.
func NewBaseController ¶
func NewBaseController() *BaseController
NewBaseController is a constructor func for a basic HTTP controller.
func (*BaseController) AddMiddleware ¶
func (bc *BaseController) AddMiddleware(method string, chain ...Middleware) Controller
AddMiddleware adds middleware funcs to existing ones for provided HTTP method.
func (*BaseController) Init ¶
func (bc *BaseController) Init() error
Init does nothing. This is a default function to avoid explicit declaration when controller does not require any Init logic.
func (*BaseController) Middleware ¶
func (bc *BaseController) Middleware(method string) Middleware
Middleware returns middleware func registered for provided method or an empty list.
type ClaimsFactory ¶
type ClaimsFactory func() Claims
ClaimsFactory is a func that returns a new custom claims when called.
type Codecs ¶
type Codecs interface { // Lookup should find appropriate Codec by MimeType or return nil if not found. Lookup(mimeType string) codec.Codec }
Codecs represents any kind of codec registry, thus it can be global registry or a custom list of codecs that is supposed to be used for particular route.
type Controller ¶
type Controller interface { // AddMiddleware should make the provided chain available by HTTP method. AddMiddleware(method string, chain ...Middleware) Controller // Middleware should return the list of middleware functions registered for provided method. Middleware(method string) Middleware }
Controller represents simple HTTP controller containing middleware for each method.
type HandlerTask ¶
type HandlerTask interface { // Do should execute provided closure. Do(context.Context, func(<-chan struct{}) error) // Status should return the status of current job/task. Status() JobStatus // Complete is supposed to be called inside Do's closure when job is done in // order to change job status and be able to return the result by calling // Resolve() func. Complete(interface{}, error) error // Resolve returns the result (which should be returned from the clousere using // Complete()) and error. Resolve() (interface{}, error) }
HandlerTask represents sync/async handler task.
func GetHandlerTask ¶
func GetHandlerTask(ctx context.Context) (HandlerTask, bool)
GetHandlerTask extracts current job from context.
type JWTParser ¶
JWTParser interface is responsible for token validation, meanwhile it parses token to the provided receiver.
type Middleware ¶
Middleware in itself simply takes a http.Handler as the first parameter, wraps it and returns a new http.Handler for the server to call (wraps handlers with closures according to the principle of Russian doll).
func AsyncRequest ¶
func AsyncRequest(reqTimeout, asyncTimeout, keepResult time.Duration) Middleware
AsyncRequest func creates a middleware that provides a mechanism to run the handler in a background (if HTTP request timeout was reached) and keep result until it is demanded again or result expires. Function parameters:
reqTimeout - time allotted for processing HTTP request, if request has not been processed completely - returns an ID of request (to retrieve result later).
asyncTimeout - maximum time for async job to be done (actual context deadline), this logic should be implemented in asynchronous handler or skipped - in that case handler cannot be interrupted.
keepResult - at the expiration of a given period of time the result will be unavailable (deleted).
NOTE: Do not use defer statements to check the status of task, send error or any response when using PanicRecover middleware.
func Codec ¶
func Codec(fn errors.HandlerFunc, codecs Codecs) Middleware
Codec middleware searches for suitable request/response codecs according to "Content-Type"/"Accept" headers and puts the correct codecs into the context.
func ContextDeadline ¶
func ContextDeadline(timeout time.Duration) Middleware
ContextDeadline adds timeout to request's context.
func JWT ¶
func JWT(parser JWTParser, cf ClaimsFactory) Middleware
JWT is a JSON Web token middleware that parses token with provided parser to the provided Claims receiver and puts it to the request context.
func New ¶
func New(middlewares ...Middleware) Middleware
New is a Middleware constructor func. The call without arguments returns an empty Middleware.
Usage (all examples below are equal):
- mw.New().Use(mwOne, mwTwo, mwThree).Then(handler)
- mw.New(mwOne).Use(mwTwo, mwThree).Then(handler)
- mw.New(mwOne, mwTwo, mwThree).Then(handler)
func PanicRecover ¶
func PanicRecover(onPanic OnPanic) Middleware
PanicRecover returns a middleware that recovers from the panic.
A trivial example (retrieving an error from the panic and sending to the client using errors package) is:
package main import ( "log" "net/http" "github.com/tiny-go/errors" "github.com/tiny-go/middleware" ) var ( panicHandler http.HandlerFunc = func(w http.ResponseWriter, r *http.Request) { panic("something went wrong") } ) func main() { http.Handle( "/", mw. // with HTTP panic handler New(mw.PanicRecover(errors.Send)). Then(panicHandler), ) log.Fatal(http.ListenAndServe(":8080", nil)) }
func RequestLimiter ¶
func RequestLimiter(fn errors.HandlerFunc, maxConcurrentRequests int) Middleware
RequestLimiter middleware apply concurrent request limit TODO: provide a choise either "wait" or "send error"
func SetHeaders ¶
func SetHeaders(headers map[string]string) Middleware
SetHeaders allows to set response headers.
func Throttle ¶
func Throttle(count int64, duration time.Duration) Middleware
Throttle provides a middleware that limits the amount of messages processed per unit of time. Note that middleware func can be defined globally to be shared by multiple handlers
Example:
var mw = Throttle(10, time.Second) http.Handle("/one", mw.Then(handlerOne)) http.Handle("/two", mw.Then(handlerTwo))
func (Middleware) Then ¶
func (mw Middleware) Then(final http.Handler) http.Handler
Then injects handler into middleware chain.
func (Middleware) Use ¶
func (mw Middleware) Use(middlewares ...Middleware) Middleware
Use transforms provided middleware function(s) (including current one) into a single middleware func.
type MiddlewareFunc ¶
MiddlewareFunc is a classic middleware - decides itself whether to call next handler or return an HTTP error directly to the client and breaks the chain.
type OnPanic ¶
type OnPanic func(http.ResponseWriter, interface{})
OnPanic is a function that should contain the logic responsible for any kind of error/panic reporting (to the console, file, directly to the client or simply ignore them).