From 526a8742688ed58ae40ba1f254c2e7f1f7bbd866 Mon Sep 17 00:00:00 2001 From: grm Date: Fri, 18 Sep 2026 13:48:27 +0300 Subject: Security: Check the CSRF token on logout /logout was the one management POST without the token. A blog lives on a subdomain of the root domain, which is same-site, so SameSite=Lax does not keep the cookie off a form a blog page submits: any blogger's custom HTML could log the superadmin out at will. The logout form already carried _csrf; the handler now checks it through guardPOST. Co-Authored-By: Claude Opus 5 Claude-Session: https://claude.ai/code/session_01Sd8UPWrvyYCLj97JexNw3A --- AGENTS.md | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) (limited to 'AGENTS.md') diff --git a/AGENTS.md b/AGENTS.md index 4f5e893..4640647 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -133,7 +133,10 @@ internal/web/ server.go (host router, middleware, render helpers) `guardPOST(blog.UploadLimit(cfg))`, and `withBlogFiles(n, …)` allows n limits for the Files page's multi-upload (`maxUploadFiles` = 10). Errors from `guardPOST` go through `s.fail`, which answers JSON when the request - has `Accept: application/json` (the upload scripts). + has `Accept: application/json` (the upload scripts). `POST /logout` runs + `guardPOST` too when a user is logged in (blogs are same-site with the + root domain, so `SameSite=Lax` alone would let a blog page log a + superadmin out). - **Hardening** (`web/ratelimit.go`): a per-key token bucket throttles the anonymous endpoints worth abusing — `loginLimit` on `POST /webadmin`, keyed by client address *and* by lowercased username (10 at once, then 10 a -- cgit v1.2.3