track full mod & stack metadata in queued deprecation warnings
This commit is contained in:
parent
1a3befa93e
commit
fd136d34c5
|
@ -83,7 +83,7 @@ namespace StardewModdingAPI
|
|||
get
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: SCore.DeprecationManager.GetSourceNameFromStack(),
|
||||
source: SCore.DeprecationManager.GetModFromStack(),
|
||||
nounPhrase: $"{nameof(Constants)}.{nameof(Constants.ExecutionPath)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
|
|
@ -32,7 +32,7 @@ namespace StardewModdingAPI.Framework.Content
|
|||
get
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: SCore.DeprecationManager.GetSourceNameFromStack(),
|
||||
source: SCore.DeprecationManager.GetModFromStack(),
|
||||
nounPhrase: $"{nameof(IAssetInfo)}.{nameof(IAssetInfo.AssetName)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
@ -68,7 +68,7 @@ namespace StardewModdingAPI.Framework.Content
|
|||
public bool AssetNameEquals(string path)
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: SCore.DeprecationManager.GetSourceNameFromStack(),
|
||||
source: SCore.DeprecationManager.GetModFromStack(),
|
||||
nounPhrase: $"{nameof(IAssetInfo)}.{nameof(IAssetInfo.AssetNameEquals)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Diagnostics;
|
||||
using System.Linq;
|
||||
|
||||
namespace StardewModdingAPI.Framework
|
||||
|
@ -35,34 +36,33 @@ namespace StardewModdingAPI.Framework
|
|||
this.ModRegistry = modRegistry;
|
||||
}
|
||||
|
||||
/// <summary>Get the source name for a mod from its unique ID.</summary>
|
||||
public string? GetSourceNameFromStack()
|
||||
/// <summary>Get a mod for the closest assembly registered as a source of deprecation warnings.</summary>
|
||||
/// <returns>Returns the source name, or <c>null</c> if no registered assemblies were found.</returns>
|
||||
public IModMetadata? GetModFromStack()
|
||||
{
|
||||
return this.ModRegistry.GetFromStack()?.DisplayName;
|
||||
return this.ModRegistry.GetFromStack();
|
||||
}
|
||||
|
||||
/// <summary>Get the source name for a mod from its unique ID.</summary>
|
||||
/// <summary>Get a mod from its unique ID.</summary>
|
||||
/// <param name="modId">The mod's unique ID.</param>
|
||||
public string? GetSourceName(string modId)
|
||||
public IModMetadata? GetMod(string modId)
|
||||
{
|
||||
return this.ModRegistry.Get(modId)?.DisplayName;
|
||||
return this.ModRegistry.Get(modId);
|
||||
}
|
||||
|
||||
/// <summary>Log a deprecation warning.</summary>
|
||||
/// <param name="source">The friendly mod name which used the deprecated code.</param>
|
||||
/// <param name="source">The mod which used the deprecated code, if known.</param>
|
||||
/// <param name="nounPhrase">A noun phrase describing what is deprecated.</param>
|
||||
/// <param name="version">The SMAPI version which deprecated it.</param>
|
||||
/// <param name="severity">How deprecated the code is.</param>
|
||||
public void Warn(string? source, string nounPhrase, string version, DeprecationLevel severity)
|
||||
public void Warn(IModMetadata? source, string nounPhrase, string version, DeprecationLevel severity)
|
||||
{
|
||||
source ??= this.GetSourceNameFromStack() ?? "<unknown>";
|
||||
|
||||
// ignore if already warned
|
||||
if (!this.MarkWarned(source, nounPhrase, version))
|
||||
return;
|
||||
|
||||
// queue warning
|
||||
this.QueuedWarnings.Add(new DeprecationWarning(source, nounPhrase, version, severity, Environment.StackTrace));
|
||||
this.QueuedWarnings.Add(new DeprecationWarning(source, nounPhrase, version, severity, new StackTrace(skipFrames: 1)));
|
||||
}
|
||||
|
||||
/// <summary>A placeholder method used to track deprecated code for which a separate warning will be shown.</summary>
|
||||
|
@ -104,7 +104,7 @@ namespace StardewModdingAPI.Framework
|
|||
else
|
||||
{
|
||||
this.Monitor.Log(message, level);
|
||||
this.Monitor.Log(warning.StackTrace, LogLevel.Debug);
|
||||
this.Monitor.Log(warning.StackTrace.ToString(), LogLevel.Debug);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -116,16 +116,13 @@ namespace StardewModdingAPI.Framework
|
|||
** Private methods
|
||||
*********/
|
||||
/// <summary>Mark a deprecation warning as already logged.</summary>
|
||||
/// <param name="source">The friendly name of the assembly which used the deprecated code.</param>
|
||||
/// <param name="source">The mod which used the deprecated code.</param>
|
||||
/// <param name="nounPhrase">A noun phrase describing what is deprecated (e.g. "the Extensions.AsInt32 method").</param>
|
||||
/// <param name="version">The SMAPI version which deprecated it.</param>
|
||||
/// <returns>Returns whether the deprecation was successfully marked as warned. Returns <c>false</c> if it was already marked.</returns>
|
||||
private bool MarkWarned(string source, string nounPhrase, string version)
|
||||
private bool MarkWarned(IModMetadata? source, string nounPhrase, string version)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(source))
|
||||
throw new InvalidOperationException("The deprecation source cannot be empty.");
|
||||
|
||||
string key = $"{source}::{nounPhrase}::{version}";
|
||||
string key = $"{source?.DisplayName ?? "<unknown>"}::{nounPhrase}::{version}";
|
||||
if (this.LoggedDeprecations.Contains(key))
|
||||
return false;
|
||||
this.LoggedDeprecations.Add(key);
|
||||
|
|
|
@ -1,3 +1,5 @@
|
|||
using System.Diagnostics;
|
||||
|
||||
namespace StardewModdingAPI.Framework
|
||||
{
|
||||
/// <summary>A deprecation warning for a mod.</summary>
|
||||
|
@ -6,8 +8,11 @@ namespace StardewModdingAPI.Framework
|
|||
/*********
|
||||
** Accessors
|
||||
*********/
|
||||
/// <summary>The affected mod's display name.</summary>
|
||||
public string ModName { get; }
|
||||
/// <summary>The affected mod.</summary>
|
||||
public IModMetadata? Mod { get; }
|
||||
|
||||
/// <summary>Get the display name for the affected mod.</summary>
|
||||
public string ModName => this.Mod?.DisplayName ?? "<unknown mod>";
|
||||
|
||||
/// <summary>A noun phrase describing what is deprecated.</summary>
|
||||
public string NounPhrase { get; }
|
||||
|
@ -19,21 +24,21 @@ namespace StardewModdingAPI.Framework
|
|||
public DeprecationLevel Level { get; }
|
||||
|
||||
/// <summary>The stack trace when the deprecation warning was raised.</summary>
|
||||
public string StackTrace { get; }
|
||||
public StackTrace StackTrace { get; }
|
||||
|
||||
|
||||
/*********
|
||||
** Public methods
|
||||
*********/
|
||||
/// <summary>Construct an instance.</summary>
|
||||
/// <param name="modName">The affected mod's display name.</param>
|
||||
/// <param name="mod">The affected mod.</param>
|
||||
/// <param name="nounPhrase">A noun phrase describing what is deprecated.</param>
|
||||
/// <param name="version">The SMAPI version which deprecated it.</param>
|
||||
/// <param name="level">The deprecation level for the affected code.</param>
|
||||
/// <param name="stackTrace">The stack trace when the deprecation warning was raised.</param>
|
||||
public DeprecationWarning(string modName, string nounPhrase, string version, DeprecationLevel level, string stackTrace)
|
||||
public DeprecationWarning(IModMetadata? mod, string nounPhrase, string version, DeprecationLevel level, StackTrace stackTrace)
|
||||
{
|
||||
this.ModName = modName;
|
||||
this.Mod = mod;
|
||||
this.NounPhrase = nounPhrase;
|
||||
this.Version = version;
|
||||
this.Level = level;
|
||||
|
|
|
@ -36,7 +36,7 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
public bool Trigger(string name, string[] arguments)
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: SCore.DeprecationManager.GetSourceName(this.ModID),
|
||||
source: SCore.DeprecationManager.GetMod(this.ModID),
|
||||
nounPhrase: $"{nameof(IModHelper)}.{nameof(IModHelper.ConsoleCommands)}.{nameof(ICommandHelper.Trigger)}",
|
||||
version: "3.8.1",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
|
|
@ -29,9 +29,6 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
/// <summary>A content manager for this mod which manages files from the mod's folder.</summary>
|
||||
private readonly ModContentManager ModContentManager;
|
||||
|
||||
/// <summary>The friendly mod name for use in errors.</summary>
|
||||
private readonly string ModName;
|
||||
|
||||
/// <summary>Encapsulates monitoring and logging.</summary>
|
||||
private readonly IMonitor Monitor;
|
||||
|
||||
|
@ -60,7 +57,7 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
get
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: this.ModName,
|
||||
source: this.Mod,
|
||||
nounPhrase: $"{nameof(IContentHelper)}.{nameof(IContentHelper.AssetLoaders)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
@ -76,7 +73,7 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
get
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: this.ModName,
|
||||
source: this.Mod,
|
||||
nounPhrase: $"{nameof(IContentHelper)}.{nameof(IContentHelper.AssetEditors)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
@ -94,18 +91,16 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
/// <param name="contentCore">SMAPI's core content logic.</param>
|
||||
/// <param name="modFolderPath">The absolute path to the mod folder.</param>
|
||||
/// <param name="mod">The mod using this instance.</param>
|
||||
/// <param name="modName">The friendly mod name for use in errors.</param>
|
||||
/// <param name="monitor">Encapsulates monitoring and logging.</param>
|
||||
/// <param name="reflection">Simplifies access to private code.</param>
|
||||
public ContentHelper(ContentCoordinator contentCore, string modFolderPath, IModMetadata mod, string modName, IMonitor monitor, Reflector reflection)
|
||||
public ContentHelper(ContentCoordinator contentCore, string modFolderPath, IModMetadata mod, IMonitor monitor, Reflector reflection)
|
||||
: base(mod)
|
||||
{
|
||||
string managedAssetPrefix = contentCore.GetManagedAssetPrefix(mod.Manifest.UniqueID);
|
||||
|
||||
this.ContentCore = contentCore;
|
||||
this.GameContentManager = contentCore.CreateGameContentManager(managedAssetPrefix + ".content");
|
||||
this.ModContentManager = contentCore.CreateModContentManager(managedAssetPrefix, modName, modFolderPath, this.GameContentManager);
|
||||
this.ModName = modName;
|
||||
this.ModContentManager = contentCore.CreateModContentManager(managedAssetPrefix, this.Mod.DisplayName, modFolderPath, this.GameContentManager);
|
||||
this.Monitor = monitor;
|
||||
this.Reflection = reflection;
|
||||
}
|
||||
|
@ -128,12 +123,12 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
return this.ModContentManager.LoadExact<T>(assetName, useCache: false);
|
||||
|
||||
default:
|
||||
throw new SContentLoadException($"{this.ModName} failed loading content asset '{key}' from {source}: unknown content source '{source}'.");
|
||||
throw new SContentLoadException($"{this.Mod.DisplayName} failed loading content asset '{key}' from {source}: unknown content source '{source}'.");
|
||||
}
|
||||
}
|
||||
catch (Exception ex) when (ex is not SContentLoadException)
|
||||
{
|
||||
throw new SContentLoadException($"{this.ModName} failed loading content asset '{key}' from {source}.", ex);
|
||||
throw new SContentLoadException($"{this.Mod.DisplayName} failed loading content asset '{key}' from {source}.", ex);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -32,7 +32,7 @@ namespace StardewModdingAPI.Framework.ModHelpers
|
|||
get
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: SCore.DeprecationManager.GetSourceName(this.ModID),
|
||||
source: SCore.DeprecationManager.GetMod(this.ModID),
|
||||
nounPhrase: $"{nameof(IModHelper)}.{nameof(IModHelper.Content)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
|
|
@ -1598,7 +1598,7 @@ namespace StardewModdingAPI.Framework
|
|||
if (metadata.Mod is IAssetEditor editor)
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: metadata.DisplayName,
|
||||
source: metadata,
|
||||
nounPhrase: $"{nameof(IAssetEditor)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
@ -1610,7 +1610,7 @@ namespace StardewModdingAPI.Framework
|
|||
if (metadata.Mod is IAssetLoader loader)
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
source: metadata.DisplayName,
|
||||
source: metadata,
|
||||
nounPhrase: $"{nameof(IAssetLoader)}",
|
||||
version: "3.14.0",
|
||||
severity: DeprecationLevel.Notice
|
||||
|
@ -1846,7 +1846,7 @@ namespace StardewModdingAPI.Framework
|
|||
ICommandHelper commandHelper = new CommandHelper(mod, this.CommandManager);
|
||||
CaseInsensitivePathCache relativePathCache = this.ContentCore.GetCaseInsensitivePathCache(mod.DirectoryPath);
|
||||
#pragma warning disable CS0612 // deprecated code
|
||||
ContentHelper contentHelper = new(contentCore, mod.DirectoryPath, mod, mod.DisplayName, monitor, this.Reflection);
|
||||
ContentHelper contentHelper = new(contentCore, mod.DirectoryPath, mod, monitor, this.Reflection);
|
||||
#pragma warning restore CS0612
|
||||
GameContentHelper gameContentHelper = new(contentCore, mod, mod.DisplayName, monitor, this.Reflection);
|
||||
IModContentHelper modContentHelper = new ModContentHelper(contentCore, mod.DirectoryPath, mod, mod.DisplayName, gameContentHelper.GetUnderlyingContentManager(), relativePathCache, this.Reflection);
|
||||
|
|
|
@ -96,7 +96,7 @@ namespace StardewModdingAPI.Utilities
|
|||
if (!nullExpected)
|
||||
{
|
||||
SCore.DeprecationManager.Warn(
|
||||
SCore.DeprecationManager.GetSourceNameFromStack(),
|
||||
SCore.DeprecationManager.GetModFromStack(),
|
||||
$"calling the {nameof(PerScreen<T>)} constructor with null",
|
||||
"3.14.0",
|
||||
DeprecationLevel.Notice
|
||||
|
|
Loading…
Reference in New Issue