Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 37 additions & 0 deletions .github/workflows/cd.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
name: CD

on:
release:
types: [published]
workflow_dispatch:
inputs:
TAG:
required: true
description: Docker image tag
default: latest

jobs:
publish:
name: Publish the Docker image
# runs-on: ubuntu-latest
runs-on: zerion-arm-runners # self-hosted arm64 runner
permissions:
id-token: write
contents: read
steps:
- name: Generate token
id: app-token
uses: actions/create-github-app-token@v1
with:
app-id: ${{ secrets.ZERION_CI_APP_ID }}
private-key: ${{ secrets.ZERION_CI_APP_PRIVATE_KEY }}
owner: zeriontech
- name: Zerion AWS
uses: zeriontech/zerion-github-actions/aws@v5
with:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
AWS_REGION: us-east-1
ECR_REPOSITORY: ${{ github.event.repository.name }}
ZERION_PAT: ${{ steps.app-token.outputs.token }}
PLATFORM: linux/arm64
IMAGE_TAG: ${{ github.event.inputs.TAG || github.ref_name }}
48 changes: 0 additions & 48 deletions .github/workflows/codeql.yml

This file was deleted.

57 changes: 0 additions & 57 deletions .github/workflows/main.yaml

This file was deleted.

36 changes: 0 additions & 36 deletions .github/workflows/release.yaml

This file was deleted.

69 changes: 0 additions & 69 deletions .github/workflows/scorecard.yml

This file was deleted.

48 changes: 0 additions & 48 deletions .github/workflows/stale.yml

This file was deleted.

8 changes: 8 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,14 @@ endif
.PHONY: bootstrap
bootstrap: ;

.PHONY: proto
proto:
protoc \
--proto_path=api \
--go_out=. --go_opt=module=$(MODULE) \
--go-grpc_out=. --go-grpc_opt=module=$(MODULE) \
api/ratelimit/corrector/v1/corrector.proto

define REDIS_STUNNEL
cert = private.pem
pid = /var/run/stunnel.pid
Expand Down
38 changes: 38 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,7 @@
- [Prometheus](#prometheus)
- [HTTP Port](#http-port)
- [/json endpoint](#json-endpoint)
- [Corrector Service](#corrector-service)
- [Debug Port](#debug-port)
- [Local Cache](#local-cache)
- [Redis](#redis)
Expand Down Expand Up @@ -1251,6 +1252,43 @@ The response is a RateLimitResponse encoded with
}
```

# Corrector Service

`CorrectorService.DecrementCounter` is an internal admin RPC for refunding
quota that was charged but never actually consumed (for example, when an
upstream returns a non-2xx and the caller decides to roll the slot back).
It is exposed on the existing gRPC port and on the HTTP/1 listener at
`/json/corrector/decrement`.

Trust model: same as the data plane. No per-RPC authentication; access is
gated by network isolation and the existing TLS configuration.

Semantics:

- Only limits with units of HOUR or larger are eligible. Sub-hour units are
refused with `UNIT_NOT_ALLOWED` — an out-of-band correction loop can't
keep up with shorter windows.
- The caller must echo back the current bucket-start timestamp in
`original_bucket_timestamp`; if the bucket has rolled, the call returns
`BUCKET_EXPIRED` and the caller knows to drop the correction.
- Underflow is clamped at 0 atomically inside Redis (Lua). Over-decrement
returns `OK` with `new_value == 0` rather than letting the counter go
negative.
- Backend support is Redis only. Memcached returns `Unimplemented`.

Companion setting: `LOCAL_CACHE_MAX_UNIT_SECONDS` (default `0`, no cap)
restricts the per-replica freecache "over limit" markers to units at or
below the configured cap. Set it to `3600` so HOUR+ limits — the ones the
Comment thread
oclaw marked this conversation as resolved.
corrector touches — never go through the local cache; otherwise a stale
marker can outlive a decrement until the bucket boundary.
Comment on lines +1280 to +1283

Observability:

- Prometheus counter `ratelimit_corrector_decrements_total{domain, limit_unit, result}`.
`result` values: `ok`, `bucket_expired`, `key_not_found`, `unit_not_allowed`, `limit_not_found`, `invalid_argument`, `unimplemented`, `no_config`, `transport_error`, `service_error`, `error` (fallback for non-status backend errors). Caller-controlled `domain` collapses to `<unresolved>` whenever no configured limit was matched, so cardinality stays bounded.
- Structured audit log line (`component=corrector`) on every accepted call.
Validation failures log at Debug to avoid flooding on hostile traffic.

# Debug Port

The debug port can be used to interact with the running process.
Expand Down
Loading
Loading