HarperFast / HarperFast/harper
Operations API / main-thread hardening: auth-stage gate against control-plane resource exhaustion
- Dominant language
- JavaScript
- Stars
- 89
- Forks
- 10
- Avg merge
- 2d 6h
- Merged PRs (30d)
- 200
Description
## Problem
The main thread serves the **operations API only** — no application requests, and no other thread services the ops API — and it also carries the control plane (replication coordination, config/rule propagation, component management). It is a shared-fate chokepoint: exhausting it degrades everything at once, *including the ability to push the configuration change that would end an attack*.
The application-plane request-filtering middleware does **not** protect this surface: the ops API is served by its own server on the main thread, outside the worker middleware chain (the same reason config-applied response headers don't reach ops responses). So main-thread protection needs its own mechanism — deliberately simpler than an app-plane filter, and matched to a very different traffic profile.
## Why a different strategy fits here
Ops-API consumers are **few, privileged, and enumerable**, with low request volume. That inverts the usual availability-vs-filtering tradeoff: hardening concentrated at the auth stage plus deny-by-default is feasible here in a way it never is for the application plane. Where the app plane leans fail-open (availability wins), the control-plane gate can lean **fail-closed** (deny unknown) because legitimate consumers are a known set.
## Proposed mechanism (auth-stage gate, config-driven, opt-in)
- **Optional IP allowlist** for the ops listener (deny-by-default when configured).
- **Unauthenticated-connection deadline** — close/ban sockets that don't successfully authenticate within a short window of connecting (cheap defense against slow-loris-style hold-open and pre-auth floods).
- **Escalating bans on failed authentication** (per-IP backoff → temporary ban).
- **Per-IP connection caps and tighter rate limits** than the application plane.
All opt-in and config-driven; defaults chosen so a normal single/low-consumer deployment is unaffected.
## Explicit limits (not solved by this)
- Auth-stage hardening runs **post-TLS**, so it cannot stop TLS-handshake exhaustion on the ops listener. The first line remains **network posture** (the ops port is not meant to be publicly exposed) and, where the listener is reachable, an L4 shedding layer in front of it.
- This is control-plane *availability* hardening, not a WAF; it does no L7 request-content inspection.
## Relation to other work
- Complements the two-tier enforcement direction (detect at L7, shed at L4): the same connection-level blocklist feed that protects the app plane can front the ops listener.
- Part of the broader WAF/deployment-posture design (internal proposal): the app-plane filter is fail-open, this control-plane gate is fail-closed — two postures on one platform, each matched to its traffic profile. Protecting the main thread is also what keeps rule propagation and the health/telemetry signal alive under load.
## Scope note
Auth-stage hooks + listener-level connection controls are core (OSS-posture-credible, consistent with keeping baseline security primitives in core). A richer policy surface / feed integration can build on top in pro.
---
Filed by KrAIs (Claude) on Kris's behalf, from the WAF deployment-posture review.
Contributor guide
Research direction
The issue names no files, tests, or concrete entry points. Start by locating the operations API server and its authentication and listener setup; done would require an agreed, config-driven design covering the auth-stage deadline, allowlist, failed-auth bans, connection caps, and rate limits.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- javascript, node.js
- Domain
- api, backend, performance, security
- Issue type
- Feature
- Difficulty
- 5/5
- Estimated time
- Over a week
- Activity status
- Quiet
- Clarity
- Needs clarification
- Newbie friendliness
- 25/100