Added test program

This commit is contained in:
2023-07-12 18:19:28 +02:00
parent 1742537612
commit 4627e103fe
13 changed files with 351 additions and 306 deletions

View File

@@ -5,16 +5,42 @@ VisualStudioVersion = 17.3.32811.315
MinimumVisualStudioVersion = 10.0.40219.1 MinimumVisualStudioVersion = 10.0.40219.1
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "EonaCat.Logger", "EonaCat.Logger\EonaCat.Logger.csproj", "{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}" Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "EonaCat.Logger", "EonaCat.Logger\EonaCat.Logger.csproj", "{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}"
EndProject EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "LoggerTest", "LoggerTest\LoggerTest.csproj", "{3530C36E-E245-43E1-8C5C-9FBCA450728F}"
EndProject
Global Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU Debug|Any CPU = Debug|Any CPU
Debug|x64 = Debug|x64
Debug|x86 = Debug|x86
Release|Any CPU = Release|Any CPU Release|Any CPU = Release|Any CPU
Release|x64 = Release|x64
Release|x86 = Release|x86
EndGlobalSection EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution GlobalSection(ProjectConfigurationPlatforms) = postSolution
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU {DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|Any CPU.Build.0 = Debug|Any CPU {DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|Any CPU.Build.0 = Debug|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|x64.ActiveCfg = Debug|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|x64.Build.0 = Debug|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|x86.ActiveCfg = Debug|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Debug|x86.Build.0 = Debug|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|Any CPU.ActiveCfg = Release|Any CPU {DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|Any CPU.ActiveCfg = Release|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|Any CPU.Build.0 = Release|Any CPU {DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|Any CPU.Build.0 = Release|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|x64.ActiveCfg = Release|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|x64.Build.0 = Release|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|x86.ActiveCfg = Release|Any CPU
{DCD1D32E-0F24-4D0F-A6B6-59941C0F9BB7}.Release|x86.Build.0 = Release|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Debug|Any CPU.Build.0 = Debug|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Debug|x64.ActiveCfg = Debug|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Debug|x64.Build.0 = Debug|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Debug|x86.ActiveCfg = Debug|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Debug|x86.Build.0 = Debug|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Release|Any CPU.ActiveCfg = Release|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Release|Any CPU.Build.0 = Release|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Release|x64.ActiveCfg = Release|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Release|x64.Build.0 = Release|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Release|x86.ActiveCfg = Release|Any CPU
{3530C36E-E245-43E1-8C5C-9FBCA450728F}.Release|x86.Build.0 = Release|Any CPU
EndGlobalSection EndGlobalSection
GlobalSection(SolutionProperties) = preSolution GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE HideSolutionNode = FALSE

View File

@@ -35,8 +35,33 @@ namespace EonaCat.Logger
return ELogType.WARNING; return ELogType.WARNING;
case LogLevel.Trace: case LogLevel.Trace:
return ELogType.TRACE; return ELogType.TRACE;
default: case LogLevel.Information:
return ELogType.INFO; return ELogType.INFO;
default:
return ELogType.TRAFFIC;
}
}
public static LogLevel ToLogLevel(this ELogType logLevel)
{
switch (logLevel)
{
case ELogType.NONE:
return LogLevel.None;
case ELogType.ERROR:
return LogLevel.Error;
case ELogType.DEBUG:
return LogLevel.Debug;
case ELogType.CRITICAL:
return LogLevel.Critical;
case ELogType.WARNING:
return LogLevel.Warning;
case ELogType.TRACE:
return LogLevel.Trace;
case ELogType.INFO:
return LogLevel.Information;
default:
return LogLevel.Trace;
} }
} }
@@ -49,17 +74,38 @@ namespace EonaCat.Logger
case ESeverity.Warn: case ESeverity.Warn:
return ELogType.WARNING; return ELogType.WARNING;
case ESeverity.Emergency: case ESeverity.Emergency:
return ELogType.CRITICAL; return ELogType.TRACE;
case ESeverity.Critical: case ESeverity.Critical:
return ELogType.CRITICAL; return ELogType.CRITICAL;
case ESeverity.Alert: case ESeverity.Alert:
return ELogType.ERROR; return ELogType.TRAFFIC;
case ESeverity.Error: case ESeverity.Error:
return ELogType.ERROR; return ELogType.ERROR;
default: default:
return ELogType.INFO; return ELogType.INFO;
} }
} }
public static ESeverity ToSeverity(this ELogType logLevel)
{
switch (logLevel)
{
case ELogType.DEBUG:
return ESeverity.Debug;
case ELogType.WARNING:
return ESeverity.Warn;
case ELogType.CRITICAL:
return ESeverity.Critical;
case ELogType.TRACE:
return ESeverity.Emergency;
case ELogType.ERROR:
return ESeverity.Error;
case ELogType.TRAFFIC:
return ESeverity.Alert;
default:
return ESeverity.Info;
}
}
} }
/// <summary> /// <summary>

