import { Component, OnInit } from '@angular/core';
import { Submodules, SubmodulesResponse } from '../../interfaces/submodules.interface';
import { EncService } from '../../services/enc.service';
import { ModulesService } from '../../services/modules.service';
import { MatDialog } from '@angular/material/dialog';
import { Router } from '@angular/router';
import { Permissions, PermissionsInterface } from '../../interfaces/permissions.interface';
import { lastValueFrom } from 'rxjs';
import { SubmoduleFunctionsComponent } from '../template/menu-item/submodule-functions/submodule-functions.component';
import { PurchasePurpose } from '../../interfaces/acquisition-management/purchase-purpose.interface';
import { FunctionsService } from '../../services/functions.service';
import { ModuleFunction } from '../../interfaces/module-functions.interface';
import { ProfileInterface } from '../../interfaces/profile.interface';
import { UserConsultResponse } from '../../interfaces/user.interface';
import { SocketService } from '../../services/socket.service';
import { UsersProfilesService } from '../../services/users-profiles.service';
import { ResourcesService } from '../../services/resources.service';

const ID_MODULE = "S002V01M15IDUE";

@Component({
  selector: 'app-initial-data-upload',
  standalone: false,
  templateUrl: './initial-data-upload.component.html',
  styleUrl: './initial-data-upload.component.css',
})
export class InitialDataUploadComponent implements OnInit {
  isLoading: boolean;
  hasError: boolean;
  errorStr: string;
  submodules: Submodules[];
  submodulesAux: Submodules[];
 
  constructor(
    private _encService: EncService,
    private _modulesService: ModulesService,
    private _dialog: MatDialog,
    private _router: Router,
    private _socketService: SocketService,
    private _usersProfilesService: UsersProfilesService,
    private _resourcesService: ResourcesService,
    private _functionsService: FunctionsService,
  ) { 
    this._functionsService.consultModuleStatus(ID_MODULE);
    this.isLoading = true;
    this.hasError = false;
    this.errorStr = "";
    this.submodules = [];
    this.submodulesAux = [];
  }
 
  ngOnInit(): void {
    this.getSubmodules();
    this.setupSocketListeners();
  }

  private setupSocketListeners(): void {
    this._socketService.refreshPermissions().subscribe(async (profUpdEnc) => {
      try {
        await this.handlePermissionRefresh(profUpdEnc);
      } catch (error: any) {
        this.handleError(error, 'PAD');
      }
    });

    this._socketService.refreshModules().subscribe(async () => {
      this._functionsService.consultModuleStatus(ID_MODULE);
    });
  }

  private async handlePermissionRefresh(profUpdEnc: any): Promise<void> {
    const idUser = localStorage.getItem('idusuario');
    if (!idUser) {
      throw new Error('Usuario no encontrado');
    }

    const usrInfo: UserConsultResponse = await lastValueFrom(
      this._usersProfilesService.getUser(idUser, idUser, 1)
    );
    
    if (usrInfo.error) {
      this._resourcesService.openSnackBar('ERR_NPE000: Ocurrió un error inesperado.');
      return;
    }

    const idProfDec = await this._encService.decrypt(usrInfo.response.PERFIL);
    const currentProfile = await this._encService.decrypt(localStorage.getItem('perfil')!);

    if (idProfDec !== currentProfile) {
      this._router.navigate(['/sam/home']);
      return;
    }
    
    const profileUpdated = await this._encService.decrypt(`${profUpdEnc}`);
    if (profileUpdated === currentProfile) {
      await this.updateSubmodulesWithPermissions(idUser);
    }
  }

  private async updateSubmodulesWithPermissions(idUser: string): Promise<void> {
    const profile = localStorage.getItem('perfil')!;
    const profInfo: ProfileInterface = await lastValueFrom(
      this._usersProfilesService.getProfile(profile, idUser, 1)
    );

    const permArr = await this._functionsService.processPermissions(profInfo.response.PERMISOS.permissions);
    const modPerm = permArr.filter(item => item.id === ID_MODULE);
    
    if (modPerm.length > 0) {
      this.submodules = this.filterSubmodulesByPermissions(this.submodulesAux, modPerm[0]);
    }
  }

  private filterSubmodulesByPermissions(submodules: Submodules[], modulePermission: any): Submodules[] {
    return submodules.filter(submodule => {
      const subPermission = modulePermission.children.find(
        (child: any) => child.id === submodule.IDSUBMODULO
      );
      return subPermission && subPermission.access > 0;
    });
  }
 
