From 9afbcee163d58b8ff649cd4b0cbea1e93fe2ef9e Mon Sep 17 00:00:00 2001 From: JustArchi Date: Mon, 3 May 2021 01:08:12 +0200 Subject: [PATCH] STD: Add feature to skip appIDs, packageIDs and depotIDs --- .../GlobalCache.cs | 6 +- .../GlobalConfigExtension.cs | 5 +- .../Localization/Strings.Designer.cs | 9 ++ .../Localization/Strings.resx | 4 + .../SteamTokenDumperConfig.cs | 44 +++++++++ .../SteamTokenDumperPlugin.cs | 98 ++++++++++++++----- 6 files changed, 138 insertions(+), 28 deletions(-) create mode 100644 ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperConfig.cs diff --git a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalCache.cs b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalCache.cs index a1b0aa728..38b471253 100644 --- a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalCache.cs +++ b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalCache.cs @@ -63,9 +63,9 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { internal ulong GetAppToken(uint appID) => AppTokens[appID]; - internal Dictionary GetAppTokensForSubmission() => AppTokens.Where(appToken => (appToken.Value > 0) && (!SubmittedApps.TryGetValue(appToken.Key, out ulong token) || (appToken.Value != token))).ToDictionary(appToken => appToken.Key, appToken => appToken.Value); - internal Dictionary GetDepotKeysForSubmission() => DepotKeys.Where(depotKey => !string.IsNullOrEmpty(depotKey.Value) && (!SubmittedDepots.TryGetValue(depotKey.Key, out string? key) || (depotKey.Value != key))).ToDictionary(depotKey => depotKey.Key, depotKey => depotKey.Value); - internal Dictionary GetPackageTokensForSubmission() => PackageTokens.Where(packageToken => (packageToken.Value > 0) && (!SubmittedPackages.TryGetValue(packageToken.Key, out ulong token) || (packageToken.Value != token))).ToDictionary(packageToken => packageToken.Key, packageToken => packageToken.Value); + internal Dictionary GetAppTokensForSubmission() => AppTokens.Where(appToken => (SteamTokenDumperPlugin.Config?.SecretAppIDs.Contains(appToken.Key) == false) && (appToken.Value > 0) && (!SubmittedApps.TryGetValue(appToken.Key, out ulong token) || (appToken.Value != token))).ToDictionary(appToken => appToken.Key, appToken => appToken.Value); + internal Dictionary GetDepotKeysForSubmission() => DepotKeys.Where(depotKey => (SteamTokenDumperPlugin.Config?.SecretDepotIDs.Contains(depotKey.Key) == false) && !string.IsNullOrEmpty(depotKey.Value) && (!SubmittedDepots.TryGetValue(depotKey.Key, out string? key) || (depotKey.Value != key))).ToDictionary(depotKey => depotKey.Key, depotKey => depotKey.Value); + internal Dictionary GetPackageTokensForSubmission() => PackageTokens.Where(packageToken => (SteamTokenDumperPlugin.Config?.SecretPackageIDs.Contains(packageToken.Key) == false) && (packageToken.Value > 0) && (!SubmittedPackages.TryGetValue(packageToken.Key, out ulong token) || (packageToken.Value != token))).ToDictionary(packageToken => packageToken.Key, packageToken => packageToken.Value); internal static async Task Load() { if (!File.Exists(SharedFilePath)) { diff --git a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalConfigExtension.cs b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalConfigExtension.cs index 441461947..55f796a3b 100644 --- a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalConfigExtension.cs +++ b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/GlobalConfigExtension.cs @@ -23,7 +23,10 @@ using Newtonsoft.Json; namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { public sealed class GlobalConfigExtension { - [JsonProperty] + [JsonProperty(Required = Required.DisallowNull)] + public SteamTokenDumperConfig? SteamTokenDumper { get; private set; } + + [JsonProperty(Required = Required.DisallowNull)] public bool SteamTokenDumperPluginEnabled { get; private set; } [JsonConstructor] diff --git a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.Designer.cs b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.Designer.cs index d1296a358..6d1b3a507 100644 --- a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.Designer.cs +++ b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.Designer.cs @@ -195,6 +195,15 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper.Localization { } } + /// + /// Looks up a localized string similar to {0} initialized, the plugin will not resolve any of those: {1}.. + /// + internal static string PluginSecretListInitialized { + get { + return ResourceManager.GetString("PluginSecretListInitialized", resourceCulture); + } + } + /// /// Looks up a localized string similar to The submission has failed due to too many requests sent, we'll try again in approximately {0} from now.. /// diff --git a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.resx b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.resx index 16eb5f6b9..e649f447b 100644 --- a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.resx +++ b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/Localization/Strings.resx @@ -195,4 +195,8 @@ The data has been successfully submitted. The server has registered a total of new apps/subs/depots: {0}/{1}/{2}. {0} will be replaced by the number of new app access tokens that the server has registered, {1} will be replaced by the number of new package access tokens that the server has registered, {2} will be replaced by the number of new depot keys that the server has registered + + {0} initialized, the plugin will not resolve any of those: {1}. + {0} will be replaced by the name of the config property (e.g. "SecretPackageIDs"), {1} will be replaced by list of the objects (IDs, numbers), separated by a comma + diff --git a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperConfig.cs b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperConfig.cs new file mode 100644 index 000000000..0ca7d5e91 --- /dev/null +++ b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperConfig.cs @@ -0,0 +1,44 @@ +// _ _ _ ____ _ _____ +// / \ _ __ ___ | |__ (_)/ ___| | |_ ___ __ _ _ __ ___ | ___|__ _ _ __ _ __ ___ +// / _ \ | '__|/ __|| '_ \ | |\___ \ | __|/ _ \ / _` || '_ ` _ \ | |_ / _` || '__|| '_ ` _ \ +// / ___ \ | | | (__ | | | || | ___) || |_| __/| (_| || | | | | || _|| (_| || | | | | | | | +// /_/ \_\|_| \___||_| |_||_||____/ \__|\___| \__,_||_| |_| |_||_| \__,_||_| |_| |_| |_| +// | +// Copyright 2015-2021 Łukasz "JustArchi" Domeradzki +// Contact: JustArchi@JustArchi.net +// | +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// | +// http://www.apache.org/licenses/LICENSE-2.0 +// | +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +using System.Collections.Immutable; +using System.Diagnostics.CodeAnalysis; +using Newtonsoft.Json; + +namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { + [SuppressMessage("ReSharper", "ClassCannotBeInstantiated")] + public sealed class SteamTokenDumperConfig { + [JsonProperty(Required = Required.DisallowNull)] + public bool Enabled { get; internal set; } + + [JsonProperty(Required = Required.DisallowNull)] + public ImmutableHashSet SecretAppIDs { get; private set; } = ImmutableHashSet.Empty; + + [JsonProperty(Required = Required.DisallowNull)] + public ImmutableHashSet SecretDepotIDs { get; private set; } = ImmutableHashSet.Empty; + + [JsonProperty(Required = Required.DisallowNull)] + public ImmutableHashSet SecretPackageIDs { get; private set; } = ImmutableHashSet.Empty; + + [JsonConstructor] + internal SteamTokenDumperConfig() { } + } +} diff --git a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperPlugin.cs b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperPlugin.cs index 98d96546e..7366d9ca0 100644 --- a/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperPlugin.cs +++ b/ArchiSteamFarm.OfficialPlugins.SteamTokenDumper/SteamTokenDumperPlugin.cs @@ -38,6 +38,9 @@ using SteamKit2; namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { [Export(typeof(IPlugin))] internal sealed class SteamTokenDumperPlugin : OfficialPlugin, IASF, IBot, IBotSteamClient, ISteamPICSChanges { + [JsonProperty] + internal static SteamTokenDumperConfig? Config { get; private set; } + private static readonly ConcurrentDictionary BotSubscriptions = new(); private static readonly ConcurrentDictionary BotSynchronizations = new(); private static readonly SemaphoreSlim SubmissionSemaphore = new(1, 1); @@ -45,16 +48,13 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { private static GlobalCache? GlobalCache; - [JsonProperty] - private static bool IsEnabled; - [JsonProperty] public override string Name => nameof(SteamTokenDumperPlugin); [JsonProperty] public override Version Version => typeof(SteamTokenDumperPlugin).Assembly.GetName().Version ?? throw new InvalidOperationException(nameof(Version)); - public Task GetPreferredChangeNumberToStartFrom() => Task.FromResult(IsEnabled ? GlobalCache?.LastChangeNumber ?? 0 : 0); + public Task GetPreferredChangeNumberToStartFrom() => Task.FromResult(Config?.Enabled == true ? GlobalCache?.LastChangeNumber ?? 0 : 0); public async void OnASFInit(IReadOnlyDictionary? additionalConfigProperties = null) { if (!SharedInfo.HasValidToken) { @@ -63,32 +63,54 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { return; } - bool enabled = false; + bool isEnabled = false; + SteamTokenDumperConfig? config = null; if (additionalConfigProperties != null) { foreach ((string configProperty, JToken configValue) in additionalConfigProperties) { try { - if (configProperty == nameof(GlobalConfigExtension.SteamTokenDumperPluginEnabled)) { - enabled = configValue.Value(); + switch (configProperty) { + case nameof(GlobalConfigExtension.SteamTokenDumper): + config = configValue.Value(); - break; + break; + case nameof(GlobalConfigExtension.SteamTokenDumperPluginEnabled): + isEnabled = configValue.Value(); + + break; } } catch (Exception e) { ASF.ArchiLogger.LogGenericException(e); - - break; } } } - IsEnabled = enabled; + config ??= new SteamTokenDumperConfig(); - if (!enabled) { + if (isEnabled) { + config.Enabled = true; + } + + Config = config; + + if (!config.Enabled) { ASF.ArchiLogger.LogGenericInfo(string.Format(CultureInfo.CurrentCulture, Strings.PluginDisabledInConfig, nameof(SteamTokenDumperPlugin))); return; } + if (!config.SecretAppIDs.IsEmpty) { + ASF.ArchiLogger.LogGenericInfo(string.Format(CultureInfo.CurrentCulture, Strings.PluginSecretListInitialized, nameof(config.SecretAppIDs), string.Join(", ", config.SecretAppIDs))); + } + + if (!config.SecretPackageIDs.IsEmpty) { + ASF.ArchiLogger.LogGenericInfo(string.Format(CultureInfo.CurrentCulture, Strings.PluginSecretListInitialized, nameof(config.SecretPackageIDs), string.Join(", ", config.SecretPackageIDs))); + } + + if (!config.SecretDepotIDs.IsEmpty) { + ASF.ArchiLogger.LogGenericInfo(string.Format(CultureInfo.CurrentCulture, Strings.PluginSecretListInitialized, nameof(config.SecretDepotIDs), string.Join(", ", config.SecretDepotIDs))); + } + if (GlobalCache == null) { GlobalCache? globalCache = await GlobalCache.Load().ConfigureAwait(false); @@ -131,7 +153,11 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new ArgumentNullException(nameof(bot)); } - if (!IsEnabled) { + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } + + if (!Config.Enabled) { return; } @@ -158,7 +184,11 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { subscription.Dispose(); } - if (!IsEnabled) { + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } + + if (!Config.Enabled) { return; } @@ -186,7 +216,11 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new ArgumentNullException(nameof(packageChanges)); } - if (!IsEnabled) { + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } + + if (!Config.Enabled) { return; } @@ -202,7 +236,11 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new ArgumentOutOfRangeException(nameof(currentChangeNumber)); } - if (!IsEnabled) { + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } + + if (!Config.Enabled) { return; } @@ -222,7 +260,11 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new ArgumentNullException(nameof(callback)); } - if (!IsEnabled) { + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } + + if (!Config.Enabled) { return; } @@ -230,7 +272,7 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new InvalidOperationException(nameof(GlobalCache)); } - Dictionary packageTokens = callback.LicenseList.GroupBy(license => license.PackageID).ToDictionary(group => group.Key, group => group.OrderByDescending(license => license.TimeCreated).First().AccessToken); + Dictionary packageTokens = callback.LicenseList.Where(license => !Config.SecretPackageIDs.Contains(license.PackageID)).GroupBy(license => license.PackageID).ToDictionary(group => group.Key, group => group.OrderByDescending(license => license.TimeCreated).First().AccessToken); GlobalCache.UpdatePackageTokens(packageTokens); @@ -242,7 +284,11 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new ArgumentNullException(nameof(bot)); } - if (!IsEnabled) { + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } + + if (!Config.Enabled) { return; } @@ -271,13 +317,13 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { HashSet appIDsToRefresh = new(); - foreach (uint packageID in packageIDs) { + foreach (uint packageID in packageIDs.Where(packageID => !Config.SecretPackageIDs.Contains(packageID))) { if (!ASF.GlobalDatabase.PackagesDataReadOnly.TryGetValue(packageID, out (uint ChangeNumber, ImmutableHashSet? AppIDs) packageData) || (packageData.AppIDs == null)) { // ASF might not have the package info for us at the moment, we'll retry later continue; } - appIDsToRefresh.UnionWith(packageData.AppIDs.Where(appID => GlobalCache.ShouldRefreshAppInfo(appID))); + appIDsToRefresh.UnionWith(packageData.AppIDs.Where(appID => !Config.SecretAppIDs.Contains(appID) && GlobalCache.ShouldRefreshAppInfo(appID))); } if (appIDsToRefresh.Count == 0) { @@ -375,7 +421,7 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { } foreach (KeyValue depot in app.KeyValues["depots"].Children) { - if (uint.TryParse(depot.Name, out uint depotID) && GlobalCache.ShouldRefreshDepotKey(depotID)) { + if (uint.TryParse(depot.Name, out uint depotID) && !Config.SecretDepotIDs.Contains(depotID) && GlobalCache.ShouldRefreshDepotKey(depotID)) { depotTasks.Add(bot.SteamApps.GetDepotDecryptionKey(depotID, app.ID).ToLongRunningTask()); } } @@ -417,12 +463,16 @@ namespace ArchiSteamFarm.OfficialPlugins.SteamTokenDumper { throw new InvalidOperationException(nameof(Bot.Bots)); } - const string request = SharedInfo.ServerURL + "/submit"; + if (Config == null) { + throw new InvalidOperationException(nameof(Config)); + } - if (!IsEnabled) { + if (!Config.Enabled) { return; } + const string request = SharedInfo.ServerURL + "/submit"; + if (GlobalCache == null) { throw new InvalidOperationException(nameof(GlobalCache)); }