import { router, publicProcedure, protectedProcedure, adminProcedure } from '../_core/trpc.ts';
import { paymentMethodsService, PaymentMethodType } from '../paymentMethodsService';
import { z } from 'zod';
import { TRPCError } from '@trpc/server';

export const paymentMethodsRouter = router({
  // Get all available payment methods
  getAvailableMethods: publicProcedure.query(async () => {
    return paymentMethodsService.getAvailableMethods();
  }),

  // Get specific payment method
  getPaymentMethod: publicProcedure
    .input(z.object({ type: z.enum(['square', 'paypal', 'google_pay', 'chime', 'cash_app', 'check', 'bitcoin']) }))
    .query(async ({ input }) => {
      const method = paymentMethodsService.getPaymentMethod(input.type as PaymentMethodType);
      if (!method) {
        throw new TRPCError({
          code: 'NOT_FOUND',
          message: 'Payment method not found',
        });
      }
      return method;
    }),

  // Process Square payment
  processSquarePayment: protectedProcedure
    .input(
      z.object({
        amount: z.number().min(0.5),
        sourceId: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processSquarePayment(
        ctx.user.id.toString(),
        input.amount,
        input.sourceId,
        input.metadata
      );
    }),

  // Process PayPal payment
  processPayPalPayment: protectedProcedure
    .input(
      z.object({
        amount: z.number().min(1),
        paypalOrderId: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processPayPalPayment(
        ctx.user.id.toString(),
        input.amount,
        input.paypalOrderId,
        input.metadata
      );
    }),

  // Process Google Pay payment
  processGooglePayPayment: protectedProcedure
    .input(
      z.object({
        amount: z.number().min(0.5),
        sourceId: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processGooglePayPayment(
        ctx.user.id.toString(),
        input.amount,
        input.sourceId,
        input.metadata
      );
    }),

  // Process Chime payment
  processChimePayment: protectedProcedure
    .input(
      z.object({
        amount: z.number().min(1),
        chimeAccountId: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processChimePayment(
        ctx.user.id.toString(),
        input.amount,
        input.chimeAccountId,
        input.metadata
      );
    }),

  // Process Cash App payment
  processCashAppPayment: protectedProcedure
    .input(
      z.object({
        amount: z.number().min(1),
        cashAppUserId: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processCashAppPayment(
        ctx.user.id.toString(),
        input.amount,
        input.cashAppUserId,
        input.metadata
      );
    }),

  // Process check payment
  processCheckPayment: protectedProcedure
    .input(
      z.object({
        amount: z.number().min(10),
        checkNumber: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processCheckPayment(
        ctx.user.id.toString(),
        input.amount,
        input.checkNumber,
        input.metadata
      );
    }),

  // Convert USD to Bitcoin
  convertUSDToBitcoin: publicProcedure
    .input(z.object({ usdAmount: z.number().min(0.0001) }))
    .query(async ({ input }) => {
      return paymentMethodsService.convertUSDToBitcoin(input.usdAmount);
    }),

  // Process Bitcoin payment
  processBitcoinPayment: protectedProcedure
    .input(
      z.object({
        usdAmount: z.number().min(0.0001),
        bitcoinAddress: z.string(),
        metadata: z.record(z.any()).optional(),
      })
    )
    .mutation(async ({ ctx, input }) => {
      return paymentMethodsService.processBitcoinPayment(
        ctx.user.id.toString(),
        input.usdAmount,
        input.bitcoinAddress,
        input.metadata
      );
    }),

  // Get user transaction history
  getUserTransactions: protectedProcedure
    .input(z.object({ limit: z.number().default(50) }))
    .query(async ({ ctx, input }) => {
      return paymentMethodsService.getUserTransactions(ctx.user.id.toString(), input.limit);
    }),

  // Get payment statistics (admin only)
  getPaymentStatistics: adminProcedure.query(async () => {
    return paymentMethodsService.getPaymentStatistics();
  }),
});
