Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Unity target #13

Open
wants to merge 1 commit into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .UniLogger/Packages/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
"com.boundfoxstudios.fluentassertions": "6.8.0",
"com.dbrizov.naughtyattributes": "2.1.4",
"com.unity.2d.sprite": "1.0.0",
"com.unity.ide.rider": "3.0.25",
"com.unity.ide.rider": "3.0.26",
"com.unity.mobile.android-logcat": "1.3.2",
"com.unity.test-framework": "1.1.33",
"com.unity.textmeshpro": "3.0.6",
Expand Down
2 changes: 1 addition & 1 deletion .UniLogger/Packages/packages-lock.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@
"url": "https://packages.unity.com"
},
"com.unity.ide.rider": {
"version": "3.0.25",
"version": "3.0.26",
"depth": 0,
"source": "registry",
"dependencies": {
Expand Down
27 changes: 18 additions & 9 deletions Runtime/Services/Target.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,46 +3,55 @@

namespace UnityEngine
{
public abstract class Target
public abstract class TargetBase
{
private readonly bool[] _stackTraceLogType;

[NotNull]
public Formatter Formatter { get; }

[NotNull]
public Filterer Filterer { get; }

protected Target() : this(null, null)
protected TargetBase() : this(null, null)
{
}

protected Target([CanBeNull] Formatter formatter = null, [CanBeNull] Filterer filterer = null)
protected TargetBase([CanBeNull] Formatter formatter = null, [CanBeNull] Filterer filterer = null)
{
Formatter = formatter ?? new Formatter();
Filterer = filterer ?? new Filterer(true);
}
}

public abstract class Target : TargetBase
{
private readonly bool[] _stackTraceLogType;

protected Target() : this(null, null)
{
}

protected Target([CanBeNull] Formatter formatter = null, [CanBeNull] Filterer filterer = null) : base(formatter, filterer)
{
_stackTraceLogType = new bool[LogTypes.Count];
foreach (var logType in LogTypes)
{
SetStackTraceEnabled(logType, true);
}
}

public Target SetStackTraceEnabled(LogLevel logLevel, bool enabled)
public void SetStackTraceEnabled(LogLevel logLevel, bool enabled)
{
_stackTraceLogType[(int)logLevel] = enabled;
return this;
}

public bool GetStackTraceEnabled(LogLevel logLevel)
{
return _stackTraceLogType[(int)logLevel];
}

public abstract void Log(string message, [CanBeNull] string stackTrace);
protected internal abstract void Log(string message, [CanBeNull] string stackTrace);

public virtual void Flush()
protected internal virtual void Flush()
{
}
}
Expand Down
8 changes: 8 additions & 0 deletions Runtime/Targets.meta

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

11 changes: 11 additions & 0 deletions Runtime/Targets/UnityTarget.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
using JetBrains.Annotations;

namespace UnityEngine
{
public class UnityTarget : TargetBase
{
internal UnityTarget([NotNull] Formatter formatter, [NotNull] Filterer filterer) : base(formatter, filterer)
{
}
}
}
11 changes: 11 additions & 0 deletions Runtime/Targets/UnityTarget.cs.meta

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

29 changes: 24 additions & 5 deletions Runtime/ULogger.Static.cs
Original file line number Diff line number Diff line change
Expand Up @@ -35,17 +35,36 @@ public partial class ULogger

[CanBeNull]
private static ULoggerData Data { get; set; }

[CanBeNull]
public static List<Target> Targets => Data?.Targets;

public static IEnumerable<TargetBase> GetTargets()
{
if (Data == null) yield break;
yield return Data.UnityTarget;
foreach (var target in Data.Targets)
{
yield return target;
}
}

public static T GetTarget<T>() where T : TargetBase
{
if (Data == null) return null;
if (Data.UnityTarget is T unityTarget)
{
return unityTarget;
}
return Data.Targets.First(c => c is T) as T;
}

public static void Initialize(Formatter unityFormatter = null, Filterer unityFilterer = null)
{
// prepare default loggers and swap unity logger to custom
unityFormatter ??= new Formatter();
unityFilterer ??= new Filterer(true);
var unityTarget = new UnityTarget(unityFormatter, unityFilterer);
Data = new ULoggerData
{
UnityFormatter = unityFormatter ?? new Formatter(),
UnityFilterer = unityFilterer ?? new Filterer(true),
UnityTarget = unityTarget,
LogHandler = new UnityLogger(Debug.unityLogger.logHandler),
};
Debug.unityLogger.logHandler = Data.LogHandler;
Expand Down
11 changes: 6 additions & 5 deletions Runtime/ULogger.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,14 +21,15 @@ internal void SendLogToUnity(LogLevel logLevel, string message, Color color, Obj
}

// means it is possible to send log to Unity, catch using Application.logMessageReceivedThreaded and broadcast to other targets
if (WillBeAllowedByFilterer(Data.UnityFilterer, logLevel, _tags))
if (WillBeAllowedByFilterer(Data.UnityTarget.Filterer, logLevel, _tags))
{
var line = new LogEntry(_tags.Where(c => Data.UnityFilterer.IsAllowed(logLevel, c)), logLevel, message, color, context);
var formattedMessage = Data.UnityFormatter.Format(line);
var line = new LogEntry(_tags.Where(c => Data.UnityTarget.Filterer.IsAllowed(logLevel, c)), logLevel, message, color, context);
var formattedMessage = Data.UnityTarget.Formatter.Format(line);

// manually extract stack trace if stack it disabled by unity but some target needs it
// manually extract stack trace if stack it disabled by unity (or we are in separate thread) but some target needs it
var manualStacktrace = string.Empty;
if (Application.GetStackTraceLogType(logLevel.ConvertToLogType()) == StackTraceLogType.None &&
if (!ThreadDispatcher.IsMainThread ||
Application.GetStackTraceLogType(logLevel.ConvertToLogType()) == StackTraceLogType.None &&
Data.Targets.Any(c => WillBeAllowedByFilterer(c.Filterer, logLevel, _tags) && c.GetStackTraceEnabled(logLevel)))
{
manualStacktrace = StackTraceUtility.ExtractStackTrace();
Expand Down
7 changes: 3 additions & 4 deletions Runtime/ULoggerData.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,8 @@ namespace UnityEngine
{
internal class ULoggerData
{
public List<Target> Targets { get; } = new List<Target>();
public Formatter UnityFormatter { get; set; }
public Filterer UnityFilterer { get; set; }
public UnityLogger LogHandler { get; set; }
public List<Target> Targets { get; } = new();
public UnityTarget UnityTarget { get; init; }
public UnityLogger LogHandler { get; init; }
}
}
9 changes: 9 additions & 0 deletions Runtime/Utilities/IsExternalInit.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
// ReSharper disable once CheckNamespace
namespace System.Runtime.CompilerServices
{
// this is needed to enable the record feature in .NET framework and .NET core <= 3.1 projects
// ReSharper disable once UnusedType.Global
internal static class IsExternalInit
{
}
}
3 changes: 3 additions & 0 deletions Runtime/Utilities/IsExternalInit.cs.meta

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

17 changes: 17 additions & 0 deletions Runtime/Utilities/ThreadDispatcher.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
using System.Threading;

namespace UnityEngine
{
internal static class ThreadDispatcher
{
public static Thread MainThread { get; private set; }

public static bool IsMainThread => MainThread != null && MainThread.ManagedThreadId == Thread.CurrentThread.ManagedThreadId;

[RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.SubsystemRegistration)]
private static void AutoConfigureLogger()
{
MainThread = Thread.CurrentThread;
}
}
}
3 changes: 3 additions & 0 deletions Runtime/Utilities/ThreadDispatcher.cs.meta

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.