import { useEffect, useRef, useReducer, useEffectEvent } from "react";
import { 
    airwallexInit,
    airwallexManager,
    AirwallexCartNumberElementType,
    AirwallexCvcElementType,
    AirwallexExpiryDateElementType
} from "@/lib/Airwallex/airwallexInit";
import { AirwallexCardStateType } from "@/types/checkout/type";

interface EventCallback {
  focusCallback: (e: any) => void;
  blurCallback: (e: any) => void;
  changeCallback: (e: any) => void;
  readyCallback: (e: any) => void;

}

function airwallexCardReducer(state: AirwallexCardStateType, action: Partial<AirwallexCardStateType>) { 
    // 这里不需要action的type属性，因为这里只需要覆盖state
    const newState = Object.assign({}, {...state}, {...action});
    return {...newState};
}



export function useAirwallexCard(
  enabled: boolean, 
  mountId: { cardNumber: string; cvc: string; expiry: string; },
  // callback: EventCallback
) {

  const defaultAirwallexCardState: AirwallexCardStateType = {
      cardNumberReady: false,
      cvcReady: false,
      expiryReady: false,

      cardNumberValid: false,
      cvcValid: false,
      expiryValid: false,

      cardNumberErrorMsg: "",
      cvcErrorMsg: "",
      expiryErrorMsg: "",
  };
  const [airwallexCardState, airwallexCardDispatch] = useReducer(airwallexCardReducer, defaultAirwallexCardState);
  const readyAirwallexElement = useEffectEvent((event: any): void => {
      console.log('----------------------------onReady---------------------');
      const { type } = event.detail;
      if (type === 'cardNumber') {
          airwallexCardDispatch({
              cardNumberReady: true
          });
      }
      if (type === 'cvc') {
          airwallexCardDispatch({
              cvcReady: true
          });
      }
      if (type === 'expiry') {
          airwallexCardDispatch({
              expiryReady: true
          });
      }
  });


    const changeAirwallexElement = useEffectEvent((event: any) => {
        console.log('----------------------------onChange---------------------');
        const { type, complete, error } = event.detail;
        const msg = error?.message ?? '';
        if (type === 'cardNumber') {
            airwallexCardDispatch({
                cardNumberValid: complete,
                cardNumberErrorMsg: msg
            });
        }
        if (type === 'cvc') {
            airwallexCardDispatch({
                cvcValid: complete,
                cvcErrorMsg: msg
            });
        }
        if (type === 'expiry') {
            airwallexCardDispatch({
                expiryValid: complete,
                expiryErrorMsg: msg
            });
        }
    });

    const focusAirwallexElement = useEffectEvent((event: any) => {
        console.log('----------------------------onFocus---------------------');
        const { type } = event.detail;
        if (type === 'cardNumber') {
            airwallexCardDispatch({
                cardNumberErrorMsg: ''
            });
        }
        if (type === 'cvc') {
            airwallexCardDispatch({
                cvcErrorMsg: ''
            });
        }
        if (type === 'expiry') {
            airwallexCardDispatch({
                expiryErrorMsg: ''
            });
        }
    });

    const blurAirwallexElement = useEffectEvent((event: any) => {
        console.log('----------------------------onBlur---------------------');
        const { type, error } = event.detail;
        const msg = error?.message ?? JSON.stringify(error);
        if (type === 'cardNumber') {
            airwallexCardDispatch({
                cardNumberErrorMsg: msg,
            });
        }
        if (type === 'cvc') {
            airwallexCardDispatch({
                cvcErrorMsg: msg,
            });
        }
        if (type === 'expiry') {
            airwallexCardDispatch({
                expiryErrorMsg: msg,
            });
        }
    });






  const mountedRef = useRef(false);
  const elementRef = useRef<{
    cardNumber?: AirwallexCartNumberElementType;
    cvc?: AirwallexCvcElementType;
    expiry?: AirwallexExpiryDateElementType;
  }>({});

  useEffect(() => {
    if (!enabled) return;

    let destroyed = false;

    const init = async () => {
      await airwallexInit();
    //   await airwallexManager.init();

      const els = await airwallexManager.createElements();
      elementRef.current = els;

      if (destroyed) return;

      airwallexManager.mount({
        cardNumber: mountId.cardNumber,
        cvc: mountId.cvc,
        expiry: mountId.expiry
      });

      mountedRef.current = true;

      // register events ONLY ONCE
      bindEvents(els,{
        focusCallback: focusAirwallexElement,
        blurCallback: blurAirwallexElement, 
        changeCallback: changeAirwallexElement, 
        readyCallback: readyAirwallexElement
      });
    };

    init();

    return () => {
      destroyed = true;
      if (mountedRef.current) {
        airwallexManager.unmount();// 解除挂载
        mountedRef.current = false;
      }
    };
  }, [enabled]);



  return {
      getCardElements:() => elementRef.current,
      airwallexCardState: airwallexCardState
  };

}

function bindEvents(els: any,callback:EventCallback) {
  const { cardNumber, cvc, expiry } = els;
  const {focusCallback,blurCallback, changeCallback, readyCallback} = callback;

  airwallexManager.on(cardNumber,"focus", focusCallback);
  airwallexManager.on(cardNumber,"blur", blurCallback);
  airwallexManager.on(cardNumber,"change", changeCallback);
  airwallexManager.on(cardNumber,"ready", readyCallback);

  airwallexManager.on(cvc,"focus", focusCallback);
  airwallexManager.on(cvc,"blur", blurCallback);
  airwallexManager.on(cvc,"change", changeCallback);
  airwallexManager.on(cvc,"ready", readyCallback);

  airwallexManager.on(expiry,"focus", focusCallback);
  airwallexManager.on(expiry,"blur", blurCallback);
  airwallexManager.on(expiry,"change", changeCallback);
  airwallexManager.on(expiry,"ready", readyCallback);

  // ⚠️ 关键：绑定只发生一次（manager内部防重复）
//   cardNumber.on("focus", focusCallback);
//   cardNumber.on("blur", blurCallback);
//   cardNumber.on("change", changeCallback);
//   cardNumber.on("ready", readyCallback);


//   cvc.on("focus", focusCallback);
//   cvc.on("blur", blurCallback);
//   cvc.on("change", changeCallback);
//   cvc.on("ready", readyCallback);

//   expiry.on("focus", focusCallback);
//   expiry.on("blur", blurCallback);
//   expiry.on("change", changeCallback);
//   expiry.on("ready", readyCallback);
}