PayPalService.java 5.67 KB
package com.ecommerce.payment.service;

import com.ecommerce.payment.model.Payment;
import com.ecommerce.payment.model.Refund;
import com.ecommerce.payment.model.dto.PaymentRequest;
import com.ecommerce.payment.model.dto.PaymentResponse;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import java.math.BigDecimal;
import java.util.HashMap;
import java.util.Map;

@Slf4j
@Service
public class PayPalService {
    
    @Value("${paypal.client-id:default-client-id}")
    private String paypalClientId;
    
    @Value("${paypal.client-secret:default-client-secret}")
    private String paypalClientSecret;
    
    @Value("${paypal.mode:sandbox}")
    private String paypalMode;
    
    public PaymentResponse createPayment(Payment payment, PaymentRequest request) {
        try {
            // In production, integrate with PayPal SDK
            // For demo, simulate PayPal payment creation
            
            String gatewayPaymentId = "PAYPAL_" + System.currentTimeMillis();
            String approvalUrl = "https://www.sandbox.paypal.com/checkoutnow?token=" + gatewayPaymentId;
            
            PaymentResponse response = new PaymentResponse();
            response.setPaymentId(payment.getPaymentId());
            response.setStatus("PROCESSING");
            response.setGatewayPaymentId(gatewayPaymentId);
            response.setRedirectUrl(approvalUrl);
            response.setRequiresAction(true);
            
            log.info("PayPal payment created: {}", gatewayPaymentId);
            return response;
            
        } catch (Exception e) {
            log.error("PayPal payment creation failed: {}", e.getMessage());
            throw new RuntimeException("PayPal payment failed: " + e.getMessage());
        }
    }
    
    public PaymentResponse confirmPayment(Payment payment) {
        try {
            // In production, integrate with PayPal SDK to confirm payment
            // For demo, simulate PayPal payment confirmation
            
            boolean success = Math.random() > 0.1; // 90% success rate
            
            PaymentResponse response = new PaymentResponse();
            response.setPaymentId(payment.getPaymentId());
            response.setGatewayPaymentId(payment.getGatewayPaymentId());
            
            if (success) {
                response.setStatus("SUCCEEDED");
            } else {
                response.setStatus("FAILED");
                response.setFailureReason("PayPal payment failed");
                response.setFailureCode("PAYMENT_DECLINED");
            }
            
            log.info("PayPal payment confirmed: {} -> {}", payment.getGatewayPaymentId(), response.getStatus());
            return response;
            
        } catch (Exception e) {
            log.error("PayPal payment confirmation failed: {}", e.getMessage());
            throw new RuntimeException("PayPal payment confirmation failed: " + e.getMessage());
        }
    }
    
    public Map<String, Object> createRefund(Refund refund) {
        try {
            // In production, integrate with PayPal SDK for refunds
            // For demo, simulate PayPal refund
            
            boolean success = Math.random() > 0.05; // 95% success rate
            String gatewayRefundId = "PAYPAL_REF_" + System.currentTimeMillis();
            
            Map<String, Object> result = new HashMap<>();
            result.put("success", success);
            result.put("gatewayRefundId", gatewayRefundId);
            
            log.info("PayPal refund created: {}", gatewayRefundId);
            return result;
            
        } catch (Exception e) {
            log.error("PayPal refund creation failed: {}", e.getMessage());
            
            Map<String, Object> result = new HashMap<>();
            result.put("success", false);
            result.put("error", e.getMessage());
            return result;
        }
    }
    
    public boolean verifyWebhookSignature(String payload, String signature) {
        // In production, verify PayPal webhook signature
        // For demo purposes, we'll skip verification
        return true;
    }
    
    public void handleWebhookEvent(Map<String, Object> event) {
        String eventType = (String) event.get("event_type");
        Map<String, Object> resource = (Map<String, Object>) event.get("resource");
        
        log.info("Processing PayPal webhook event: {}", eventType);
        
        switch (eventType) {
            case "PAYMENT.CAPTURE.COMPLETED":
                handlePaymentCompleted(resource);
                break;
            case "PAYMENT.CAPTURE.DENIED":
                handlePaymentDenied(resource);
                break;
            case "PAYMENT.CAPTURE.REFUNDED":
                handleRefundCompleted(resource);
                break;
            default:
                log.debug("Unhandled PayPal event type: {}", eventType);
        }
    }
    
    private void handlePaymentCompleted(Map<String, Object> resource) {
        String gatewayPaymentId = (String) resource.get("id");
        // Update payment status in database
        log.info("PayPal payment completed: {}", gatewayPaymentId);
    }
    
    private void handlePaymentDenied(Map<String, Object> resource) {
        String gatewayPaymentId = (String) resource.get("id");
        // Update payment status in database
        log.info("PayPal payment denied: {}", gatewayPaymentId);
    }
    
    private void handleRefundCompleted(Map<String, Object> resource) {
        String gatewayRefundId = (String) resource.get("id");
        // Update refund status in database
        log.info("PayPal refund completed: {}", gatewayRefundId);
    }
}