From e5576d9c925210c83ba9f123c2ced86377ece560 Mon Sep 17 00:00:00 2001 From: Jesse Plamondon-Willard Date: Sun, 29 Jan 2023 16:37:22 -0500 Subject: require subkey for update manifest checks --- src/SMAPI.Web/Framework/Clients/GenericModPage.cs | 4 +-- .../UpdateManifest/UpdateManifestModPage.cs | 2 +- src/SMAPI.Web/Framework/IModPage.cs | 4 +-- src/SMAPI.Web/Framework/ModSiteManager.cs | 29 +++++++++------------- src/SMAPI.Web/Framework/RemoteModStatus.cs | 3 +++ 5 files changed, 20 insertions(+), 22 deletions(-) diff --git a/src/SMAPI.Web/Framework/Clients/GenericModPage.cs b/src/SMAPI.Web/Framework/Clients/GenericModPage.cs index e939f1d8..63ca5a95 100644 --- a/src/SMAPI.Web/Framework/Clients/GenericModPage.cs +++ b/src/SMAPI.Web/Framework/Clients/GenericModPage.cs @@ -40,8 +40,8 @@ namespace StardewModdingAPI.Web.Framework.Clients [MemberNotNullWhen(true, nameof(IModPage.Name), nameof(IModPage.Url))] public bool IsValid => this.Status == RemoteModStatus.Ok; - /// Whether this mod page requires string subkey matching, in which case a subkey that isn't found will return no update instead of falling back to one without. - public bool IsSubkeyStrict { get; set; } = false; + /// Whether this mod page requires update subkeys and does not allow matching downloads without them. + public bool RequireSubkey { get; set; } = false; /********* diff --git a/src/SMAPI.Web/Framework/Clients/UpdateManifest/UpdateManifestModPage.cs b/src/SMAPI.Web/Framework/Clients/UpdateManifest/UpdateManifestModPage.cs index befad268..7537eb24 100644 --- a/src/SMAPI.Web/Framework/Clients/UpdateManifest/UpdateManifestModPage.cs +++ b/src/SMAPI.Web/Framework/Clients/UpdateManifest/UpdateManifestModPage.cs @@ -24,7 +24,7 @@ namespace StardewModdingAPI.Web.Framework.Clients.UpdateManifest public UpdateManifestModPage(string url, UpdateManifestModel manifest) : base(ModSiteKey.UpdateManifest, url) { - this.IsSubkeyStrict = true; + this.RequireSubkey = true; this.Mods = manifest.Mods ?? new Dictionary(); this.SetInfo(name: url, url: url, version: null, downloads: this.ParseDownloads(manifest.Mods).ToArray()); } diff --git a/src/SMAPI.Web/Framework/IModPage.cs b/src/SMAPI.Web/Framework/IModPage.cs index 84af9516..85be41e2 100644 --- a/src/SMAPI.Web/Framework/IModPage.cs +++ b/src/SMAPI.Web/Framework/IModPage.cs @@ -39,8 +39,8 @@ namespace StardewModdingAPI.Web.Framework [MemberNotNullWhen(false, nameof(IModPage.Error))] bool IsValid { get; } - /// Whether this mod page requires string subkey matching, in which case a subkey that isn't found will return no update instead of falling back to one without. - bool IsSubkeyStrict { get; } + /// Whether this mod page requires update subkeys and does not allow matching downloads without them. + bool RequireSubkey { get; } /********* diff --git a/src/SMAPI.Web/Framework/ModSiteManager.cs b/src/SMAPI.Web/Framework/ModSiteManager.cs index f1a088d5..4bb72f78 100644 --- a/src/SMAPI.Web/Framework/ModSiteManager.cs +++ b/src/SMAPI.Web/Framework/ModSiteManager.cs @@ -64,27 +64,26 @@ namespace StardewModdingAPI.Web.Framework /// Whether to allow non-standard versions. public ModInfoModel GetPageVersions(IModPage page, UpdateKey updateKey, bool allowNonStandardVersions, ChangeDescriptor? mapRemoteVersions) { - bool isManifest = updateKey.Site == ModSiteKey.UpdateManifest; + // get ID to show in errors + string displayId = page.RequireSubkey + ? page.Id + updateKey.Subkey + : page.Id; - // get base model + // validate ModInfoModel model = new(); if (!page.IsValid) - { - model.SetError(page.Status, page.Error); - return model; - } - else if (!isManifest) // if this is a manifest, the 'mod page' is the JSON file + return model.SetError(page.Status, page.Error); + if (page.RequireSubkey && updateKey.Subkey is null) + return model.SetError(RemoteModStatus.RequiredSubkeyMissing, $"The {page.Site} mod with ID '{displayId}' requires an update subkey indicating which mod to fetch."); + + // add basic info (unless it's a manifest, in which case the 'mod page' is the JSON file) + if (updateKey.Site != ModSiteKey.UpdateManifest) model.SetBasicInfo(page.Name, page.Url); // fetch versions bool hasVersions = this.TryGetLatestVersions(page, updateKey.Subkey, allowNonStandardVersions, mapRemoteVersions, out ISemanticVersion? mainVersion, out ISemanticVersion? previewVersion, out string? mainModPageUrl, out string? previewModPageUrl); if (!hasVersions) - { - string displayId = isManifest - ? page.Id + updateKey.Subkey - : page.Id; return model.SetError(RemoteModStatus.InvalidData, $"The {page.Site} mod with ID '{displayId}' has no valid versions."); - } // apply mod page info model.SetBasicInfo( @@ -212,14 +211,10 @@ namespace StardewModdingAPI.Web.Framework // get versions for subkey if (subkey is not null) - { TryGetVersions(out main, out preview, out mainModPageUrl, out previewModPageUrl, filter: entry => entry.download?.MatchesSubkey(subkey) == true); - if (mod.IsSubkeyStrict) - return main != null; - } // fallback to non-subkey versions - if (main is null) + if (main is null && !mod.RequireSubkey) TryGetVersions(out main, out preview, out mainModPageUrl, out previewModPageUrl); return main != null; } diff --git a/src/SMAPI.Web/Framework/RemoteModStatus.cs b/src/SMAPI.Web/Framework/RemoteModStatus.cs index 139ecfd3..235bcec4 100644 --- a/src/SMAPI.Web/Framework/RemoteModStatus.cs +++ b/src/SMAPI.Web/Framework/RemoteModStatus.cs @@ -12,6 +12,9 @@ namespace StardewModdingAPI.Web.Framework /// The mod does not exist. DoesNotExist, + /// The mod page exists, but it requires a subkey and none was provided. + RequiredSubkeyMissing, + /// The mod was temporarily unavailable (e.g. the site could not be reached or an unknown error occurred). TemporaryError } -- cgit