<?php

namespace App\Services;

use Illuminate\Support\Facades\Http;
use Exception;

class PhonePeService
{
    protected $merchantId;
    protected $saltKey;
    protected $saltIndex;
    protected $apiUrl;

    public function __construct()
    {
        $this->merchantId = config('services.phonepe.merchant_id');
        $this->saltKey = config('services.phonepe.salt_key');
        $this->saltIndex = config('services.phonepe.salt_index', 1);
        $this->apiUrl = config('services.phonepe.api_url', 'https://api.phonepe.com/apis/hermes');
    }

    /**
     * Create a payment request
     */
    public function createPayment($amount, $transactionId, $userId, $redirectUrl, $callbackUrl)
    {
        try {
            $payload = [
                'merchantId' => $this->merchantId,
                'merchantTransactionId' => $transactionId,
                'merchantUserId' => $userId,
                'amount' => $amount * 100, // Amount in paise
                'redirectUrl' => $redirectUrl,
                'redirectMode' => 'POST',
                'callbackUrl' => $callbackUrl,
                'mobileNumber' => '',
                'paymentInstrument' => [
                    'type' => 'PAY_PAGE'
                ]
            ];

            $base64Payload = base64_encode(json_encode($payload));
            $checksum = hash('sha256', $base64Payload . '/pg/v1/pay' . $this->saltKey) . '###' . $this->saltIndex;

            $response = Http::withHeaders([
                'Content-Type' => 'application/json',
                'X-VERIFY' => $checksum,
            ])->post($this->apiUrl . '/pg/v1/pay', [
                'request' => $base64Payload
            ]);

            $data = $response->json();

            if ($data['success'] ?? false) {
                return [
                    'success' => true,
                    'payment_url' => $data['data']['instrumentResponse']['redirectInfo']['url'],
                    'transaction_id' => $transactionId,
                ];
            }

            throw new Exception($data['message'] ?? 'Payment creation failed');
        } catch (Exception $e) {
            throw new Exception('PhonePe payment creation failed: ' . $e->getMessage());
        }
    }

    /**
     * Check payment status
     */
    public function checkPaymentStatus($transactionId)
    {
        try {
            $checksum = hash('sha256', "/pg/v1/status/{$this->merchantId}/{$transactionId}" . $this->saltKey) . '###' . $this->saltIndex;

            $response = Http::withHeaders([
                'Content-Type' => 'application/json',
                'X-VERIFY' => $checksum,
                'X-MERCHANT-ID' => $this->merchantId,
            ])->get($this->apiUrl . "/pg/v1/status/{$this->merchantId}/{$transactionId}");

            $data = $response->json();

            if ($data['success'] ?? false) {
                return [
                    'success' => true,
                    'status' => $data['data']['state'],
                    'amount' => ($data['data']['amount'] ?? 0) / 100,
                    'transaction_id' => $data['data']['merchantTransactionId'],
                    'payment_instrument' => $data['data']['paymentInstrument'] ?? null,
                ];
            }

            return [
                'success' => false,
                'message' => $data['message'] ?? 'Status check failed',
            ];
        } catch (Exception $e) {
            throw new Exception('Status check failed: ' . $e->getMessage());
        }
    }

    /**
     * Verify callback
     */
    public function verifyCallback($base64Response, $receivedChecksum)
    {
        try {
            $calculatedChecksum = hash('sha256', $base64Response . $this->saltKey) . '###' . $this->saltIndex;
            return $calculatedChecksum === $receivedChecksum;
        } catch (Exception $e) {
            return false;
        }
    }

    /**
     * Process refund
     */
    public function processRefund($transactionId, $originalTransactionId, $amount)
    {
        try {
            $payload = [
                'merchantId' => $this->merchantId,
                'merchantTransactionId' => $transactionId,
                'originalTransactionId' => $originalTransactionId,
                'amount' => $amount * 100,
                'callbackUrl' => config('app.url') . '/api/phonepe/refund-callback',
            ];

            $base64Payload = base64_encode(json_encode($payload));
            $checksum = hash('sha256', $base64Payload . '/pg/v1/refund' . $this->saltKey) . '###' . $this->saltIndex;

            $response = Http::withHeaders([
                'Content-Type' => 'application/json',
                'X-VERIFY' => $checksum,
            ])->post($this->apiUrl . '/pg/v1/refund', [
                'request' => $base64Payload
            ]);

            $data = $response->json();

            if ($data['success'] ?? false) {
                return [
                    'success' => true,
                    'transaction_id' => $transactionId,
                    'status' => $data['data']['state'] ?? 'PENDING',
                ];
            }

            throw new Exception($data['message'] ?? 'Refund failed');
        } catch (Exception $e) {
            throw new Exception('PhonePe refund failed: ' . $e->getMessage());
        }
    }
}
