[Auto-update] Auto-update improvements (#11356)

* [Updating] Refactor autoupdate mechanism to use Settings window buttons

* [Updating] Don't use underscores in update_state (#11029)

* [Updating] Rename action_runner to be consisent with accepted format

* [Updating] Make UpdateState values explicit

* [Setup] Set default bootstrapper log severity to debug

* [BugReport] Include all found bootstrapper logs

* [Setup] Use capital letter for ActionRunner

* [Updating] Simple UI to test UpdateState

* [Action Runner]  cleanup and coding style

* [BugReportTool] fix coding convension

* [Auto-update][PT Settings] Updated general page in the Settings (#11227)

* [Auto-update][PT Settings] File watcher monitoring UpdateState.json (#11282)

* Handle button clicks (#11288)

* [Updating] Document ActionRunner cmd flags

* [Auto-update][PT Settings] Updated UI (#11335)

* [Updating] Do not reset update state when msi cancellation detected

* [Updating] Directly launch update_now PT action instead of using custom URI scheme

* Checking for updates UI (#11354)

* [Updating] Fix cannotDownload state in action runner

* [Updating] Reset update state to CannotDownload if action runner encountered an error

* [Updating][PT Settings] downloading label, disable button in error state

* Changed error message

* [Updating rename CannotDownload to ErrorDownloading

* [Updating] Add trace logging for Check for updates callback

* [Updating][PT Settings] simplify downloading checks

* [Updating][PT Settings] Updated text labels

* [Updating][PT Settings] Retry to load settings if failed

* [Updating][PT Settings] Text fix

* [Updating][PT Settings] Installed version links removed

* [Updating][PT Settings] Error text updated

* [Updating][PT Settings] Show label after version checked

* [Updating][PT Settings] Text foreground fix

* [Updating][PT Settings] Clean up

* [Updating] Do not reset releasePageUrl in case of error/cancellation

* [Updating][PT Settings] fixed missing string

* [Updating][PT Settings] checked for updates state fix

Co-authored-by: yuyoyuppe <a.yuyoyuppe@gmail.com>
Co-authored-by: Andrey Nekrasov <yuyoyuppe@users.noreply.github.com>
Co-authored-by: Enrico Giordani <enrico.giordani@gmail.com>
This commit is contained in:
Seraphima Zykova
2021-05-21 13:32:34 +03:00
committed by GitHub
parent d55badf14a
commit b96b4fcb0f
68 changed files with 1065 additions and 761 deletions

View File

@@ -57,6 +57,5 @@ namespace notifications
}
RegCloseKey(key);
return timeutil::diff::in_days(timeutil::now(), last_disabled_time) < disable_interval_in_days;
return false;
}
}

View File

@@ -81,7 +81,7 @@ namespace updating
}
catch (...)
{
updating::notifications::show_uninstallation_error(strings);
MessageBoxW(nullptr, strings.UNINSTALLATION_UNKNOWN_ERROR.c_str(), strings.NOTIFICATION_TITLE.c_str(), MB_OK | MB_ICONERROR);
}
}
return false;

View File

@@ -14,7 +14,7 @@ namespace updating
namespace notifications
{
using namespace ::notifications;
std::wstring current_version_to_next_version(const updating::new_version_download_info& info)
std::wstring current_version_to_next_version(const new_version_download_info& info)
{
auto current_version_to_next_version = VersionHelper{ VERSION_MAJOR, VERSION_MINOR, VERSION_REVISION }.toWstring();
current_version_to_next_version += L" -> ";
@@ -22,15 +22,7 @@ namespace updating
return current_version_to_next_version;
}
void show_unavailable(const notifications::strings& strings, std::wstring reason)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
toast_params toast_params{ UPDATING_PROCESS_TOAST_TAG, false };
show_toast(std::move(reason), strings.TOAST_TITLE, std::move(toast_params));
}
void show_available(const updating::new_version_download_info& info, const notifications::strings& strings)
void show_new_version_available(const new_version_download_info& info, const strings& strings)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
@@ -40,106 +32,30 @@ namespace updating
contents += current_version_to_next_version(info);
show_toast_with_activations(std::move(contents),
strings.TOAST_TITLE,
strings.NOTIFICATION_TITLE,
{},
{ link_button{ strings.GITHUB_NEW_VERSION_UPDATE_NOW,
L"powertoys://download_and_install_update/" },
L"powertoys://update_now/" },
link_button{ strings.GITHUB_NEW_VERSION_MORE_INFO,
info.release_page_uri.ToString().c_str() } },
L"powertoys://open_settings/" } },
std::move(toast_params));
}
void show_download_start(const updating::new_version_download_info& info, const notifications::strings& strings)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
progress_bar_params progress_bar_params;
std::wstring progress_title{ info.version.toWstring() };
progress_title += L' ';
progress_title += strings.DOWNLOAD_IN_PROGRESS;
progress_bar_params.progress_title = progress_title;
progress_bar_params.progress = .0f;
toast_params toast_params{ UPDATING_PROCESS_TOAST_TAG, false, std::move(progress_bar_params) };
show_toast_with_activations(strings.GITHUB_NEW_VERSION_DOWNLOAD_STARTED,
strings.TOAST_TITLE,
{},
{},
std::move(toast_params));
}
void show_visit_github(const updating::new_version_download_info& info, const notifications::strings& strings)
void show_open_settings_for_update(const strings& strings)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
toast_params toast_params{ UPDATING_PROCESS_TOAST_TAG, false };
std::wstring contents = strings.GITHUB_NEW_VERSION_AVAILABLE_OFFER_VISIT;
contents += L'\n';
contents += current_version_to_next_version(info);
show_toast_with_activations(std::move(contents),
strings.TOAST_TITLE,
std::vector<action_t> actions = {
link_button{ strings.GITHUB_NEW_VERSION_MORE_INFO,
L"powertoys://open_settings/" },
};
show_toast_with_activations(strings.GITHUB_NEW_VERSION_AVAILABLE,
strings.NOTIFICATION_TITLE,
{},
{ link_button{ strings.GITHUB_NEW_VERSION_VISIT,
info.release_page_uri.ToString().c_str() } },
std::move(actions),
std::move(toast_params));
}
void show_install_error(const updating::new_version_download_info& info, const notifications::strings& strings)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
toast_params toast_params{ UPDATING_PROCESS_TOAST_TAG, false };
std::wstring contents = strings.GITHUB_NEW_VERSION_DOWNLOAD_INSTALL_ERROR;
contents += L'\n';
contents += current_version_to_next_version(info);
show_toast_with_activations(std::move(contents),
strings.TOAST_TITLE,
{},
{ link_button{ strings.GITHUB_NEW_VERSION_VISIT, info.release_page_uri.ToString().c_str() } },
std::move(toast_params));
}
void show_version_ready(const updating::new_version_download_info& info, const notifications::strings& strings)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
toast_params toast_params{ UPDATING_PROCESS_TOAST_TAG, false };
std::wstring new_version_ready{ strings.GITHUB_NEW_VERSION_READY_TO_INSTALL };
new_version_ready += L'\n';
new_version_ready += current_version_to_next_version(info);
show_toast_with_activations(std::move(new_version_ready),
strings.TOAST_TITLE,
{},
{ link_button{ strings.GITHUB_NEW_VERSION_UPDATE_NOW,
L"powertoys://update_now/" + info.installer_filename },
link_button{ strings.GITHUB_NEW_VERSION_UPDATE_AFTER_RESTART,
L"powertoys://schedule_update/" + info.installer_filename },
snooze_button{
strings.GITHUB_NEW_VERSION_SNOOZE_TITLE,
{ { strings.GITHUB_NEW_VERSION_UPDATE_SNOOZE_1D, 24 * 60 },
{ strings.GITHUB_NEW_VERSION_UPDATE_SNOOZE_5D, 120 * 60 } },
strings.SNOOZE_BUTTON } },
std::move(toast_params));
}
void show_uninstallation_error(const notifications::strings& strings)
{
remove_toasts_by_tag(UPDATING_PROCESS_TOAST_TAG);
show_toast(strings.UNINSTALLATION_UNKNOWN_ERROR, strings.TOAST_TITLE);
}
void update_download_progress(const updating::new_version_download_info& info, float progress, const notifications::strings& strings)
{
progress_bar_params progress_bar_params;
std::wstring progress_title{ info.version.toWstring() };
progress_title += L' ';
progress_title += progress < 1 ? strings.DOWNLOAD_IN_PROGRESS : strings.DOWNLOAD_COMPLETE;
progress_bar_params.progress_title = progress_title;
progress_bar_params.progress = progress;
update_toast_progress_bar(UPDATING_PROCESS_TOAST_TAG, progress_bar_params);
}
}
}

