export const ROLE_SUPER_ADMIN = "super_admin";
export const ROLE_USER = "user";

export type AdminRole = typeof ROLE_SUPER_ADMIN | typeof ROLE_USER;

export type TenantAccessSubject = {
  id?: string | null;
  role?: string | null;
  tenantId?: string | null;
  tenantSlug?: string | null;
  tenant?: {
    id?: string | null;
    slug?: string | null;
  } | null;
  manageableTenants?: Array<{
    id?: string | null;
    slug?: string | null;
  }> | null;
};

export function normalizeAdminRole(role?: string | null): AdminRole {
  const normalized = role?.trim().toLowerCase() ?? "";

  switch (normalized) {
    case ROLE_SUPER_ADMIN:
    case "superadmin":
    case "super-admin":
      return ROLE_SUPER_ADMIN;
    case ROLE_USER:
    case "tenant_admin":
    case "tenantadmin":
    case "tenant-admin":
    case "admin":
    case "rp_admin":
    case "rpadmin":
    case "rp-admin":
    case "tenant_member":
    case "member":
      return ROLE_USER;
    default:
      return ROLE_USER;
  }
}

export function isSuperAdminRole(role?: string | null) {
  return normalizeAdminRole(role) === ROLE_SUPER_ADMIN;
}

function normalizeTenantAccessKey(value?: string | null) {
  const normalized = value?.trim().toLowerCase();
  return normalized ? normalized : null;
}

export function getManageableTenantAccessKeys(
  profile?: TenantAccessSubject | null,
) {
  const keys = new Set<string>();
  for (const tenant of profile?.manageableTenants ?? []) {
    const id = normalizeTenantAccessKey(tenant.id);
    const slug = normalizeTenantAccessKey(tenant.slug);
    if (id) keys.add(id);
    if (slug) keys.add(slug);
  }
  return keys;
}

export function canManageTenantScopedUsers(
  profile?: TenantAccessSubject | null,
) {
  return (
    isSuperAdminRole(profile?.role) ||
    getManageableTenantAccessKeys(profile).size > 0
  );
}

export function canManageUserInTenantScope({
  profile,
  user,
}: {
  profile?: TenantAccessSubject | null;
  user?: TenantAccessSubject | null;
}) {
  if (isSuperAdminRole(profile?.role)) {
    return true;
  }

  if (profile?.id && user?.id && profile.id === user.id) {
    return true;
  }

  const manageableKeys = getManageableTenantAccessKeys(profile);
  if (manageableKeys.size === 0) {
    return false;
  }

  const userTenantKeys = [
    normalizeTenantAccessKey(user?.tenantId),
    normalizeTenantAccessKey(user?.tenantSlug),
    normalizeTenantAccessKey(user?.tenant?.id),
    normalizeTenantAccessKey(user?.tenant?.slug),
  ];

  return userTenantKeys.some((key) => key !== null && manageableKeys.has(key));
}
