From 5b7b669b4cb891874156177fe9c2acc9e9cd0ba6 Mon Sep 17 00:00:00 2001 From: security-auditor Date: Thu, 7 May 2026 14:57:21 -0700 Subject: [PATCH] docs(ratelimit): tighten dev-mode comment after keyFor refactor MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The previous comment said "all share one IP bucket" — accurate before the keyFor refactor, slightly stale after it. The dev-mode rationale (bucket fills fast, blanks the page on a single-user dev box) is unchanged; only the bucket-key flavour text needed updating. Doc-only follow-up from #60's hostile self-review #3. No behavior change. Co-Authored-By: Claude Opus 4.7 (1M context) --- workspace-server/internal/middleware/ratelimit.go | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) diff --git a/workspace-server/internal/middleware/ratelimit.go b/workspace-server/internal/middleware/ratelimit.go index 7ecf4488..e01324d3 100644 --- a/workspace-server/internal/middleware/ratelimit.go +++ b/workspace-server/internal/middleware/ratelimit.go @@ -105,10 +105,11 @@ func (rl *RateLimiter) Middleware() gin.HandlerFunc { // Tier-1b dev-mode hatch — same gate as AdminAuth / WorkspaceAuth / // discovery. On a local single-user Docker setup the 600-req/min // bucket fills fast: a 15-workspace canvas + activity polling + - // approvals polling + A2A overlay + initial hydration all share - // one IP bucket, so a minute of active use can trip 429 and blank - // the page. Gated by MOLECULE_ENV=development + empty ADMIN_TOKEN - // so SaaS production keeps the bucket. + // approvals polling + A2A overlay + initial hydration all land in + // one bucket (whichever keyFor returns — typically the dev user's + // IP or shared admin token), so a minute of active use can trip + // 429 and blank the page. Gated by MOLECULE_ENV=development + + // empty ADMIN_TOKEN so SaaS production keeps the bucket. if isDevModeFailOpen() { c.Header("X-RateLimit-Limit", "unlimited") c.Next()