View File

@@ -10,71 +10,31 @@ namespace updating
{
struct strings
{
std::wstring DOWNLOAD_COMPLETE;
std::wstring DOWNLOAD_IN_PROGRESS;
std::wstring GITHUB_NEW_VERSION_ABORT;
std::wstring GITHUB_NEW_VERSION_AVAILABLE;
std::wstring GITHUB_NEW_VERSION_AVAILABLE_OFFER_VISIT;
std::wstring GITHUB_NEW_VERSION_CHECK_ERROR;
std::wstring GITHUB_NEW_VERSION_DOWNLOAD_INSTALL_ERROR;
std::wstring GITHUB_NEW_VERSION_DOWNLOAD_STARTED;
std::wstring GITHUB_NEW_VERSION_MORE_INFO;
std::wstring GITHUB_NEW_VERSION_READY_TO_INSTALL;
std::wstring GITHUB_NEW_VERSION_SNOOZE_TITLE;
std::wstring GITHUB_NEW_VERSION_UP_TO_DATE;
std::wstring GITHUB_NEW_VERSION_UPDATE_NOW;
std::wstring GITHUB_NEW_VERSION_UPDATE_AFTER_RESTART;
std::wstring GITHUB_NEW_VERSION_UPDATE_SNOOZE_1D;
std::wstring GITHUB_NEW_VERSION_UPDATE_SNOOZE_5D;
std::wstring GITHUB_NEW_VERSION_USING_LOCAL_BUILD_ERROR;
std::wstring GITHUB_NEW_VERSION_VISIT;
std::wstring OFFER_UNINSTALL_MSI;
std::wstring OFFER_UNINSTALL_MSI_TITLE;
std::wstring SNOOZE_BUTTON;
std::wstring TOAST_TITLE;
std::wstring NOTIFICATION_TITLE;
std::wstring UNINSTALLATION_UNKNOWN_ERROR;
};
void show_unavailable(const notifications::strings& strings, std::wstring reason);
void show_available(const updating::new_version_download_info& info, const strings&);
void show_download_start(const updating::new_version_download_info& info, const strings&);
void show_visit_github(const updating::new_version_download_info& info, const strings&);
void show_install_error(const updating::new_version_download_info& info, const strings&);
void show_version_ready(const updating::new_version_download_info& info, const strings&);
void show_uninstallation_error(const notifications::strings& strings);
void update_download_progress(const updating::new_version_download_info& info, float progress, const notifications::strings& strings);
void show_new_version_available(const new_version_download_info& info, const strings& strings);
void show_open_settings_for_update(const strings& strings);
}
}
#define create_notifications_strings() \
::updating::notifications::strings \
{ \
.DOWNLOAD_COMPLETE = GET_RESOURCE_STRING(IDS_DOWNLOAD_COMPLETE), \
.DOWNLOAD_IN_PROGRESS = GET_RESOURCE_STRING(IDS_DOWNLOAD_IN_PROGRESS), \
.GITHUB_NEW_VERSION_ABORT = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_ABORT), \
.GITHUB_NEW_VERSION_AVAILABLE = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_AVAILABLE), \
.GITHUB_NEW_VERSION_AVAILABLE_OFFER_VISIT = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_AVAILABLE_OFFER_VISIT), \
.GITHUB_NEW_VERSION_CHECK_ERROR = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_CHECK_ERROR), \
.GITHUB_NEW_VERSION_DOWNLOAD_INSTALL_ERROR = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_DOWNLOAD_INSTALL_ERROR), \
.GITHUB_NEW_VERSION_DOWNLOAD_STARTED = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_DOWNLOAD_STARTED), \
.GITHUB_NEW_VERSION_MORE_INFO = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_MORE_INFO), \
.GITHUB_NEW_VERSION_READY_TO_INSTALL = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_READY_TO_INSTALL), \
.GITHUB_NEW_VERSION_SNOOZE_TITLE = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_SNOOZE_TITLE), \
.GITHUB_NEW_VERSION_UP_TO_DATE = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_UP_TO_DATE), \
.GITHUB_NEW_VERSION_UPDATE_NOW = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_UPDATE_NOW), \
.GITHUB_NEW_VERSION_UPDATE_AFTER_RESTART = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_UPDATE_AFTER_RESTART), \
.GITHUB_NEW_VERSION_UPDATE_SNOOZE_1D = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_UPDATE_SNOOZE_1D), \
.GITHUB_NEW_VERSION_UPDATE_SNOOZE_5D = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_UPDATE_SNOOZE_5D), \
.GITHUB_NEW_VERSION_USING_LOCAL_BUILD_ERROR = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_USING_LOCAL_BUILD_ERROR), \
.GITHUB_NEW_VERSION_VISIT = GET_RESOURCE_STRING(IDS_GITHUB_NEW_VERSION_VISIT), \
.OFFER_UNINSTALL_MSI = GET_RESOURCE_STRING(IDS_OFFER_UNINSTALL_MSI), \
.OFFER_UNINSTALL_MSI_TITLE = GET_RESOURCE_STRING(IDS_OFFER_UNINSTALL_MSI_TITLE), \
.SNOOZE_BUTTON = GET_RESOURCE_STRING(IDS_SNOOZE_BUTTON), \
.TOAST_TITLE = GET_RESOURCE_STRING(IDS_TOAST_TITLE), \
.NOTIFICATION_TITLE = GET_RESOURCE_STRING(IDS_TOAST_TITLE), \
.UNINSTALLATION_UNKNOWN_ERROR = GET_RESOURCE_STRING(IDS_UNINSTALLATION_UNKNOWN_ERROR) \
}

