Documentation ¶
Overview ¶
Example (Basic) ¶
Example_basic creates a new service under path "/" and serves requests for the count resource.
package main import ( "github.com/codehack/go-relax" "github.com/codehack/go-relax/limits" "time" ) type Count int func (c *Count) Index(ctx *relax.Context) { *c += 1 ctx.Respond(c) } // Example_basic creates a new service under path "/" and serves requests // for the count resource. func main() { c := Count(0) svc := relax.NewService("/") // Memory limit check, allocation 250kb svc.Use(&limits.Memory{Alloc: 250 * 1024}) // Throttle limit, 1 request per 200ms svc.Use(&limits.Throttle{ Burst: 5, Requests: 1, Per: time.Minute * 3, }) // Usage limit check, 10 tokens svc.Use(&limits.Usage{ Container: limits.NewRedisBucket("tcp://127.0.0.1", 10, 1), }) svc.Resource(&c) svc.Run() }
Output:
Index ¶
Examples ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func MD5RequestKey ¶
func MD5RequestKey(c relax.Context) string
MD5RequestKey returns a key made from MD5 hash of Request.RemoteAddr and Request.UserAgent. But if the client has been authenticated, it will use the username as key.
Types ¶
type Container ¶
type Container interface { // Capacity returns the max number of tokens per client. Capacity() int // Consume takes tokens from a bucket. // Returns the number of tokens available, time in seconds for next one, and // a boolean indicating whether of not a token was consumed. Consume(string, int) (int, int, bool) // Reset will fill-up a bucket regardless of time/count. Reset(string) }
Objects that implement the Container interface can serve as token bucket containers.
func NewMemBucket ¶
NewMemBucket returns a new MemBucket container object. It initializes the LRU cache with 'maxKeys'.
type MemBucket ¶
type MemBucket struct { Size int // max tokens allowed, capacity. Rate int // tokens added per minute Cache *lru.Cache // LRU cache storage }
MemBucket implements Container using an in-memory LRU cache. This container is ideal for single-host applications, and it's go-routine safe.
type Memory ¶
type Memory struct { // Allow sets a limit on current used memory size, in bytes. This value // ideally should be a number multiple of 2. // Defaults to 0 (disabled) // Alloc: 5242880 // 5MB Alloc uint64 // Sys sets a limit on system memory usage size, in bytes. This value // ideally should be a number multiple of 2. // Defaults to 1e9 (1000000000 bytes) Sys uint64 // RetryAfter is a suggested retry-after period, in seconds, as recommended // in http://tools.ietf.org/html/rfc7231#section-6.6.4 // If zero, no header is sent. // Defaults to 0 (no header sent) RetryAfter int }
Memory sets limits on application and system memory usage. The memory stats are updated every minute and compared. If any limit is reached, a response is sent with HTTP status 503-"Service Unavailable". See also, runtime.MemStats
type RedisBucket ¶
type RedisBucket struct { Size int // max tokens allowed Rate int // tokens added per second Pool *redis.Pool }
RedisBucket implements Container using Redis strings.
func NewRedisBucket ¶
func NewRedisBucket(uri string, capacity, rate int) *RedisBucket
func NewRedisBucket(uri string, capacity, rate int) Container {
func (*RedisBucket) Capacity ¶
func (b *RedisBucket) Capacity() int
func (*RedisBucket) Reset ¶
func (b *RedisBucket) Reset(key string)
type Throttle ¶
type Throttle struct { // Request is the number of requests to allow per time duration. // Defaults to 100 Requests int // Burst is the number of burst requests allowed before enforcing a time limit. // Defaults to 0 Burst int // Per is the unit of time to quantize requests. This value is divided by the // value of Requests to get the time period to throttle. // Defaults to 1 second (time.Second) Per time.Duration }
Throttle allows to limit the rate of requests to a resource per specific time duration. It uses Go's channels to receive time tick updates. If a request is made before the channel is updated, the request is dropped with HTTP status code 429-"Too Many Requests".
type Usage ¶
type Usage struct { // Container is an interface implemented by the bucket device. // The default container, MemBucket, is a memory-based container which stores // keys in an LRU cache. This container monitors a maximum number of keys, // and this value should be according to the system's available memory. // Defaults to a MemBucket container, with the values: // // maxKeys = 1000 // number of keys to monitor. // capacity = 100 // total tokens per key. // fillrate = 1 // tokens renewed per minute per key. // // See also, MemBucket Container // Ration is the number of tokens to consume per request. // Defaults to 1. Ration int // Keygen is a function used to generate semi-unique ID's for each client. // The default function, MD5RequestKey, uses an MD5 hash on client address // and user agent, or the username of an authenticated client. Keygen func(relax.Context) string }
Usage monitors request usage limits to the service, resource or to specific route(s). It uses Container objects to implement the token-bucket (TB) algorithm. TB is useful for limiting number of requests and burstiness.
Each client is assigned a (semi) unique key and given a bucket of tokens to spend per request. If a client consumes all its tokens, a response is sent with HTTP status 429-"Too Many Requests". At this time the client won't be allowed any more requests until a renewal period has passed. Repeated attempts while the timeout is in effect will simply reset the timer, prolonging the wait and dropping then new request.