= HAProxy Stick Table = <> ---- == Sticky Counters == A '''stick table''' is a relational table of connection data (usually IP address of requester: `src`) to '''sticky counters'''. By default, only three sticky counters are allowed. (This is a compilation option.) They can be referred to as `sc0`, `sc1`, and `sc2`. This means that a connection can only be inserted into three distinct, concurrent sticky tables. Sticky tables relate connection data to a variety of rates and counters. The most common usecases have a builtin data type and setter/getter functions. There are also '''general purpose counters''' and '''general purpose tags'''. Up to 100 of these can be used on any sticky table (`gpc(0)` .. `gpc(99)`). But similar to the sticky tables themselves, there are convenient names for the first three: `gpc0`, `gpc1`, and `gpc2`. ---- == Usage == === Rate Limiting === To track the rate of HTTP requests, allocate an IP address (`type ip`) sticky table to store `http_req_rate(10s)` (`store http_req_rate(10s)`). This data type represents the number of HTTP requests in the last 10 seconds. {{{ backend my_backend stick-table type ip size 1m expire 30s store http_req_rate(10s) }}} Note also that the table is allocated to track 1 million IP addresses, and entries expire after 30 seconds. To insert a new connection into the sticky table (which defaulted to `sc0`), use the `track-sc0` directive. Then the current rate can be accessed with `sc_http_req_rate(0)`. (Note the `0` is the sticky table index.) {{{ backend my_backend stick-table type ip size 1m expire 30s store http_req_rate(10s) http-request track-sc0 src http-request deny deny_status 429 if { sc_http_req_rate(0) gt 15 } }}} It may be necessary to exclude certain requests from rate limiting, such as stylesheets and images. {{{ backend my_backend http-request track-sc0 src if ! { path_end .css .png .jpg } }}} === Abuse Tracking === To monitor and ban abusive clients, use a general purpose counter. Allocate an IP address (`type ip`) sticky table to store `gpc0` (`store gcp0`). {{{ backend my_backend stick-table type ip size 1m expire 1m store gpc0 }}} Note that these entries expire after 1 minute. To increment the counter for a client, use the `sc-inc-gpc0(0)` directive. Then the counter can be accessed with `sc_get_gpc0(0)`. (Again, and in both cases, the `0` is the sticky table index.) {{{ backend my_backend stick-table type ip size 1m expire 1m store gpc0 http-request sc-inc-gpc0(0) if { path_end .php } http-request silent-drop if { sc_get_gpc0(0) gt 0 } }}} This will cause the abusive clients' programs to hang after making a request to any URL ending in `.php`, and any new requests made for the next minute will similarly hang. ---- CategoryRicottone