Hello!
I’ve been trying to apply rate-limiting for a service that clients connect to via WebSocket connections.
Following the guide: https://istio.io/latest/docs/tasks/policy-enforcement/rate-limit/#local-rate-limit. At first, I thought that the rate-limiting wasn’t working because I applied it to the wrong port. On then forward I proceeded to limit to port 0 (which limited the connections on all ports as far as I understood how it works) but the WebSocket connections weren’t limited. I couldn’t find any documentation around envoy nor Istio around websocket filters or any examples of how to handle this use case.
P.S. Circuit breaking isn’t a possible solution since I want to rate-limit the burst of traffic type of scenarios to the service.
Here’s the config that I use.
apiVersion: networking.istio.io/v1alpha3
kind: EnvoyFilter
metadata:
name: service-name
spec:
workloadSelector:
labels:
app: service-name
configPatches:
- applyTo: HTTP_FILTER
match:
context: SIDECAR_INBOUND
listener:
filterChain:
filter:
name: "envoy.filters.network.http_connection_manager"
patch:
operation: INSERT_BEFORE
value:
name: envoy.filters.http.local_ratelimit
typed_config:
"@type": type.googleapis.com/udpa.type.v1.TypedStruct
type_url: type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
value:
stat_prefix: http_local_rate_limiter
- applyTo: HTTP_ROUTE
match:
context: SIDECAR_INBOUND
routeConfiguration:
portNumber: 0
patch:
operation: MERGE
value:
typed_per_filter_config:
envoy.filters.http.local_ratelimit:
"@type": type.googleapis.com/udpa.type.v1.TypedStruct
type_url: type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
value:
stat_prefix: http_local_rate_limiter
token_bucket:
max_tokens: 10
tokens_per_fill: 1
fill_interval: 9000s
filter_enabled:
runtime_key: local_rate_limit_enabled
default_value:
numerator: 100
denominator: HUNDRED
filter_enforced:
runtime_key: local_rate_limit_enforced
default_value:
numerator: 100
denominator: HUNDRED
response_headers_to_add:
- append: true
header:
key: x-local-rate-limit
value: 'true'
The non-specific config also doesn’t seem to limit the websocket connections.
apiVersion: networking.istio.io/v1alpha3
kind: EnvoyFilter
metadata:
name: a-service
spec:
workloadSelector:
labels:
app: a-service
configPatches:
- applyTo: HTTP_FILTER
match:
context: SIDECAR_INBOUND
listener:
filterChain:
filter:
name: "envoy.filters.network.http_connection_manager"
patch:
operation: INSERT_BEFORE
value:
name: envoy.filters.http.local_ratelimit
typed_config:
"@type": type.googleapis.com/udpa.type.v1.TypedStruct
type_url: type.googleapis.com/envoy.extensions.filters.http.local_ratelimit.v3.LocalRateLimit
value:
stat_prefix: http_local_rate_limiter
token_bucket:
max_tokens: 10
tokens_per_fill: 10
fill_interval: 30s
filter_enabled:
runtime_key: local_rate_limit_enabled
default_value:
numerator: 100
denominator: HUNDRED
filter_enforced:
runtime_key: local_rate_limit_enforced
default_value:
numerator: 100
denominator: HUNDRED
response_headers_to_add:
- append: false
header:
key: x-local-rate-limit
value: 'true'
Any tips and or help is appreciated!
Best,
Risto