package com.saas.subscription.service;

import com.saas.shared.exception.BusinessException;
import com.saas.shared.exception.ErrorCode;
import com.stripe.Stripe;
import com.stripe.exception.StripeException;
import com.stripe.model.Customer;
import com.stripe.model.checkout.Session;
import com.stripe.param.CustomerCreateParams;
import com.stripe.param.checkout.SessionCreateParams;
import jakarta.annotation.PostConstruct;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

@Service
@RequiredArgsConstructor
@Slf4j
public class StripeService {

    @Value("${stripe.api.key}")
    private String stripeApiKey;

    @PostConstruct
    public void init() {
        Stripe.apiKey = stripeApiKey;
    }

    /**
     * Create a Stripe Customer for a tenant
     */
    public String createCustomer(String tenantId, String email, String name) {
        try {
            CustomerCreateParams params = CustomerCreateParams.builder()
                    .setEmail(email)
                    .setName(name)
                    .putMetadata("tenantId", tenantId)
                    .build();

            Customer customer = Customer.create(params);
            log.info("Created Stripe customer {} for tenant {}", customer.getId(), tenantId);
            return customer.getId();
        } catch (StripeException e) {
            log.error("Error creating Stripe customer", e);
            throw new BusinessException(ErrorCode.INTERNAL_ERROR, "Failed to create Stripe customer");
        }
    }

    /**
     * Create a Checkout Session for subscription
     */
    public String createCheckoutSession(String tenantId, String stripeCustomerId, String priceId, String successUrl,
            String cancelUrl) {
        try {
            SessionCreateParams params = SessionCreateParams.builder()
                    .setCustomer(stripeCustomerId)
                    .setMode(SessionCreateParams.Mode.SUBSCRIPTION)
                    .setSuccessUrl(successUrl)
                    .setCancelUrl(cancelUrl)
                    .addLineItem(SessionCreateParams.LineItem.builder()
                            .setPrice(priceId)
                            .setQuantity(1L)
                            .build())
                    .putMetadata("tenantId", tenantId)
                    .setAllowPromotionCodes(true)
                    .build();

            Session session = Session.create(params);
            return session.getUrl();
        } catch (StripeException e) {
            log.error("Error creating Stripe checkout session", e);
            throw new BusinessException(ErrorCode.INTERNAL_ERROR, "Failed to create checkout session");
        }
    }

    /**
     * Create a Customer Portal Session for managing subscription
     */
    public String createCustomerPortalSession(String stripeCustomerId, String returnUrl) {
        try {
            com.stripe.param.billingportal.SessionCreateParams params = com.stripe.param.billingportal.SessionCreateParams
                    .builder()
                    .setCustomer(stripeCustomerId)
                    .setReturnUrl(returnUrl)
                    .build();

            com.stripe.model.billingportal.Session session = com.stripe.model.billingportal.Session.create(params);
            return session.getUrl();
        } catch (StripeException e) {
            log.error("Error creating Stripe portal session", e);
            throw new BusinessException(ErrorCode.INTERNAL_ERROR, "Failed to create portal session");
        }
    }
}
