import { Middleware } from "@lib/router.ts"; import log from "@shared/utils/logger.ts"; const requestCounts: Partial< Record > = {}; const MAX_REQUESTS_PER_WINDOW = 300; const RATE_LIMIT_WINDOW = 60000; const rateLimitMiddleware: Middleware = async (c, next) => { const hostnameOpt = c.hostname; if (hostnameOpt.isSome()) { const hostname = hostnameOpt.value; const clientCount = requestCounts[hostname]; const now = Date.now(); if (!clientCount || now - clientCount.lastReset > RATE_LIMIT_WINDOW) { requestCounts[hostname] = { count: 1, lastReset: now }; } else if (clientCount.count < MAX_REQUESTS_PER_WINDOW) { clientCount.count++; } else if (c.preferredType.isSome()) { log.info(`client ${hostname} is rate limeted`); switch (c.preferredType.value) { case "html": { return c.html("429 Too Many Requests", { status: 429, }); } case "json": { return c.json( { err: "429 Too Many Requests", }, { status: 429, }, ); } } } else { return new Response("429 Too Many Request", { status: 429, }); } } await next(); }; export default rateLimitMiddleware;