import { Component, OnDestroy, OnInit, ViewEncapsulation, TemplateRef } from "@angular/core";
import { OrderPrescription } from "@shared/entities";
import { ApiResources, UtilHelper } from "@shared/helpers";
import { AppData, HttpService, NotifyService, ResourceService } from "@shared/services";
import { takeUntil, finalize } from "rxjs/operators";
import { HttpErrorResponse } from "@angular/common/http";
import { NgbModal, NgbModalRef } from "@ng-bootstrap/ng-bootstrap";
import { FormGroup, Validators, FormBuilder } from "@angular/forms";
import { Page, IUserAccount, IResource, Pagination } from "@shared/models";
import * as ClassicEditor from "@ckeditor/ckeditor5-build-classic";


class FilterOptions {

    encounterTypeId: number;
    providerId: number;
    name: string;
}

class Filters {
    options: FilterOptions;
    applied: boolean;

    constructor() {
        this.init();
    }

    init() {
        this.options = new FilterOptions();
        this.applied = undefined;
    }
}

@Component({
    templateUrl: "./encounter-order-master.html",
    encapsulation: ViewEncapsulation.None
})
export class EncounterOrderMasterPage implements OnInit, OnDestroy {
    page: Page;
    pagination: Pagination;
    orderMasterForm: FormGroup;
    loading: boolean;
    record: Array<OrderPrescription>;
    orders: Array<OrderPrescription>;
    selectedOrder: OrderPrescription;
    filters: Filters;
    modalRef: NgbModalRef;
    submitting: boolean;
    submitted: boolean;
    modifying: boolean;
    modifyingContent: string;

   
    notesEditor = ClassicEditor;
    encounterType: IResource[];
    providerResources: Array<IResource>;
    loadingproviderResources: boolean;
   

    constructor(
        private readonly appData: AppData,
        private readonly modalService: NgbModal,
        private readonly formBuilder: FormBuilder,
        private readonly notifyService: NotifyService,
        private readonly httpService: HttpService,
        private readonly resourceService: ResourceService
    ) {
        this.loading = true;
        this.page = new Page();
        this.initPagination();
        this.record = new Array<OrderPrescription>();
        this.providerResources = new Array<IResource>();
        this.filters = new Filters();
       
    }
    private initPagination() {
        this.pagination = new Pagination();
        this.pagination.pageIndex = 1;
        this.pagination.pageSize = 10;
    }
    private buildForm() {
        this.orderMasterForm = this.formBuilder.group({
            name: [null],
            encounterTypeId: [null, [Validators.required]],
            providerId: [null],
            orderPrescriptionMasterId:0
        });
    }

    onOpenModel(content: TemplateRef<any>, record?: OrderPrescription) {
        this.buildForm();
        if (record) {
            this.selectedOrder = record;
            this.updateForm();
        }

        this.modalRef = this.modalService.open(content, {
            backdrop: "static",
            keyboard: false,
            centered: true,
            windowClass: "custom-modal effect-scale"
        });
    }

   
    private fetchEncounterType() {
        this.resourceService.encounterType()
            .pipe(takeUntil(this.page.unSubscribe))
            .subscribe((response: Array<IResource>) => {
                this.encounterType = response;
            });
    }

    private fetchProviderResources() {
        this.loadingproviderResources = true;
        this.resourceService.providers()
            .pipe(finalize(() => { this.loadingproviderResources = false }))
            .pipe(takeUntil(this.page.unSubscribe))
            .subscribe((response: Array<IResource>) => {
                this.providerResources = response;
            });
    }

  
  

