import { ApiProperty } from "@nestjs/swagger";
import { documentTypes, type DocumentType } from "../types/constants";
import { IsIn, IsNumber, IsOptional, isString, IsString, Length, Matches, MaxLength } from "class-validator";

export class DocumentPaymentDto {

    @ApiProperty({description: "ID Pagamento"})
    @IsNumber()
    id?: number;

    @ApiProperty({description: "Totale pagamento"})
    @IsNumber()
    amount?: number;

}

export class DocumentRowDto {

    @ApiProperty({description: "Codice articolo riga"})
    @MaxLength(100)
    @IsString()
    code?: string;
    
    @ApiProperty({description: "Titolo articolo riga"})
    @MaxLength(100)
    @IsString()
    title?: string;
    
    @ApiProperty({description: "Barcode articolo riga"})
    @IsOptional()
    @MaxLength(20)
    @IsString()
    barcode?: string;

    @ApiProperty({description: "Quantità venduta"})
    @IsNumber()
    quantity?: number;

    @ApiProperty({description: "Prezzo linea"})
    @IsNumber()
    price?: number;

    @ApiProperty({description: "Imponibile linea"})
    @IsNumber()
    taxable?: number;

    @ApiProperty({description: "Imposta linea"})
    @IsNumber()
    tax?: number;

    @ApiProperty({description: "Totale linea"})
    @IsNumber()
    amount?: number;

    @ApiProperty({description: "Totale imponibile linea"})
    @IsNumber()
    amountTaxable?: number;

    @ApiProperty({description: "Totale imposta linea"})
    @IsNumber()
    amountTax?: number;

    @ApiProperty({description: "Prezzo linea scontato"})
    @IsNumber()
    priceDiscount?: number;

    @ApiProperty({description: "Imponibile linea scontato"})
    @IsNumber()
    taxableDiscount?: number;

    @ApiProperty({description: "Imposta linea scontato"})
    @IsNumber()
    taxDiscount?: number;
    
    @ApiProperty({description: "Totale scontato"})
    @IsNumber()
    amountDiscount?: number;

    @ApiProperty({description: "Totale imponibile scontato"})
    @IsNumber()
    amountTaxableDiscount?: number;

    @ApiProperty({description: "Totale imposta scontato"})
    @IsNumber()
    amountTaxDiscount?: number;

    @ApiProperty({description: "Aliquota articolo"})
    @IsNumber()
    rate?: number;

    @ApiProperty({description: "Natura"})
    @IsString()
    @IsOptional()
    nature?: string;

    @ApiProperty({description: "Esigibilità"})
    @IsString()
    @IsOptional()
    enforceability?: string;

    @ApiProperty({description: "ID Articolo"})
    @IsNumber()
    idArticle?: number;

}

export class DocumentCreateDto {

    @ApiProperty({description: "ID documento"})
    @IsOptional()
    id?: number;

    @ApiProperty({description: "Tipo documento"})
    @IsString()
    documentArea?: DocumentType;

    @ApiProperty({description: "Data documento"})
    @Matches(/^\d{4}-\d{2}-\d{2}$/)
    @IsString()
    documentDate?: string;

    @ApiProperty({description: "Tempo documento"})
    @Matches(/^(?:[01]\d|2[0-3]):[0-5]\d:[0-5]\d$/)
    @IsString()
    documentTime?: string;

    @ApiProperty({description: "ID contatore fattura"})
    @IsOptional()
    @IsNumber()
    idInvoiceCounter?: number;

    @ApiProperty({description: "ID contatore nota di credito"})
    @IsOptional()
    @IsNumber()
    idCreditNoteCounter?: number;

    @ApiProperty({description: "Numero scontrino"})
    @IsOptional()
    @Length(4,4)
    @IsString()
    receiptNumber?: string;

    @ApiProperty({description: "Chiusura scontrino"})
    @IsOptional()
    @Length(4,4)
    @IsString()
    receiptClose?: string;

    @ApiProperty({description: "Totale"})
    @IsNumber()
    amount?: number;

    @ApiProperty({description: "Totale imponibile"})
    @IsNumber()
    amountTaxable?: number;