View File

@@ -27,9 +27,11 @@
#include <winrt/Windows.Foundation.h>
#include <winrt/Windows.Foundation.Collections.h>
#include <winrt/Windows.Networking.Connectivity.h>
#include <winrt/Windows.ApplicationModel.h>
#include <winrt/Windows.Management.Deployment.h>
#include <winrt/Windows.System.h>
#include <wil/resource.h>
#endif //PCH_H

View File

@@ -0,0 +1,70 @@
#include "pch.h"
#include "updateState.h"
#include <common/utils/json.h>
#include <common/utils/timeutil.h>
#include <common/SettingsAPI/settings_helpers.h>
namespace
{
const wchar_t PERSISTENT_STATE_FILENAME[] = L"\\UpdateState.json";
const wchar_t UPDATE_STATE_MUTEX[] = L"Local\\PowerToysRunnerUpdateStateMutex";
}
UpdateState deserialize(const json::JsonObject& json)
{
UpdateState result;
result.state = static_cast<UpdateState::State>(json.GetNamedNumber(L"state", UpdateState::upToDate));
result.releasePageUrl = json.GetNamedString(L"releasePageUrl", L"");
result.githubUpdateLastCheckedDate = timeutil::from_string(json.GetNamedString(L"githubUpdateLastCheckedDate", L"invalid").c_str());
result.downloadedInstallerFilename = json.GetNamedString(L"downloadedInstallerFilename", L"");
return result;
}
json::JsonObject serialize(const UpdateState& state)
{
json::JsonObject json;
if (state.githubUpdateLastCheckedDate.has_value())
{
json.SetNamedValue(L"githubUpdateLastCheckedDate", json::value(timeutil::to_string(*state.githubUpdateLastCheckedDate)));
}
json.SetNamedValue(L"releasePageUrl", json::value(state.releasePageUrl));
json.SetNamedValue(L"state", json::value(static_cast<double>(state.state)));
json.SetNamedValue(L"downloadedInstallerFilename", json::value(state.downloadedInstallerFilename));
return json;
}
UpdateState UpdateState::read()
{
const auto filename = PTSettingsHelper::get_root_save_folder_location() + PERSISTENT_STATE_FILENAME;
std::optional<json::JsonObject> json;
{
wil::unique_mutex_nothrow mutex{ CreateMutexW(nullptr, FALSE, UPDATE_STATE_MUTEX) };
auto lock = mutex.acquire();
json = json::from_file(filename);
}
return json ? deserialize(*json) : UpdateState{};
}
void UpdateState::store(std::function<void(UpdateState&)> stateModifier)
{
const auto filename = PTSettingsHelper::get_root_save_folder_location() + PERSISTENT_STATE_FILENAME;
std::optional<json::JsonObject> json;
{
wil::unique_mutex_nothrow mutex{ CreateMutexW(nullptr, FALSE, UPDATE_STATE_MUTEX) };
auto lock = mutex.acquire();
json = json::from_file(filename);
UpdateState state;
if (json)
{
state = deserialize(*json);
}
stateModifier(state);
json.emplace(serialize(state));
json::to_file(filename, *json);
}
}

