import { z } from 'zod';
import { StripeClient } from '../clients/stripe.js';
import { Dispute } from '../types/index.js';

const metadataSchema = z.record(z.string()).optional().describe('Set of key-value pairs for storing additional information');

export default [
  {
    name: 'stripe_list_disputes',
    description: 'List all disputes with optional filtering and pagination',
    inputSchema: z.object({
      limit: z.number().min(1).max(100).optional().describe('Number of disputes to return (1-100)'),
      starting_after: z.string().optional().describe('Cursor for pagination'),
      ending_before: z.string().optional().describe('Cursor for pagination'),
      charge: z.string().optional().describe('Filter by charge ID'),
      payment_intent: z.string().optional().describe('Filter by payment intent ID'),
      created: z.union([
        z.number(),
        z.object({
          gt: z.number().optional(),
          gte: z.number().optional(),
          lt: z.number().optional(),
          lte: z.number().optional(),
        })
      ]).optional().describe('Filter by creation timestamp or range'),
    }),
    handler: async (client: StripeClient, args: any) => {
      return await client.list<Dispute>('/disputes', args);
    }
  },
  {
    name: 'stripe_get_dispute',
    description: 'Retrieve a specific dispute by ID',
    inputSchema: z.object({
      dispute_id: z.string().describe('The ID of the dispute to retrieve'),
      expand: z.array(z.string()).optional().describe('Fields to expand (e.g., ["charge"])')
    }),
    handler: async (client: StripeClient, args: any) => {
      const { dispute_id, expand } = args;
      const params = expand ? { expand } : undefined;
      return await client.retrieve<Dispute>('/disputes', dispute_id, params);
    }
  },
  {
    name: 'stripe_update_dispute',
    description: 'Update a dispute with evidence',
    inputSchema: z.object({
      dispute_id: z.string().describe('The ID of the dispute to update'),
      evidence: z.object({
        access_activity_log: z.string().optional().describe('Activity logs showing customer usage'),
        billing_address: z.string().optional().describe('Billing address'),
        cancellation_policy: z.string().optional().describe('Cancellation policy file ID'),
        cancellation_policy_disclosure: z.string().optional(),
        cancellation_rebuttal: z.string().optional().describe('Explanation of cancellation policy'),
        customer_communication: z.string().optional().describe('Communication file ID'),
        customer_email_address: z.string().optional(),
        customer_name: z.string().optional(),
        customer_purchase_ip: z.string().optional().describe('Customer IP at time of purchase'),
        customer_signature: z.string().optional().describe('Signature file ID'),
        duplicate_charge_documentation: z.string().optional(),
        duplicate_charge_explanation: z.string().optional(),
        duplicate_charge_id: z.string().optional().describe('ID of the original, non-disputed charge'),
        product_description: z.string().optional(),
        receipt: z.string().optional().describe('Receipt file ID'),
        refund_policy: z.string().optional().describe('Refund policy file ID'),
        refund_policy_disclosure: z.string().optional(),
        refund_refusal_explanation: z.string().optional(),
        service_date: z.string().optional().describe('Date service was provided'),
        service_documentation: z.string().optional().describe('Documentation file ID'),
        shipping_address: z.string().optional(),
        shipping_carrier: z.string().optional(),
        shipping_date: z.string().optional(),
        shipping_documentation: z.string().optional().describe('Proof of shipping file ID'),
        shipping_tracking_number: z.string().optional(),
        uncategorized_file: z.string().optional().describe('Additional file ID'),
        uncategorized_text: z.string().optional().describe('Additional text evidence')
      }).optional().describe('Evidence to support your case'),
      metadata: metadataSchema,
      submit: z.boolean().optional().describe('Whether to submit the dispute evidence (default false)')
    }),
    handler: async (client: StripeClient, args: any) => {
      const { dispute_id, ...data } = args;
      return await client.update<Dispute>('/disputes', dispute_id, data);
    }
  },
  {
    name: 'stripe_close_dispute',
    description: 'Close a dispute (accepting the dispute)',
    inputSchema: z.object({
      dispute_id: z.string().describe('The ID of the dispute to close')
    }),
    handler: async (client: StripeClient, args: any) => {
      return await client.post<Dispute>(`/disputes/${args.dispute_id}/close`, {});
    }
  }
];
