import { Component, OnInit } from '@angular/core';
import { FormBuilder, FormGroup, ReactiveFormsModule, UntypedFormGroup, Validators } from '@angular/forms';
import {
    CircleButtonComponent,
    getConfig,
    HasScrollbarDirective,
    HelpButtonComponent,
    IconButtonComponent,
    IqserDenyDirective,
    IqserDialogComponent,
} from '@iqser/common-ui';
import { JustificationsService } from '@services/entity-services/justifications.service';
import { Dossier, ILegalBasisChangeRequest } from '@red/domain';
import { firstValueFrom } from 'rxjs';
import { AnnotationWrapper } from '@models/file/annotation.wrapper';
import { Roles } from '@users/roles';
import { marker as _ } from '@biesbjerg/ngx-translate-extract-marker';
import {
    SelectedAnnotationsTableComponent,
    ValueColumn,
} from '../../components/selected-annotations-table/selected-annotations-table.component';
import { NgForOf, NgIf } from '@angular/common';
import { MatOption, MatSelect, MatSelectTrigger } from '@angular/material/select';
import { DetailsRadioOption } from '@common-ui/inputs/details-radio/details-radio-option';
import { ForceAnnotationData, ForceAnnotationOption, ForceAnnotationResult, LegalBasisOption } from '../../utils/dialog-types';
import { getForceAnnotationOptions } from '../../utils/dialog-options';
import { SystemDefaults } from '../../../account/utils/dialog-defaults';
import { MatFormField } from '@angular/material/form-field';
import { MatTooltip } from '@angular/material/tooltip';
import { TranslateModule } from '@ngx-translate/core';
import { DetailsRadioComponent } from '@common-ui/inputs/details-radio/details-radio.component';

const DOCUMINE_LEGAL_BASIS = 'n-a.';

@Component({
    templateUrl: './force-annotation-dialog.component.html',
    styleUrls: ['./force-annotation-dialog.component.scss'],
    standalone: true,
    imports: [
        ReactiveFormsModule,
        NgIf,
        SelectedAnnotationsTableComponent,
        MatFormField,
        MatSelectTrigger,
        MatSelect,
        MatOption,
        MatTooltip,
        HasScrollbarDirective,
        TranslateModule,
        IconButtonComponent,
        IqserDenyDirective,
        CircleButtonComponent,
        NgForOf,
        HelpButtonComponent,
        DetailsRadioComponent,
    ],
})
export class ForceAnnotationDialogComponent
    extends IqserDialogComponent<ForceAnnotationDialogComponent, ForceAnnotationData, ForceAnnotationResult>
    implements OnInit
{
    readonly isDocumine = getConfig().IS_DOCUMINE;
    readonly options: DetailsRadioOption<ForceAnnotationOption>[];

    readonly form: FormGroup;
    readonly tableColumns: ValueColumn[] = [{ label: 'Value' }, { label: 'Type' }];
    readonly tableData: ValueColumn[][] = this.data.annotations.map(redaction => [
        { label: redaction.value, bold: true },
        { label: redaction.typeLabel },
    ]);

    legalOptions: LegalBasisOption[] = [];
    protected readonly roles = Roles;

    constructor(
        private readonly _justificationsService: JustificationsService,
        private readonly _formBuilder: FormBuilder,
    ) {
        super();
        this.options = getForceAnnotationOptions(this.isDocumine, this.isHintDialog, this.isImageDialog);
        this.form = this.#getForm();
    }

    get isImageHint() {
        return this.data.annotations.every(annotation => annotation.IMAGE_HINT);
    }

    get isHintDialog() {
        return this.data.hint;
    }

    get isImageDialog() {
        return this.data.image;
    }

    get disabled(): boolean {
        return !this.valid;
    }

    get dialogTitle(): string {
        return this.isImageHint
            ? _('manual-annotation.dialog.header.force-redaction-image-hint')
            : this.isHintDialog
              ? _('manual-annotation.dialog.header.force-hint')
              : _('manual-annotation.dialog.header.force-redaction');
    }

    async ngOnInit() {
        if (!this.isDocumine) {
            const data = await firstValueFrom(this._justificationsService.getForDossierTemplate(this.data.dossier.dossierTemplateId));

            this.legalOptions = data.map(lbm => ({
                legalBasis: lbm.reason,
                description: lbm.description,
                label: lbm.name,
            }));

            this.legalOptions.sort((a, b) => a.label.localeCompare(b.label));

            // Set pre-existing reason if it exists
            const existingReason = this.legalOptions.find(option => option.legalBasis === this.data.annotations[0].legalBasis);
            if (!this.data.hint && existingReason) {
                this.form.patchValue({ reason: existingReason }, { emitEvent: false });
            }
        }
        this.initialFormValue = this.form.getRawValue();
    }

    save() {
        this.close(this.#createForceRedactionRequest());
    }

    #getForm(): UntypedFormGroup {
        return this._formBuilder.group({
            reason: this.data.hint ? ['Forced Hint'] : [null, !this.isDocumine ? Validators.required : null],
            comment: [null],
            option: this.options.find(o => o.value === SystemDefaults.FORCE_REDACTION_DEFAULT),
        });
    }

    #createForceRedactionRequest(): ILegalBasisChangeRequest {
        const request: ILegalBasisChangeRequest = {};

        request.legalBasis = !this.isDocumine ? this.form.get('reason').value.legalBasis : DOCUMINE_LEGAL_BASIS;
        request.comment = this.form.get('comment').value;
        request.reason = this.form.get('reason').value.description;
        request.option = this.form.get('option').value?.value;

        return request;
    }
}
