/** * Cross-replica per-key request rate limiter ([ref] P0-2) — a thin {@link RateGate} over the shared * {@link WriteBehindCounter}. Like the in-memory {@link RateLimiter}, `check` both COUNTS the request * and decides; here the count is summed fleet-wide via atomic write-behind aggregation. * * **SOFT limiting** (the WriteBehindCounter is eventually consistent): a replica may briefly admit a few * requests over the ceiling at a window boundary before peers' counts propagate. That is fine for a * fairness / hot-caller cap (the use case here). A HARD global cap would need a linearizable CAS, not * write-behind — same trade as the cross-replica circuit breaker and cost quota. */ import type { Pool } from "mysql2/promise"; import type { RateDecision, RateGate, RateLimits } from "../observability/rate-limit.js"; import { type CounterDegradeHook } from "./write-behind-counter.js"; export declare class TiDBRateLimiter implements RateGate { private readonly counter; /** 🔴 [ref]:限额是比较参数、不是行状态(SQL 腿的行里只有计数),所以换代只动它,库里一行都不用碰。 */ private limit; /** 装配点表达过的运维意图(「这条腿该有刷新环」)。关断哨兵靠它把环真正停掉/重开 —— 0 态零 SQL。 */ private refreshRequested; private refreshIntervalMs; constructor(pool: Pool, limit: number, windowMs?: number, now?: () => number, onDegraded?: CounterDegradeHook, queryTimeoutMs?: number); setLimits(next: RateLimits): void; /** off ⇒ 停环(零 SQL);on 且装配点要过环 ⇒ 起环(幂等,counter 内部 `??=`)。 */ private syncRefresh; check(key: string): RateDecision; /** The flush loop self-reaps old windows; the periodic sweeper has nothing to do for this backend. */ sweep(): void; flush(): Promise; refresh(): Promise; startRefresh(intervalMs?: number): this; stop(): void; } //# sourceMappingURL=tidb-rate-limiter.d.ts.map