Files
NextChair/src/lib/security/request-ip.ts
T
2026-08-03 21:15:24 +01:00

23 lines
959 B
TypeScript

import { headers } from "next/headers";
/**
* Best-effort caller IP for rate-limiting Server Actions, which (unlike
* Route Handlers) never receive a `Request` object directly. Reads the
* headers a reverse proxy/hosting platform sets — `x-forwarded-for` first
* (its first entry is the original client, per the standard convention),
* falling back to `x-real-ip`. Returns a constant placeholder if neither
* is present (e.g. a direct connection with no proxy in front, or a test
* environment) — that collapses everyone onto one shared bucket rather
* than silently disabling the limit, which is the safer failure mode.
*/
export async function getRequestIp(): Promise<string> {
const headerList = await headers();
const forwardedFor = headerList.get("x-forwarded-for");
if (forwardedFor) return forwardedFor.split(",")[0]!.trim();
const realIp = headerList.get("x-real-ip");
if (realIp) return realIp.trim();
return "unknown";
}