tigertonic

package module
v0.0.0-...-fe6b9f0 Latest Latest
Warning

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

Go to latest
Published: Apr 20, 2017 License: BSD-2-Clause-Views Imports: 25 Imported by: 124

README

Tiger Tonic

Build Status

A Go framework for building JSON web services inspired by Dropwizard. If HTML is your game, this will hurt a little.

Like the Go language itself, Tiger Tonic strives to keep features orthogonal. It defers what it can to the Go standard library and a few other packages.

Documentation

Articles and talks
Reference

http://godoc.org/github.com/rcrowley/go-tigertonic

Community

Synopsis

tigertonic.TrieServeMux

HTTP routing in the Go standard library is pretty anemic. Enter tigertonic.TrieServeMux. It accepts an HTTP method, a URL pattern, and an http.Handler or an http.HandlerFunc. Components in the URL pattern wrapped in curly braces - { and } - are wildcards: their values (which don't cross slashes) are added to the URL as u.Query().Get("name").

HandleNamespace is like Handle but additionally strips the namespace from the URL, making API versioning, multitenant services, and relative links easier to manage. This is roughly equivalent to http.ServeMux's behavior.

tigertonic.HostServeMux

Use tigertonic.HostServeMux to serve multiple domain names from the same net.Listener.

tigertonic.Marshaled

Wrap a function in tigertonic.Marshaled to turn it into an http.Handler. The function signature must be something like this or tigertonic.Marshaled will panic:

func myHandler(*url.URL, http.Header, *MyRequest) (int, http.Header, *MyResponse, error)

Request bodies will be unmarshaled into a MyRequest struct and response bodies will be marshaled from MyResponse structs.

Should you need to respond with an error, the tigertonic.HTTPEquivError interface is implemented by tigertonic.BadRequest (and so on for every other HTTP response status) that can be wrapped around any error:

func myHandler(*url.URL, http.Header, *MyRequest) (int, http.Header, *MyResponse, error) {
    return 0, nil, nil, tigertonic.BadRequest{errors.New("Bad Request")}
}

Alternatively, you can return a valid status as the first output parameter and an error as the last; that status will be used in the error response.

If the return type of a tigertonic.Marshaled handler interface implements the io.Reader interface the stream will be written directly to the requestor. A Content-Type header is required to be specified in the response headers and the Accept header for these particular requests can be anything.

Additionally, if the return type of the tigertonic.Marshaled handler implements the io.Closer interface the stream will be automatically closed after it is flushed to the requestor.

tigertonic.Logged, tigertonic.JSONLogged, and tigertonic.ApacheLogged

Wrap an http.Handler in tigertonic.Logged to have the request and response headers and bodies logged to standard output. The second argument is an optional func(string) string called as requests and responses are logged to give the caller the opportunity to redact sensitive information from log entries.

Wrap an http.Handler in tigertonic.JSONLogged to have the request and response headers and bodies logged to standard output as JSON suitable for sending to ElasticSearch, Flume, Logstash, and so on. The JSON will be prefixed with @json: . The second argument is an optional func(string) string called as requests and responses are logged to give the caller the opportunity to redact sensitive information from log entries.

Wrap an http.Handler in tigertonic.ApacheLogged to have the request and response logged in the more traditional Apache combined log format.

tigertonic.Counted and tigertonic.Timed

Wrap an http.Handler in tigertonic.Counted or tigertonic.Timed to have the request counted or timed with go-metrics.

tigertonic.CountedByStatus and tigertonic.CountedByStatusXX

Wrap an http.Handler in tigertonic.CountedByStatus or tigertonic.CountedByStatusXX to have the response counted with go-metrics with a metrics.Counter for each HTTP status code or family of status codes (1xx, 2xx, and so on).

tigertonic.First

Call tigertonic.First with a variadic slice of http.Handlers. It will call ServeHTTP on each in succession until the first one that calls w.WriteHeader.

tigertonic.If

tigertonic.If expresses the most common use of tigertonic.First more naturally. Call tigertonic.If with a func(*http.Request) (http.Header, error) and an http.Handler. It will conditionally call the handler unless the function returns an error. In that case, the error is used to create a response.

tigertonic.PostProcessed and tigertonic.TeeResponseWriter

tigertonic.PostProcessed uses a tigertonic.TeeResponseWriter to record the response and call a func(*http.Request, *http.Response) after the response is written to the client to allow post-processing requests and responses.

tigertonic.HTTPBasicAuth

Wrap an http.Handler in tigertonic.HTTPBasicAuth, providing a map[string]string of authorized usernames to passwords, to require the request include a valid Authorization header.

tigertonic.CORSHandler and tigertonic.CORSBuilder

Wrap an http.Handler in tigertonic.CORSHandler (using CORSBuilder.Build()) to inject CORS-related headers. Currently only Origin-related headers (used for cross-origin browser requests) are supported.

tigertonic.Configure

Call tigertonic.Configure to read and unmarshal a JSON configuration file into a configuration structure of your own design. This is mere convenience and what you do with it after is up to you.

tigertonic.WithContext and tigertonic.Context

Wrap an http.Handler and a zero value of any non-interface type in tigertonic.WithContext to enable per-request context. Each request may call tigertonic.Context with the *http.Request in progress to get a pointer to the context which is of the type passed to tigertonic.WithContext.

tigertonic.Version

Respond with a version string that may be set at compile-time.

Usage

Install dependencies:

sh bootstrap.sh

Then define your service. The working example may be a more convenient place to start.

Requests that have bodies have types. JSON is deserialized by adding tigertonic.Marshaled to your routes.

type MyRequest struct {
	ID     string      `json:"id"`
	Stuff  interface{} `json:"stuff"`
}

Responses, too, have types. JSON is serialized by adding tigertonic.Marshaled to your routes.

type MyResponse struct {
	ID     string      `json:"id"`
	Stuff  interface{} `json:"stuff"`
}

Routes are just functions with a particular signature. You control the request and response types.

func myHandler(u *url.URL, h http.Header, *MyRequest) (int, http.Header, *MyResponse, error) {
    return http.StatusOK, nil, &MyResponse{"ID", "STUFF"}, nil
}

Wire it all up in main.main!

mux := tigertonic.NewTrieServeMux()
mux.Handle("POST", "/stuff", tigertonic.Timed(tigertonic.Marshaled(myHandler), "myHandler", nil))
tigertonic.NewServer(":8000", tigertonic.Logged(mux, nil)).ListenAndServe()

Ready for more? See the full example which includes all of these handlers plus an example of how to use tigertonic.Server to stop gracefully. Build it with go build, run it with ./example, and test it out:

curl -H"Host: example.com" -sv "http://127.0.0.1:8000/1.0/stuff/ID"
curl -H"Host: example.com" -X"POST" -d'{"id":"ID","stuff":"STUFF"}' -sv "http://127.0.0.1:8000/1.0/stuff"
curl -H"Host: example.com" -X"POST" -d'{"id":"ID","stuff":"STUFF"}' -sv "http://127.0.0.1:8000/1.0/stuff/ID"
curl -H"Host: example.com" -sv "http://127.0.0.1:8000/1.0/forbidden"

WTF?

Dropwizard was named after http://gunshowcomic.com/316 so Tiger Tonic was named after http://gunshowcomic.com/338.

If Tiger Tonic isn't your cup of tea, perhaps one of these fine tools suits you:

Documentation

Overview

Tiger Tonic [1] is a Go framework for building JSON web services inspired by Dropwizard [2]. If HTML is your game, this will hurt a little.

Like the Go language itself, Tiger Tonic strives to keep features orthogonal. It defers what it can to the Go standard library, go-metrics [3], and a few other packages.

[1] <https://github.com/rcrowley/go-tigertonic> [2] <http://dropwizard.codahale.com> [3] <https://github.com/rcrowley/go-metrics>

Index

Constants

View Source
const (
	CORSRequestOrigin  string = "Origin"
	CORSRequestMethod  string = "Access-Control-Request-Method"
	CORSRequestHeaders string = "Access-Control-Request-Headers"
)
View Source
const (
	CORSAllowOrigin      string = "Access-Control-Allow-Origin"
	CORSAllowMethods     string = "Access-Control-Allow-Methods"
	CORSAllowHeaders     string = "Access-Control-Allow-Headers"
	CORSExposeHeaders    string = "Access-Control-Expose-Headers"
	CORSAllowCredentials string = "Access-Control-Allow-Credentials"
)
View Source
const ONE_YEAR_IN_HOURS = time.Hour * 24 * 365

Variables

View Source
var ConfigExt = make(map[string]configParser)
View Source
var SnakeCaseHTTPEquivErrors bool

SnakeCaseHTTPEquivErrors being true will cause tigertonic.HTTPEquivError error responses to be written as (for example) "not_found" rather than "tigertonic.NotFound".

Functions

func Configure

func Configure(pathname string, i interface{}) error

Configure delegates reading and unmarshaling of the given configuration file to the appropriate function from ConfigExt. For convenient use with the flags package, an empty pathname is not considered an error.

func ConfigureJSON

func ConfigureJSON(pathname string, i interface{}) error

ConfigureJSON reads the given configuration file and unmarshals the JSON found into the given configuration structure. For convenient use with the flags package, an empty pathname is not considered an error.

func Context

func Context(r *http.Request) interface{}

Context returns the request context as an interface{} given a pointer to the request itself.

func NewHTTPEquivError

func NewHTTPEquivError(err error, code int) error

Return a new HTTPEquivError whose StatusCode method returns the given status code.

func RandomBase62Bytes

func RandomBase62Bytes(ii int) []byte

func RandomBase62String

func RandomBase62String(ii int) string

func RegisterConfigExt

func RegisterConfigExt(ext string, f configParser)

Types

type Accepted

type Accepted struct {
	Err
}

func (Accepted) Name

func (err Accepted) Name() string

func (Accepted) StatusCode

func (err Accepted) StatusCode() int

type ApacheLogger

type ApacheLogger struct {
	Logger Logger
	// contains filtered or unexported fields
}

ApacheLogger is an http.Handler that logs requests and responses in the Apache combined log format.

func ApacheLogged

func ApacheLogged(handler http.Handler) *ApacheLogger

ApacheLogged returns an http.Handler that logs requests and responses in the Apache combined log format.

func (*ApacheLogger) Output

func (l *ApacheLogger) Output(calldepth int, s string) error

func (*ApacheLogger) Print

func (l *ApacheLogger) Print(v ...interface{})

func (*ApacheLogger) Printf

func (l *ApacheLogger) Printf(format string, v ...interface{})

func (*ApacheLogger) ServeHTTP

func (l *ApacheLogger) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP wraps the http.Request and http.ResponseWriter to log to standard output and pass through to the underlying http.Handler.

type BadGateway

type BadGateway struct {
	Err
}

func (BadGateway) Name

func (err BadGateway) Name() string

func (BadGateway) StatusCode

func (err BadGateway) StatusCode() int

type BadRequest

type BadRequest struct {
	Err
}

func (BadRequest) Name

func (err BadRequest) Name() string

func (BadRequest) StatusCode

func (err BadRequest) StatusCode() int

type CORSBuilder

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

CORSBuilder facilitates the application of the same set of CORS rules to a number of endpoints. One would use CORSBuilder.Build() the same way one might wrap a handler in a call to Timed() or Logged().

func NewCORSBuilder

func NewCORSBuilder() *CORSBuilder

func (*CORSBuilder) AddAllowCredentials

func (self *CORSBuilder) AddAllowCredentials(allowed bool) *CORSBuilder

func (*CORSBuilder) AddAllowedHeaders

func (self *CORSBuilder) AddAllowedHeaders(headers ...string) *CORSBuilder

func (*CORSBuilder) AddAllowedOrigins

func (self *CORSBuilder) AddAllowedOrigins(origins ...string) *CORSBuilder

AddAllowedOrigins sets the list of domain for which cross-origin requests are allowed

func (*CORSBuilder) AddExposedHeaders

func (self *CORSBuilder) AddExposedHeaders(headers ...string) *CORSBuilder

func (*CORSBuilder) Build

func (self *CORSBuilder) Build(handler http.Handler) *CORSHandler

type CORSHandler

type CORSHandler struct {
	http.Handler
	// contains filtered or unexported fields
}

CORSHandler wraps an http.Handler while correctly handling CORS related functionality, such as Origin headers. It also allows tigertonic core to correctly respond to OPTIONS headers for CORS-enabled endpoints

func (*CORSHandler) HandleCORS

func (self *CORSHandler) HandleCORS(w http.ResponseWriter, r *http.Request)

HandleCORS checks for CORS related request headers and writes the matching response headers for both OPTIONS and regular requests

func (*CORSHandler) ServeHTTP

func (self *CORSHandler) ServeHTTP(w http.ResponseWriter, r *http.Request)

type CacheControl

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

CacheControl is an http.Handler that sets cache headers.

func Cached

func Cached(handler http.Handler, o CacheOptions) *CacheControl

Cached returns an http.Handler that sets appropriate Cache headers on the outgoing response and passes requests to a wrapped http.Handler.

func (*CacheControl) ServeHTTP

func (c *CacheControl) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP sets the header and passes the request and response to the wrapped http.Handler

type CacheOptions

type CacheOptions struct {
	Immutable       bool
	IsPrivate       bool
	NoCache         bool
	NoStore         bool
	NoTransform     bool
	MustRevalidate  bool
	ProxyRevalidate bool
	MaxAge          time.Duration
	SharedMaxAge    time.Duration
}

These set the relevant headers in the response per http://www.w3.org/Protocols/rfc2616/rfc2616-sec13.html

func (CacheOptions) String

func (o CacheOptions) String() string

type Conflict

type Conflict struct {
	Err
}

func (Conflict) Name

func (err Conflict) Name() string

func (Conflict) StatusCode

func (err Conflict) StatusCode() int

type Conn

type Conn struct {
	net.Conn
	// contains filtered or unexported fields
}

Conn is just a net.Conn that accounts for itself so the listener can be stopped gracefully.

func (*Conn) Close

func (c *Conn) Close() (err error)

Close closes the connection and notifies the listener that accepted it.

type ContextHandler

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

ContextHandler is an http.Handler that associates a context object of any type with each request it handles.

func WithContext

func WithContext(handler http.Handler, i interface{}) *ContextHandler

WithContext wraps an http.Handler and associates a new context object of the same type as the second parameter with each request it handles. You must wrap any handler that uses Context or the four-parameter form of Marshaled in WithContext.

func (*ContextHandler) ServeHTTP

func (ch *ContextHandler) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP adds and removes the per-request context and calls the wrapped http.Handler in between.

type Continue

type Continue struct {
	Err
}

func (Continue) Name

func (err Continue) Name() string

func (Continue) StatusCode

func (err Continue) StatusCode() int

type Counter

type Counter struct {
	metrics.Counter
	// contains filtered or unexported fields
}

Counter is an http.Handler that counts requests via go-metrics.

func Counted

func Counted(
	handler http.Handler,
	name string,
	registry metrics.Registry,
) *Counter

Counted returns an http.Handler that passes requests to an underlying http.Handler and then counts the request via go-metrics.

func (*Counter) ServeHTTP

func (c *Counter) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP passes the request to the underlying http.Handler and then counts the request via go-metrics.

type CounterByStatus

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

CounterByStatus is an http.Handler that counts responses by their HTTP status code via go-metrics.

func CountedByStatus

func CountedByStatus(
	handler http.Handler,
	name string,
	registry metrics.Registry,
) *CounterByStatus

CountedByStatus returns an http.Handler that passes requests to an underlying http.Handler and then counts the response by its HTTP status code via go-metrics.

func (*CounterByStatus) ServeHTTP

func (c *CounterByStatus) ServeHTTP(w0 http.ResponseWriter, r *http.Request)

ServeHTTP passes the request to the underlying http.Handler and then counts the response by its HTTP status code via go-metrics.

type CounterByStatusXX

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

CounterByStatusXX is an http.Handler that counts responses by the first digit of their HTTP status code via go-metrics.

func CountedByStatusXX

func CountedByStatusXX(
	handler http.Handler,
	name string,
	registry metrics.Registry,
) *CounterByStatusXX

CountedByStatusXX returns an http.Handler that passes requests to an underlying http.Handler and then counts the response by the first digit of its HTTP status code via go-metrics.

func (*CounterByStatusXX) ServeHTTP

func (c *CounterByStatusXX) ServeHTTP(w0 http.ResponseWriter, r *http.Request)

ServeHTTP passes the request to the underlying http.Handler and then counts the response by its HTTP status code via go-metrics.

type Created

type Created struct {
	Err
}

func (Created) Name

func (err Created) Name() string

func (Created) StatusCode

func (err Created) StatusCode() int

type Err

type Err error

Err is an alias for the built-in error type so that it can be publicly exported when embedding.

type ErrorWriter

type ErrorWriter interface {
	WriteError(r *http.Request, w http.ResponseWriter, err error)
	WriteJSONError(w http.ResponseWriter, err error)
	WritePlaintextError(w http.ResponseWriter, err error)
}
var ResponseErrorWriter ErrorWriter = defaultErrorWriter{}

ResponseErrorWriter is a handler for outputting errors to the http.ResponseWriter

type ExpectationFailed

type ExpectationFailed struct {
	Err
}

func (ExpectationFailed) Name

func (err ExpectationFailed) Name() string

func (ExpectationFailed) StatusCode

func (err ExpectationFailed) StatusCode() int

type FirstHandler

type FirstHandler []http.Handler

FirstHandler is an http.Handler that, for each handler in its slice of handlers, calls ServeHTTP until the first one that calls w.WriteHeader.

func First

func First(handlers ...http.Handler) FirstHandler

First returns an http.Handler that, for each handler in its slice of handlers, calls ServeHTTP until the first one that calls w.WriteHeader.

func HTTPBasicAuth

func HTTPBasicAuth(
	credentials map[string]string,
	realm string,
	h http.Handler,
) FirstHandler

HTTPBasicAuth returns an http.Handler that conditionally calls another http.Handler if the request includes an Authorization header with a username and password that appear in the map of credentials. Otherwise, respond 401 Unauthorized.

func HTTPBasicAuthFunc

func HTTPBasicAuthFunc(
	f func(string, string) error,
	realm string,
	h http.Handler,
) FirstHandler

HTTPBasicAuthFunc returns an http.Handler that conditionally calls another http.Handler if the request includes an Authorization header with a username and password that produce a nil error when passed to the given function. Otherwise, respond 401 Unauthorized.

func If

func If(f func(*http.Request) (http.Header, error), h http.Handler) FirstHandler

If returns an http.Handler that conditionally calls another http.Handler unless the given function returns an error. In that case, the error is used to create a plaintext or JSON response as dictated by the Accept header.

func (FirstHandler) ServeHTTP

func (fh FirstHandler) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP calls each handler in its slice of handlers until the first one that calls w.WriteHeader.

type Forbidden

type Forbidden struct {
	Err
}

func (Forbidden) Name

func (err Forbidden) Name() string

func (Forbidden) StatusCode

func (err Forbidden) StatusCode() int

type Found

type Found struct {
	Err
}

func (Found) Name

func (err Found) Name() string

func (Found) StatusCode

func (err Found) StatusCode() int

type GatewayTimeout

type GatewayTimeout struct {
	Err
}

func (GatewayTimeout) Name

func (err GatewayTimeout) Name() string

func (GatewayTimeout) StatusCode

func (err GatewayTimeout) StatusCode() int

type Gone

type Gone struct {
	Err
}

func (Gone) Name

func (err Gone) Name() string

func (Gone) StatusCode

func (err Gone) StatusCode() int

type HTTPEquivError

type HTTPEquivError interface {
	error
	StatusCode() int
}

type HTTPVersionNotSupported

type HTTPVersionNotSupported struct {
	Err
}

func (HTTPVersionNotSupported) Name

func (err HTTPVersionNotSupported) Name() string

func (HTTPVersionNotSupported) StatusCode

func (err HTTPVersionNotSupported) StatusCode() int

type HostServeMux

type HostServeMux map[string]http.Handler

HostServeMux is an HTTP request multiplexer that implements http.Handler with an API similar to http.ServeMux. It is only sensitive to the hostname and doesn't even look at the rest of the request.

func NewHostServeMux

func NewHostServeMux() HostServeMux

NewHostServeMux makes a new HostServeMux.

func (HostServeMux) Handle

func (mux HostServeMux) Handle(hostname string, handler http.Handler)

Handle registers an http.Handler for the given hostname.

func (HostServeMux) HandleFunc

func (mux HostServeMux) HandleFunc(hostname string, handler func(http.ResponseWriter, *http.Request))

HandleFunc registers a handler function for the given hostname.

func (HostServeMux) Handler

func (mux HostServeMux) Handler(r *http.Request) (http.Handler, string)

Handler returns the handler to use for the given HTTP request.

func (HostServeMux) ServeHTTP

func (mux HostServeMux) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP routes an HTTP request to the http.Handler registered for the requested hostname. It responds 404 if the hostname is not registered.

type InternalServerError

type InternalServerError struct {
	Err
}

func (InternalServerError) Name

func (err InternalServerError) Name() string

func (InternalServerError) StatusCode

func (err InternalServerError) StatusCode() int

type JSONLogger

type JSONLogger struct {
	Logger Logger

	RequestIDCreator RequestIDCreator
	// contains filtered or unexported fields
}

JSONLogged is an http.Handler that logs requests and responses in a parse-able json line. complete with paths, statuses, headers, and bodies. Sensitive information may be redacted by a user-defined function.

func JSONLogged

func JSONLogged(handler http.Handler, redactor Redactor) *JSONLogger

JSONLogged returns an http.Handler that logs requests and responses in a parse-able json line. complete with paths, statuses, headers, and bodies. Sensitive information may be redacted by a user-defined function.

func (*JSONLogger) Output

func (jl *JSONLogger) Output(calldepth int, s string) error

func (*JSONLogger) Print

func (jl *JSONLogger) Print(v ...interface{})

func (*JSONLogger) Printf

func (jl *JSONLogger) Printf(format string, v ...interface{})

func (*JSONLogger) Println

func (jl *JSONLogger) Println(v ...interface{})

func (*JSONLogger) ServeHTTP

func (jl *JSONLogger) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP wraps the http.Request and http.ResponseWriter to capture the input and output for logging

type LengthRequired

type LengthRequired struct {
	Err
}

func (LengthRequired) Name

func (err LengthRequired) Name() string

func (LengthRequired) StatusCode

func (err LengthRequired) StatusCode() int

type Listener

type Listener struct {
	net.Listener
	// contains filtered or unexported fields
}

Listener is just a net.Listener that accounts for connections it accepts so it can be stopped gracefully.

func (*Listener) Accept

func (l *Listener) Accept() (c net.Conn, err error)

Accept waits for, accounts for, and returns the next connection to the listener.

func (*Listener) Close

func (l *Listener) Close() (err error)

Close closes the listener. It does not wait for all connections accepted through the listener to be closed.

type Logger

type Logger interface {
	Output(calldepth int, s string) error
	Print(v ...interface{})
	Printf(format string, v ...interface{})
	Println(v ...interface{})
}

type Marshaler

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

Marshaler is an http.Handler that unmarshals JSON input, handles the request via a function, and marshals JSON output. It refuses to answer requests without an Accept header that includes the application/json content type.

func Marshaled

func Marshaled(i interface{}) *Marshaler

Marshaled returns an http.Handler that implements its ServeHTTP method by calling the given function, the signature of which must be

func(*url.URL, http.Header, *Request) (int, http.Header, *Response)

where Request and Response may be any struct type of your choosing.

func (*Marshaler) ServeHTTP

func (m *Marshaler) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP unmarshals JSON input, handles the request via the function, and marshals JSON output. If the output of the handler function implements io.Reader the headers must contain a 'Content-Type'; the stream will be written directly to the requestor without being marshaled to JSON. Additionally if the output implements the io.Closer the stream will be automatically closed after flushing.

type MarshalerError

type MarshalerError string

MarshalerError is the response body for some 500 responses and panics when a handler function is not suitable.

func NewMarshalerError

func NewMarshalerError(format string, args ...interface{}) MarshalerError

func (MarshalerError) Error

func (e MarshalerError) Error() string

type MethodNotAllowed

type MethodNotAllowed struct {
	Err
}

func (MethodNotAllowed) Name

func (err MethodNotAllowed) Name() string

func (MethodNotAllowed) StatusCode

func (err MethodNotAllowed) StatusCode() int

type MethodNotAllowedHandler

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

MethodNotAllowedHandler responds 405 to every request with an Allow header and possibly with a JSON body.

func (MethodNotAllowedHandler) ServeHTTP

type MovedPermanently

type MovedPermanently struct {
	Err
}

func (MovedPermanently) Name

func (err MovedPermanently) Name() string

func (MovedPermanently) StatusCode

func (err MovedPermanently) StatusCode() int

type MultilineLogger

type MultilineLogger struct {
	Logger Logger

	RequestIDCreator RequestIDCreator
	// contains filtered or unexported fields
}

MultilineLogger is an http.Handler that logs requests and responses, complete with paths, statuses, headers, and bodies. Sensitive information may be redacted by a user-defined function.

func Logged

func Logged(handler http.Handler, redactor Redactor) *MultilineLogger

Logged returns an http.Handler that logs requests and responses, complete with paths, statuses, headers, and bodies. Sensitive information may be redacted by a user-defined function.

func (*MultilineLogger) Output

func (l *MultilineLogger) Output(calldepth int, s string) error

Output overrides log.Logger's Output method, calling our redactor first.

func (*MultilineLogger) Print

func (l *MultilineLogger) Print(v ...interface{})

Print is identical to log.Logger's Print but uses our overridden Output.

func (*MultilineLogger) Printf

func (l *MultilineLogger) Printf(format string, v ...interface{})

Printf is identical to log.Logger's Print but uses our overridden Output.

func (*MultilineLogger) Println

func (l *MultilineLogger) Println(v ...interface{})

Println is identical to log.Logger's Print but uses our overridden Output.

func (*MultilineLogger) ServeHTTP

func (l *MultilineLogger) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP wraps the http.Request and http.ResponseWriter to log to standard output and pass through to the underlying http.Handler.

type MultipleChoices

type MultipleChoices struct {
	Err
}

func (MultipleChoices) Name

func (err MultipleChoices) Name() string

func (MultipleChoices) StatusCode

func (err MultipleChoices) StatusCode() int

type NamedError

type NamedError interface {
	error
	Name() string
}

type NoContent

type NoContent struct {
	Err
}

func (NoContent) Name

func (err NoContent) Name() string

func (NoContent) StatusCode

func (err NoContent) StatusCode() int

type NonAuthoritativeInfo

type NonAuthoritativeInfo struct {
	Err
}

func (NonAuthoritativeInfo) Name

func (err NonAuthoritativeInfo) Name() string

func (NonAuthoritativeInfo) StatusCode

func (err NonAuthoritativeInfo) StatusCode() int

type NotAcceptable

type NotAcceptable struct {
	Err
}

func (NotAcceptable) Name

func (err NotAcceptable) Name() string

func (NotAcceptable) StatusCode

func (err NotAcceptable) StatusCode() int

type NotFound

type NotFound struct {
	Err
}

func (NotFound) Name

func (err NotFound) Name() string

func (NotFound) StatusCode

func (err NotFound) StatusCode() int

type NotFoundHandler

type NotFoundHandler struct{}

NotFoundHandler responds 404 to every request, possibly with a JSON body.

func (NotFoundHandler) ServeHTTP

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

type NotImplemented

type NotImplemented struct {
	Err
}

func (NotImplemented) Name

func (err NotImplemented) Name() string

func (NotImplemented) StatusCode

func (err NotImplemented) StatusCode() int

type NotModified

type NotModified struct {
	Err
}

func (NotModified) Name

func (err NotModified) Name() string

func (NotModified) StatusCode

func (err NotModified) StatusCode() int

type OK

type OK struct {
	Err
}

func (OK) Name

func (err OK) Name() string

func (OK) StatusCode

func (err OK) StatusCode() int

type PartialContent

type PartialContent struct {
	Err
}

func (PartialContent) Name

func (err PartialContent) Name() string

func (PartialContent) StatusCode

func (err PartialContent) StatusCode() int

type PaymentRequired

type PaymentRequired struct {
	Err
}

func (PaymentRequired) Name

func (err PaymentRequired) Name() string

func (PaymentRequired) StatusCode

func (err PaymentRequired) StatusCode() int

type PostProcessor

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

func PostProcessed

func PostProcessed(
	handler http.Handler,
	f func(*http.Request, *http.Response),
) *PostProcessor

func (*PostProcessor) ServeHTTP

func (pp *PostProcessor) ServeHTTP(w0 http.ResponseWriter, r *http.Request)

type PreconditionFailed

type PreconditionFailed struct {
	Err
}

func (PreconditionFailed) Name

func (err PreconditionFailed) Name() string

func (PreconditionFailed) StatusCode

func (err PreconditionFailed) StatusCode() int

type ProxyAuthRequired

type ProxyAuthRequired struct {
	Err
}

func (ProxyAuthRequired) Name

func (err ProxyAuthRequired) Name() string

func (ProxyAuthRequired) StatusCode

func (err ProxyAuthRequired) StatusCode() int

type Redactor

type Redactor func(string) string

A Redactor is a function that takes and returns a string. It is called to allow sensitive information to be redacted before it is logged.

type RequestEntityTooLarge

type RequestEntityTooLarge struct {
	Err
}

func (RequestEntityTooLarge) Name

func (err RequestEntityTooLarge) Name() string

func (RequestEntityTooLarge) StatusCode

func (err RequestEntityTooLarge) StatusCode() int

type RequestID

type RequestID string

A unique RequestID is given to each request and is included with each line of each log entry.

func NewRequestID

func NewRequestID() RequestID

NewRequestID returns a new 16-character random RequestID.

type RequestIDCreator

type RequestIDCreator func(r *http.Request) RequestID

A RequestIDCreator is a function that takes a request and returns a unique RequestID for it.

type RequestTimeout

type RequestTimeout struct {
	Err
}

func (RequestTimeout) Name

func (err RequestTimeout) Name() string

func (RequestTimeout) StatusCode

func (err RequestTimeout) StatusCode() int

type RequestURITooLong

type RequestURITooLong struct {
	Err
}

func (RequestURITooLong) Name

func (err RequestURITooLong) Name() string

func (RequestURITooLong) StatusCode

func (err RequestURITooLong) StatusCode() int

type RequestedRangeNotSatisfiable

type RequestedRangeNotSatisfiable struct {
	Err
}

func (RequestedRangeNotSatisfiable) Name

func (RequestedRangeNotSatisfiable) StatusCode

func (err RequestedRangeNotSatisfiable) StatusCode() int

type ResetContent

type ResetContent struct {
	Err
}

func (ResetContent) Name

func (err ResetContent) Name() string

func (ResetContent) StatusCode

func (err ResetContent) StatusCode() int

type SeeOther

type SeeOther struct {
	Err
}

func (SeeOther) Name

func (err SeeOther) Name() string

func (SeeOther) StatusCode

func (err SeeOther) StatusCode() int

type Server

type Server struct {
	http.Server
	// contains filtered or unexported fields
}

Server is an http.Server with better defaults and built-in graceful stop.

func NewServer

func NewServer(addr string, handler http.Handler) *Server

NewServer returns an http.Server with better defaults and built-in graceful stop.

func NewTLSServer

func NewTLSServer(
	addr, cert, key string,
	handler http.Handler,
) (*Server, error)

NewTLSServer returns an http.Server with better defaults configured to use the certificate and private key files.

func (*Server) CA

func (s *Server) CA(ca string) error

CA overrides the certificate authority on the Server's TLSConfig field.

func (*Server) ClientCA

func (s *Server) ClientCA(ca string) error

ClientCA configures the CA pool for verifying client side certificates.

func (*Server) Close

func (s *Server) Close() error

Close closes all the net.Listeners passed to Serve (even via ListenAndServe) and signals open connections to close at their earliest convenience. That is either after responding to the current request or after a short grace period for idle keepalive connections. Close blocks until all connections have been closed.

func (*Server) ListenAndServe

func (s *Server) ListenAndServe() error

ListenAndServe calls net.Listen with s.Addr and then calls s.Serve.

func (*Server) ListenAndServeTLS

func (s *Server) ListenAndServeTLS(cert, key string) error

ListenAndServeTLS calls s.TLS with the given certificate and private key files and then calls s.ListenAndServe.

func (*Server) Serve

func (s *Server) Serve(l net.Listener) error

Serve behaves like http.Server.Serve with the added option to stop the Server gracefully with the s.Close method.

func (*Server) TLS

func (s *Server) TLS(cert, key string) error

TLS configures this Server to be a TLS server using the given certificate and private key files.

type ServiceUnavailable

type ServiceUnavailable struct {
	Err
}

func (ServiceUnavailable) Name

func (err ServiceUnavailable) Name() string

func (ServiceUnavailable) StatusCode

func (err ServiceUnavailable) StatusCode() int

type SwitchingProtocols

type SwitchingProtocols struct {
	Err
}

func (SwitchingProtocols) Name

func (err SwitchingProtocols) Name() string

func (SwitchingProtocols) StatusCode

func (err SwitchingProtocols) StatusCode() int

type Teapot

type Teapot struct {
	Err
}

func (Teapot) Name

func (err Teapot) Name() string

func (Teapot) StatusCode

func (err Teapot) StatusCode() int

type TeeHeaderResponseWriter

type TeeHeaderResponseWriter struct {
	http.Flusher
	http.ResponseWriter
	StatusCode int
}

TeeHeaderResponseWriter is an http.ResponseWriter that both writes and records the response status and headers for post-processing.

func NewTeeHeaderResponseWriter

func NewTeeHeaderResponseWriter(w http.ResponseWriter) *TeeHeaderResponseWriter

NewTeeHeaderResponseWriter constructs a new TeeHeaderResponseWriter that writes responses through another http.ResponseWriter and records the response status and headers for post-processing.

func (*TeeHeaderResponseWriter) Flush

func (w *TeeHeaderResponseWriter) Flush()

Flush implements the http.Flusher interface, if possible, to support streaming responses to clients.

func (*TeeHeaderResponseWriter) WriteHeader

func (w *TeeHeaderResponseWriter) WriteHeader(code int)

WriteHeader writes the response line and headers to the client via the underlying http.ResponseWriter and records the status for post-processing.

type TeeResponseWriter

type TeeResponseWriter struct {
	http.Flusher
	http.ResponseWriter
	Body       bytes.Buffer
	StatusCode int
}

TeeResponseWriter is an http.ResponseWriter that both writes and records the response status, headers, and body for post-processing.

func NewTeeResponseWriter

func NewTeeResponseWriter(w http.ResponseWriter) *TeeResponseWriter

NewTeeResponseWriter constructs a new TeeResponseWriter that writes responses through another http.ResponseWriter and records the response status, headers, and body for post-processing.

func (*TeeResponseWriter) Flush

func (w *TeeResponseWriter) Flush()

Flush implements the http.Flusher interface, if possible, to support streaming responses to clients.

func (*TeeResponseWriter) Write

func (w *TeeResponseWriter) Write(p []byte) (int, error)

Write writes the byte slice to the client via the underlying http.ResponseWriter and records it for post-processing.

func (*TeeResponseWriter) WriteHeader

func (w *TeeResponseWriter) WriteHeader(code int)

WriteHeader writes the response line and headers to the client via the underlying http.ResponseWriter and records the status for post-processing.

type TemporaryRedirect

type TemporaryRedirect struct {
	Err
}

func (TemporaryRedirect) Name

func (err TemporaryRedirect) Name() string

func (TemporaryRedirect) StatusCode

func (err TemporaryRedirect) StatusCode() int

type Timer

type Timer struct {
	metrics.Timer
	// contains filtered or unexported fields
}

Timer is an http.Handler that counts requests via go-metrics.

func Timed

func Timed(handler http.Handler, name string, registry metrics.Registry) *Timer

Timed returns an http.Handler that starts a timer, passes requests to an underlying http.Handler, stops the timer, and updates the timer via go-metrics.

func (*Timer) ServeHTTP

func (t *Timer) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP starts a timer, passes the request to the underlying http.Handler, stops the timer, and updates the timer via go-metrics.

type TrieServeMux

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

TrieServeMux is an HTTP request multiplexer that implements http.Handler with an API similar to http.ServeMux. It is expanded to be sensitive to the HTTP method and treats URL patterns as patterns rather than simply prefixes.

Components of the URL pattern surrounded by braces (for example: "{foo}") match any string and create an entry for the string plus the string surrounded by braces in the query parameters (for example: "foo" and "{foo}").

func NewTrieServeMux

func NewTrieServeMux() *TrieServeMux

NewTrieServeMux makes a new TrieServeMux.

func (*TrieServeMux) Handle

func (mux *TrieServeMux) Handle(method, pattern string, handler http.Handler)

Handle registers an http.Handler for the given HTTP method and URL pattern.

func (*TrieServeMux) HandleFunc

func (mux *TrieServeMux) HandleFunc(method, pattern string, handler func(http.ResponseWriter, *http.Request))

HandleFunc registers a handler function for the given HTTP method and URL pattern.

func (*TrieServeMux) HandleNamespace

func (mux *TrieServeMux) HandleNamespace(namespace string, handler http.Handler)

HandleNamespace registers an http.Handler for the given URL namespace. The matching namespace is stripped from the URL before it is passed to the underlying http.Handler.

func (*TrieServeMux) Handler

func (mux *TrieServeMux) Handler(r *http.Request) (http.Handler, string)

Handler returns the handler to use for the given HTTP request and mutates the querystring to add wildcards extracted from the URL.

It sanitizes out any query params that might collide with params parsed from the URL to avoid surprises. See TestCollidingQueryParam for the use case

func (*TrieServeMux) ServeHTTP

func (mux *TrieServeMux) ServeHTTP(w http.ResponseWriter, r *http.Request)

ServeHTTP routes an HTTP request to the http.Handler registered for the URL pattern which matches the requested path. It responds 404 if there is no matching URL pattern and 405 if the requested HTTP method is not allowed.

type Unauthorized

type Unauthorized struct {
	Err
}

func (Unauthorized) Name

func (err Unauthorized) Name() string

func (Unauthorized) StatusCode

func (err Unauthorized) StatusCode() int

type UnsupportedMediaType

type UnsupportedMediaType struct {
	Err
}

func (UnsupportedMediaType) Name

func (err UnsupportedMediaType) Name() string

func (UnsupportedMediaType) StatusCode

func (err UnsupportedMediaType) StatusCode() int

type UseProxy

type UseProxy struct {
	Err
}

func (UseProxy) Name

func (err UseProxy) Name() string

func (UseProxy) StatusCode

func (err UseProxy) StatusCode() int

type Version

type Version string

Version is an http.Handler that responds to every request with itself in plain text. The version string may be anything you like and may be set at compile-time by adding

-ldflags "-X main.Version VERSION"

to your build command.

func (Version) ServeHTTP

func (v Version) ServeHTTP(w http.ResponseWriter, _ *http.Request)

ServeHTTP responds 200 with the version string or 404 if the version string is empty.

Directories

Path Synopsis
Package mocking makes testing Tiger Tonic services easier.
Package mocking makes testing Tiger Tonic services easier.

Jump to

Keyboard shortcuts

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