import { BN } from '@ocap/util';

import { DidnamesAdapter } from './didnames-adapter';
import { LauncherAdapter } from './launcher-adapter';
import { VendorAdapter } from './types';
import { ProductVendor } from '../../../store/models';

export function calculateVendorCommission(
  totalAmount: string,
  commissionRate: number,
  commissionType: 'percentage' | 'fixed_amount',
  itemAmount?: string
): string {
  const amount = itemAmount || totalAmount || '0';

  if (commissionType === 'percentage') {
    return new BN(amount)
      .mul(new BN(commissionRate || 0))
      .div(new BN(100))
      .toString();
  }
  return new BN(commissionRate).toString();
}

export class VendorAdapterFactory {
  static async create(vendorKey: string): Promise<VendorAdapter> {
    const vendorConfig = await ProductVendor.findOne({ where: { vendor_key: vendorKey } });
    if (!vendorConfig) {
      throw new Error(`Vendor not found: ${vendorKey}`);
    }

    switch (vendorConfig.vendor_type) {
      case 'launcher':
        return new LauncherAdapter(vendorConfig);
      case 'didnames':
        return new DidnamesAdapter(vendorConfig);
      default:
        throw new Error(`Unsupported vendor: ${vendorConfig.vendor_type}`);
    }
  }

  /**
   * Create coordinated adapters for domain binding workflow
   * @param vendorKeys Array of vendor keys in execution order
   */
  static async createCoordinated(vendorKeys: string[]): Promise<{
    didnamesAdapter?: DidnamesAdapter;
    launcherAdapter?: LauncherAdapter;
  }> {
    const adapters: { [key: string]: VendorAdapter } = {};

    for (const vendorKey of vendorKeys) {
      adapters[vendorKey] = await this.create(vendorKey); // eslint-disable-line no-await-in-loop
    }

    return {
      didnamesAdapter: adapters.didnames as DidnamesAdapter,
      launcherAdapter: adapters.launcher as LauncherAdapter,
    };
  }

  static getSupportedVendors(): string[] {
    return ['launcher', 'didnames'];
  }

  static isSupported(vendorKey: string): boolean {
    return this.getSupportedVendors().includes(vendorKey);
  }
}
