Documentation
¶
Overview ¶
Package gate implements a simple atomic boolean that controls access to HTTP client or server functionality
Index ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
This section is empty.
Types ¶
type Client ¶
type Client struct {
// Closed is the optional round tripper invoked when the gate is closed. If this
// field is unset, then a nil *http.Response and a *ClosedError are returned when
// the gate status indicates closed.
Closed http.RoundTripper
// Gate is the Status that indicates whether a gate allows traffic. If this field
// is unset, this middleware is a nop.
Gate Status
}
Client defines a clientside middleware that controls access to round trippers based upon a gate status
func (Client) Then ¶ added in v0.1.2
func (c Client) Then(next http.RoundTripper) http.RoundTripper
Then decorates a round tripper so that it is controlled by the Gate field.
The returned http.RoundTripper will always supply a CloseIdleConnections method. If next also supplies that method, it will be invoked whenever the decorator's method is invoked. Otherwise, the decorator's CloseIdleConnections will do nothing.
For consistency with other libraries, if next is nil then http.DefaultTransport is used as the decorated round tripper.
type ClosedError ¶
type ClosedError struct {
// Gate represents the gate instance that was closed at the time of the error.
// Note that this gate may have been opened in the time that a caller waited on
// the call to produce this error.
Gate Status
}
ClosedError is returned by any decorated infrastructure to indicate that the gate disallowed the client request.
func (*ClosedError) Error ¶
func (ce *ClosedError) Error() string
Error satisfies the error interface
type Config ¶
type Config struct {
// Name is an optional identifier for this gate. The Gate itself does not make
// use of this value. It's purely for distinguishing gates when an application
// uses more than one (1) gate.
Name string
// InitiallyClosed indicates the state of a Gate when it is created. The default
// is to create a Gate that is open. If this field is true, the Gate is created
// in the closed state.
InitiallyClosed bool
// Hooks is the optional set of preregistered callbacks when a gate is created with this
// configuration. Any empty hooks are silently ignored.
//
// Any callbacks that match the initial state of the gate, e.g. OnOpen when InitiallyClosed
// is false, are immediately invoked before New returns.
Hooks Hooks
}
Config describes all the various configurable settings for creating a Gate
type Control ¶
type Control interface {
// Open raises this gate to allow traffic. This method is atomic and idempotent. It returns
// true if there was a state change, false to indicate the gate was already open.
Open() bool
// Close lowers this gate to reject traffic. This method is atomic and idempotent. It returns
// true if there was a state change, false to indicate the gate was already closed.
Close() bool
// Register adds a tuple of callbacks to this status instance. If the given Hook
// has no callbacks set, this method does nothing.
//
// Callbacks registered for the current state, e.g. OnOpen registered against an open gate,
// will be immediately invoked prior to this method returning.
Register(Hook)
}
Control allows a gate to be open and closed atomically. All methods of this interface are safe for concurrent access.
All methods of this interface mutate the underlying gate and thus involve synchronization. In particular, Register is atomic with respect to Open/Close.
type ControlHandler ¶
type ControlHandler struct {
// StateChange is the required strategy for determining how to change a gate
// given an HTTP request. This closure can examine any aspect of the request, e.g.
// URL parameters, request URI, etc, to determine what state change should occur.
//
// This closure can return StateNoChange to indicate that the handler should do nothing
// to a gate. For example, the request may fail a security permissions check.
StateChange func(*http.Request) StateChange
// Gate is the required gate control instance used to open and close the gate
Gate Control
}
ControlHandler is an http.Handler that allows HTTP requests to open or close a gate
func (ControlHandler) ServeHTTP ¶
func (ch ControlHandler) ServeHTTP(response http.ResponseWriter, request *http.Request)
ServeHTTP invokes the StateChange closure and takes the appropriate action
type Hook ¶
type Hook struct {
// OnOpen is invoked any time a gate is opened. If a gate is open when this callback
// is registered, it will be immediately invoked.
//
// Note: Callbacks should never modify the gate. The Status instance passed to all callbacks
// is not castable to Control.
OnOpen func(Status)
// OnClose is invoked any time a gate is closed. If a gate is closed when this
// callback is registered, it will be immediately invoked.
//
// Note: Callbacks should never modify the gate. The Status instance passed to all callbacks
// is not castable to Control.
OnClosed func(Status)
}
Hook is a tuple of callbacks for gate state
type Server ¶
type Server struct {
// Closed is the optional handler to be invoked with the gate is closed.
// If this field is not set, http.StatusServiceUnavailable is written
// to the response.
//
// A convenient, configurable handler for this field is httpaux.ConstantHandler.
Closed http.Handler
// Gate is the Status that indicates whether a gate allows traffic. If this field
// is unset, this middleware is a nop.
Gate Status
}
Server defines a serverside middleware that controls access to handlers based upon a gate status
type StateChange ¶
type StateChange int
StateChange indicates what to do to a gate
const ( // StateNoChange indicates that no control operation should be performed StateNoChange StateChange = iota // StateOpen indicates that the gate should be opened StateOpen // StateClose indicates that the gate should be closed StateClose )
type Status ¶
type Status interface {
// Name is an optional identifier for this atomic boolean. No guarantees
// as to uniqueness are made. This value is completely up to client configuration.
//
// A non-empty name is often useful when an application uses multiple gates. This
// name can be used in log files, metrics, etc.
Name() string
// IsOpen checks if this instance is open and thus allowing traffic
IsOpen() bool
}
Status is implemented by anything that can check an atomic boolean. All methods of this interface are safe for concurrent access. None of the methods in this interface mutate the underlying gate.
Note: although New returns a type that also implements this interface, Status instances passed to callbacks ARE NOT castable to Control. This prevents modification of the gate by callbacks.