import { Type } from 'class-transformer';
import { IsIn, IsInt, IsNotEmpty, IsObject, IsOptional, IsString, ValidateNested } from 'class-validator';

const EXTERNAL_CHANNELS = ['EMAIL', 'SMS'] as const;
const ALL_CHANNELS = ['EMAIL', 'SMS', 'INTERNAL'] as const;

/** Inline template content — an ad-hoc source (e.g. finished HTML from marketing). */
export class InlineTemplateDto {
  @IsOptional() @IsString() subject?: string;
  @IsOptional() @IsString() html?: string;
  @IsOptional() @IsString() text?: string;
  @IsOptional() @IsString({ each: true }) variables?: string[];
}

/** Body of POST /v1/templates/send. Provide EITHER `key` (stored) OR `inline` (ad-hoc). */
export class SendTemplateDto {
  @IsOptional() @IsString() @IsNotEmpty() key?: string;
  @IsOptional() @IsInt() version?: number;
  @IsOptional() @ValidateNested() @Type(() => InlineTemplateDto) inline?: InlineTemplateDto;

  @IsIn(EXTERNAL_CHANNELS) channel!: (typeof EXTERNAL_CHANNELS)[number];
  @IsString() @IsNotEmpty() target!: string;
  @IsOptional() @IsObject() vars?: Record<string, unknown>;
  @IsOptional() @IsString() locale?: string;
  @IsString() @IsNotEmpty() idempotencyKey!: string;
  @IsOptional() @IsString() purpose?: string;
}

/** Body of POST /v1/templates/preview — render only, no send. INTERNAL allowed (preview only). */
export class PreviewTemplateDto {
  @IsOptional() @IsString() @IsNotEmpty() key?: string;
  @IsOptional() @IsInt() version?: number;
  @IsOptional() @ValidateNested() @Type(() => InlineTemplateDto) inline?: InlineTemplateDto;

  @IsIn(ALL_CHANNELS) channel!: (typeof ALL_CHANNELS)[number];
  @IsOptional() @IsObject() vars?: Record<string, unknown>;
  @IsOptional() @IsString() locale?: string;
}
