ale

package module
v0.27.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Sep 14, 2022 License: MIT Imports: 14 Imported by: 1

README

Ale logo

Ale

Ale is a collection of HTTP-related tools to be used with roll-your-own Go web applications.

This software is released under the MIT license, as outlined in the included LICENSE.md file.

Documentation

Overview

Package ale provides some utilites to extend standard HTTP handlers for easier error handling.

The core of this package is the ErrorHandler and ErrorHandlerFunc types, which simply extends their standard library companion types (http.Handler and http.HandlerFunc respectively) to return errors.

Such a handler (or middleware) should either write a response to the standard http.ResponseWriter _or_ return an error. Any such errors are converted to a response by an ErrorReporter. This allows putting all error-handling logic in a single location, rather than scattered throughout your application.

Index

Constants

This section is empty.

Variables

View Source
var DefaultReporter = BasicReporter

DefaultReporter is used by Std() any time an error has not been injected with HandleErrors.

Functions

func BasicReporter added in v0.15.0

func BasicReporter(w http.ResponseWriter, r *http.Request, err error)

BasicReporter is a bare ErrorReporter, which wraps http.Error. If err satisfies the interface{ HTTPStatus() int } interface, the method is called to determine the HTTP status.

If w is a UsedWriter, and returns true, then nothing is written to the response.

func ConvertMiddleware added in v0.13.0

func ConvertMiddleware(emw Middleware) func(http.Handler) http.Handler

ConvertMiddleware converts ale middleware to standard middleware. See Std() to understand how errors are handled.

func IsUsed added in v0.17.0

func IsUsed(w http.ResponseWriter) (bool, error)

WriterIsDIsUsedone returns true if a response has been written. An error is returned if the underlying writer is not a DoneWriter.

func LogData added in v0.18.0

func LogData(ctx context.Context, key string, value interface{})

LogData adds key/value to the context, to be included in the LogContext by the RequestLogger middleware. If called outside of the RequestLogger chain, it will panic.

func PanicToError added in v0.19.0

func PanicToError(p interface{}) error

PanicToError converts a recovered panic to an error. The returned error implements the HTTPStatus() and GRPCStatus() methods, for compatibility.

func Recover added in v0.13.0

func Recover() func(Handler) Handler

Recover converts any panic into an error. Requires use of HandleErrors.

func RequestLogger added in v0.13.0

func RequestLogger(cb func(*LogContext)) func(Handler) Handler

RequestLogger gathers request statistics for logging, and calls cb to do the actual logging. Any error will be included in the logging context, and consumed. This handler always returns a nil error.

func ServeJSON

func ServeJSON(w http.ResponseWriter, i interface{}, status ...int) error

ServeJSON marshals i and serves it on w. If the Content-Type header is not yet set on w, it will be set to "application/json; charset=utf-8". If status is passed, the first status value will be passed to w.WriteHeader, otherwise the default of http.StatusOK is used.

func Std added in v0.14.0

func Std(h Handler) http.Handler

Std converts h into a standard http.Handler. If h returns an error, it is panicked such that it can be recovered by the Recover() middleware or Chain.Handler().

func StdRequestLogger added in v0.14.0

func StdRequestLogger(cb func(*LogContext)) func(http.Handler) http.Handler

StdRequestLogger gathers request statistics for logging, and calls cb to do the actual logging. If HandleErrors was called first, any error will be included in the logging context.

func StdTrackWriterUsage added in v0.17.0

func StdTrackWriterUsage(next http.Handler) http.Handler

StdTrackWriterUsage is an http middleware equivalent of WrapWriter.

Types

type Chain added in v0.16.0

type Chain struct {
	// contains filtered or unexported fields
}

Chain represents a complete middleware chain and adapter.

func New added in v0.16.0

func New() *Chain

New returns an empty Ale middleware chain.

func (*Chain) Handler added in v0.16.0

func (c *Chain) Handler(h http.Handler) http.Handler

Handler applies the middleware chain to h.

func (*Chain) SetErrorReporter added in v0.16.0

func (c *Chain) SetErrorReporter(r ErrorReporter)

SetErrerReporter sets the ErrorReporter, to handle any errors generated by a request. If unset, BasicReporter is used.

func (*Chain) SetLogger added in v0.16.0

func (c *Chain) SetLogger(l func(*LogContext))

SetLogger sets a request logger. If unset, requests are not logged by ale.

func (*Chain) Use added in v0.16.0

func (m *Chain) Use(mw ...Middleware)

Use adds mw to the end of the middleware chain.

func (*Chain) UseStd added in v0.16.0

func (m *Chain) UseStd(mws ...func(http.Handler) http.Handler)

UseStd adds mw to the end of the middleware chain.

type ErrorReporter

type ErrorReporter func(w http.ResponseWriter, r *http.Request, err error)

