New feature ( #153 ): in-place upgrade

This commit is contained in:
Robert McRackan 2022-05-20 16:20:28 -04:00
parent b9e789bbcf
commit 98c3940297
17 changed files with 91 additions and 91 deletions

View File

@ -3,7 +3,7 @@
<PropertyGroup>
<TargetFramework>net6.0-windows</TargetFramework>
<Version>7.6.3.1</Version>
<Version>7.7.0.1</Version>
</PropertyGroup>
<ItemGroup>

View File

@ -282,22 +282,20 @@ namespace AppScaffolding
});
}
public static (bool hasUpgrade, string zipUrl, string htmlUrl, string zipName) GetLatestRelease()
public static UpgradeProperties GetLatestRelease()
{
(bool, string, string, string) isFalse = (false, null, null, null);
// timed out
var latest = getLatestRelease(TimeSpan.FromSeconds(10));
if (latest is null)
return isFalse;
return null;
var latestVersionString = latest.TagName.Trim('v');
if (!Version.TryParse(latestVersionString, out var latestRelease))
return isFalse;
return null;
// we're up to date
if (latestRelease <= BuildVersion)
return isFalse;
return null;
// we have an update
var zip = latest.Assets.FirstOrDefault(a => a.BrowserDownloadUrl.EndsWith(".zip"));
@ -310,7 +308,7 @@ namespace AppScaffolding
zipUrl
});
return (true, zipUrl, latest.HtmlUrl, zip.Name);
return new(zipUrl, latest.HtmlUrl, zip.Name, latestRelease);
}
private static Octokit.Release getLatestRelease(TimeSpan timeout)
{

View File

@ -0,0 +1,6 @@
using System;
namespace AppScaffolding
{
public record UpgradeProperties(string ZipUrl, string HtmlUrl, string ZipName, Version LatestRelease);
}

View File

@ -12,7 +12,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Dinah.EntityFrameworkCore" Version="4.0.1.1" />
<PackageReference Include="Dinah.EntityFrameworkCore" Version="4.1.0.1" />
<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.5">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
@ -29,7 +29,7 @@
</ItemGroup>
<ItemGroup>
<None Update="appsettings.json">
<None Update="migrate.json">
<CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
</None>
</ItemGroup>

View File

@ -1,31 +0,0 @@
using System;
using System.Net.Http;
using System.Threading.Tasks;
using Dinah.Core.Net.Http;
namespace FileLiberator
{
// currently only used to download the .zip flies for upgrade
public class DownloadFile : Streamable
{
public async Task<string> PerformDownloadFileAsync(string downloadUrl, string proposedDownloadFilePath)
{
var client = new HttpClient();
var progress = new Progress<DownloadProgress>(OnStreamingProgressChanged);
OnStreamingBegin(proposedDownloadFilePath);
try
{
var actualDownloadedFilePath = await client.DownloadFileAsync(downloadUrl, proposedDownloadFilePath, progress);
OnFileCreated("Upgrade", actualDownloadedFilePath);
return actualDownloadedFilePath;
}
finally
{
OnStreamingCompleted(proposedDownloadFilePath);
}
}
}
}

View File

@ -9,7 +9,6 @@ using FileLiberator;
namespace LibationCli
{
// streamlined, non-Forms copy of ProcessorAutomationController
public abstract class ProcessableOptionsBase : OptionsBase
{
protected static TProcessable CreateProcessable<TProcessable>(EventHandler<LibraryBook> completedAction = null)

View File

@ -34,15 +34,15 @@ namespace LibationCli
private static void checkForUpdate()
{
var (hasUpgrade, zipUrl, htmlUrl, zipName) = LibationScaffolding.GetLatestRelease();
if (!hasUpgrade)
var upgradeProperties = LibationScaffolding.GetLatestRelease();
if (upgradeProperties is null)
return;
var origColor = Console.ForegroundColor;
try
{
Console.ForegroundColor = ConsoleColor.Red;
Console.WriteLine($"UPDATE AVAILABLE @ {zipUrl}");
Console.WriteLine($"UPDATE AVAILABLE @ {upgradeProperties.ZipUrl}");
}
finally
{

View File

@ -421,7 +421,7 @@ namespace LibationFileManager
return libationFilesPathCache;
// FIRST: must write here before SettingsFilePath in next step reads cache
libationFilesPathCache = getLiberationFilesSettingFromJson();
libationFilesPathCache = getLibationFilesSettingFromJson();
// SECOND. before setting to json file with SetWithJsonPath, PersistentDictionary must exist
persistentDictionary = new PersistentDictionary(SettingsFilePath);
@ -443,7 +443,7 @@ namespace LibationFileManager
private static string libationFilesPathCache;
private string getLiberationFilesSettingFromJson()
private string getLibationFilesSettingFromJson()
{
string startingContents = null;
try
@ -482,6 +482,14 @@ namespace LibationFileManager
{
libationFilesPathCache = null;
// ensure exists
if (!File.Exists(APPSETTINGS_JSON))
{
// getter creates new file, loads PersistentDictionary
var _ = LibationFiles;
System.Threading.Thread.Sleep(100);
}
var startingContents = File.ReadAllText(APPSETTINGS_JSON);
var jObj = JObject.Parse(startingContents);

View File

@ -6,7 +6,7 @@
<ItemGroup>
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="6.0.0" />
<PackageReference Include="Serilog.Exceptions" Version="8.1.0" />
<PackageReference Include="Serilog.Exceptions" Version="8.2.0" />
</ItemGroup>
<ItemGroup>

View File

@ -28,6 +28,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Autoupdater.NET.Official" Version="1.7.0" />
<PackageReference Include="Dinah.Core.WindowsDesktop" Version="4.2.2.1" />
</ItemGroup>

View File

@ -3,14 +3,9 @@ using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Windows.Forms;
using AudibleApi.Authorization;
using AudibleUtilities;
using DataLayer;
using Dinah.Core;
using LibationFileManager;
using LibationWinForms.Dialogs;
using Microsoft.EntityFrameworkCore;
using Newtonsoft.Json.Linq;
using Serilog;
namespace LibationWinForms
@ -165,15 +160,12 @@ namespace LibationWinForms
private static void checkForUpdate()
{
string zipUrl;
string htmlUrl;
string zipName;
AppScaffolding.UpgradeProperties upgradeProperties;
try
{
bool hasUpgrade;
(hasUpgrade, zipUrl, htmlUrl, zipName) = AppScaffolding.LibationScaffolding.GetLatestRelease();
if (!hasUpgrade)
upgradeProperties = AppScaffolding.LibationScaffolding.GetLatestRelease();
if (upgradeProperties is null)
return;
}
catch (Exception ex)
@ -182,36 +174,13 @@ namespace LibationWinForms
return;
}
if (zipUrl is null)
if (upgradeProperties.ZipUrl is null)
{
MessageBox.Show(htmlUrl, "New version available");
MessageBox.Show(upgradeProperties.HtmlUrl, "New version available");
return;
}
var result = MessageBox.Show($"New version available @ {htmlUrl}\r\n\r\nWould you like to upgrade?", "New version available", MessageBoxButtons.YesNo, MessageBoxIcon.Question);
if (result != DialogResult.Yes)
return;
try
{
//Download the upgrader app from github
string fileName = "ht" + "tps://github.com/Mbucari/Upgrader/raw/master/Upgrader/win-x86/Upgrader.exe";
var cli = new System.Net.Http.HttpClient();
var upgrader = cli.GetByteArrayAsync(fileName).GetAwaiter().GetResult();
string upgraderPath = Path.Combine(Path.GetTempPath(), "Upgrader.exe");
File.WriteAllBytes(upgraderPath, upgrader);
var thisExe = System.Diagnostics.Process.GetCurrentProcess().MainModule.FileName;
//usage is Upgrader.exe [zip url] [extract directory] [exe to launch]
System.Diagnostics.Process.Start(upgraderPath, new string[] { zipUrl, Path.GetDirectoryName(thisExe), "Libation.exe" });
Environment.Exit(0);
}
catch (Exception ex)
{
MessageBoxLib.ShowAdminAlert("Error downloading update", "Error downloading update", ex);
}
Updater.Run(upgradeProperties.LatestRelease, upgradeProperties.ZipUrl);
}
}
}

View File

@ -0,0 +1,50 @@
using System;
using System.Windows.Forms;
using AutoUpdaterDotNET;
namespace LibationWinForms
{
public static class Updater
{
private const string REPO_URL = "https://github.com/rmcrackan/Libation/releases/latest";
public static void Run(Version latestVersionOnServer, string downloadZipUrl)
=> Run(latestVersionOnServer.ToString(), downloadZipUrl);
public static void Run(string latestVersionOnServer, string downloadZipUrl)
{
AutoUpdater.ParseUpdateInfoEvent +=
args => args.UpdateInfo = new()
{
CurrentVersion = latestVersionOnServer,
DownloadURL = downloadZipUrl,
ChangelogURL = REPO_URL
};
AutoUpdater.CheckForUpdateEvent += AutoUpdaterOnCheckForUpdateEvent;
AutoUpdater.Start(REPO_URL);
}
private static void AutoUpdaterOnCheckForUpdateEvent(UpdateInfoEventArgs args)
{
if (args is null || !args.IsUpdateAvailable)
return;
var dialogResult = MessageBox.Show(string.Format(
$"There is a new version avilable. Would you like to update?\r\n\r\nAfter you close Libation, the upgrade will start automatically."),
"Update Available",
MessageBoxButtons.YesNo,
MessageBoxIcon.Information);
if (dialogResult != DialogResult.Yes)
return;
try
{
Serilog.Log.Logger.Information("Start upgrade. {@DebugInfo}", new { CurrentlyInstalled = args.InstalledVersion, TargetVersion = args.CurrentVersion });
AutoUpdater.DownloadUpdate(args);
}
catch (Exception ex)
{
MessageBoxLib.ShowAdminAlert("Error downloading update", "Error downloading update", ex);
}
}
}
}

View File

@ -7,7 +7,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="FluentAssertions" Version="6.6.0" />
<PackageReference Include="FluentAssertions" Version="6.7.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="Moq" Version="4.18.1" />
<PackageReference Include="MSTest.TestAdapter" Version="2.2.10" />

View File

@ -7,7 +7,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="FluentAssertions" Version="6.6.0" />
<PackageReference Include="FluentAssertions" Version="6.7.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="MSTest.TestAdapter" Version="2.2.10" />
<PackageReference Include="MSTest.TestFramework" Version="2.2.10" />

View File

@ -7,7 +7,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="FluentAssertions" Version="6.6.0" />
<PackageReference Include="FluentAssertions" Version="6.7.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="MSTest.TestAdapter" Version="2.2.10" />
<PackageReference Include="MSTest.TestFramework" Version="2.2.10" />

View File

@ -7,7 +7,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="FluentAssertions" Version="6.6.0" />
<PackageReference Include="FluentAssertions" Version="6.7.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="MSTest.TestAdapter" Version="2.2.10" />
<PackageReference Include="MSTest.TestFramework" Version="2.2.10" />

View File

@ -7,7 +7,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="FluentAssertions" Version="6.6.0" />
<PackageReference Include="FluentAssertions" Version="6.7.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="Moq" Version="4.18.1" />
<PackageReference Include="MSTest.TestAdapter" Version="2.2.10" />