import {
  Entity,
  PrimaryGeneratedColumn,
  Column,
  Index,
  CreateDateColumn,
  UpdateDateColumn,
  DeleteDateColumn,
} from 'typeorm';
import { GeneratedLinkSourceType } from '../enum/generated-link-source-type.enum';
import { OnlineSessionRegistrationStatus } from '../enum/online-session-registration-status.enum';

/**
 * One row per pre-generated Zoom registrant with no `hdb_program_registration` row of
 * its own — a real staff user matched by role (`sourceType: ROLE`) or a placeholder slot
 * from a caller-named batch (`sourceType: PLACEHOLDER`, e.g. "Staff" x20). Distinct from
 * `ProgramRegistrationOnlineSession` (real seeker registrations) and
 * `ZoomAnalyticsAttendeeSummary` (read-only per-session attendance analytics).
 */
@Entity('zoom_generated_registrant_link')
@Index('uq_zoom_generated_link_session_user', ['programSessionId', 'userId'], {
  unique: true,
  where: '"source_type" = \'ROLE\' AND "deleted_at" IS NULL',
})
@Index(
  'uq_zoom_generated_link_session_batch_seq',
  ['programSessionId', 'batchName', 'sequenceNumber'],
  { unique: true, where: '"source_type" = \'PLACEHOLDER\' AND "deleted_at" IS NULL' },
)
export class ZoomGeneratedRegistrantLink {
  @PrimaryGeneratedColumn('increment', { type: 'bigint' })
  id: number;

  @Column({ name: 'program_id', type: 'bigint' })
  programId: number;

  @Index()
  @Column({ name: 'program_session_id', type: 'bigint' })
  programSessionId: number;

  @Column({ name: 'source_type', type: 'varchar', length: 20 })
  sourceType: GeneratedLinkSourceType;

  @Column({ name: 'user_id', type: 'bigint', nullable: true })
  userId: number | null;

  /** Matched role key for `sourceType: ROLE` rows; `'SYSTEM'` for `sourceType: PLACEHOLDER` rows. */
  @Column({ name: 'role_key', type: 'varchar', length: 50, nullable: true })
  roleKey: string | null;

  @Column({ name: 'batch_name', type: 'varchar', length: 100, nullable: true })
  batchName: string | null;

  @Column({ name: 'sequence_number', type: 'int', nullable: true })
  sequenceNumber: number | null;

  @Column({ name: 'display_name', type: 'varchar', length: 255 })
  displayName: string;

  @Column({ name: 'registrant_email', type: 'varchar', length: 255 })
  registrantEmail: string;

  @Column({ name: 'source_email', type: 'varchar', length: 255, nullable: true })
  sourceEmail: string | null;

  @Column({ name: 'source_mobile', type: 'varchar', length: 255, nullable: true })
  sourceMobile: string | null;

  @Column({ name: 'join_url', type: 'text', nullable: true })
  joinUrl: string | null;

  @Column({ name: 'external_registrant_id', type: 'varchar', length: 255, nullable: true })
  externalRegistrantId: string | null;

  @Column({
    name: 'status',
    type: 'varchar',
    length: 20,
    default: OnlineSessionRegistrationStatus.REGISTERED,
  })
  status: OnlineSessionRegistrationStatus;

  @Column({ name: 'failure_reason', type: 'varchar', length: 500, nullable: true })
  failureReason: string | null;

  @CreateDateColumn({ name: 'created_at', type: 'timestamptz', default: () => 'CURRENT_TIMESTAMP' })
  createdAt: Date;

  @UpdateDateColumn({
    name: 'updated_at',
    type: 'timestamptz',
    default: () => 'CURRENT_TIMESTAMP',
    onUpdate: 'CURRENT_TIMESTAMP',
  })
  updatedAt: Date;

  @DeleteDateColumn({ name: 'deleted_at', type: 'timestamptz', nullable: true })
  deletedAt: Date | null;

  @Column({ name: 'created_by', type: 'bigint', nullable: true })
  createdBy: number | null;

  @Column({ name: 'updated_by', type: 'bigint', nullable: true })
  updatedBy: number | null;

  constructor(partial?: Partial<ZoomGeneratedRegistrantLink>) {
    Object.assign(this, partial ?? {});
  }
}
