TrainingUtils.JVSM.psm1

[string]$TimeFormat = "yyyy-MM-ddTHH:mm:ss.f"
$LogLevelConfig = ""
[bool]$LogToFile = $false
[string]$LogFilePath = $null

$LogLevels = @{ 
    "DEBUG" = 0
    "VERBOSE" = 1
    "INFO" = 2
    "WARNING" = 3
    "ERROR" = 4
}

# Mapea las funciones según el nivel de log
$ScreenLogFunction = @{
    "DEBUG" = {param($msg) Write-Debug $msg}
    "VERBOSE" = {param($msg) Write-Verbose $msg}
    "INFO" = {param($msg) Write-Output $msg} #Write-Information
    "WARNING" = {param($msg) Write-Output $msg} #Write-Warning
    "ERROR" = {param($msg) Write-Output $msg} #Write-Error
}

function LoggerSetup {
    param (
        [Parameter(Mandatory=$false)]
        [String]$LogLevelConfigParam = "",
        [Parameter(Mandatory=$false)]
        [bool]$LogToFileParam = $false,
        [Parameter(Mandatory=$false)]
        [string]$LogFilePathParam,
        [Parameter(Mandatory=$false)]
        [String]$TimeFormatParam = "yyyy-MM-ddTHH:mm:ss.f"
    )
    if (("" -ne $LogLevelConfigParam) -and ($LogLevelConfigParam -notin $script:LogLevels.Keys)) {
        Write-Host "LogLevel: '$LogLevelConfigParam' no es válido, usando valor por defecto 'VERBOSE'"
        $script:LogLevelConfig = "VERBOSE"
    } else {
        $script:LogLevelConfig=$LogLevelConfigParam
    }
    $script:LogToFile = $LogToFileParam
    $script:LogFilePath = $LogFilePathParam
    if (($LogToFileParam) -and (-not($LogFilePathParam))) {
        Write-Host "Se ha configurado la opción log to file sin definir un path para el archivo, se deshabilita la opción"
        $script:LogToFile = $False
    }
}

function LogEntry {
    param (
        [Parameter(Mandatory=$true)]
        [string]$LogLevel,
        [Parameter(Mandatory=$true)]
        [string]$LogMsg
    )
    if ($LogLevel -notin $script:LogLevels.Keys) {
        Write-Host "LogLevel inválido" -ForegroundColor Red
        return
    }
    if ("" -eq $script:LogLevelConfig){
        # se aplica la logica segun las banderas o switchs de log
        Write-Host "logica switch -> " -NoNewline
        [string]$TimeStamp = TimeStampGenerator
        [string]$LogLine = "$TimeStamp-[$LogLevel.ToUpper()]:$LogMsg"
        # Debug y Verbose no se imprimen en pantalla a menos de que su respectivo switch esté activado.
        & $script:ScreenLogFunction[$LogLevel] $LogLine
        # Todos los logs se escriben a archivo si el path está configurado
        if ($script:LogToFile) {
            WriteLog $LogLine
            Write-Host "logica switch, escrito a archivo -> $LogLine"
        }
    } else {
        # Aplica la logica del nivel de log
        Write-Host "logica nivel -> " -NoNewline
        if ($script:LogLevels[$LogLevel] -lt $script:LogLevels[$script:LogLevelConfig]) {
            # Si el log level del mesage es menor que el log level configurado, no hay nada que hacer.
            return
        }
        [string]$TimeStamp = TimeStampGenerator
        [string]$LogLine = "$TimeStamp-[$LogLevel.ToUpper()]:$LogMsg"
        Write-Host $LogLine
        if ($script:LogToFile) {
            WriteLog $LogLine
            Write-Host "logica nivel, escrito a archivo -> $LogLine"
        }
    }
}

function TimeStampGenerator {
    return (Get-Date).ToString($TimeFormat)
}

function WriteLog ([string]$LogLine){
    if (-not($script:LogFilePath)){
        Write-Host "Can not write log, LogFilePath is not defined"
        return
    }
    # Write-Host "Tring to write log in $script:LogFilePath"
    Add-Content -Path $script:LogFilePath -Value $LogLine
}