import { ApiProperty, ApiPropertyOptional } from '@nestjs/swagger';
import { PropertyType, TransactionType, Direction, Furnishing, PropertyCondition } from '@prisma/client';
import { Type, Transform } from 'class-transformer';
import {
  IsString,
  IsNumber,
  IsEnum,
  IsOptional,
  IsNotEmpty,
  MinLength,
  MaxLength,
  Min,
  Max,
  IsArray,
  IsBoolean,
} from 'class-validator';

export class CreateListingDto {
  @ApiProperty({ enum: TransactionType, example: 'SALE', description: 'Transaction type (SALE or RENT)' })
  @IsEnum(TransactionType)
  transactionType!: TransactionType;

  @ApiProperty({ type: String, example: '5500000000', description: 'Price in VND (as string to support bigint)' })
  @IsNotEmpty()
  @Transform(({ value }) => BigInt(value))
  priceVND!: bigint;

  @ApiProperty({ enum: PropertyType, example: 'APARTMENT', description: 'Type of property' })
  @IsEnum(PropertyType)
  propertyType!: PropertyType;

  @ApiProperty({ example: 'Căn hộ 3PN view sông Sài Gòn - Vinhomes Central Park', description: 'Listing title (min 5 chars)' })
  @IsString()
  @MinLength(5)
  title!: string;

  @ApiProperty({ example: 'Căn hộ cao cấp 3 phòng ngủ, nội thất đầy đủ, view trực diện sông Sài Gòn. Tiện ích hồ bơi, gym, công viên nội khu.', description: 'Detailed description (min 10 chars)' })
  @IsString()
  @MinLength(10)
  description!: string;

  @ApiProperty({ example: '208 Nguyễn Hữu Cảnh', description: 'Street address' })
  @IsString()
  address!: string;

  @ApiProperty({ example: 'Phường 22', description: 'Ward name' })
  @IsString()
  ward!: string;

  @ApiProperty({ example: 'Bình Thạnh', description: 'District name' })
  @IsString()
  district!: string;

  @ApiProperty({ example: 'Hồ Chí Minh', description: 'City / province' })
  @IsString()
  city!: string;

  @ApiProperty({ example: 10.7942, description: 'Latitude (-90 to 90)' })
  @IsNumber()
  @Type(() => Number)
  @Min(-90)
  @Max(90)
  latitude!: number;

  @ApiProperty({ example: 106.7219, description: 'Longitude (-180 to 180)' })
  @IsNumber()
  @Type(() => Number)
  @Min(-180)
  @Max(180)
  longitude!: number;

  @ApiProperty({ example: 85.5, description: 'Total area in square metres' })
  @IsNumber()
  @Type(() => Number)
  @Min(1)
  areaM2!: number;

  @ApiPropertyOptional({ example: 78.0, description: 'Usable area in square metres' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  usableAreaM2?: number;

  @ApiPropertyOptional({ example: 3, description: 'Number of bedrooms' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  bedrooms?: number;

  @ApiPropertyOptional({ example: 2, description: 'Number of bathrooms' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  bathrooms?: number;

  @ApiPropertyOptional({ example: 1, description: 'Number of floors (for houses)' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  floors?: number;

  @ApiPropertyOptional({ example: 15, description: 'Floor number (for apartments)' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  floor?: number;

  @ApiPropertyOptional({ example: 30, description: 'Total floors in the building' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  totalFloors?: number;

  @ApiPropertyOptional({ enum: Direction, example: 'EAST', description: 'Primary facing direction' })
  @IsOptional()
  @IsEnum(Direction)
  direction?: Direction;

  @ApiPropertyOptional({ example: 2020, description: 'Year the property was built' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  yearBuilt?: number;

  @ApiPropertyOptional({ example: 'Sổ hồng', description: 'Legal document status (e.g. Sổ hồng, Sổ đỏ, Hợp đồng mua bán)' })
  @IsOptional()
  @IsString()
  legalStatus?: string;

  @ApiPropertyOptional({ example: ['Hồ bơi', 'Gym', 'Sân chơi trẻ em'], description: 'List of amenities' })
  @IsOptional()
  @IsArray()
  amenities?: string[];

  @ApiPropertyOptional({ example: { schools: ['Trường Quốc tế ISHCMC'], hospitals: ['Bệnh viện FV'] }, description: 'Nearby points of interest' })
  @IsOptional()
  nearbyPOIs?: unknown;

  @ApiPropertyOptional({ example: 500, description: 'Distance to nearest metro station in metres' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  metroDistanceM?: number;

  @ApiPropertyOptional({ example: 'Vinhomes Central Park', description: 'Name of the residential project' })
  @IsOptional()
  @IsString()
  projectName?: string;

  @ApiPropertyOptional({ example: 'agent-uuid-1234', description: 'Assigned agent ID' })
  @IsOptional()
  @IsString()
  agentId?: string;

  @ApiPropertyOptional({ type: String, example: '25000000', description: 'Monthly rent price in VND (as string to support bigint)' })
  @IsOptional()
  @Transform(({ value }) => (value != null ? BigInt(value) : undefined))
  rentPriceMonthly?: bigint;

  @ApiPropertyOptional({ example: 2.5, description: 'Agent commission percentage' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  commissionPct?: number;

  @ApiPropertyOptional({ enum: Furnishing, example: 'FULLY_FURNISHED', description: 'Furnishing level' })
  @IsOptional()
  @IsEnum(Furnishing)
  furnishing?: Furnishing;

  @ApiPropertyOptional({ enum: PropertyCondition, example: 'NEW', description: 'Property condition' })
  @IsOptional()
  @IsEnum(PropertyCondition)
  propertyCondition?: PropertyCondition;

  @ApiPropertyOptional({ enum: Direction, example: 'SOUTH', description: 'Balcony / terrace facing direction' })
  @IsOptional()
  @IsEnum(Direction)
  balconyDirection?: Direction;

  @ApiPropertyOptional({ type: String, example: '2500000', description: 'Monthly maintenance fee in VND (as string to support bigint)' })
  @IsOptional()
  @Transform(({ value }) => (value != null && value !== '' ? BigInt(value) : undefined))
  maintenanceFeeVND?: bigint;

  @ApiPropertyOptional({ example: 2, description: 'Number of parking slots' })
  @IsOptional()
  @IsNumber()
  @Type(() => Number)
  @Min(0)
  parkingSlots?: number;

  @ApiPropertyOptional({ example: ['Sông', 'Thành phố'], description: 'View types (multi-select)' })
  @IsOptional()
  @IsArray()
  @IsString({ each: true })
  viewType?: string[];

  @ApiPropertyOptional({ example: true, description: 'Whether pets are allowed (null = unknown)' })
  @IsOptional()
  @IsBoolean()
  petFriendly?: boolean;

  @ApiPropertyOptional({ example: ['Gia đình có con nhỏ'], description: 'Personas selected by admin' })
  @IsOptional()
  @IsArray()
  @IsString({ each: true })
  suitableFor?: string[];

  @ApiPropertyOptional({ example: 'Khu vực gần trường học, dễ di chuyển...', description: 'Admin narrative for why this location suits buyers' })
  @IsOptional()
  @IsString()
  @MaxLength(2000)
  whyThisLocation?: string;
}
