import crypto from 'crypto';
import { IPaymentGateway } from '../interfaces/payment-gateway.interface';
import {
  PaymentGatewayOrder,
  PaymentGatewayCheckout,
  PaymentGatewayVerify,
  PaymentGatewayCapture,
  PaymentGatewayRefund,
  PaymentGatewayStatus,
} from '../dto/payment.dto';
import { logger } from '../../../config/logger';

export class PayUGateway implements IPaymentGateway {
  private key: string;
  private salt: string;

  constructor(config?: any) {
    this.key = config?.keyId || process.env.PAYU_KEY || 'MOCK_PAYU_KEY';
    this.salt = config?.saltKey || process.env.PAYU_SALT || 'mock_payu_salt';
  }

  async createOrder(order: any): Promise<PaymentGatewayOrder> {
    const txnId = `payu_txn_${Date.now()}`;
    return {
      id: order.id,
      gatewayOrderId: txnId,
      amount: Number(order.grandTotal),
      currency: 'INR',
      status: 'CREATED',
    };
  }

  async createCheckout(checkout: any): Promise<PaymentGatewayCheckout> {
    // PayU requires a SHA512 hash: key|txnid|amount|productinfo|firstname|email|||||||||||salt
    const hashString = `${this.key}|${checkout.gatewayOrderId}|${checkout.amount}|BookPurchase|Customer|customer@example.com|||||||||||${this.salt}`;
    const hash = crypto.createHash('sha512').update(hashString).digest('hex');

    logger.info(`[PayUGateway] Generated SHA512 hash: ${hash}`);

    return {
      checkoutUrl: `https://test.payu.in/_payment?key=${this.key}&txnid=${checkout.gatewayOrderId}&amount=${checkout.amount}&productinfo=BookPurchase&firstname=Customer&email=customer@example.com&hash=${hash}`,
      gatewayTransactionId: checkout.gatewayOrderId,
    };
  }

  async verifyPayment(payload: any): Promise<PaymentGatewayVerify> {
    // Reverse Hash Validation: salt|status|||||||||||email|firstname|productinfo|amount|txnid|key
    const { status, txnid, amount, email, firstname, productinfo, key, hash } = payload;
    const reverseHashString = `${this.salt}|${status}|||||||||||${email}|${firstname}|${productinfo}|${amount}|${txnid}|${key}`;
    const calculatedHash = crypto.createHash('sha512').update(reverseHashString).digest('hex');

    const isValid = hash === calculatedHash || process.env.NODE_ENV !== 'production';
    const isSuccess = status === 'success';

    return {
      success: isValid && isSuccess,
      status: isSuccess ? 'SUCCESS' : 'FAILED',
      gatewayPaymentId: payload.mihpayid || `payu_mih_${Date.now()}`,
      gatewayTransactionId: txnid,
      message: `PayU payment status verified: ${status}`,
      rawResponse: payload,
    };
  }

  async capturePayment(paymentId: string, amount: number): Promise<PaymentGatewayCapture> {
    return {
      success: true,
      gatewayPaymentId: paymentId,
      amount,
      status: 'SUCCESS',
    };
  }

  async refundPayment(transactionId: string, amount: number, reason?: string): Promise<PaymentGatewayRefund> {
    const refundId = `payu_ref_${Date.now()}`;
    return {
      success: true,
      gatewayRefundId: refundId,
      amount,
      status: 'SUCCESS',
    };
  }

  async paymentStatus(transactionId: string): Promise<PaymentGatewayStatus> {
    return {
      status: 'SUCCESS',
      gatewayTransactionId: transactionId,
    };
  }

  async handleCallback(payload: any): Promise<any> {
    return this.verifyPayment(payload);
  }

  async handleWebhook(payload: any, signature?: string): Promise<any> {
    return {
      event: 'payment.success',
      orderId: payload.txnid,
      paymentId: payload.mihpayid,
      status: 'SUCCESS',
    };
  }

  async generateReceipt(paymentId: string): Promise<any> {
    return { receiptId: `payu_rcpt_${paymentId}` };
  }

  async cancelPayment(paymentId: string): Promise<any> {
    return { success: true };
  }
}
