diff --git a/ArchiSteamFarm/ASF.cs b/ArchiSteamFarm/ASF.cs index 6efe0807e..c309b3a6d 100644 --- a/ArchiSteamFarm/ASF.cs +++ b/ArchiSteamFarm/ASF.cs @@ -170,12 +170,12 @@ namespace ArchiSteamFarm { await UpdateSemaphore.WaitAsync().ConfigureAwait(false); try { - ArchiLogger.LogGenericInfo(Strings.UpdateCheckingNewVersion); - // If backup directory from previous update exists, it's a good idea to purge it now string backupDirectory = Path.Combine(SharedInfo.HomeDirectory, SharedInfo.UpdateDirectory); if (Directory.Exists(backupDirectory)) { + ArchiLogger.LogGenericInfo(Strings.UpdateCleanup); + // It's entirely possible that old process is still running, wait a short moment for eventual cleanup await Task.Delay(5000).ConfigureAwait(false); @@ -186,8 +186,12 @@ namespace ArchiSteamFarm { return null; } + + ArchiLogger.LogGenericInfo(Strings.Done); } + ArchiLogger.LogGenericInfo(Strings.UpdateCheckingNewVersion); + GitHub.ReleaseResponse releaseResponse = await GitHub.GetLatestRelease(GlobalConfig.UpdateChannel == GlobalConfig.EUpdateChannel.Stable).ConfigureAwait(false); if (releaseResponse == null) { @@ -659,8 +663,7 @@ namespace ArchiSteamFarm { // Firstly we'll move all our existing files to a backup directory string backupDirectory = Path.Combine(targetDirectory, SharedInfo.UpdateDirectory); - // We can't use EnumerateFiles here as we're going to actively move them - foreach (string file in Directory.GetFiles(targetDirectory, "*", SearchOption.AllDirectories)) { + foreach (string file in Directory.EnumerateFiles(targetDirectory, "*", SearchOption.AllDirectories)) { string fileName = Path.GetFileName(file); if (string.IsNullOrEmpty(fileName)) { @@ -680,11 +683,12 @@ namespace ArchiSteamFarm { string relativeDirectoryName = Path.GetDirectoryName(relativeFilePath); switch (relativeDirectoryName) { - // Files in those directories we want to keep in their current place - case SharedInfo.ConfigDirectory: - case SharedInfo.PluginsDirectory: + case null: + ArchiLogger.LogNullError(nameof(relativeDirectoryName)); - continue; + return false; + + // No directory, root folder case "": switch (fileName) { @@ -696,10 +700,21 @@ namespace ArchiSteamFarm { } break; - case null: - ArchiLogger.LogNullError(nameof(relativeDirectoryName)); - return false; + // Files in those directories we want to keep in their current place + case SharedInfo.ConfigDirectory: + case SharedInfo.PluginsDirectory: + case SharedInfo.UpdateDirectory: + + continue; + default: + + // Files in subdirectories of those directories we want to keep as well + if (Utilities.RelativeDirectoryStartsWith(relativeDirectoryName, SharedInfo.ConfigDirectory, SharedInfo.PluginsDirectory, SharedInfo.UpdateDirectory)) { + continue; + } + + break; } string targetBackupDirectory = relativeDirectoryName.Length > 0 ? Path.Combine(backupDirectory, relativeDirectoryName) : backupDirectory; @@ -710,8 +725,10 @@ namespace ArchiSteamFarm { } // We can now get rid of directories that are empty - foreach (string directory in Directory.EnumerateDirectories(targetDirectory).Where(directory => !Directory.EnumerateFiles(directory).Any())) { - Directory.Delete(directory, true); + Utilities.DeleteEmptyDirectoriesRecursively(targetDirectory); + + if (!Directory.Exists(targetDirectory)) { + Directory.CreateDirectory(targetDirectory); } // Now enumerate over files in the zip archive, skip directory entries that we're not interested in (we can create them ourselves if needed) @@ -724,23 +741,26 @@ namespace ArchiSteamFarm { continue; } - string directory = Path.GetDirectoryName(file); + // Check if this file requires its own folder + if (zipFile.Name != zipFile.FullName) { + string directory = Path.GetDirectoryName(file); - if (string.IsNullOrEmpty(directory)) { - ArchiLogger.LogNullError(nameof(directory)); + if (string.IsNullOrEmpty(directory)) { + ArchiLogger.LogNullError(nameof(directory)); - return false; - } + return false; + } - if (!Directory.Exists(directory)) { - Directory.CreateDirectory(directory); - } + if (!Directory.Exists(directory)) { + Directory.CreateDirectory(directory); + } - // We're not interested in extracting placeholder files (but we still want directories created for them, done above) - switch (zipFile.Name) { - case ".gitkeep": + // We're not interested in extracting placeholder files (but we still want directories created for them, done above) + switch (zipFile.Name) { + case ".gitkeep": - continue; + continue; + } } zipFile.ExtractToFile(file); diff --git a/ArchiSteamFarm/ArchiSteamFarm.csproj b/ArchiSteamFarm/ArchiSteamFarm.csproj index 8cde5dd02..f4d5b81e2 100644 --- a/ArchiSteamFarm/ArchiSteamFarm.csproj +++ b/ArchiSteamFarm/ArchiSteamFarm.csproj @@ -2,7 +2,7 @@ ASF.ico - 4.0.1.9 + 4.0.1.7 JustArchi JustArchi true @@ -11,7 +11,7 @@ $(DefaultItemExcludes);config/**;debug/**;out/**;overlay/** ASF is an application that allows you to farm steam cards using multiple steam accounts simultaneously. none - 4.0.1.9 + 4.0.1.7 true latest 1591 diff --git a/ArchiSteamFarm/Localization/Strings.Designer.cs b/ArchiSteamFarm/Localization/Strings.Designer.cs index 9c07bc959..36e038b2f 100644 --- a/ArchiSteamFarm/Localization/Strings.Designer.cs +++ b/ArchiSteamFarm/Localization/Strings.Designer.cs @@ -1422,6 +1422,15 @@ namespace ArchiSteamFarm.Localization { } } + /// + /// Wyszukuje zlokalizowany ciąg podobny do ciągu Cleaning up old files after update.... + /// + public static string UpdateCleanup { + get { + return ResourceManager.GetString("UpdateCleanup", resourceCulture); + } + } + /// /// Wyszukuje zlokalizowany ciąg podobny do ciągu Downloading new version: {0} ({1} MB)... While waiting, consider donating if you appreciate the work being done! :). /// diff --git a/ArchiSteamFarm/Localization/Strings.resx b/ArchiSteamFarm/Localization/Strings.resx index 7853d8a8a..fbb8022df 100644 --- a/ArchiSteamFarm/Localization/Strings.resx +++ b/ArchiSteamFarm/Localization/Strings.resx @@ -728,4 +728,7 @@ StackTrace: Waiting up to {0} to ensure that we're free to start idling... {0} will be replaced by translated TimeSpan string (such as "1 minute") + + Cleaning up old files after update... + \ No newline at end of file diff --git a/ArchiSteamFarm/Utilities.cs b/ArchiSteamFarm/Utilities.cs index af2d94107..2ade47308 100644 --- a/ArchiSteamFarm/Utilities.cs +++ b/ArchiSteamFarm/Utilities.cs @@ -22,6 +22,7 @@ using System; using System.Collections.Generic; using System.Globalization; +using System.IO; using System.Linq; using System.Net; using System.Text; @@ -241,6 +242,30 @@ namespace ArchiSteamFarm { [PublicAPI] public static string ToHumanReadable(this TimeSpan timeSpan) => timeSpan.Humanize(3, maxUnit: TimeUnit.Year, minUnit: TimeUnit.Second); + internal static void DeleteEmptyDirectoriesRecursively(string directory) { + if (string.IsNullOrEmpty(directory)) { + ASF.ArchiLogger.LogNullError(nameof(directory)); + + return; + } + + if (!Directory.Exists(directory)) { + return; + } + + try { + foreach (string subDirectory in Directory.EnumerateDirectories(directory)) { + DeleteEmptyDirectoriesRecursively(subDirectory); + } + + if (!Directory.EnumerateFileSystemEntries(directory).Any()) { + Directory.Delete(directory); + } + } catch (Exception e) { + ASF.ArchiLogger.LogGenericException(e); + } + } + internal static string GetCookieValue(this CookieContainer cookieContainer, string url, string name) { if ((cookieContainer == null) || string.IsNullOrEmpty(url) || string.IsNullOrEmpty(name)) { ASF.ArchiLogger.LogNullError(nameof(cookieContainer) + " || " + nameof(url) + " || " + nameof(name)); @@ -268,5 +293,15 @@ namespace ArchiSteamFarm { return Random.Next(); } } + + internal static bool RelativeDirectoryStartsWith(string directory, params string[] prefixes) { + if (string.IsNullOrEmpty(directory) || (prefixes == null) || (prefixes.Length == 0)) { + ASF.ArchiLogger.LogNullError(nameof(directory) + " || " + nameof(prefixes)); + + return false; + } + + return (from prefix in prefixes where directory.Length > prefix.Length let pathSeparator = directory[prefix.Length] where (pathSeparator == Path.DirectorySeparatorChar) || (pathSeparator == Path.AltDirectorySeparatorChar) select prefix).Any(prefix => directory.StartsWith(prefix, StringComparison.Ordinal)); + } } }