ErrorReporter is a function that can report an HTTP error returned by a ErrorHandlerFunc.

func (ErrorReporter) HTTPHandlerFunc deprecated

func (c ErrorReporter) HTTPHandlerFunc(f HandlerFunc) http.HandlerFunc

HTTPHandlerFunc wraps a HandlerFunc, such that it can be used as a standard http.HandlerFunc.

Deprecated: Use Middleware() method.

func (ErrorReporter) Middleware added in v0.22.2

func (c ErrorReporter) Middleware(next Handler) Handler

Middleware converts c into a middleware function.

type Handler added in v0.14.0

type Handler interface {
	// ServeHTTPE serves the same purpose as http.Handler's ServeHTTP, except
	// that it may return an error. The function should _either_ write to
	// http.ResponseWriter _or_ return an error.
	ServeHTTPE(http.ResponseWriter, *http.Request) error
}

Handler extends http.Handler with an error return value.

func TrackWriterUsage added in v0.17.0

func TrackWriterUsage(next Handler) Handler

TrackWriterUsage is an ale middleware which wraps the standard http.ResponseWriter with a DoneWriter. Subsequent middlewares or handlers should use the WriterIsDone method to check the status.

func Wrap added in v0.22.0

func Wrap(h http.Handler) Handler

Wrap wraps a standard http.Handler to satisfy the Handler interface.

type HandlerFunc added in v0.14.0

type HandlerFunc func(http.ResponseWriter, *http.Request) error

HandlerFunc extends the standard http.HandlerFunc to support error handling more easily.

HandlerFunc also satisfies the http.Handler interface by implementing the ServeHTTP() method, which will panic on error, such that the panic can be recovered properly by the Recover() middleware or Chain.Handler().

func (HandlerFunc) ServeHTTP added in v0.14.0

func (f HandlerFunc) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP calls f, and if it returns an error, it is panicked such that it can be properly recovered by the Recover() middleware or Chain.Handler().

func (HandlerFunc) ServeHTTPE added in v0.14.0

func (f HandlerFunc) ServeHTTPE(w http.ResponseWriter, r *http.Request) error

type LogContext

type LogContext struct {

	// Request is the client request.
	Request *http.Request

	// StatusCode is the HTTP status code sent to the client.
	StatusCode int
	// ResponseHeader is the list of header values sent to the client.
	ResponseHeader http.Header
	// ResponseHeader is the list of trailer values sent to the client.
	ResponseTrailer http.Header
	// ResponseBytes is the number of bytes written in the response body.
	ResponseBytes int64
	// RequestBytes is the number of bytes read from the request body. This
	// can differ from the Content-Length value if reading is not completed, or
	// in case Content-Length is unset.
	RequestBytes int64

	// StartTime is the time the request was received by the server
	StartTime time.Time
	// ElapsedTime is the duration it took to serve the request
	ElapsedTime time.Duration

	// Error is the error, if any, returned from the handler/middlware chain.
	Error error

	// Data is a collection of arbitrary request-scoped data to be logged.
	// Add to this by calling LogData.
	Data map[string]interface{}
	// contains filtered or unexported fields
}

LogContext captures data about a request and response, for logging.

func NewLogContext

func NewLogContext(w http.ResponseWriter, r *http.Request) *LogContext

NewLogContext returns a new log context, which should be used as a ResponseWriter for subsequent handlers in middleware.

Example:

func LogMiddleware(next http.Handler) http.Handler {
    return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
        logCtx := NewLogContext(w,r)
        next.ServeHTTP(logCtx, r)
        logCtx.Finalize()
        // Log logCtx here
    })
}

func (*LogContext) Finalize

func (l *LogContext) Finalize()

Finalize should be called after ServeHTTP, to finalize the response values. Without this call, trailers will not be set, and elapsed time is not calculated.

func (*LogContext) Header

func (l *LogContext) Header() http.Header

Header returns the header map that will be sent by WriteHeader.

func (*LogContext) Used added in v0.17.2

func (l *LogContext) Used() bool

Used returns true if the this http.ResponseWriter has been written to.

func (*LogContext) Write

func (l *LogContext) Write(p []byte) (int, error)

Write writes the data to the connection as part of an HTTP reply.

func (*LogContext) WriteHeader

func (l *LogContext) WriteHeader(status int)

WriteHeader sends an HTTP response header with the provided status code.

type Middleware added in v0.14.0

type Middleware func(Handler) Handler

Middleware extends the standard middleware with error handling.

func StdMiddleware added in v0.23.0

func StdMiddleware(mw func(http.Handler) http.Handler) Middleware

StdMiddleware adapts a standard middleware function for use with ale.

type Router added in v0.21.0