    @ApiProperty({description: "Totale imposta"})
    @IsNumber()
    amountTax?: number;

    @ApiProperty({description: "Totale scontato"})
    @IsNumber()
    amountDiscount?: number;

    @ApiProperty({description: "Totale imponibile scontato"})
    @IsNumber()
    amountTaxableDiscount?: number;

    @ApiProperty({description: "Totale imposta scontato"})
    @IsNumber()
    amountTaxDiscount?: number;

    @ApiProperty({description: "Nota documento"})
    @MaxLength(100)
    @IsString()
    @IsOptional()
    note?: string;

    @ApiProperty({description: "Eventuali sconti applicati", type: Number, isArray: true})
    @IsOptional()
    discounts?: number[];

    // _____ Relations _____

    @ApiProperty({description: "ID cliente"})
    @IsOptional()
    @IsNumber()
    idCustomer?: number;

    @ApiProperty({description: "ID fornitore"})
    @IsOptional()
    @IsNumber()
    idSupplier?: number;

    @ApiProperty({description: "ID punto vendita"})
    @IsNumber()
    idStore?: number;

    @ApiProperty({description: "ID deposito"})
    @IsNumber()
    idStorage?: number;

    @ApiProperty({description: "ID utente"})
    @IsOptional()
    @IsNumber()
    idUser?: number;

    @ApiProperty({description: "ID documento correlato"})
    @IsOptional()
    @IsNumber()
    idRefDocument?: number;

    @ApiProperty({description: "ID operatore"})
    @IsOptional()
    @IsNumber()
    idOperator?: number;

    @ApiProperty({description: "ID dispositivo"})
    @IsOptional()
    @IsNumber()
    idDevice?: number;

    @ApiProperty({description: "ID listino"})
    @IsOptional()
    @IsNumber()
    idPrice?: number;

    @ApiProperty({description: "Pagamenti", type: DocumentPaymentDto, isArray: true})
    @IsOptional()
    payments?: DocumentPaymentDto[];

    @ApiProperty({description: "Linee", type: DocumentRowDto, isArray: true})
    @IsOptional()
    rows?: DocumentRowDto[];

    @ApiProperty({description: "ID documento da cancellare"})
    @IsOptional()
    @IsNumber()
    idDocumentToCancel?: number;

}

export class DocumentFilterDto {

    @ApiProperty(
        { description: "Area documento da ricercare" }
    )
    @IsIn(documentTypes)
    @IsOptional()
    documentArea?: string;

    @ApiProperty(
        { description: "Data inizio ricerca" }
    )
    @Matches(/^\d{4}-\d{2}-\d{2}$/)
    @IsOptional()
    documentDateStart?: string;

    @ApiProperty(
        { description: "Data fine ricerca" }
    )
    @Matches(/^\d{4}-\d{2}-\d{2}$/)
    @IsOptional()
    documentDateEnd?: string;

    @ApiProperty(
        { description: "ID cliente" }
    )
    @IsOptional()
    idCustomer?: number;

    @ApiProperty(
        { description: "ID fornitore" }
    )
    @IsOptional()
    idSupplier?: number;

}

export class DocumentMovementListDto {

    @ApiProperty(
        { description: "Documento da filtrare movimenti" }
    )
    @IsOptional()
    @IsNumber()
    idDocument?: number;

    @ApiProperty(
        { description: "ID Articolo per filtro movimenti" }
    )
    @IsOptional()
    @IsNumber()
    idArticle?: number;

    @ApiProperty(
        { description: "ID Store per filtro movimenti" }
    )
    @IsOptional()
    @IsNumber()
    idStore?: number;

    @ApiProperty(
        { description: "ID Storage per filtro movimenti" }
    )
    @IsOptional()
    @IsNumber()
    idStorage?: number;

    @ApiProperty(
        { description: "Data inizio ricerca" }
    )
    @Matches(/^\d{4}-\d{2}-\d{2}$/)
    @IsOptional()
    movementDateStart?: string;

    @ApiProperty(
        { description: "Data fine ricerca" }
    )
    @Matches(/^\d{4}-\d{2}-\d{2}$/)
    @IsOptional()
    movementDateEnd?: string;

}