mirror of
https://github.com/fosrl/docs-v2.git
synced 2026-09-30 17:59:10 +02:00
add search, chat, and feedback analytics with dashboard
This commit is contained in:
+21
-17
@@ -6,29 +6,33 @@ import 'server-only';
|
||||
* reverse proxy's) in front if you run several replicas.
|
||||
*/
|
||||
const windowMs = 60_000;
|
||||
const limit = Number(process.env.AI_RATE_LIMIT_PER_MINUTE ?? 10);
|
||||
const hits = new Map<string, number[]>();
|
||||
|
||||
export function checkRateLimit(key: string): { ok: boolean; retryAfter: number } {
|
||||
if (!Number.isFinite(limit) || limit <= 0) return { ok: true, retryAfter: 0 };
|
||||
export function createRateLimiter(limit: number) {
|
||||
const hits = new Map<string, number[]>();
|
||||
|
||||
const now = Date.now();
|
||||
const recent = (hits.get(key) ?? []).filter((t) => now - t < windowMs);
|
||||
if (recent.length >= limit) {
|
||||
return function check(key: string): { ok: boolean; retryAfter: number } {
|
||||
if (!Number.isFinite(limit) || limit <= 0) return { ok: true, retryAfter: 0 };
|
||||
|
||||
const now = Date.now();
|
||||
const recent = (hits.get(key) ?? []).filter((t) => now - t < windowMs);
|
||||
if (recent.length >= limit) {
|
||||
hits.set(key, recent);
|
||||
return { ok: false, retryAfter: Math.ceil((windowMs - (now - recent[0])) / 1000) };
|
||||
}
|
||||
|
||||
recent.push(now);
|
||||
hits.set(key, recent);
|
||||
return { ok: false, retryAfter: Math.ceil((windowMs - (now - recent[0])) / 1000) };
|
||||
}
|
||||
|
||||
recent.push(now);
|
||||
hits.set(key, recent);
|
||||
|
||||
// keep the map from growing forever
|
||||
if (hits.size > 10_000) {
|
||||
for (const [k, v] of hits) if (v.every((t) => now - t >= windowMs)) hits.delete(k);
|
||||
}
|
||||
return { ok: true, retryAfter: 0 };
|
||||
// keep the map from growing forever
|
||||
if (hits.size > 10_000) {
|
||||
for (const [k, v] of hits) if (v.every((t) => now - t >= windowMs)) hits.delete(k);
|
||||
}
|
||||
return { ok: true, retryAfter: 0 };
|
||||
};
|
||||
}
|
||||
|
||||
export const checkRateLimit = createRateLimiter(Number(process.env.AI_RATE_LIMIT_PER_MINUTE ?? 10));
|
||||
|
||||
export function clientKey(req: Request) {
|
||||
return (
|
||||
req.headers.get('x-forwarded-for')?.split(',')[0]?.trim() ||
|
||||
|
||||
Reference in New Issue
Block a user