import { Component, Inject, OnInit } from '@angular/core';
import { PreventiveWorkOrder, PreventiveWorkOrderResponse } from '../../../../interfaces/preventive-work-order.interface';
import { Activator } from '../../../../interfaces/activator.interface';
import { PriorityInterface } from '../../../system-admin/system-params/system-params.component';
import { MAT_DIALOG_DATA } from '@angular/material/dialog';
import { DOCUMENT } from '@angular/common';
import { EncService } from '../../../../services/enc.service';
import { PreventiveMaintenanceService } from '../../../../services/preventive-maintenance.service';
import { FunctionsService } from '../../../../services/functions.service';
import { SystemAdminService } from '../../../../services/system-admin.service';
import { DocumentManagementService } from '../../../../services/document-management.service';
import { ResourcesService } from '../../../../services/resources.service';
import { lastValueFrom } from 'rxjs';
import { Instruction } from '../new-work-order/new-work-order.component';
import { TempFileInfo } from '../../../../interfaces/temp-file-info.interface';
import { apiTemp } from '../../../../../environments/environment.prod';

@Component({
    selector: 'app-order-details',
    templateUrl: './order-details.component.html',
    styleUrl: './order-details.component.css',
    standalone: false
})
export class OrderDetailsComponent implements OnInit {
  idOrder: number;
  isLoading: boolean;
  hasError: boolean;
  errorStr: string;
  workOrder: PreventiveWorkOrder | null;
  activator: Activator | null;

  MONTHS = ['Enero', 'Febrero', 'Marzo', 'Abril', 'Mayo', 'Junio', 'Julio', 'Agosto', 'Septiembre', 'Octubre', 'Noviembre', 'Diciembre'];
  dayNames = ['Domingos', 'Lunes', 'Martes', 'Miércoles', 'Jueves', 'Viernes', 'Sábados'];
  orderPriorities: PriorityInterface[];
  staffArr: any[];

  constructor(
    @Inject(MAT_DIALOG_DATA) private _data: any,
    @Inject(DOCUMENT) private _document: Document,
    private _encService: EncService,
    private _prevMaintService: PreventiveMaintenanceService,
    private _funcService: FunctionsService,
    private _sysAdminService: SystemAdminService,
    private _docMangeService: DocumentManagementService,
    private _resourcesService: ResourcesService,
  ) { 
    this.idOrder = 0;
    this.isLoading = true;
    this.hasError = false;
    this.errorStr = "";
    this.workOrder = null;
    this.activator = null;
    this.orderPriorities = [];
    this.staffArr = [];
  }

  ngOnInit(): void {
    this.idOrder = parseInt(this._data.idOrder);
    this.getOrderPriorities();
  }

  async getOrderPriorities(){
    try{
      let idUser = localStorage.getItem('idusuario')!;
      let priorities = await lastValueFrom(this._sysAdminService.getOrderPriorities(idUser, 1));

      if(priorities.error){
        this.errorStr = priorities.msg;
        this.hasError = true;
        this.isLoading = false;
      }else{
        let prioritiesArr: PriorityInterface[] = [];
        for(const priority of priorities.response.order_priorities as PriorityInterface[]){
          let priorityEnc = await this._encService.encrypt(priority.value);

          priority.label = `${priority.label} (${priority.value})`;
          priority.value = priorityEnc;

          prioritiesArr.push(priority);
        }

        this.orderPriorities = prioritiesArr;
        this.getPreventiveOrder();
      }
    }catch(error: any){
      if(error.error == undefined){
        this.errorStr = 'Ocurrió un error inesperado.';
      }else if(error.error.msg == undefined){
        this.errorStr = 'Ocurrió un error inesperado.';
      }else{
        this.errorStr = error.error.msg;
      }

      this.hasError = true;
      this.isLoading = false;
    }
  }

