import { Polar } from "@polar-sh/sdk";
import { validateEvent, WebhookVerificationError } from "@polar-sh/sdk/webhooks";
import { PlanService } from "../../services/plan.service.js";
let polarInstance = null;
function getPolar() {
  if (!polarInstance) {
    if (!process.env.POLAR_ACCESS_TOKEN) {
      throw new Error("POLAR_ACCESS_TOKEN is not configured");
    }
    polarInstance = new Polar({
      accessToken: process.env.POLAR_ACCESS_TOKEN
    });
  }
  return polarInstance;
}
class PolarGateway {
  async createCheckoutSession(params) {
    const { teamId, planSlug, billingPeriod, successUrl, cancelUrl, customerEmail } = params;
    const productId = PlanService.getPriceId(planSlug, billingPeriod);
    if (!productId) {
      throw new Error(`No product ID configured for ${planSlug} ${billingPeriod}`);
    }
    const checkoutParams = {
      products: [productId],
      successUrl,
      metadata: { teamId, planSlug, billingPeriod },
      ...customerEmail && { customerEmail },
      // Polar uses returnUrl for back navigation (equivalent to Stripe's cancel_url)
      ...cancelUrl && { returnUrl: cancelUrl }
    };
    const result = await getPolar().checkouts.create(checkoutParams);
    return {
      id: result.id,
      url: result.url ?? null
    };
  }
  async createOneTimeCheckout(params) {
    const { teamId, priceId, successUrl, cancelUrl, customerEmail, customerId, metadata } = params;
    const checkoutParams = {
      products: [priceId],
      successUrl,
      metadata: { teamId, ...metadata },
      allowTrial: false,
      // one-time purchases should never start a trial
      ...cancelUrl && { returnUrl: cancelUrl },
      ...customerEmail && { customerEmail },
      ...customerId && { customerId }
    };
    const result = await getPolar().checkouts.create(checkoutParams);
    return { id: result.id, url: result.url ?? null };
  }
  async createPortalSession(params) {
    const { customerId, returnUrl } = params;
    const result = await getPolar().customerSessions.create({
      customerId
    });
    return {
      url: result.customerPortalUrl
    };
  }
  verifyWebhookSignature(payload, signatureOrHeaders) {
    const webhookSecret = process.env.POLAR_WEBHOOK_SECRET;
    if (!webhookSecret) {
      throw new Error("POLAR_WEBHOOK_SECRET is not configured");
    }
    const headers = typeof signatureOrHeaders === "string" ? { "webhook-id": "", "webhook-timestamp": "", "webhook-signature": signatureOrHeaders } : signatureOrHeaders;
    const body = typeof payload === "string" ? payload : payload.toString("utf-8");
    try {
      const event = validateEvent(body, headers, webhookSecret);
      return {
        id: event.id || crypto.randomUUID(),
        type: event.type,
        data: event.data
      };
    } catch (error) {
      if (error instanceof WebhookVerificationError) {
        throw new Error(`Polar webhook verification failed: ${error.message}`);
      }
      throw error;
    }
  }
  async getCustomer(customerId) {
    const customer = await getPolar().customers.get({ id: customerId });
    return {
      id: customer.id,
      email: customer.email ?? null,
      name: customer.name ?? null
    };
  }
  async createCustomer(params) {
    const { email, name, metadata } = params;
    const customerParams = {
      email,
      ...name && { name },
      ...metadata && { metadata },
      // Add organization ID if available
      ...process.env.POLAR_ORGANIZATION_ID && {
        organizationId: process.env.POLAR_ORGANIZATION_ID
      }
    };
    const customer = await getPolar().customers.create(customerParams);
    return {
      id: customer.id,
      email: customer.email ?? null,
      name: customer.name ?? null
    };
  }
  async updateSubscriptionPlan(params) {
    const { subscriptionId, newPriceId } = params;
    const result = await getPolar().subscriptions.update({
      id: subscriptionId,
      subscriptionUpdate: {
        productId: newPriceId
      }
    });
    return {
      id: result.id,
      status: result.status,
      cancelAtPeriodEnd: result.cancelAtPeriodEnd ?? false
    };
  }
  async cancelSubscriptionAtPeriodEnd(subscriptionId) {
    const result = await getPolar().subscriptions.update({
      id: subscriptionId,
      subscriptionUpdate: {
        cancelAtPeriodEnd: true
      }
    });
    return {
      id: result.id,
      status: result.status,
      cancelAtPeriodEnd: true
    };
  }
  async cancelSubscriptionImmediately(subscriptionId) {
    const result = await getPolar().subscriptions.revoke({
      id: subscriptionId
    });
    return {
      id: result.id,
      status: result.status ?? "canceled",
      cancelAtPeriodEnd: false
    };
  }
  getProviderName() {
    return "Polar";
  }
  getResourceHintDomains() {
    return { preconnect: [], dnsPrefetch: [] };
  }
  getSubscriptionDashboardUrl(externalSubscriptionId) {
    if (!externalSubscriptionId) return null;
    return "https://polar.sh/dashboard/sales/subscriptions";
  }
  async reactivateSubscription(subscriptionId) {
    const result = await getPolar().subscriptions.update({
      id: subscriptionId,
      subscriptionUpdate: {
        cancelAtPeriodEnd: false
      }
    });
    return {
      id: result.id,
      status: result.status,
      cancelAtPeriodEnd: false
    };
  }
}
function getPolarInstance() {
  return getPolar();
}
export {
  PolarGateway,
  getPolarInstance
};