    onSubmit() {
        this.submitted = true;

        if (!this.orderMasterForm.valid) {
            return;
        }

        this.submitting = true;
        const request = Object.assign(UtilHelper.clone(this.orderMasterForm.getRawValue()));
        request["modifiedByName"] = this.page.userAccount.fullName;
        if (this.orderMasterForm.value.orderPrescriptionMasterId === 0) {
            request.createdBy = this.page.userAccount.accountId;
            this.httpService.post(ApiResources.getURI(ApiResources.orders.base, ApiResources.orders.addOrderMaster), request)
                .pipe(takeUntil(this.page.unSubscribe))
                .pipe(finalize(() => {
                    this.submitting = false;
                    this.submitted = false;
                }))
                .subscribe((response: number) => {
                    if (response > 0) {
                        this.onCloseModal();
                        this.fetch();
                        this.notifyService.success("Orders details has been added successfully.");
                    }
                    else if (response < 0) {
                        this.notifyService.info("Order detail already exists. Please try with different name");
                    }
 
                }, (error: HttpErrorResponse) => {
                    const errorMessage = UtilHelper.handleError(error);
                    if (errorMessage) {
                        this.notifyService.warning(errorMessage);
                    } else {
                        this.notifyService.defaultError();
                    }
                });
        } else {
            request.modifiedBy = this.page.userAccount.accountId;
            request["modifiedByName"] = this.page.userAccount.fullName;
            request["modifiedBy"] = this.page.userAccount.accountId;
            request["name"] = this.orderMasterForm.value.name;
            request["providerId"] = this.orderMasterForm.value.providerId;
            request["encounterTypeId"] = this.orderMasterForm.value.encounterTypeId;
            request["orderPrescriptionMasterId"] = this.orderMasterForm.value.orderPrescriptionMasterId;
            this.httpService.put(ApiResources.getURI(ApiResources.orders.base, ApiResources.orders.updateOrderMaster), request)
                .pipe(takeUntil(this.page.unSubscribe))
                .pipe(finalize(() => {
                    this.submitting = false;
                    this.submitted = false;
                }))
                .subscribe((response: number) => {
                    if (response > 0) {
                        this.onCloseModal();
                        this.fetch();
                        this.notifyService.success("Orders details has been updated successfully.");
                    }
                    else if (response <0) {
                        this.notifyService.info("Order detail already exists. Please try with different name");
                    }
                }, (error: HttpErrorResponse) => {
                    const errorMessage = UtilHelper.handleError(error);
                    if (errorMessage) {
                        this.notifyService.warning(errorMessage);
                    } else {
                        this.notifyService.defaultError();
                    }
                });
        }
    }

    get form() {
        
        return this.orderMasterForm.controls;
    }

    private updateForm() {
        this.orderMasterForm.patchValue({
            name: this.selectedOrder.name,
            providerId: this.selectedOrder.providerId,
            encounterTypeId: this.selectedOrder.encounterTypeId,
            orderPrescriptionMasterId: this.selectedOrder.orderPrescriptionMasterId
        });
    }

    onDelete(record: OrderPrescription) {
        this.notifyService.confirm(
            `Are you sure to Delete <span class='font-weight-bold'>${record.valueName}</span>`,
            () => {
                const request = {
                    orderPrescriptionMasterId: record.orderPrescriptionMasterId,
                    modifiedByName: this.page.userAccount.fullName,
                    createdBy: this.page.userAccount.accountId,
                    modifiedBy: this.page.userAccount.accountId
                };
                this.httpService
                    .post(ApiResources.getURI(ApiResources.orders.base, ApiResources.orders.deleteOrderMaster), request)
                    .pipe(takeUntil(this.page.unSubscribe))
                    .pipe(finalize(() => { }))
                    .subscribe(
                        () => {
                            this.notifyService.success("Orders deleted successfully.");
                            this.fetch();
                        },
                        () => {
                            this.notifyService.defaultError();
                        });
            });
    }

    fetch() {
        this.loading = true;
        const request = {
            ...this.pagination,
            ...this.filters.options
        }
        this.httpService
            .post<Array<OrderPrescription>>(ApiResources.getURI(ApiResources.orders.base, ApiResources.orders.fetchOrderMaster), request)
            .pipe(takeUntil(this.page.unSubscribe))
            .pipe(finalize(() => this.loading = false))
            .subscribe(
                (response: Array<OrderPrescription>) => {
                    this.record = response;
                    UtilHelper.applyPagination(this.record, this.pagination);
                   
                },
                () => {
                    this.record = [];
                }
            );
    }
   

    onCloseModal() {
        try {
            this.modalRef.close();
            this.modalRef = undefined;
        } catch (e) {
            // ignored;
        }

        this.loading = false;
        this.submitting = undefined;
        this.submitted = undefined;
    }
 


    ngOnInit() {
        this.appData.userAccount
            .pipe(takeUntil(this.page.unSubscribe))
            .subscribe((userAccount: IUserAccount) => {
                if (userAccount) {
                    this.page.userAccount = userAccount;
                    this.fetchEncounterType();
                    this.fetchProviderResources();
                    this.fetch();
                } else {
                    this.page.userAccount = undefined;
                }
            });
     
    }
    onNextPage() {
        $("body,html").animate({ scrollTop: 0 });
        this.fetch();
    }

    ngOnDestroy() {
        this.onCloseModal();
        this.page.unsubscribeAll();
    }
    onApplyFilters() {
        this.filters.applied = UtilHelper.isFiltersApplied(this.filters.options);
        this.initPagination();
        this.fetch();
    }
    onResetFilters() {
        this.filters.init()
        this.fetch();
        
    }
}