import type {
  NotificationSettingApiData,
  NotificationSettingApiResponse,
  UpdateNotificationSettingPayload,
} from "../types/notification-setting-types";

const API_BASE_URL =
  process.env.NEXT_PUBLIC_API_URL ??
  "http://localhost:3001/api/v1";

type ApiErrorResponse = {
  success?: boolean;
  statusCode?: number;
  message?: string | string[];
  error?: string;
};

async function parseErrorResponse(
  response: Response,
): Promise<string> {
  try {
    const errorData =
      (await response.json()) as ApiErrorResponse;

    if (Array.isArray(errorData.message)) {
      return errorData.message.join(", ");
    }

    if (typeof errorData.message === "string") {
      return errorData.message;
    }

    if (typeof errorData.error === "string") {
      return errorData.error;
    }
  } catch {
    // Response មិនមែន JSON
  }

  return (
    response.statusText ||
    `Request failed with status ${response.status}`
  );
}

async function apiRequest<T>(
  path: string,
  options: RequestInit = {},
): Promise<T> {
  const response = await fetch(
    `${API_BASE_URL}${path}`,
    {
      ...options,

      headers: {
        Accept: "application/json",
        "Content-Type": "application/json",
        ...options.headers,
      },

      /*
       * Backend login របស់អ្នករក្សា authentication
       * ក្នុង HttpOnly Cookie។
       */
      credentials: "include",

      cache: "no-store",
    },
  );

  if (!response.ok) {
    const message = await parseErrorResponse(
      response,
    );

    throw new Error(message);
  }

  return response.json() as Promise<T>;
}

export async function getNotificationSetting(): Promise<NotificationSettingApiData> {
  const response =
    await apiRequest<NotificationSettingApiResponse>(
      "/notification-settings/me",
      {
        method: "GET",
      },
    );

  if (!response.success || !response.data) {
    throw new Error(
      response.message ||
        "Failed to load notification settings.",
    );
  }

  return response.data;
}

export async function updateNotificationSetting(
  payload: UpdateNotificationSettingPayload,
): Promise<NotificationSettingApiData> {
  const response =
    await apiRequest<NotificationSettingApiResponse>(
      "/notification-settings/me",
      {
        method: "PATCH",
        body: JSON.stringify(payload),
      },
    );

  if (!response.success || !response.data) {
    throw new Error(
      response.message ||
        "Failed to update notification settings.",
    );
  }

  return response.data;
}

export const notificationSettingService = {
  getMySetting: getNotificationSetting,
  updateMySetting: updateNotificationSetting,
};