View File

@@ -0,0 +1,25 @@
#pragma once
#include <ctime>
#include <optional>
#include <functional>
// All fields must be default-initialized
struct UpdateState
{
enum State
{
upToDate = 0,
errorDownloading = 1,
readyToDownload = 2,
readyToInstall = 3
} state = upToDate;
std::wstring releasePageUrl;
std::optional<std::time_t> githubUpdateLastCheckedDate;
std::wstring downloadedInstallerFilename;
// To prevent concurrent modification of the file, we enforce this interface, which locks the file while
// the state_modifier is active.
static void store(std::function<void(UpdateState&)> stateModifier);
static UpdateState read();
};

View File

@@ -15,12 +15,27 @@ namespace // Strings in this namespace should not be localized
{
const wchar_t LATEST_RELEASE_ENDPOINT[] = L"https://api.github.com/repos/microsoft/PowerToys/releases/latest";
const wchar_t ALL_RELEASES_ENDPOINT[] = L"https://api.github.com/repos/microsoft/PowerToys/releases";
const wchar_t LOCAL_BUILD_ERROR[] = L"Local build cannot be updated";
const wchar_t NETWORK_ERROR[] = L"Network error";
const size_t MAX_DOWNLOAD_ATTEMPTS = 3;
}
namespace updating
{
Uri extract_release_page_url(const json::JsonObject& release_object)
{
try
{
return Uri{ release_object.GetNamedString(L"html_url") };
}
catch (...)
{
}
return nullptr;
}
std::optional<VersionHelper> extract_version_from_release_object(const json::JsonObject& release_object)
{
try
@@ -66,7 +81,7 @@ namespace updating
// If the current version starts with 0.0.*, it means we're on a local build from a farm and shouldn't check for updates.
if (VERSION_MAJOR == 0 && VERSION_MINOR == 0)
{
co_return nonstd::make_unexpected(strings.GITHUB_NEW_VERSION_USING_LOCAL_BUILD_ERROR);
co_return nonstd::make_unexpected(LOCAL_BUILD_ERROR);
}
try
@@ -109,24 +124,16 @@ namespace updating
co_return version_up_to_date{};
}
Uri release_page_url{ release_object.GetNamedString(L"html_url") };
auto installer_download_url = extract_installer_asset_download_info(release_object);
co_return new_version_download_info{ std::move(release_page_url),
auto [installer_download_url, installer_filename] = extract_installer_asset_download_info(release_object);
co_return new_version_download_info{ extract_release_page_url(release_object),
std::move(github_version),
std::move(installer_download_url.first),
std::move(installer_download_url.second) };
std::move(installer_download_url),
std::move(installer_filename) };
}
catch (...)
{
}
co_return nonstd::make_unexpected(strings.GITHUB_NEW_VERSION_CHECK_ERROR);
}
bool could_be_costly_connection()
{
using namespace winrt::Windows::Networking::Connectivity;
ConnectionProfile internetConnectionProfile = NetworkInformation::GetInternetConnectionProfile();
return internetConnectionProfile.IsWwanConnectionProfile();
co_return nonstd::make_unexpected(NETWORK_ERROR);
}
std::filesystem::path get_pending_updates_path()
@@ -136,86 +143,40 @@ namespace updating
return { std::move(path_str) };
}
std::filesystem::path create_download_path()
std::optional<std::filesystem::path> create_download_path()
{
auto installer_download_dst = get_pending_updates_path();
std::error_code _;
std::filesystem::create_directories(installer_download_dst, _);
return installer_download_dst;
auto installer_download_path = get_pending_updates_path();
std::error_code ec;
std::filesystem::create_directories(installer_download_path, ec);
return !ec ? std::optional{ installer_download_path } : std::nullopt;
}
std::future<bool> try_autoupdate(const bool download_updates_automatically, const notifications::strings& strings)
std::future<std::optional<std::filesystem::path>> download_new_version(const new_version_download_info& new_version)
{
const auto version_check_result = co_await get_github_version_info_async(strings);
if (!version_check_result)
auto installer_download_path = create_download_path();
if (!installer_download_path)
{
co_return false;
co_return std::nullopt;
}
if (std::holds_alternative<version_up_to_date>(*version_check_result))
{
co_return true;
}
const auto new_version = std::get<new_version_download_info>(*version_check_result);
if (download_updates_automatically && !could_be_costly_connection())
*installer_download_path /= new_version.installer_filename;
bool download_success = false;
for (size_t i = 0; i < MAX_DOWNLOAD_ATTEMPTS; ++i)
{
auto installer_download_dst = create_download_path() / new_version.installer_filename;
bool download_success = false;
for (size_t i = 0; i < MAX_DOWNLOAD_ATTEMPTS; ++i)
try
{
try
{
http::HttpClient client;
co_await client.download(new_version.installer_download_url, installer_download_dst);
download_success = true;
break;
}
catch (...)
{
// reattempt to download or do nothing
}
http::HttpClient client;
co_await client.download(new_version.installer_download_url, *installer_download_path);
download_success = true;
break;
}
if (!download_success)
catch (...)
{
updating::notifications::show_install_error(new_version, strings);
co_return false;
// reattempt to download or do nothing
}
updating::notifications::show_version_ready(new_version, strings);
}
else
{
updating::notifications::show_visit_github(new_version, strings);
}
co_return true;
co_return download_success ? installer_download_path : std::nullopt;
}
std::future<std::wstring> download_update(const notifications::strings& strings)
{
const auto version_check_result = co_await get_github_version_info_async(strings);
if (!version_check_result || std::holds_alternative<version_up_to_date>(*version_check_result))
{
co_return L"";
}
const auto new_version = std::get<new_version_download_info>(*version_check_result);
auto installer_download_dst = create_download_path() / new_version.installer_filename;
updating::notifications::show_download_start(new_version, strings);
try
{
auto progressUpdateHandle = [&](float progress) {
updating::notifications::update_download_progress(new_version, progress, strings);
};
http::HttpClient client;
co_await client.download(new_version.installer_download_url, installer_download_dst, progressUpdateHandle);
}
catch (...)
{
updating::notifications::show_install_error(new_version, strings);
co_return L"";
}
co_return new_version.installer_filename;
}
}

