import { validateSession, hasPermission, type User } from "./db";

const COOKIE_NAME = "blastoise_session";

export function getSessionToken(req: Request): string | null {
  const cookie = req.headers.get("cookie");
  if (!cookie) return null;
  
  const match = cookie.match(new RegExp(`${COOKIE_NAME}=([^;]+)`));
  return match ? match[1] : null;
}

export function getClientInfo(req: Request, server?: { requestIP?: (req: Request) => { address: string } | null }): { userAgent: string; ipAddress: string } {
  const userAgent = req.headers.get("user-agent") ?? "unknown";
  const ipAddress = req.headers.get("x-forwarded-for")?.split(",")[0]?.trim() 
    ?? req.headers.get("x-real-ip") 
    ?? server?.requestIP?.(req)?.address
    ?? "unknown";
  return { userAgent, ipAddress };
}

export function getRequestMeta(req: Request, server?: { requestIP?: (req: Request) => { address: string } | null }): { userAgent?: string; ipAddress?: string } {
  const userAgent = req.headers.get("user-agent") ?? undefined;
  const ipAddress = req.headers.get("x-forwarded-for")?.split(",")[0]?.trim() 
    ?? req.headers.get("x-real-ip") 
    ?? server?.requestIP?.(req)?.address
    ?? undefined;
  return { userAgent, ipAddress };
}

export function getUser(req: Request, server?: { requestIP?: (req: Request) => { address: string } | null }): User | null {
  const token = getSessionToken(req);
  if (!token) return null;
  const { userAgent, ipAddress } = getRequestMeta(req, server);
  return validateSession(token, userAgent, ipAddress);
}

export function requireUser(req: Request, server?: { requestIP?: (req: Request) => { address: string } | null }): User {
  const user = getUser(req, server);
  if (!user) {
    throw new Response("Unauthorized", { status: 401 });
  }
  return user;
}

export function requirePermission(
  req: Request,
  resourceType: string,
  resourceId: string | null,
  permission: string,
  server?: { requestIP?: (req: Request) => { address: string } | null }
): User {
  const user = requireUser(req, server);
  if (!user.is_admin && !hasPermission(user.id, resourceType, resourceId, permission)) {
    throw new Response("Forbidden", { status: 403 });
  }
  return user;
}

export function setSessionCookie(token: string): string {
  const maxAge = 7 * 24 * 60 * 60; // 7 days
  return `${COOKIE_NAME}=${token}; Path=/; HttpOnly; SameSite=Strict; Max-Age=${maxAge}`;
}

export function clearSessionCookie(): string {
  return `${COOKIE_NAME}=; Path=/; HttpOnly; SameSite=Strict; Max-Age=0`;
}
