import { MigrationInterface, QueryRunner } from 'typeorm';

/**
 * Phase D §12d D2.5 — extend payment_collections to support Agent
 * (trip-source) collections alongside the existing Customer flow.
 *
 * Changes:
 *   - Add `party_type` ∈ {'CUSTOMER','SOURCE'}; default 'CUSTOMER' so
 *     every existing row keeps its current semantics with no
 *     backfill needed.
 *   - Add `source_id` FK to trip_sources for SOURCE-mode receipts.
 *   - Relax `customer_mobile` to nullable — SOURCE collections have
 *     no individual customer.
 *   - Add a CHECK so each party_type carries exactly the right key
 *     (CUSTOMER → customer_mobile, SOURCE → source_id) and never the
 *     other one as a stray.
 *   - Add an index for source-side lookups (mirrors the existing
 *     customer-mobile index).
 */
export class PaymentCollectionsAgentParty1782100000000 implements MigrationInterface {
  name = 'PaymentCollectionsAgentParty1782100000000';

  public async up(qr: QueryRunner): Promise<void> {
    await qr.query(`
      ALTER TABLE payment_collections
        ADD COLUMN party_type varchar(16) NOT NULL DEFAULT 'CUSTOMER',
        ADD COLUMN source_id uuid REFERENCES trip_sources(id);
    `);
    await qr.query(`
      ALTER TABLE payment_collections
        ALTER COLUMN customer_mobile DROP NOT NULL;
    `);
    await qr.query(`
      ALTER TABLE payment_collections
        ADD CONSTRAINT payment_collections_party_type_valid
          CHECK (party_type IN ('CUSTOMER','SOURCE'));
    `);
    await qr.query(`
      ALTER TABLE payment_collections
        ADD CONSTRAINT payment_collections_party_key_consistency
          CHECK (
            (party_type = 'CUSTOMER' AND customer_mobile IS NOT NULL AND source_id IS NULL)
            OR
            (party_type = 'SOURCE' AND source_id IS NOT NULL AND customer_mobile IS NULL)
          );
    `);
    await qr.query(`
      CREATE INDEX idx_payment_collections_tenant_source_date
        ON payment_collections (tenant_id, source_id, payment_date DESC)
        WHERE source_id IS NOT NULL;
    `);
  }

  public async down(qr: QueryRunner): Promise<void> {
    await qr.query(`DROP INDEX IF EXISTS idx_payment_collections_tenant_source_date;`);
    await qr.query(`
      ALTER TABLE payment_collections
        DROP CONSTRAINT IF EXISTS payment_collections_party_key_consistency;
    `);
    await qr.query(`
      ALTER TABLE payment_collections
        DROP CONSTRAINT IF EXISTS payment_collections_party_type_valid;
    `);
    await qr.query(`
      ALTER TABLE payment_collections
        ALTER COLUMN customer_mobile SET NOT NULL;
    `);
    await qr.query(`
      ALTER TABLE payment_collections
        DROP COLUMN IF EXISTS source_id,
        DROP COLUMN IF EXISTS party_type;
    `);
  }
}