View File

@@ -14,9 +14,9 @@
namespace updating
{
using winrt::Windows::Foundation::Uri;
struct version_up_to_date {};
using github_version_info = std::variant<new_version_download_info, version_up_to_date>;
struct version_up_to_date
{
};
struct new_version_download_info
{
Uri release_page_uri = nullptr;
@@ -24,11 +24,10 @@ namespace updating
Uri installer_download_url = nullptr;
std::wstring installer_filename;
};
using github_version_info = std::variant<new_version_download_info, version_up_to_date>;
// Returns whether the update check has succeeded
std::future<bool> try_autoupdate(const bool download_updates_automatically, const notifications::strings&);
std::future<std::optional<std::filesystem::path>> download_new_version(const new_version_download_info& new_version);
std::filesystem::path get_pending_updates_path();
std::future<std::wstring> download_update(const notifications::strings&);
std::future<nonstd::expected<github_version_info, std::wstring>> get_github_version_info_async(const notifications::strings& strings, const bool prerelease = false);
// non-localized

View File

@@ -40,6 +40,7 @@
<ClInclude Include="installer.h" />
<ClInclude Include="notifications.h" />
<ClInclude Include="updating.h" />
<ClInclude Include="updateState.h" />
<ClInclude Include="pch.h" />
<ClInclude Include="winstore.h" />
</ItemGroup>
@@ -49,6 +50,7 @@
<ClCompile Include="installer.cpp" />
<ClCompile Include="notifications.cpp" />
<ClCompile Include="updating.cpp" />
<ClCompile Include="updateState.cpp" />
<ClCompile Include="pch.cpp">
<PrecompiledHeader Condition="'$(CIBuild)'!='true'">Create</PrecompiledHeader>
</ClCompile>