View File

@@ -8,7 +8,7 @@
net7.0; net7.0;
</TargetFrameworks> </TargetFrameworks>
<ApplicationIcon>icon.ico</ApplicationIcon> <ApplicationIcon>icon.ico</ApplicationIcon>
<Version>1.1.1</Version> <Version>1.1.4</Version>
<Authors>EonaCat (Jeroen Saey)</Authors> <Authors>EonaCat (Jeroen Saey)</Authors>
<GeneratePackageOnBuild>true</GeneratePackageOnBuild> <GeneratePackageOnBuild>true</GeneratePackageOnBuild>
<Company>EonaCat (Jeroen Saey)</Company> <Company>EonaCat (Jeroen Saey)</Company>

View File

@@ -1,5 +1,6 @@
using System; using System;
using EonaCat.Logger.EonaCatCoreLogger.Models; using EonaCat.Logger.EonaCatCoreLogger.Models;
using EonaCat.Logger.Extensions;
using EonaCat.Logger.Managers; using EonaCat.Logger.Managers;
using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging;

View File

@@ -3,6 +3,7 @@ using System.Collections.Concurrent;
using System.Collections.Generic; using System.Collections.Generic;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
using EonaCat.Logger.Managers;
using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options; using Microsoft.Extensions.Options;
@@ -40,7 +41,11 @@ namespace EonaCat.Logger.EonaCatCoreLogger.Internal
private async Task ProcessLogQueueAsync(object state) private async Task ProcessLogQueueAsync(object state)
{ {
await WriteMessagesAsync(new List<LogMessage> { new LogMessage { Message = $"[{DllInfo.ApplicationName}] {DllInfo.ApplicationName} started.{Environment.NewLine}", Timestamp = DateTimeOffset.Now } }, _cancellationTokenSource.Token).ConfigureAwait(false); var startupMessage = $"{DllInfo.ApplicationName} started.{Environment.NewLine}";
startupMessage = LogHelper.FormatMessageWithHeader(new LoggerSettings(), ELogType.INFO, startupMessage, DateTime.Now);
AddMessage(DateTimeOffset.Now, startupMessage);
while (!_cancellationTokenSource.IsCancellationRequested) while (!_cancellationTokenSource.IsCancellationRequested)
{ {
int limit = _batchSize <= 0 ? int.MaxValue : _batchSize; int limit = _batchSize <= 0 ? int.MaxValue : _batchSize;

View File

@@ -0,0 +1,72 @@
using System;
using System.Collections;
using System.Diagnostics;
using System.Text;
namespace EonaCat.Logger.Extensions
{
public static class ExceptionExtensions
{
public static string FormatExceptionToMessage(this Exception exception, string module = null, string method = null)
{
if (exception == null)
return string.Empty;
var st = new StackTrace(exception, true);
var frame = st.GetFrame(0);
int fileLine = frame.GetFileLineNumber();
string filename = frame.GetFileName();
StringBuilder sb = new StringBuilder();
sb.AppendLine();
sb.AppendLine("--- Exception details provided by EonaCatLogger ---");
if (!string.IsNullOrEmpty(module))
sb.AppendLine(" Module : " + module);
if (!string.IsNullOrEmpty(method))
sb.AppendLine(" Method : " + method);
sb.Append(" Type : ").AppendLine(exception.GetType().ToString());
sb.Append(" Data : ").AppendLine(exception.Data != null && exception.Data.Count > 0 ? FormatExceptionData(exception.Data) : "(none)");
sb.Append(" Inner : ").AppendLine(exception.InnerException != null ? FormatInnerException(exception.InnerException) : "(null)");
sb.Append(" Message : ").AppendLine(exception.Message);
sb.Append(" Source : ").AppendLine(exception.Source);
sb.Append(" StackTrace : ").AppendLine(exception.StackTrace);
sb.Append(" Line : ").AppendLine(fileLine.ToString());
sb.Append(" File : ").AppendLine(filename);
sb.Append(" ToString : ").AppendLine(exception.ToString());
sb.AppendLine("---");
return sb.ToString();
}
private static string FormatExceptionData(IDictionary data)
{
StringBuilder sb = new StringBuilder();
foreach (DictionaryEntry entry in data)
{
sb.Append(" | ")
.Append(entry.Key)
.Append(": ")
.AppendLine(entry.Value.ToString());
}
return sb.ToString();
}
private static string FormatInnerException(Exception innerException)
{
StringBuilder sb = new StringBuilder();
sb.AppendLine(innerException.GetType().ToString())
.AppendLine(" Message : " + innerException.Message)
.AppendLine(" Source : " + innerException.Source)
.AppendLine(" StackTrace : " + innerException.StackTrace)
.AppendLine(" ToString : " + innerException.ToString())
.Append(" Data : ")
.AppendLine(innerException.Data != null && innerException.Data.Count > 0 ? FormatExceptionData(innerException.Data) : "(none)");
return sb.ToString();
}
}
}

View File

@@ -1,8 +0,0 @@
namespace EonaCat.Logger.Managers
{
public enum EFileLoggingMode
{
Enabled = 0,
Disabled = 1,
}
}

View File

@@ -1,7 +1,13 @@
namespace EonaCat.Logger.Managers using System;
using System.Threading.Tasks;
namespace EonaCat.Logger.Managers
{ {
public interface ILogManager public interface ILogManager
{ {
void Write(string message, ELogType logType = ELogType.INFO, bool? writeToConsole = null); void Write(string message, ELogType logType = ELogType.INFO, bool? writeToConsole = null);
void Write(Exception exception, string module = null, string method = null, bool criticalException = false,
bool? writeToConsole = null);
} }
} }

View File

@@ -1,160 +1,98 @@
using System; using System;
using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Diagnostics;
using System.Linq; using System.Linq;
using System.Net; using System.Net;
using System.Text; using System.Text;
using System.Threading;
using System.Threading.Tasks;
using EonaCat.Logger.Syslog; using EonaCat.Logger.Syslog;
using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging;
namespace EonaCat.Logger.Managers namespace EonaCat.Logger.Managers
{ {
public static class LogHelper internal static class LogHelper
{ {
private static readonly object FileLock = new object();
internal static string FormatMessageWithHeader(LoggerSettings settings, ELogType logType, string currentMessage, DateTime dateTime) internal static string FormatMessageWithHeader(LoggerSettings settings, ELogType logType, string currentMessage, DateTime dateTime)
{ {
if (string.IsNullOrWhiteSpace(currentMessage)) if (string.IsNullOrWhiteSpace(currentMessage))
return currentMessage; return currentMessage;
string header = settings?.HeaderFormat ?? "[EonaCatLogger]";
if (header.Contains("{ts}"))
header = header.Replace("{ts}", dateTime.ToString(settings?.TimestampFormat));
if (header.Contains("{host}"))
header = header.Replace("{host}", Dns.GetHostName());
if (header.Contains("{thread}"))
header = header.Replace("{thread}", Thread.CurrentThread.ManagedThreadId.ToString());
if (header.Contains("{sev}"))
header = header.Replace("{sev}", logType.ToString());
string fullMessage = AddHeaderIfNotExists(settings, header, currentMessage);
return fullMessage;
}
private static string AddHeaderIfNotExists(LoggerSettings settings, string header, string currentMessage)
{
if (settings == null || !settings.RemoveMessagePrefix)
{
if (!currentMessage.Contains("[EonaCatLogger]"))
return "[EonaCatLogger] " + header + " " + currentMessage;
}
return header + " " + currentMessage;
}
public static string FormatExceptionToMessage(this Exception exception, string module = null, string method = null)
{
if (exception == null)
return string.Empty;
var st = new StackTrace(exception, true);
var frame = st.GetFrame(0);
int fileLine = frame.GetFileLineNumber();
string filename = frame.GetFileName();
string message =
Environment.NewLine +
"--- Exception details provided by EonaCatLogger ---" + Environment.NewLine +
(!string.IsNullOrEmpty(module) ? " Module : " + module + Environment.NewLine : "") +
(!string.IsNullOrEmpty(method) ? " Method : " + method + Environment.NewLine : "") +
" Type : " + exception.GetType().ToString() + Environment.NewLine +
" Data : " + (exception.Data != null && exception.Data.Count > 0 ? Environment.NewLine + FormatExceptionData(exception.Data) : "(none)") + Environment.NewLine +
" Inner : " + (exception.InnerException != null ? FormatInnerException(exception.InnerException) : "(null)") + Environment.NewLine +
" Message : " + exception.Message + Environment.NewLine +
" Source : " + exception.Source + Environment.NewLine +
" StackTrace : " + exception.StackTrace + Environment.NewLine +
" Line : " + fileLine + Environment.NewLine +
" File : " + filename + Environment.NewLine +
" ToString : " + exception.ToString() + Environment.NewLine +
"---";
return message;
}
private static string FormatExceptionData(IDictionary data)
{
StringBuilder sb = new StringBuilder(); StringBuilder sb = new StringBuilder();
foreach (DictionaryEntry entry in data) sb.Append(settings?.HeaderFormat ?? "[EonaCatLogger]");
if (settings != null)
{ {
sb.Append(" | ") if (sb.ToString().Contains("{ts}"))
.Append(entry.Key) sb.Replace("{ts}", dateTime.ToString(settings.TimestampFormat));
.Append(": ")
.Append(entry.Value) if (sb.ToString().Contains("{host}"))
.Append(Environment.NewLine); sb.Replace("{host}", $"[Host:{Dns.GetHostName()}]");
if (sb.ToString().Contains("{thread}"))
sb.Replace("{thread}", $"[ThreadId:{Environment.CurrentManagedThreadId.ToString()}]");
if (sb.ToString().Contains("{sev}"))
sb.Replace("{sev}", $"[{logType.ToString()}]");
if (!settings.RemoveMessagePrefix && !currentMessage.Contains("[EonaCatLogger]"))
sb.Insert(0, "[EonaCatLogger] ");
} }
sb.Append(" ");
sb.Append(currentMessage);
return sb.ToString(); return sb.ToString();
} }
private static string FormatInnerException(Exception innerException)
{
StringBuilder sb = new StringBuilder();
sb.AppendLine(innerException.GetType().ToString()) internal static void SendToConsole(LoggerSettings settings, ELogType logType, string message, bool writeToConsole)
.AppendLine(" Message : " + innerException.Message)
.AppendLine(" Source : " + innerException.Source)
.AppendLine(" StackTrace : " + innerException.StackTrace)
.AppendLine(" ToString : " + innerException.ToString())
.Append(" Data : ")
.AppendLine(innerException.Data != null && innerException.Data.Count > 0 ? Environment.NewLine + FormatExceptionData(innerException.Data) : "(none)");
return sb.ToString();
}
internal static void SendConsole(LoggerSettings settings, ELogType logType, string message, bool writeToConsole)
{ {
if (settings == null || !writeToConsole || string.IsNullOrWhiteSpace(message)) if (settings == null || !writeToConsole || string.IsNullOrWhiteSpace(message))
return; return;
if (settings.EnableColors) if (settings.EnableColors && settings.Colors != null)
{ {
ConsoleColor prevForeground = Console.ForegroundColor; ConsoleColor prevForeground = Console.ForegroundColor;
ConsoleColor prevBackground = Console.BackgroundColor; ConsoleColor prevBackground = Console.BackgroundColor;
if (settings.Colors != null) ConsoleColor foregroundColor;
ConsoleColor backgroundColor;
switch (logType)
{ {
switch (logType) case ELogType.DEBUG:
{ foregroundColor = settings.Colors.Debug.Foreground;
case ELogType.DEBUG: backgroundColor = settings.Colors.Debug.Background;
Console.ForegroundColor = settings.Colors.Debug.Foreground; break;
Console.BackgroundColor = settings.Colors.Debug.Background; case ELogType.INFO:
break; foregroundColor = settings.Colors.Info.Foreground;
case ELogType.INFO: backgroundColor = settings.Colors.Info.Background;
Console.ForegroundColor = settings.Colors.Info.Foreground; break;
Console.BackgroundColor = settings.Colors.Info.Background; case ELogType.WARNING:
break; foregroundColor = settings.Colors.Warning.Foreground;
case ELogType.WARNING: backgroundColor = settings.Colors.Warning.Background;
Console.ForegroundColor = settings.Colors.Warning.Foreground; break;
Console.BackgroundColor = settings.Colors.Warning.Background; case ELogType.ERROR:
break; foregroundColor = settings.Colors.Error.Foreground;
case ELogType.ERROR: backgroundColor = settings.Colors.Error.Background;
Console.ForegroundColor = settings.Colors.Error.Foreground; break;
Console.BackgroundColor = settings.Colors.Error.Background; case ELogType.TRAFFIC:
break; foregroundColor = settings.Colors.Traffic.Foreground;
case ELogType.TRAFFIC: backgroundColor = settings.Colors.Traffic.Background;
Console.ForegroundColor = settings.Colors.Traffic.Foreground; break;
Console.BackgroundColor = settings.Colors.Traffic.Background; case ELogType.CRITICAL:
break; foregroundColor = settings.Colors.Critical.Foreground;
case ELogType.CRITICAL: backgroundColor = settings.Colors.Critical.Background;
Console.ForegroundColor = settings.Colors.Critical.Foreground; break;
Console.BackgroundColor = settings.Colors.Critical.Background; case ELogType.TRACE:
break; foregroundColor = settings.Colors.Trace.Foreground;
case ELogType.TRACE: backgroundColor = settings.Colors.Trace.Background;
Console.ForegroundColor = settings.Colors.Trace.Foreground; break;
Console.BackgroundColor = settings.Colors.Trace.Background; default:
break; return;
}
} }
Console.ForegroundColor = foregroundColor;
Console.BackgroundColor = backgroundColor;
Console.WriteLine(message); Console.WriteLine(message);
Console.ForegroundColor = prevForeground; Console.ForegroundColor = prevForeground;
Console.BackgroundColor = prevBackground; Console.BackgroundColor = prevBackground;
@@ -165,54 +103,20 @@ namespace EonaCat.Logger.Managers
} }
} }
internal static void SendFile(ILogger logger, LoggerSettings settings, ELogType logType, string message, int maxTries = 3) internal static void SendToFile(ILogger logger, LoggerSettings settings, ELogType logType, string message)
{ {
lock (FileLock) if (logger == null || settings == null || !settings.EnableFileLogging || string.IsNullOrWhiteSpace(message))
{ return;
if (logger == null || settings == null || !settings.EnableFileLogging || string.IsNullOrWhiteSpace(message))
return;
int tries = 0; LogLevel logLevel = logType.ToLogLevel();
bool completed = false;
while (!completed) if (logLevel >= settings.MaxLogType.ToLogLevel()) // Filter out log levels
{ Log(logger, logLevel, message);
try }
{
switch (logType) private static void Log(ILogger logger, LogLevel logLevel, string message)
{ {
case ELogType.CRITICAL: logger.Log(logLevel, message);
logger.LogCritical(message);
break;
case ELogType.DEBUG:
logger.LogDebug(message);
break;
case ELogType.ERROR:
logger.LogError(message);
break;
case ELogType.INFO:
logger.LogInformation(message);
break;
case ELogType.TRACE:
logger.LogTrace(message);
break;
case ELogType.TRAFFIC:
logger.LogTrace($"[TRAFFIC] {message}");
break;
case ELogType.WARNING:
logger.LogWarning(message);
break;
}
completed = true;
}
catch (Exception exc)
{
tries++;
Task.Delay(100);
if (tries >= maxTries)
throw;
}
}
}
} }
internal static void SendToSysLogServers(LoggerSettings settings, string message) internal static void SendToSysLogServers(LoggerSettings settings, string message)
@@ -227,31 +131,31 @@ namespace EonaCat.Logger.Managers
byte[] data = Encoding.UTF8.GetBytes(message); byte[] data = Encoding.UTF8.GetBytes(message);
var sysLogServers = settings.SysLogServers.ToList(); foreach (SyslogServer server in settings.SysLogServers)
foreach (SyslogServer server in sysLogServers)
{ {
if (string.IsNullOrWhiteSpace(server.Hostname))
{
Console.WriteLine("Server hostname not specified, skipping syslog server");
continue;
}
if (server.Port < 0)
{
Console.WriteLine("Server port must be zero or greater, skipping syslog server");
continue;
}
lock (server.SendLock) lock (server.SendLock)
{ {
if (string.IsNullOrWhiteSpace(server.Hostname))
{
Console.WriteLine("Server hostname not specified, skipping syslog server");
}
if (server.Port < 0)
{
Console.WriteLine("Server port must be zero or greater, skipping syslog server");
}
try try
{ {
server.Udp.Send(data, data.Length); server.Udp.Send(data, data.Length);
} }
catch (Exception) catch
{ {
// Do nothing
} }
} }
} }
} }
} }
}
}

View File

@@ -1,21 +1,19 @@
using EonaCat.Logger.Exceptions; using EonaCat.Logger.Syslog;
using EonaCat.Logger.Syslog;
using Microsoft.Extensions.DependencyInjection; using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging; using Microsoft.Extensions.Logging;
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.IO; using System.IO;
using System.Runtime.CompilerServices;
using System.Threading; using System.Threading;
using System.Threading.Tasks; using System.Threading.Tasks;
using EonaCat.Logger.EonaCatCoreLogger; using EonaCat.Logger.EonaCatCoreLogger;
using EonaCat.Logger.EonaCatCoreLogger.Extensions; using EonaCat.Logger.EonaCatCoreLogger.Extensions;
using EonaCat.Logger.EonaCatCoreLogger.Models; using EonaCat.Logger.EonaCatCoreLogger.Models;
using EonaCat.Logger.Extensions;
namespace EonaCat.Logger.Managers namespace EonaCat.Logger.Managers
{ {
// This file is part of the EonaCat project(s) which is released under the Apache License.
// See the LICENSE file or go to https://EonaCat.com/License for full license details.
public partial class LogManager : ILogManager, IDisposable public partial class LogManager : ILogManager, IDisposable
{ {
private DateTime _logDate; private DateTime _logDate;
@@ -25,47 +23,41 @@ namespace EonaCat.Logger.Managers
public string CurrentLogFile => LoggerProvider is FileLoggerProvider fileLoggerProvider ? fileLoggerProvider.LogFile : string.Empty; public string CurrentLogFile => LoggerProvider is FileLoggerProvider fileLoggerProvider ? fileLoggerProvider.LogFile : string.Empty;
public bool IsRunning { get; private set; } public bool IsRunning { get; private set; }
public string CategoryName { get; set; }
public string Id { get; }
private bool _disposed;
private static LogManager _instance; private static LogManager _instance;
private LoggerSettings _settings;
private readonly CancellationTokenSource _tokenSource = new CancellationTokenSource(); private readonly CancellationTokenSource _tokenSource = new CancellationTokenSource();
public static LogManager Instance => InstanceInit(); public static LogManager Instance => InstanceInit();
public LoggerSettings Settings public LoggerSettings Settings { get; } = CreateDefaultSettings();
{
get
{
_settings ??= new LoggerSettings();
return _settings;
}
set => _settings = value;
}
private static LogManager InstanceInit() private static LogManager InstanceInit()
{ {
_instance ??= new LogManager(null, id: "EonaCat"); if (_instance == null)
{
_instance = new LogManager(CreateDefaultSettings());
}
return _instance; return _instance;
} }
protected virtual void Dispose(bool disposing) private static LoggerSettings CreateDefaultSettings()
{ {
if (_disposed) var settings = new LoggerSettings();
return; settings.Id = "EonaCatLogger";
settings.MaxLogType = ELogType.TRACE;
if (disposing) return settings;
{
StopLogging();
_tokenSource.Cancel();
}
_disposed = true;
} }
private void StartNewLog() protected virtual async Task DisposeAsync(bool disposing)
{
if (disposing)
{
await StopLoggingAsync().ConfigureAwait(false);
}
}
public async Task StartNewLogAsync()
{ {
if (_tokenSource.IsCancellationRequested) if (_tokenSource.IsCancellationRequested)
return; return;
@@ -73,10 +65,19 @@ namespace EonaCat.Logger.Managers
DateTime now = DateTime.UtcNow; DateTime now = DateTime.UtcNow;
if (IsRunning && now.Date > _logDate.Date) if (IsRunning && now.Date > _logDate.Date)
StopLogging(); await StopLoggingAsync().ConfigureAwait(false);
IsRunning = true; IsRunning = true;
CreateLogger();
Directory.CreateDirectory(Settings.FileLoggerOptions.LogDirectory);
_logDate = now;
}
private void CreateLogger()
{
IServiceCollection serviceCollection = new ServiceCollection(); IServiceCollection serviceCollection = new ServiceCollection();
serviceCollection.AddLogging(builder => builder.AddEonaCatFileLogger(configuration => serviceCollection.AddLogging(builder => builder.AddEonaCatFileLogger(configuration =>
{ {
@@ -95,55 +96,40 @@ namespace EonaCat.Logger.Managers
var serviceProvider = serviceCollection.BuildServiceProvider(); var serviceProvider = serviceCollection.BuildServiceProvider();
LoggerProvider = serviceProvider.GetService<ILoggerProvider>(); LoggerProvider = serviceProvider.GetService<ILoggerProvider>();
LoggerFactory = serviceProvider.GetService<ILoggerFactory>(); LoggerFactory = serviceProvider.GetService<ILoggerFactory>();
Logger = LoggerFactory.CreateLogger(Settings.Id);
CategoryName ??= string.Empty;
Logger = LoggerFactory.CreateLogger(CategoryName);
Directory.CreateDirectory(Settings.FileLoggerOptions.LogDirectory);
_logDate = now;
Write(now, $"{DllInfo.ApplicationName} started.");
} }
public void Assert(bool condition, string message) private void InternalWriteAsync(DateTime dateTime, string message, ELogType logType = ELogType.INFO, bool? writeToConsole = null)
{ {
if (!condition) if (string.IsNullOrEmpty(message) || logType == ELogType.NONE || (int)logType >= (int)Settings.MaxLogType)
throw new EonaCatLoggerAssertionException(message);
}
private void Write(DateTime dateTime, string message, ELogType logType = ELogType.INFO, bool? writeToConsole = null)
{
if (string.IsNullOrEmpty(message) || logType < ELogType.INFO)
return; return;
string currentMessage = message.Length > _settings.MaxMessageLength ? message.Substring(0, _settings.MaxMessageLength) : message; var messageWithHeader = LogHelper.FormatMessageWithHeader(Settings, logType, message, dateTime);
string remainder = message.Length > _settings.MaxMessageLength ? message.Substring(_settings.MaxMessageLength) : "";
var fullMessage = LogHelper.FormatMessageWithHeader(_settings, logType, currentMessage, dateTime); writeToConsole ??= Settings.EnableConsole;
if (writeToConsole.Value)
{
LogHelper.SendToConsole(Settings, logType, messageWithHeader, true);
}
writeToConsole ??= _settings.EnableConsole; Task.Run(() => { LogHelper.SendToFile(Logger, Settings, logType, message); });
LogHelper.SendConsole(_settings, logType, fullMessage, writeToConsole.Value);
LogHelper.SendFile(Logger, _settings, logType, fullMessage);
LogHelper.SendToSysLogServers(_settings, fullMessage);
if (!string.IsNullOrEmpty(remainder)) Task.Run(() => { LogHelper.SendToSysLogServers(Settings, messageWithHeader); });
Write(dateTime, remainder, logType, writeToConsole);
var logMessage = new EonaCatLogMessage var logMessage = new EonaCatLogMessage
{ {
DateTime = dateTime, DateTime = dateTime,
Message = currentMessage, Message = message,
LogType = logType, LogType = logType,
Origin = string.IsNullOrWhiteSpace(Settings?.LogOrigin) ? "LogManager" : Settings.LogOrigin Origin = string.IsNullOrWhiteSpace(Settings.LogOrigin) ? "LogManager" : Settings.LogOrigin
}; };
Settings?.OnLogEvent(logMessage); Settings.OnLogEvent(logMessage);
} }
public void Reset() => Settings?.ResetLogEvent(); public void Reset() => Settings.ResetLogEvent();
public LogManager(LoggerSettings settings, string serverIp, int serverPort, string id = "EonaCatLogger") public LogManager(LoggerSettings settings, string serverIp, int serverPort)
{ {
if (string.IsNullOrEmpty(serverIp)) if (string.IsNullOrEmpty(serverIp))
throw new ArgumentNullException(nameof(serverIp)); throw new ArgumentNullException(nameof(serverIp));
@@ -152,18 +138,16 @@ namespace EonaCat.Logger.Managers
throw new ArgumentException("Server port must be zero or greater."); throw new ArgumentException("Server port must be zero or greater.");
settings.SysLogServers = new List<SyslogServer> settings.SysLogServers = new List<SyslogServer>
{ {
new SyslogServer(serverIp, serverPort) new SyslogServer(serverIp, serverPort)
}; };
Id = id;
Settings = settings; Settings = settings;
SetupLogManager(); SetupLogManager();
} }
public LogManager(LoggerSettings settings, string id = "EonaCatLogger") public LogManager(LoggerSettings settings)
{ {
Id = id;
Settings = settings; Settings = settings;
SetupFileLogger(settings, null, true); SetupFileLogger(settings, null, true);
SetupLogManager(); SetupLogManager();
@@ -193,25 +177,31 @@ namespace EonaCat.Logger.Managers
private void Console_CancelKeyPress(object sender, ConsoleCancelEventArgs e) private void Console_CancelKeyPress(object sender, ConsoleCancelEventArgs e)
{ {
Dispose(true); Dispose();
} }
private void ProcessExit(object sender, EventArgs e) private void ProcessExit(object sender, EventArgs e)
{ {
Dispose(true); Dispose();
} }
private void StopLogging() private Task StopLoggingAsync()
{ {
IsRunning = false; IsRunning = false;
Write(DateTime.UtcNow, $"{DllInfo.ApplicationName} stopped."); InternalWriteAsync(DateTime.UtcNow, $"{DllInfo.ApplicationName} stopped.");
Task.Delay(500, _tokenSource.Token); return Task.Delay(500);
} }
public LogManager(string logFolder = null, bool defaultPrefix = true) public void DeleteCurrentLogFile()
{ {
SetupFileLogger(null, logFolder, defaultPrefix); if (CurrentLogFile != null)
SetupLogManager(); File.Delete(CurrentLogFile);
}
public void Dispose()
{
DisposeAsync(true).GetAwaiter().GetResult();
GC.SuppressFinalize(this);
} }
public void Write(Exception exception, string module = null, string method = null, bool criticalException = false, bool? writeToConsole = null) public void Write(Exception exception, string module = null, string method = null, bool criticalException = false, bool? writeToConsole = null)
@@ -227,25 +217,12 @@ namespace EonaCat.Logger.Managers
if (logType == ELogType.NONE) if (logType == ELogType.NONE)
return; return;
DateTime now = DateTime.UtcNow; var now = DateTime.UtcNow;
if (!IsRunning) if (!IsRunning)
StartNewLog(); StartNewLogAsync().ConfigureAwait(false);
Write(now, message, logType, writeToConsole); InternalWriteAsync(now, message, logType, writeToConsole);
}
public void DeleteCurrentLogFile()
{
if (!string.IsNullOrWhiteSpace(CurrentLogFile))
File.Delete(CurrentLogFile);
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
} }
} }
}
}

View File

@@ -14,6 +14,8 @@ namespace EonaCat.Logger.Managers
public event LogDelegate OnLog; public event LogDelegate OnLog;
public delegate void LogDelegate(EonaCatLogMessage message); public delegate void LogDelegate(EonaCatLogMessage message);
public string Id { get; set; } = "EonaCatLogger";
/// <summary> /// <summary>
/// Determines if we need to remove the prefix [EonaCatLogger] from each message (default: false) /// Determines if we need to remove the prefix [EonaCatLogger] from each message (default: false)
/// </summary> /// </summary>
@@ -100,6 +102,8 @@ namespace EonaCat.Logger.Managers
} }
} }
public ELogType MaxLogType { get; set; } = ELogType.TRACE;
public bool SendToSyslogServers { get; set; } public bool SendToSyslogServers { get; set; }
public List<SyslogServer> SysLogServers { get; set; } public List<SyslogServer> SysLogServers { get; set; }
@@ -136,22 +140,6 @@ namespace EonaCat.Logger.Managers
return new FileLoggerOptions(); return new FileLoggerOptions();
} }
/// <summary>
/// Maximum message length. Must be greater than or equal to 32. Default is 1024.
/// </summary>
public int MaxMessageLength
{
get
{
return _maxMessageLength;
}
set
{
if (value < 32) throw new ArgumentException("Maximum message length must be at least 32.");
_maxMessageLength = value;
}
}
/// <summary> /// <summary>
/// Set the origin of where the OnLog event was initiated /// Set the origin of where the OnLog event was initiated
/// </summary> /// </summary>

View File

@@ -0,0 +1,14 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net7.0</TargetFramework>
<ImplicitUsings>enable</ImplicitUsings>
<Nullable>enable</Nullable>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="..\EonaCat.Logger\EonaCat.Logger.csproj" />
</ItemGroup>
</Project>

14
LoggerTest/Program.cs Normal file
View File

@@ -0,0 +1,14 @@
using EonaCat.Logger;
using EonaCat.Logger.Managers;
LogManager.Instance.Write("INFO", ELogType.INFO, true);
LogManager.Instance.Write("WARNING", ELogType.WARNING, true);
LogManager.Instance.Write("ERROR", ELogType.ERROR, true);
LogManager.Instance.Write("DEBUG", ELogType.DEBUG, true);
LogManager.Instance.Write("CRITICAL", ELogType.CRITICAL, true);
LogManager.Instance.Write("TRACE", ELogType.TRACE, true);
LogManager.Instance.Write("TRAFFIC", ELogType.TRAFFIC, true);
LogManager.Instance.Write("NONE", ELogType.NONE, true);
Console.WriteLine("Press a key to exit");
Console.ReadKey();