import { URL_CONSTANTS } from "@/constants/URLS";
import { API_BASE_URL } from "@/constants/apiConfig";
import { client } from "../utils/api";

const P = URL_CONSTANTS.PAYMENTS;

/** Payment methods supported by the central payment microservice. */
export type PaymentMethod =
  | "TELEBIRR"
  | "CBE_BIRR"
  | "EBIRR"
  | "WAAFI"
  | "CARD"
  | "DMONEY"
  | "CAC_BANK";

export type PaymentPlatform = "web" | "mobile";

export interface InitiatePaymentPayload {
  bookingId: string;
  method: PaymentMethod;
  platform?: PaymentPlatform;
  payerAccount?: string;
  returnUrl?: string;
  failureUrl?: string;
}

export interface ClientAction {
  type: "REDIRECT" | "LAUNCH_APP" | "COLLECT_OTP";
  url?: string;
  appId?: string;
  receiveCode?: string;
  shortCode?: string;
  providerOrderId?: string;
  message?: string;
}

export interface InitiateResponse {
  intentId: string;
  status: string;
  clientAction?: ClientAction;
  merchantOrderId?: string;
}

export interface IntentStatus extends InitiateResponse {
  paidAt?: string;
  failureCode?: string;
  failureMessage?: string;
}

/**
 * Builds the absolute URL for the public browser-checkout page, which
 * (re)initiates the payment and auto-redirects to the provider's checkout.
 * Used as the "pay" step after a successful `initiate`.
 */
function buildCheckoutUrl(payload: {
  bookingId: string;
  method: PaymentMethod;
  platform?: PaymentPlatform;
}): string {
  const base = API_BASE_URL.replace(/\/$/, "");
  const params = new URLSearchParams({
    bookingId: payload.bookingId,
    method: payload.method,
    platform: payload.platform ?? "web",
  });
  return `${base}${P.CHECKOUT}?${params.toString()}`;
}

export const paymentsService = {
  initiate: async (
    payload: InitiatePaymentPayload,
  ): Promise<InitiateResponse> => {
    const { data } = await client.post(P.INITIATE, {
      platform: "web",
      ...payload,
    });
    return data.data ?? data;
  },

  getIntent: async (bookingId: string): Promise<IntentStatus> => {
    const { data } = await client.get(P.INTENT(bookingId));
    return data.data ?? data;
  },

  checkoutUrl: buildCheckoutUrl,
};
