Skip to content

feat(PLA-8129): runtime Redis-SET allowlist for the decay backend - #2

Merged
ysolomon-plat merged 1 commit into
redis-decay-backendfrom
pla-8129-allowlist-redis-decay
Sep 3, 2026
Merged

ysolomon-plat merged 1 commit into
redis-decay-backendfrom
pla-8129-allowlist-redis-decay

Conversation

@ysolomon-plat

Copy link
Copy Markdown

What

Adds the PLA-8129 runtime allowlist to cache_impl.go: an operator SADDs a
value to a Redis SET (allowlist:rl_ip / allowlist:rl_ua / allowlist:rl_subject)
and it's exempted from rate limiting on the very next request — no deploy,
no EnvoyFilter apply. Replaces the compiled-in Lua tables that made a config
change a deploy.

Matches ratelimiting.lua's existing, asymmetric exemption rules
(ip_rate_limit_with_pooling / user_agent_rate_limit_with_pooling /
auth_rate_limit_with_pooling, :204-253):

  • an allowlisted IP exempts rl_ip, rl_ua AND rl_subject together, for the whole request
  • an allowlisted user-agent or user-id exempts only its own bucket
  • client_id is never exempted by any allowlist

Why this PR exists now

This code has been running live in Depop's dev-default cluster since
2026-08-21, deployed via a Kubernetes ConfigMap. It was never pushed to this
repo, never opened as a PR, never reviewed, and had zero tests. Confirmed
live via ratelimit-fork debug logs on 2026-09-03 as part of proving the
PLA-8126 gRPC authorizer → PLA-8128 rate limiter join actually works. This
PR is that catch-up: real code review, on the actual running logic, plus the
test coverage it should have had from the start.

Tests

8 new tests in test/redis_decay/allowlist_test.go, matching the style of
the existing cache_impl_test.go suite:

  • IP allowlist exempts its own bucket, and separately, the cross-bucket
    exemption (IP allowlisting also exempts UA/subject descriptors elsewhere
    in the same request)
  • UA and subject allowlists each exempt only their own bucket
  • client_id is never exempted, even when IP is allowlisted
  • A non-allowlisted value is rate limited normally (allowlist machinery is a
    no-op for the common case)
  • No allowlists configured at all behaves identically to the pre-allowlist
    implementation
  • A Redis failure during the allowlist membership check panics as
    redis.RedisError, same as a decay-pipeline failure — the service layer's
    failure-mode policy must not be bypassed just because the failure
    happened in this new phase

All 18 tests in the package pass (10 pre-existing + 8 new):

go test ./test/redis_decay/... -v
ok  	github.com/envoyproxy/ratelimit/test/redis_decay	1.031s

go build ./... and go vet ./src/redis_decay/... are both clean.

Adds a per-request allowlist check to cache_impl.go, run before any decay
counter is touched: an operator SADDs a value to a Redis SET
(allowlist:rl_ip / allowlist:rl_ua / allowlist:rl_subject) and it takes
effect on the very next request, no deploy, no EnvoyFilter apply. Replaces
the compiled-in Lua tables (IP_ALLOWLIST / USER_ID_ALLOWLIST) that made a
config change a deploy.

Matches ratelimiting.lua's existing, asymmetric exemption rules exactly
(ip_rate_limit_with_pooling / user_agent_rate_limit_with_pooling /
auth_rate_limit_with_pooling, :204-253): an allowlisted IP exempts rl_ip,
rl_ua AND rl_subject together for the whole request; an allowlisted
user-agent or user-id exempts only its own bucket; client_id is never
exempted by any allowlist.

This code has been running live in Depop's dev-default cluster since
2026-08-21 (deployed via a ConfigMap, source-controlled only there) without
ever being pushed here, reviewed, or tested. Adds 8 tests covering the
asymmetric exemption rules, the client_id exclusion, the no-allowlist
baseline, and the Redis-down failure path (must still panic as
redis.RedisError, matching the existing decay-pipeline failure convention).
@ysolomon-plat
ysolomon-plat merged commit b998c20 into redis-decay-backend Sep 3, 2026
3 checks passed
@ysolomon-plat
ysolomon-plat deleted the pla-8129-allowlist-redis-decay branch September 3, 2026 07:53
ysolomon-plat added a commit that referenced this pull request Sep 3, 2026
Resolves an add/add conflict on src/redis_decay/cache_impl.go: main only
had PR #1's decay-only version; redis-decay-backend's version is that same
file with PR #2's allowlist logic layered on top (confirmed via diff -
identical base, additive change only). Took the branch's version.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant