mirror of https://github.com/status-im/consul.git
agent: add option to disable agent cache for HTTP endpoints (#8023)
This allows the operator to disable agent caching for the http endpoint. It is on by default for backwards compatibility and if disabled will ignore the url parameter `cached`.
This commit is contained in:
parent
9262d7a79a
commit
72f92ae7ca
|
@ -84,7 +84,7 @@ func (s *HTTPServer) CatalogDatacenters(resp http.ResponseWriter, req *http.Requ
|
||||||
parseCacheControl(resp, req, &args.QueryOptions)
|
parseCacheControl(resp, req, &args.QueryOptions)
|
||||||
var out []string
|
var out []string
|
||||||
|
|
||||||
if args.QueryOptions.UseCache {
|
if s.agent.config.HTTPUseCache && args.QueryOptions.UseCache {
|
||||||
raw, m, err := s.agent.cache.Get(cachetype.CatalogDatacentersName, &args)
|
raw, m, err := s.agent.cache.Get(cachetype.CatalogDatacentersName, &args)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
metrics.IncrCounterWithLabels([]string{"client", "rpc", "error", "catalog_datacenters"}, 1,
|
metrics.IncrCounterWithLabels([]string{"client", "rpc", "error", "catalog_datacenters"}, 1,
|
||||||
|
@ -166,7 +166,7 @@ func (s *HTTPServer) CatalogServices(resp http.ResponseWriter, req *http.Request
|
||||||
var out structs.IndexedServices
|
var out structs.IndexedServices
|
||||||
defer setMeta(resp, &out.QueryMeta)
|
defer setMeta(resp, &out.QueryMeta)
|
||||||
|
|
||||||
if args.QueryOptions.UseCache {
|
if s.agent.config.HTTPUseCache && args.QueryOptions.UseCache {
|
||||||
raw, m, err := s.agent.cache.Get(cachetype.CatalogListServicesName, &args)
|
raw, m, err := s.agent.cache.Get(cachetype.CatalogListServicesName, &args)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
metrics.IncrCounterWithLabels([]string{"client", "rpc", "error", "catalog_services"}, 1,
|
metrics.IncrCounterWithLabels([]string{"client", "rpc", "error", "catalog_services"}, 1,
|
||||||
|
@ -255,7 +255,7 @@ func (s *HTTPServer) catalogServiceNodes(resp http.ResponseWriter, req *http.Req
|
||||||
var out structs.IndexedServiceNodes
|
var out structs.IndexedServiceNodes
|
||||||
defer setMeta(resp, &out.QueryMeta)
|
defer setMeta(resp, &out.QueryMeta)
|
||||||
|
|
||||||
if args.QueryOptions.UseCache {
|
if s.agent.config.HTTPUseCache && args.QueryOptions.UseCache {
|
||||||
raw, m, err := s.agent.cache.Get(cachetype.CatalogServicesName, &args)
|
raw, m, err := s.agent.cache.Get(cachetype.CatalogServicesName, &args)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
metrics.IncrCounterWithLabels([]string{"client", "rpc", "error", "catalog_service_nodes"}, 1,
|
metrics.IncrCounterWithLabels([]string{"client", "rpc", "error", "catalog_service_nodes"}, 1,
|
||||||
|
|
|
@ -858,6 +858,7 @@ func (b *Builder) Build() (rt RuntimeConfig, err error) {
|
||||||
HTTPBlockEndpoints: c.HTTPConfig.BlockEndpoints,
|
HTTPBlockEndpoints: c.HTTPConfig.BlockEndpoints,
|
||||||
HTTPResponseHeaders: c.HTTPConfig.ResponseHeaders,
|
HTTPResponseHeaders: c.HTTPConfig.ResponseHeaders,
|
||||||
AllowWriteHTTPFrom: b.cidrsVal("allow_write_http_from", c.HTTPConfig.AllowWriteHTTPFrom),
|
AllowWriteHTTPFrom: b.cidrsVal("allow_write_http_from", c.HTTPConfig.AllowWriteHTTPFrom),
|
||||||
|
HTTPUseCache: b.boolValWithDefault(c.HTTPConfig.UseCache, true),
|
||||||
|
|
||||||
// Telemetry
|
// Telemetry
|
||||||
Telemetry: lib.TelemetryConfig{
|
Telemetry: lib.TelemetryConfig{
|
||||||
|
|
|
@ -611,6 +611,7 @@ type HTTPConfig struct {
|
||||||
BlockEndpoints []string `json:"block_endpoints,omitempty" hcl:"block_endpoints" mapstructure:"block_endpoints"`
|
BlockEndpoints []string `json:"block_endpoints,omitempty" hcl:"block_endpoints" mapstructure:"block_endpoints"`
|
||||||
AllowWriteHTTPFrom []string `json:"allow_write_http_from,omitempty" hcl:"allow_write_http_from" mapstructure:"allow_write_http_from"`
|
AllowWriteHTTPFrom []string `json:"allow_write_http_from,omitempty" hcl:"allow_write_http_from" mapstructure:"allow_write_http_from"`
|
||||||
ResponseHeaders map[string]string `json:"response_headers,omitempty" hcl:"response_headers" mapstructure:"response_headers"`
|
ResponseHeaders map[string]string `json:"response_headers,omitempty" hcl:"response_headers" mapstructure:"response_headers"`
|
||||||
|
UseCache *bool `json:"use_cache,omitempty" hcl:"use_cache" mapstructure:"use_cache"`
|
||||||
}
|
}
|
||||||
|
|
||||||
type Performance struct {
|
type Performance struct {
|
||||||
|
|
|
@ -342,6 +342,12 @@ type RuntimeConfig struct {
|
||||||
// hcl: dns_config { cache_max_age = "duration" }
|
// hcl: dns_config { cache_max_age = "duration" }
|
||||||
DNSCacheMaxAge time.Duration
|
DNSCacheMaxAge time.Duration
|
||||||
|
|
||||||
|
// HTTPUseCache whether or not to use cache for http queries. Defaults
|
||||||
|
// to true.
|
||||||
|
//
|
||||||
|
// hcl: http_config { use_cache = (true|false) }
|
||||||
|
HTTPUseCache bool
|
||||||
|
|
||||||
// HTTPBlockEndpoints is a list of endpoint prefixes to block in the
|
// HTTPBlockEndpoints is a list of endpoint prefixes to block in the
|
||||||
// HTTP API. Any requests to these will get a 403 response.
|
// HTTP API. Any requests to these will get a 403 response.
|
||||||
//
|
//
|
||||||
|
|
|
@ -2118,6 +2118,54 @@ func TestConfigFlagsAndEdgecases(t *testing.T) {
|
||||||
`},
|
`},
|
||||||
err: "Serf Advertise WAN address 10.0.0.1:1000 already configured for RPC Advertise",
|
err: "Serf Advertise WAN address 10.0.0.1:1000 already configured for RPC Advertise",
|
||||||
},
|
},
|
||||||
|
{
|
||||||
|
desc: "http use_cache defaults to true",
|
||||||
|
args: []string{
|
||||||
|
`-data-dir=` + dataDir,
|
||||||
|
},
|
||||||
|
json: []string{`{
|
||||||
|
"http_config": {}
|
||||||
|
}`},
|
||||||
|
hcl: []string{`
|
||||||
|
http_config = {}
|
||||||
|
`},
|
||||||
|
patch: func(rt *RuntimeConfig) {
|
||||||
|
rt.DataDir = dataDir
|
||||||
|
rt.HTTPUseCache = true
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
desc: "http use_cache is enabled when true",
|
||||||
|
args: []string{
|
||||||
|
`-data-dir=` + dataDir,
|
||||||
|
},
|
||||||
|
json: []string{`{
|
||||||
|
"http_config": { "use_cache": true }
|
||||||
|
}`},
|
||||||
|
hcl: []string{`
|
||||||
|
http_config = { use_cache = true }
|
||||||
|
`},
|
||||||
|
patch: func(rt *RuntimeConfig) {
|
||||||
|
rt.DataDir = dataDir
|
||||||
|
rt.HTTPUseCache = true
|
||||||
|
},
|
||||||
|
},
|
||||||
|
{
|
||||||
|
desc: "http use_cache is disabled when false",
|
||||||
|
args: []string{
|
||||||
|
`-data-dir=` + dataDir,
|
||||||
|
},
|
||||||
|
json: []string{`{
|
||||||
|
"http_config": { "use_cache": false }
|
||||||
|
}`},
|
||||||
|
hcl: []string{`
|
||||||
|
http_config = { use_cache = false }
|
||||||
|
`},
|
||||||
|
patch: func(rt *RuntimeConfig) {
|
||||||
|
rt.DataDir = dataDir
|
||||||
|
rt.HTTPUseCache = false
|
||||||
|
},
|
||||||
|
},
|
||||||
{
|
{
|
||||||
desc: "sidecar_service can't have ID",
|
desc: "sidecar_service can't have ID",
|
||||||
args: []string{
|
args: []string{
|
||||||
|
@ -4167,7 +4215,8 @@ func TestFullConfig(t *testing.T) {
|
||||||
"response_headers": {
|
"response_headers": {
|
||||||
"M6TKa9NP": "xjuxjOzQ",
|
"M6TKa9NP": "xjuxjOzQ",
|
||||||
"JRCrHZed": "rl0mTx81"
|
"JRCrHZed": "rl0mTx81"
|
||||||
}
|
},
|
||||||
|
"use_cache": false
|
||||||
},
|
},
|
||||||
"key_file": "IEkkwgIA",
|
"key_file": "IEkkwgIA",
|
||||||
"leave_on_terminate": true,
|
"leave_on_terminate": true,
|
||||||
|
@ -4804,6 +4853,7 @@ func TestFullConfig(t *testing.T) {
|
||||||
"M6TKa9NP" = "xjuxjOzQ"
|
"M6TKa9NP" = "xjuxjOzQ"
|
||||||
"JRCrHZed" = "rl0mTx81"
|
"JRCrHZed" = "rl0mTx81"
|
||||||
}
|
}
|
||||||
|
use_cache = false
|
||||||
}
|
}
|
||||||
key_file = "IEkkwgIA"
|
key_file = "IEkkwgIA"
|
||||||
leave_on_terminate = true
|
leave_on_terminate = true
|
||||||
|
@ -5517,6 +5567,7 @@ func TestFullConfig(t *testing.T) {
|
||||||
HTTPMaxConnsPerClient: 100,
|
HTTPMaxConnsPerClient: 100,
|
||||||
HTTPSHandshakeTimeout: 2391 * time.Millisecond,
|
HTTPSHandshakeTimeout: 2391 * time.Millisecond,
|
||||||
HTTPSPort: 15127,
|
HTTPSPort: 15127,
|
||||||
|
HTTPUseCache: false,
|
||||||
KeyFile: "IEkkwgIA",
|
KeyFile: "IEkkwgIA",
|
||||||
KVMaxValueSize: 1234567800000000,
|
KVMaxValueSize: 1234567800000000,
|
||||||
LeaveDrainTime: 8265 * time.Second,
|
LeaveDrainTime: 8265 * time.Second,
|
||||||
|
@ -6402,6 +6453,7 @@ func TestSanitize(t *testing.T) {
|
||||||
"HTTPMaxConnsPerClient": 0,
|
"HTTPMaxConnsPerClient": 0,
|
||||||
"HTTPPort": 0,
|
"HTTPPort": 0,
|
||||||
"HTTPResponseHeaders": {},
|
"HTTPResponseHeaders": {},
|
||||||
|
"HTTPUseCache": false,
|
||||||
"HTTPSAddrs": [],
|
"HTTPSAddrs": [],
|
||||||
"HTTPSHandshakeTimeout": "0s",
|
"HTTPSHandshakeTimeout": "0s",
|
||||||
"HTTPSPort": 0,
|
"HTTPSPort": 0,
|
||||||
|
|
|
@ -60,7 +60,7 @@ func (s *HTTPServer) DiscoveryChainRead(resp http.ResponseWriter, req *http.Requ
|
||||||
var out structs.DiscoveryChainResponse
|
var out structs.DiscoveryChainResponse
|
||||||
defer setMeta(resp, &out.QueryMeta)
|
defer setMeta(resp, &out.QueryMeta)
|
||||||
|
|
||||||
if args.QueryOptions.UseCache {
|
if s.agent.config.HTTPUseCache && args.QueryOptions.UseCache {
|
||||||
raw, m, err := s.agent.cache.Get(cachetype.CompiledDiscoveryChainName, &args)
|
raw, m, err := s.agent.cache.Get(cachetype.CompiledDiscoveryChainName, &args)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
|
@ -198,7 +198,7 @@ func (s *HTTPServer) healthServiceNodes(resp http.ResponseWriter, req *http.Requ
|
||||||
var out structs.IndexedCheckServiceNodes
|
var out structs.IndexedCheckServiceNodes
|
||||||
defer setMeta(resp, &out.QueryMeta)
|
defer setMeta(resp, &out.QueryMeta)
|
||||||
|
|
||||||
if args.QueryOptions.UseCache {
|
if s.agent.config.HTTPUseCache && args.QueryOptions.UseCache {
|
||||||
raw, m, err := s.agent.cache.Get(cachetype.HealthServicesName, &args)
|
raw, m, err := s.agent.cache.Get(cachetype.HealthServicesName, &args)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return nil, err
|
return nil, err
|
||||||
|
|
|
@ -121,7 +121,7 @@ func (s *HTTPServer) preparedQueryExecute(id string, resp http.ResponseWriter, r
|
||||||
var reply structs.PreparedQueryExecuteResponse
|
var reply structs.PreparedQueryExecuteResponse
|
||||||
defer setMeta(resp, &reply.QueryMeta)
|
defer setMeta(resp, &reply.QueryMeta)
|
||||||
|
|
||||||
if args.QueryOptions.UseCache {
|
if s.agent.config.HTTPUseCache && args.QueryOptions.UseCache {
|
||||||
raw, m, err := s.agent.cache.Get(cachetype.PreparedQueryName, &args)
|
raw, m, err := s.agent.cache.Get(cachetype.PreparedQueryName, &args)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
// Don't return error if StaleIfError is set and we are within it and had
|
// Don't return error if StaleIfError is set and we are within it and had
|
||||||
|
|
|
@ -1415,6 +1415,8 @@ Valid time units are 'ns', 'us' (or 'µs'), 'ms', 's', 'm', 'h'."
|
||||||
|
|
||||||
- `allow_write_http_from` This object is a list of networks in CIDR notation (eg "127.0.0.0/8") that are allowed to call the agent write endpoints. It defaults to an empty list, which means all networks are allowed. This is used to make the agent read-only, except for select ip ranges. - To block write calls from anywhere, use `[ "255.255.255.255/32" ]`. - To only allow write calls from localhost, use `[ "127.0.0.0/8" ]` - To only allow specific IPs, use `[ "10.0.0.1/32", "10.0.0.2/32" ]`
|
- `allow_write_http_from` This object is a list of networks in CIDR notation (eg "127.0.0.0/8") that are allowed to call the agent write endpoints. It defaults to an empty list, which means all networks are allowed. This is used to make the agent read-only, except for select ip ranges. - To block write calls from anywhere, use `[ "255.255.255.255/32" ]`. - To only allow write calls from localhost, use `[ "127.0.0.0/8" ]` - To only allow specific IPs, use `[ "10.0.0.1/32", "10.0.0.2/32" ]`
|
||||||
|
|
||||||
|
- `use_cache` Defaults to true. If disabled, the agent won't be using [agent caching](/api/features/caching) to answer the request. Even when the url parameter is provided.
|
||||||
|
|
||||||
- `leave_on_terminate` If enabled, when the agent receives a TERM signal, it will send a `Leave` message to the rest of the cluster and gracefully leave. The default behavior for this feature varies based on whether or not the agent is running as a client or a server (prior to Consul 0.7 the default value was unconditionally set to `false`). On agents in client-mode, this defaults to `true` and for agents in server-mode, this defaults to `false`.
|
- `leave_on_terminate` If enabled, when the agent receives a TERM signal, it will send a `Leave` message to the rest of the cluster and gracefully leave. The default behavior for this feature varies based on whether or not the agent is running as a client or a server (prior to Consul 0.7 the default value was unconditionally set to `false`). On agents in client-mode, this defaults to `true` and for agents in server-mode, this defaults to `false`.
|
||||||
|
|
||||||
- `limits` Available in Consul 0.9.3 and later, this is a nested
|
- `limits` Available in Consul 0.9.3 and later, this is a nested
|
||||||
|
|
Loading…
Reference in New Issue