  async getSubmodules(): Promise<void> {
    try {
      this.isLoading = true;
      this.hasError = false;
      this.errorStr = "";

      console.log('Iniciando carga de submodulos...');


      const permissions = await this.getPermissionsFromStorage();
      console.log('Permisos obtenidos:', permissions);


      const modulePermissions = this.filterModulePermissions(permissions);
      console.log('Permisos del módulo:', modulePermissions);


      const submodulesResponse = await this.fetchSubmodulesFromService();
      console.log('Respuesta de submodulos:', submodulesResponse);

      if (submodulesResponse.error) {
        this.hasError = true;
        this.errorStr = submodulesResponse.msg;
        return;
      }


      await this.processSubmodules(submodulesResponse.response, modulePermissions);
      
      console.log('Submodulos procesados:', this.submodules);
      console.log('Submodulos auxiliares:', this.submodulesAux);

    } catch (error: any) {
      console.error('Error en getSubmodules:', error);
      this.handleError(error, 'getSubmodules');
    } finally {
      this.isLoading = false;
    }
  }

  private async getPermissionsFromStorage(): Promise<PermissionsInterface[]> {
    const permissionsEnc = localStorage.getItem('permisos');
    let permissionsDec = '';
    
    if (!permissionsEnc || permissionsEnc === '' || permissionsEnc === 'null') {
      console.log('No se encontraron permisos en localStorage');
      return [];
    }

    try {
      permissionsDec = await this._encService.decrypt(permissionsEnc);
      const permissionsArr: Permissions = JSON.parse(permissionsDec);
      return permissionsArr.permissions || [];
    } catch (error) {
      console.error('Error al desencriptar permisos:', error);
      return [];
    }
  }

  private filterModulePermissions(permissions: PermissionsInterface[]): PermissionsInterface[] {
    return permissions.filter(item => item.id === ID_MODULE);
  }

  private async fetchSubmodulesFromService(): Promise<SubmodulesResponse> {
    const moduleEnc = await this._encService.encrypt(ID_MODULE);
    const idEnc = localStorage.getItem('idusuario')!;
    
    return await lastValueFrom(
      this._modulesService.getSubmodules(moduleEnc, idEnc, 1)
    );
  }

  private async processSubmodules(submodules: Submodules[], modulePermissions: PermissionsInterface[]): Promise<void> {

    this.submodules = [];
    this.submodulesAux = [];

    for (const submodule of submodules) {

      const idSub = await this._encService.decrypt(submodule.IDSUBMODULO);
      const processedSubmodule = { ...submodule, IDSUBMODULO: idSub };
      

      this.submodulesAux.push(processedSubmodule);

      if (this.hasSubmodulePermission(idSub, modulePermissions)) {
        this.submodules.push(processedSubmodule);
      }
    }
  }

  private hasSubmodulePermission(submoduleId: string, modulePermissions: PermissionsInterface[]): boolean {
    if (modulePermissions.length === 0) {
      console.log('No hay permisos de módulo, permitiendo acceso por defecto');
      return true; 
    }

    const modulePermission = modulePermissions[0];
    if (!modulePermission.children || modulePermission.children.length === 0) {
      console.log('No hay permisos de submodulo, permitiendo acceso por defecto');
      return true;
    }

    const subPermission = modulePermission.children.find(child => child.id === submoduleId);
    const hasAccess = Boolean(subPermission && subPermission.access > 0);
    
    console.log(`Permiso para submodulo ${submoduleId}:`, hasAccess);
    return hasAccess;
  }

  private handleError(error: any, context: string): void {
    console.error(`Error en ${context}:`, error);
    
    if (error.error?.msg) {
      this.errorStr = error.error.msg;
    } else {
      this.errorStr = "Ocurrió un error inesperado.";
    }

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


    const errorCode = context === 'PAD' ? `ERR_${context}003` : 'ERR_GEN001';
    this._resourcesService.openSnackBar(`${errorCode}: ${this.errorStr}`);
  }
 
  openMenu(submodule: Submodules): void {
    // Navegar directamente al componente del submodulo
    this.navigateToSubmodule(submodule.IDSUBMODULO);
  }

  private navigateToSubmodule(submoduleId: string): void {
    // Extraer el ID del submodulo (ejemplo: de "S002V01S15IDUP" a "15IDUP")
    const idSub = submoduleId.replace("S002V01S", "").substring(2);
    
    // Navegar directamente al submodulo
    this._router.navigate([`sam/initial-data-upload/${idSub}`]);
    
    console.log(`Navegando a submodulo: ${submoduleId} -> sam/initial-data-upload/${idSub}`);
  }

}