export const DEFAULT_SESSION_RENEW_THRESHOLD_MS = 10 * 60 * 1000;
export const DEFAULT_SESSION_RENEW_THROTTLE_MS = 30 * 1000;
export const SESSION_EXPIRY_STORAGE_KEY = "baron_session_expiry_enabled";

type SessionExpiryReadableStorage = Pick<Storage, "getItem">;
type SessionExpiryWritableStorage = Pick<Storage, "setItem">;

export type SessionRenewDecisionParams = {
  expiresAtSec?: number | null;
  nowMs: number;
  isEnabled: boolean;
  isAuthenticated: boolean;
  isLoading: boolean;
  isRenewInFlight: boolean;
  lastAttemptAtMs: number;
  thresholdMs?: number;
  throttleMs?: number;
};

export type SessionExpiryPreferenceParams = {
  defaultEnabled?: boolean;
  storage?: SessionExpiryReadableStorage | null;
};

export type DevelopmentSessionRedirectParams = {
  appMode: string;
  defaultEnabled?: boolean;
  storage?: SessionExpiryReadableStorage | null;
};

function browserStorage() {
  if (typeof window === "undefined") {
    return null;
  }

  return window.localStorage;
}

export function readSessionExpiryEnabled({
  defaultEnabled = true,
  storage = browserStorage(),
}: SessionExpiryPreferenceParams = {}) {
  const stored = storage?.getItem(SESSION_EXPIRY_STORAGE_KEY) ?? null;
  return stored === null ? defaultEnabled : stored !== "false";
}

export function writeSessionExpiryEnabled(
  isEnabled: boolean,
  storage: SessionExpiryWritableStorage | null = browserStorage(),
) {
  storage?.setItem(SESSION_EXPIRY_STORAGE_KEY, String(isEnabled));
}

export function shouldSuppressDevelopmentSessionRedirect({
  appMode,
  defaultEnabled = appMode !== "development",
  storage = browserStorage(),
}: DevelopmentSessionRedirectParams) {
  return (
    appMode === "development" &&
    !readSessionExpiryEnabled({ defaultEnabled, storage })
  );
}

function hasRenewPreconditions({
  isAuthenticated,
  isLoading,
  isRenewInFlight,
}: SessionRenewDecisionParams) {
  return isAuthenticated && !isLoading && !isRenewInFlight;
}

function isRenewWindowOpen({
  expiresAtSec,
  nowMs,
  lastAttemptAtMs,
  thresholdMs = DEFAULT_SESSION_RENEW_THRESHOLD_MS,
  throttleMs = DEFAULT_SESSION_RENEW_THROTTLE_MS,
}: SessionRenewDecisionParams) {
  if (typeof expiresAtSec !== "number") {
    return false;
  }

  const remainingMs = expiresAtSec * 1000 - nowMs;
  if (remainingMs <= 0 || remainingMs > thresholdMs) {
    return false;
  }

  if (nowMs - lastAttemptAtMs < throttleMs) {
    return false;
  }

  return true;
}

export function shouldAttemptSlidingSessionRenew(
  params: SessionRenewDecisionParams,
) {
  if (!params.isEnabled || !hasRenewPreconditions(params)) {
    return false;
  }

  return isRenewWindowOpen(params);
}

export function shouldAttemptUnlimitedSessionRenew(
  params: SessionRenewDecisionParams,
) {
  if (params.isEnabled || !hasRenewPreconditions(params)) {
    return false;
  }

  return isRenewWindowOpen(params);
}
