import { Component, OnInit } from '@angular/core';
import { TempFileInfo } from '../../../../interfaces/temp-file-info.interface';
import { MatTableDataSource } from '@angular/material/table';
import { MatchErrors } from '../../../users-profiles/profiles-admin/new-profile/new-profile.component';
import { FormControl, Validators } from '@angular/forms';
import { EncService } from '../../../../services/enc.service';
import { SystemAdminService } from '../../../../services/system-admin.service';
import { GdelService } from '../../../../services/gdel.service';
import { ResourcesService } from '../../../../services/resources.service';
import { lastValueFrom } from 'rxjs';

@Component({
    selector: 'app-upload-catalogue',
    templateUrl: './upload-catalogue.component.html',
    styleUrl: './upload-catalogue.component.css',
    standalone: false
})
export class UploadCatalogueComponent implements OnInit {
  catalogues: string[];
  fileData: any;
  fileName = "";
  fileSize = "";
  fileEmpty = true;
  sizeExceded = false;
  type = "";
  isUploading = false;
  isSaving = false;
  attached: TempFileInfo[];

  dataSource?: MatTableDataSource<TempFileInfo>;
  displayedColumns: string[] =  ['ID', 'NOMBRE', 'PESO', 'ACCIONES'];

  errorMatcher = new MatchErrors();
  catalogueType = new FormControl('', [Validators.required]);

  constructor(
    private _encService: EncService,
    private _systemAdminService: SystemAdminService,
    private _gdelService: GdelService,
    private _resourcesService: ResourcesService,
  ) { 
    this.catalogues = ["Códigos postales", "Colonias", "Localidades", "Municipios", "Estados", "Países", "Régimen fiscal", "Monedas" , "General"];
    this.attached = [];
  }

  ngOnInit(): void {
    this.dataSource = new MatTableDataSource(this.attached);
  }

  checkFile(event: any){
    let extArr = event.target.files[0].name.split(".").reverse();
    let extStr = extArr[0];

    if(extStr == 'xls' ||  extStr == 'xlsx'){
      let maxFileSize = 1048576 * 75;
      let fileSize = event.target.files[0].size;

      if(fileSize > maxFileSize){
        this._resourcesService.openSnackBar(`El tamaño del archivo supera el límite de 75 MB`);
      }else{
        let alreadyAttached = false;
        this.attached.forEach(file => {
          alreadyAttached = file.name == event.target.files[0].name && file.size == this.formatBytes(event.target.files[0].size);
        });

        if(alreadyAttached){
          this._resourcesService.openSnackBar("El archivo seleccionado ya fue adjuntado.");
        }else{
          this.isUploading = true;
          this.uploadTmp(event.target.files[0]);
        }
      }
    }else{
      this._resourcesService.openSnackBar('El archivo seleccionado no tiene el formato de Excel');
    }
  }

  formatBytes(bytes: number, decimals = 2) {
    if (bytes === 0) return '0 Bytes';

    const k = 1024;
    const dm = decimals < 0 ? 0 : decimals;
    const sizes = ['Bytes', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];

    const i = Math.floor(Math.log(bytes) / Math.log(k));

    return parseFloat((bytes / Math.pow(k, i)).toFixed(dm)) + ' ' + sizes[i];
  }

  async uploadTmp(fileData: any){
    try{
      let idUser = localStorage.getItem('idusuario');
      let formData = new FormData();

      formData.append('file', fileData);
      formData.append('id_user', idUser!);
      formData.append('linea', "1");

      let response = await lastValueFrom(this._gdelService.uploadTempFile(formData));
      console.log(response);
      
      if(response.error){
        this._resourcesService.openSnackBar(response.msg);
      }else{
        let uploadedFile: TempFileInfo = {
          id: response.response.idArchivo,
          name: fileData.name,
          size: this.formatBytes(fileData.size),
        };
        
        this.attached = [];
        this.attached.push(uploadedFile);
        this.dataSource = new MatTableDataSource(this.attached);
        this.isUploading = false;
      }
    }catch(error: any){
      this.isUploading = false;
      let msg = "";
      if(error.error == undefined){
        msg = 'Ocurrió un error insperado.';
      }else if(error.error.msg == undefined){
        msg = 'Ocurrió un error insperado.';
      }else{
        msg = error.error.msg;
      }

      this._resourcesService.openSnackBar(msg);
    }
  }

  async deleteFile(id: string){
    try{
      let idUser = localStorage.getItem('idusuario');

      let response = await lastValueFrom(this._gdelService.deleteTempFile({
        'id_user': idUser!,
        'id_file': id,
        'linea': 1,
      }));

      if(response.error){
        this._resourcesService.openSnackBar(response.msg);
      }else{
        let attachedAux: TempFileInfo[] = [];
        this.attached.forEach(file => {
          if(file.id != id) attachedAux.push(file);
        });

        this.attached = attachedAux;
        this.dataSource = new MatTableDataSource(this.attached);
      }
    }catch(error: any){
      this.isUploading = false;
      let msg = "";
      if(error.error == undefined){
        msg = 'Ocurrió un error insperado.';
      }else if(error.error.msg == undefined){
        msg = 'Ocurrió un error insperado.';
      }else{
        msg = error.error.msg;
      }

      this._resourcesService.openSnackBar(msg);
    }
  }

  async saveCatalogue(){
    try{
      if(this.attached.length == 0){
        this._resourcesService.openSnackBar('Aún no ha seleccionado ningún archivo adjunto.');
        return;
      }

      if(this.catalogueType.invalid){
        this.catalogueType.markAsTouched();
        return;
      }

      let attachedStr = JSON.stringify(this.attached);
      let idUser = localStorage.getItem('idusuario');
      let type = this.catalogueType.value;
      let body = new FormData();

      body.append('id_user', idUser!);
      body.append('linea', '1');
      body.append('tipo', type!);
      body.append('adjuntos', attachedStr);

      this.isSaving = true;
      await lastValueFrom(this._systemAdminService.saveCatalogue(body));
      this.isSaving = false;

      this._resourcesService.openSnackBar('El catálogo se registró correctamente')
      let close: HTMLElement = document.getElementById('close-button') as HTMLElement;
      close.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(error.error.msg);
      }

      this.isSaving = false;
    }
  }
}