  async getPreventiveOrder(){
    try{
      let idUser = localStorage.getItem('idusuario')!;
      let idOrderEnc = await this._encService.encrypt(`${this.idOrder}`);
      let order: PreventiveWorkOrderResponse = await lastValueFrom(this._prevMaintService.getWorkOrder(
        idOrderEnc,
        idUser,
        1
      ));

      this.hasError = order.error;
      this.errorStr = order.msg;

      if(this.hasError){
        this.isLoading = false;
      }else{
        order.response.IDORDEN = await this._encService.decrypt(order.response.IDORDEN);

        let instructionsArr: Instruction[] = JSON.parse(order.response.INSTRUCCIONES);
        for(const instruction of instructionsArr){
          instruction.ID = await this._encService.decrypt(instruction.ID);

          let startDateArr = instruction.INICIO.split(' ');
          let startDateStr = this._funcService.buildHumanDate(startDateArr[0]);
          let startHourStr = this._funcService.getDateTimeHour(instruction.INICIO);

          let endDateArr = instruction.FIN.split(' ');
          let endDateStr = this._funcService.buildHumanDate(endDateArr[0]);
          let endHourStr = this._funcService.getDateTimeHour(instruction.FIN);

          instruction.INICIO = `${startDateStr} a las ${startHourStr}`;
          instruction.FIN = `${endDateStr} a las ${endHourStr}`;
        }

        let equipmentCodeDec = await this._encService.decrypt(order.response.EQUIPAMIENTO);
        order.response.TIPO_EQUIPAMIENTO = `${equipmentCodeDec} - ${order.response.TIPO_EQUIPAMIENTO}`;

        let idEquipmentDec = await this._encService.decrypt(order.response.ID_EQUIPAMIENTO!);
        order.response.MODELO_EQUIPAMIENTO = `${order.response.MODELO_EQUIPAMIENTO} (${idEquipmentDec})`;
        order.response.INSTRUCCIONES_ARR = instructionsArr;

        let orderStartDateArr = order.response.FECHAINICIO!.split(' ');
        let orderStartDateStr = this._funcService.buildHumanDate(orderStartDateArr[0]);
        let orderStartHourStr = this._funcService.getDateTimeHour(order.response.FECHAINICIO!);

        order.response.FECHAINICIO = `${orderStartDateStr} a las ${orderStartHourStr}`;
        if(order.response.FECHAFINAL != null){
          let orderEndDateArr = order.response.FECHAFINAL.split(' ');
          let orderEndDateStr = this._funcService.buildHumanDate(orderEndDateArr[0]);
          let orderEndHourStr = this._funcService.getDateTimeHour(order.response.FECHAFINAL);

          order.response.FECHAFINAL = `${orderEndDateStr} a las ${orderEndHourStr}`;
        }

        let staffArr = JSON.parse(order.response.OPERARIOS);
        order.response.OPERARIOS_ARR = staffArr;

        let documentsArr: TempFileInfo[] = JSON.parse(order.response.DOCUMENTOS);
        for(const document of documentsArr){
          let idDocumentDec = await this._encService.decrypt(document.id);

          document.name = idDocumentDec;
          document.size = this._funcService.formatBytes(parseInt(document.size));
        }

        order.response.RECURSOS_ARR = JSON.parse(order.response.RECURSOS);
        order.response.DOCUMENTOS_ARR = documentsArr;
        let priorityDec = await this._encService.decrypt(order.response.PRIORIDAD);
        for(const priority of this.orderPriorities){
          let valueDec = await this._encService.decrypt(priority.value);
          if(priorityDec == valueDec){
            order.response.PRIORIDAD_OBJ = priority;
          }
        }

        order.response.ESTADO = this.getStatusText(order.response.ESTADO);
        this.workOrder = order.response;
        this.isLoading = false;
      }
    }catch(error: any){
      if(error.error == undefined){
        this.errorStr = 'Ocurrió un error inesperado.';
      }else if(error.error.msg == undefined){
        this.errorStr = 'Ocurrió un error inesperado.';
      }else{
        this.errorStr = error.error.msg;
      }

      this.hasError = true;
      this.isLoading = false;
    }
  }

  getStatusText(status: string): string{
    if(status == 'B'){
      return "Borrador";
    }else if(status == 'R'){
      return "Revisión";
    }else if(status == 'A'){
      return "Activo";
    }else if(status == 'E'){
      return "Eliminado";
    }
    return "";
  }

  async printOrderDetails(){
    try{
      this._resourcesService.openSnackBar('Generando PDF...');

      let idUser = localStorage.getItem('idusuario')!;
      let idOrderEnc = await this._encService.encrypt(`${this.idOrder}`);

      let orderDetails = await lastValueFrom(this._prevMaintService.printOrderDetails(
        idOrderEnc,
        idUser,
        1
      ));

      let idFileEnc = await this._encService.encrypt(orderDetails.response.fileID);
      let download = this._document.getElementById(`download`) as HTMLAnchorElement;

      let downloadToken = await lastValueFrom(this._docMangeService.getDownloadToken(
        idFileEnc,
        idUser,
        1
      ));

      download.href = `${apiTemp}download-file/${downloadToken.response.TOKEN}/${idUser}/1`;
      download.download = orderDetails.response.fileID;
      download.click();
    }catch(error: any){
      if(error.error == undefined){
        this._resourcesService.openSnackBar('Ocurrió un error inesperado.');
      }else if(error.error.msg == undefined){
        this._resourcesService.openSnackBar('Ocurrió un error inesperado.');
      }else{
        this._resourcesService.openSnackBar('Ocurrió un error inesperado.');
      }
    }
  }
}