type Router interface {
	http.Handler
	Handler

	// EarlyUse registers middlewares in the call chain before the error
	// reporter or logger. It is intended for setting metadata, such as trace
	// IDs, that are necessary to properly handle errors or log requests.
	//
	// Calling EarlyUse on a sub-router will panic.
	EarlyUse(middlewares ...Middleware)
	// ErrorReporter defines an error reporter at the top of the call chain.
	// The error reporter should turn an error value into an HTTP response to
	// be consumed by the client.
	//
	// It is not uncommon to also want to set an error handler further down the
	// call chain, to consume additional information (such as authenticated user
	// trace IDs, etc) that may be added to the context later in the middleware
	// call chain. It is therefore safe to use ErrorReporter and also call
	// Use(ale.ErrorReporter(<your func>).Middleware).  The ErrorReporter type
	// ensures that any given error is not reported more than once.
	ErrorReporter(ErrorReporter)
	Logger(func(*LogContext))

	// Use appends one or more middlewares onto the Router stack.
	Use(middlewares ...Middleware)

	// With adds inline middlewares for an endpoint handler.
	With(middlewares ...Middleware) Router

	// Group adds a new inline-Router along the current routing
	// path, with a fresh middleware stack for the inline-Router.
	Group() Router

	// Route mounts a sub-Router along a `pattern“ string.
	Route(pattern string) Router

	// Mount attaches another Handler along ./pattern/*
	Mount(pattern string, h Handler)

	// Handle and HandleFunc adds routes for `pattern` that matches
	// all HTTP methods.
	Handle(pattern string, h Handler)
	HandleFunc(pattern string, h HandlerFunc)

	// Method and MethodFunc adds routes for `pattern` that matches
	// the `method` HTTP method.
	Method(method, pattern string, h Handler)
	MethodFunc(method, pattern string, h HandlerFunc)

	// HTTP-method routing along `pattern`
	Connect(pattern string, h HandlerFunc)
	Delete(pattern string, h HandlerFunc)
	Get(pattern string, h HandlerFunc)
	Head(pattern string, h HandlerFunc)
	Options(pattern string, h HandlerFunc)
	Patch(pattern string, h HandlerFunc)
	Post(pattern string, h HandlerFunc)
	Put(pattern string, h HandlerFunc)
	Trace(pattern string, h HandlerFunc)

	// NotFound defines a handler to respond whenever a route could
	// not be found.
	NotFound(h HandlerFunc)

	// MethodNotAllowed defines a handler to respond whenever a method is
	// not allowed.
	MethodNotAllowed(h HandlerFunc)
}

Router is copied from chi, but adapted for the ale.Handler type.

func NewRouter added in v0.21.0

func NewRouter() Router

NewRouter returns a new router (based on the chi router).

Experimental

type UsedWriter added in v0.17.0

type UsedWriter interface {
	http.ResponseWriter
	Used() bool
}

UsedWriter extends the http.ResponseWriter interface to return a bool to indicate whether anything has been written.

To use it, call the TrackWriterUsage middleware early in your middleware stack. Then in other middlewares or handlers, you can use the WasUsed method to check the status.

func main() {
    r := chi.NewRouter()

    r.Use(ale.TrackWriterUsage)
    // and other middlewares

    r.Get("/", func(w http.ResponseWriter, r *http.Request) {
        if done, _ := ale.WasUsed(w); done {
            // Nothing to do, a response was already sent
            return
        }

        // Normal operation here...

    })
}

type WrapFunc added in v0.22.0

type WrapFunc func(http.ResponseWriter, *http.Request)

WrapFunc wraps a standard http.HandlerFunc to satisfy the Handler interface.

func (WrapFunc) ServeHTTPE added in v0.22.0

func (f WrapFunc) ServeHTTPE(w http.ResponseWriter, r *http.Request) (err error)

Directories

Path Synopsis
Package donewriter provides a simple wrapper around an http.ResponseWriter to track when a response has been sent.
Package donewriter provides a simple wrapper around an http.ResponseWriter to track when a response has been sent.
Package envconf provides simple functionality for reading configuration from the environment, such as for use within a 12-Factor Application.
Package envconf provides simple functionality for reading configuration from the environment, such as for use within a 12-Factor Application.
Package errors is a drop-in replacement for the errors package in the standard library, with extensions useful for developing web applications.
Package errors is a drop-in replacement for the errors package in the standard library, with extensions useful for developing web applications.
Package httperr provides HTTP-centric extensions to standard errors.
Package httperr provides HTTP-centric extensions to standard errors.
Package panicerr makes it easy to recover panics, and convert them to standard errors.
Package panicerr makes it easy to recover panics, and convert them to standard errors.
Package view provides an HTTP middleware to provide a simple View, based on Go templates.
Package view provides an HTTP middleware to provide a simple View, based on Go templates.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL