import {
  Column,
  CreateDateColumn,
  DeleteDateColumn,
  Entity,
  Index,
  JoinColumn,
  ManyToOne,
  OneToMany,
  PrimaryGeneratedColumn,
  UpdateDateColumn,
} from 'typeorm';
import { User } from './user.entity';
import { WorkflowConfigurationVariable } from './workflow-configuration-variable.entity';
import { WorkflowDataTypeEnum } from '../enum/workflow-data-type.enum';
import { WorkflowJoinTypeEnum } from '../enum/workflow-join-type.enum';
import { WorkflowVariableScopeEnum } from '../enum/workflow-variable-scope.enum';

/**
 * Global catalog of workflow variables
 * Defines reusable fields that can be fetched for workflow validations
 */
@Entity('workflow_variable_master')
@Index('idx_workflow_variable_master_key', ['variableKey'])
@Index('idx_workflow_variable_master_source_table', ['sourceTable'])
export class WorkflowVariableMaster {
  @PrimaryGeneratedColumn()
  id: number;

  @Column({ name: 'variable_key', type: 'varchar', length: 100, unique: true })
  variableKey: string;

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

  @Column({ name: 'source_table', type: 'varchar', length: 100 })
  sourceTable: string;

  @Column({ name: 'source_column', type: 'varchar', length: 100 })
  sourceColumn: string;

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

  @Column({ name: 'data_type', type: 'enum', enum: WorkflowDataTypeEnum })
  dataType: WorkflowDataTypeEnum;

  @Column({ name: 'join_type', type: 'enum', enum: WorkflowJoinTypeEnum, nullable: true })
  joinType: WorkflowJoinTypeEnum | null;

  @Column({ name: 'join_condition', type: 'text', nullable: true })
  joinCondition: string | null; // e.g., 'rpd.registration_id = pr.id AND rpd.deleted_at IS NULL'

  @Column({ name: 'table_alias', type: 'varchar', length: 50, nullable: true })
  tableAlias: string | null; // e.g., 'rpd' for registration_payment_detail

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

  @Column({ name: 'is_active', type: 'boolean', default: true })
  isActive: boolean;

  @Column({ name: 'default_value', type: 'text', nullable: true })
  defaultValue: string | null; // Default SQL expression if applicable

  @Column({ name: 'is_mandatory_join', type: 'boolean', default: false })
  isMandatoryJoin: boolean; // If true, this table must be joined

  @Column({ name: 'execution_order', type: 'int', nullable: true })
  executionOrder: number | null; // Order in which joins should be executed

  @Column({ name: 'variable_scope', type: 'enum', enum: WorkflowVariableScopeEnum, default: WorkflowVariableScopeEnum.DEFAULT })
  variableScope: WorkflowVariableScopeEnum;

  @Column({ type: 'jsonb', nullable: true })
  metadata: Record<string, unknown> | null; // Additional configuration

  @OneToMany(() => WorkflowConfigurationVariable, wfv => wfv.variableMaster)
  workflowConfigurations: WorkflowConfigurationVariable[];

  @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: 'int', nullable: true })
  createdById: number | null;

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

  @ManyToOne(() => User, { nullable: true })
  @JoinColumn({ name: 'created_by' })
  createdBy: User | null;

  @ManyToOne(() => User, { nullable: true })
  @JoinColumn({ name: 'updated_by' })
  updatedBy: User | null;

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