diff options
Diffstat (limited to '')
-rw-r--r-- | src/core/module/GlobalModuleContext.cpp | 12 | ||||
-rw-r--r-- | src/core/module/GlobalModuleContext.h | 2 | ||||
-rw-r--r-- | src/core/module/GlobalRegisterTable.cpp | 31 | ||||
-rw-r--r-- | src/core/module/GlobalRegisterTable.h | 12 | ||||
-rw-r--r-- | src/core/module/Module.cpp | 1 | ||||
-rw-r--r-- | src/core/module/Module.h | 1 | ||||
-rw-r--r-- | src/core/module/ModuleManager.cpp | 24 | ||||
-rw-r--r-- | src/core/module/ModuleManager.h | 32 | ||||
-rw-r--r-- | src/module/integrated/version_checking_module/VersionCheckTask.h | 1 | ||||
-rw-r--r-- | src/module/integrated/version_checking_module/VersionCheckingModule.cpp | 53 | ||||
-rw-r--r-- | src/ui/dialog/help/AboutDialog.cpp | 78 | ||||
-rw-r--r-- | src/ui/dialog/help/AboutDialog.h | 5 | ||||
-rw-r--r-- | src/ui/main_window/MainWindow.cpp | 1 | ||||
-rw-r--r-- | src/ui/main_window/MainWindow.h | 2 | ||||
-rw-r--r-- | src/ui/main_window/MainWindowSlotFunction.cpp | 50 | ||||
-rw-r--r-- | src/ui/struct/SoftwareVersion.cpp | 101 | ||||
-rw-r--r-- | src/ui/struct/SoftwareVersion.h | 85 | ||||
-rw-r--r-- | src/ui/thread/VersionCheckTask.cpp | 177 | ||||
-rw-r--r-- | src/ui/thread/VersionCheckTask.h | 98 |
19 files changed, 219 insertions, 547 deletions
diff --git a/src/core/module/GlobalModuleContext.cpp b/src/core/module/GlobalModuleContext.cpp index 919c744a..1e6d87b1 100644 --- a/src/core/module/GlobalModuleContext.cpp +++ b/src/core/module/GlobalModuleContext.cpp @@ -270,6 +270,10 @@ class GlobalModuleContext::Impl { return true; } + bool IsModuleExists(ModuleIdentifier id) const { + return search_module_register_table(id).has_value(); + } + private: struct ModuleRegisterInfo { int channel; @@ -305,15 +309,13 @@ class GlobalModuleContext::Impl { // Function to search for a module in the register table. std::optional<ModuleRegisterInfoPtr> search_module_register_table( - ModuleIdentifier identifier) { + ModuleIdentifier identifier) const { auto it = module_register_table_.find(identifier); if (it == module_register_table_.end()) { return std::nullopt; } return it->second; } - - std::list<ModuleIdentifier>& search_module_events_table(ModuleIdentifier); }; // Constructor for GlobalModuleContext, takes a TaskRunnerPtr as an argument. @@ -368,4 +370,8 @@ int GlobalModuleContext::GetDefaultChannel(ModuleRawPtr _) { return p_->GetDefaultChannel(_); } +bool GlobalModuleContext::IsModuleExists(ModuleIdentifier id) { + return p_->IsModuleExists(id); +} + } // namespace GpgFrontend::Module diff --git a/src/core/module/GlobalModuleContext.h b/src/core/module/GlobalModuleContext.h index e48f186e..8ef1f644 100644 --- a/src/core/module/GlobalModuleContext.h +++ b/src/core/module/GlobalModuleContext.h @@ -77,6 +77,8 @@ class GPGFRONTEND_CORE_EXPORT GlobalModuleContext : public QObject { bool TriggerEvent(EventRefrernce); + bool IsModuleExists(ModuleIdentifier); + private: class Impl; std::unique_ptr<Impl> p_; diff --git a/src/core/module/GlobalRegisterTable.cpp b/src/core/module/GlobalRegisterTable.cpp index 1346d9ab..a4910f9f 100644 --- a/src/core/module/GlobalRegisterTable.cpp +++ b/src/core/module/GlobalRegisterTable.cpp @@ -34,6 +34,8 @@ #include <shared_mutex> #include <unordered_map> +#include "spdlog/spdlog.h" + namespace GpgFrontend::Module { class GlobalRegisterTable::Impl { @@ -46,16 +48,22 @@ class GlobalRegisterTable::Impl { Value(std::any v) : value(v), type(v.type()) {} }; - Impl() : global_register_table_() {} + Impl(GlobalRegisterTable* parent) + : parent_(parent), global_register_table_() {} bool PublishKV(Namespace n, Key k, std::any v) { std::unique_lock lock(lock_); + SPDLOG_DEBUG("publishing kv to rt, n: {}, k: {}, v type: {}", n, k, + v.type().name()); + auto& sub_table = global_register_table_.emplace(n, SubTable{}).first->second; auto sub_it = sub_table.find(k); if (sub_it == sub_table.end()) { sub_it = sub_table.emplace(k, std::make_unique<Value>(Value{v})).first; + SPDLOG_DEBUG("new kv in rt, created n: {}, k: {}, v type: {}", n, k, + v.type().name()); } else { if (sub_it->second->type != v.type()) { return false; @@ -64,11 +72,14 @@ class GlobalRegisterTable::Impl { } sub_it->second->version++; + emit parent_->SignalPublish(n, k, sub_it->second->version); return true; } std::optional<std::any> LookupKV(Namespace n, Key k) { std::shared_lock lock(lock_); + SPDLOG_DEBUG("looking up kv in rt, n: {}, k: {}", n, k); + auto it = global_register_table_.find(n); if (it == global_register_table_.end()) return std::nullopt; @@ -79,15 +90,26 @@ class GlobalRegisterTable::Impl { : std::nullopt; } + bool ListenPublish(QObject* o, Namespace n, Key k, LPCallback c) { + if (o == nullptr) return false; + return QObject::connect(parent_, &GlobalRegisterTable::SignalPublish, o, + [n, k, c](Namespace pn, Key pk, int v) { + if (pn == n && pk == k) { + c(pn, pk, v); + } + }) == nullptr; + } + private: using SubTable = std::unordered_map<Key, std::unique_ptr<Value>>; using Table = std::map<Namespace, SubTable>; std::shared_mutex lock_; + GlobalRegisterTable* parent_; Table global_register_table_; }; -GlobalRegisterTable::GlobalRegisterTable() : p_(std::make_unique<Impl>()) {} +GlobalRegisterTable::GlobalRegisterTable() : p_(std::make_unique<Impl>(this)) {} GlobalRegisterTable::~GlobalRegisterTable() = default; @@ -99,4 +121,9 @@ std::optional<std::any> GlobalRegisterTable::LookupKV(Namespace n, Key v) { return p_->LookupKV(n, v); } +bool GlobalRegisterTable::ListenPublish(QObject* o, Namespace n, Key k, + LPCallback c) { + return p_->ListenPublish(o, n, k, c); +} + } // namespace GpgFrontend::Module
\ No newline at end of file diff --git a/src/core/module/GlobalRegisterTable.h b/src/core/module/GlobalRegisterTable.h index f900559e..5991efb5 100644 --- a/src/core/module/GlobalRegisterTable.h +++ b/src/core/module/GlobalRegisterTable.h @@ -29,16 +29,17 @@ #pragma once #include <any> +#include <functional> #include <optional> -#include "core/GpgFrontendCore.h" - namespace GpgFrontend::Module { using Namespace = std::string; using Key = std::string; +using LPCallback = std::function<void(Namespace, Key, int)>; -class GlobalRegisterTable { +class GlobalRegisterTable : public QObject { + Q_OBJECT public: GlobalRegisterTable(); @@ -48,6 +49,11 @@ class GlobalRegisterTable { std::optional<std::any> LookupKV(Namespace, Key); + bool ListenPublish(QObject *, Namespace, Key, LPCallback); + + signals: + void SignalPublish(Namespace, Key, int); + private: class Impl; std::unique_ptr<Impl> p_; diff --git a/src/core/module/Module.cpp b/src/core/module/Module.cpp index d66773ff..12de004a 100644 --- a/src/core/module/Module.cpp +++ b/src/core/module/Module.cpp @@ -29,6 +29,7 @@ #include "Module.h" #include <boost/format.hpp> +#include <string> #include "core/module/GlobalModuleContext.h" diff --git a/src/core/module/Module.h b/src/core/module/Module.h index d2f6aa3b..da87f88e 100644 --- a/src/core/module/Module.h +++ b/src/core/module/Module.h @@ -29,7 +29,6 @@ #pragma once #include "core/module/Event.h" -#include "core/thread/Task.h" #include "core/thread/TaskRunner.h" namespace GpgFrontend::Module { diff --git a/src/core/module/ModuleManager.cpp b/src/core/module/ModuleManager.cpp index 0bf9e972..20f9ab28 100644 --- a/src/core/module/ModuleManager.cpp +++ b/src/core/module/ModuleManager.cpp @@ -28,11 +28,12 @@ #include "ModuleManager.h" -#include <memory> +#include <boost/format.hpp> #include "core/module/GlobalModuleContext.h" #include "core/module/GlobalRegisterTable.h" #include "core/module/Module.h" +#include "core/thread/Task.h" #include "core/thread/TaskRunner.h" namespace GpgFrontend::Module { @@ -88,6 +89,10 @@ class ModuleManager::Impl { return grt_->LookupKV(n, k); } + bool ListenPublish(QObject* o, Namespace n, Key k, LPCallback c) { + return grt_->ListenPublish(o, n, k, c); + } + private: static ModuleMangerPtr global_module_manager_; TaskRunnerPtr task_runner_; @@ -95,6 +100,12 @@ class ModuleManager::Impl { GRTPtr grt_; }; +bool UpsertRTValueTyped(const std::string& namespace_, const std::string& key, + const std::any& value) { + return ModuleManager::GetInstance()->UpsertRTValue(namespace_, key, + std::any(value)); +} + ModuleManager::ModuleManager() : p_(std::make_unique<Impl>()) {} ModuleManager::~ModuleManager() = default; @@ -129,4 +140,15 @@ std::optional<std::any> ModuleManager::RetrieveRTValue(Namespace n, Key k) { return p_->RetrieveRTValue(n, k); } +bool ModuleManager::ListenPublish(QObject* o, Namespace n, Key k, + LPCallback c) { + return p_->ListenPublish(o, n, k, c); +} + +ModuleIdentifier GetRealModuleIdentifier(const ModuleIdentifier& id) { + // WARNING: when YOU need to CHANGE this line, YOU SHOULD change the same code + // in Module.cpp as well. + return (boost::format("__module_%1%") % id).str(); +} + } // namespace GpgFrontend::Module
\ No newline at end of file diff --git a/src/core/module/ModuleManager.h b/src/core/module/ModuleManager.h index 66fa9db6..586627b6 100644 --- a/src/core/module/ModuleManager.h +++ b/src/core/module/ModuleManager.h @@ -50,6 +50,10 @@ using ModuleMangerPtr = std::shared_ptr<ModuleManager>; using GMCPtr = std::shared_ptr<GlobalModuleContext>; using Namespace = std::string; using Key = std::string; +using LPCallback = std::function<void(Namespace, Key, int)>; + +ModuleIdentifier GPGFRONTEND_CORE_EXPORT +GetRealModuleIdentifier(const ModuleIdentifier& id); class GPGFRONTEND_CORE_EXPORT ModuleManager : public QObject { Q_OBJECT @@ -72,6 +76,8 @@ class GPGFRONTEND_CORE_EXPORT ModuleManager : public QObject { std::optional<std::any> RetrieveRTValue(Namespace, Key); + bool ListenPublish(QObject*, Namespace, Key, LPCallback); + private: class Impl; std::unique_ptr<Impl> p_; @@ -100,4 +106,30 @@ void TriggerEvent(const EventIdentifier& event_id, Args&&... args) { std::move(MakeEvent(event_id, std::forward<Args>(args)...))); } +bool GPGFRONTEND_CORE_EXPORT UpsertRTValueTyped(const std::string& namespace_, + const std::string& key, + const std::any& value); + +template <typename T> +std::optional<T> RetrieveRTValueTyped(const std::string& namespace_, + const std::string& key) { + auto any_value = + ModuleManager::GetInstance()->RetrieveRTValue(namespace_, key); + if (any_value && any_value->type() == typeid(T)) { + return std::any_cast<T>(*any_value); + } + return std::nullopt; +} + +template <typename T> +T RetrieveRTValueTypedOrDefault(const std::string& namespace_, + const std::string& key, const T& defaultValue) { + auto any_value = + ModuleManager::GetInstance()->RetrieveRTValue(namespace_, key); + if (any_value && any_value->type() == typeid(T)) { + return std::any_cast<T>(*any_value); + } + return defaultValue; +} + } // namespace GpgFrontend::Module
\ No newline at end of file diff --git a/src/module/integrated/version_checking_module/VersionCheckTask.h b/src/module/integrated/version_checking_module/VersionCheckTask.h index 6258507f..6f13932a 100644 --- a/src/module/integrated/version_checking_module/VersionCheckTask.h +++ b/src/module/integrated/version_checking_module/VersionCheckTask.h @@ -28,6 +28,7 @@ #pragma once +#include <core/thread/Task.h> #include <module/sdk/GpgFrontendModuleSDK.h> #include "SoftwareVersion.h" diff --git a/src/module/integrated/version_checking_module/VersionCheckingModule.cpp b/src/module/integrated/version_checking_module/VersionCheckingModule.cpp index 233b4225..bab30c33 100644 --- a/src/module/integrated/version_checking_module/VersionCheckingModule.cpp +++ b/src/module/integrated/version_checking_module/VersionCheckingModule.cpp @@ -51,6 +51,7 @@ VersionCheckingModule::~VersionCheckingModule() = default; bool VersionCheckingModule::Register() { MODULE_LOG_INFO("version checking module registering"); listenEvent("APPLICATION_LOADED"); + listenEvent("CHECK_APPLICATION_VERSION"); return true; } @@ -74,33 +75,31 @@ bool VersionCheckingModule::Deactive() { return true; } void VersionCheckingModule::SlotVersionCheckDone(SoftwareVersion version) { MODULE_LOG_DEBUG("registering software information info to rt"); - ModuleManager::GetInstance()->UpsertRTValue(GetModuleIdentifier(), - "version.current_version", - version.current_version); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.loading_done", version.loading_done); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.latest_version", version.latest_version); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.current_version_is_drafted", - version.current_version_is_drafted); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.current_version_is_a_prerelease", - version.current_version_is_a_prerelease); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.current_version_publish_in_remote", - version.current_version_publish_in_remote); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.latest_prerelease_version_from_remote", - version.latest_prerelease_version_from_remote); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.need_upgrade", version.NeedUpgrade()); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.current_version_released", - version.CurrentVersionReleased()); - ModuleManager::GetInstance()->UpsertRTValue( - GetModuleIdentifier(), "version.current_a_withdrawn_version", - version.VersionWithdrawn()); + UpsertRTValueTyped(GetModuleIdentifier(), "version.current_version", + version.current_version); + UpsertRTValueTyped(GetModuleIdentifier(), "version.loading_done", + version.loading_done); + UpsertRTValueTyped(GetModuleIdentifier(), "version.latest_version", + version.latest_version); + UpsertRTValueTyped(GetModuleIdentifier(), + "version.current_version_is_drafted", + version.current_version_is_drafted); + UpsertRTValueTyped(GetModuleIdentifier(), + "version.current_version_is_a_prerelease", + version.current_version_is_a_prerelease); + UpsertRTValueTyped(GetModuleIdentifier(), + "version.current_version_publish_in_remote", + version.current_version_publish_in_remote); + UpsertRTValueTyped(GetModuleIdentifier(), + "version.latest_prerelease_version_from_remote", + version.latest_prerelease_version_from_remote); + UpsertRTValueTyped(GetModuleIdentifier(), "version.need_upgrade", + version.NeedUpgrade()); + UpsertRTValueTyped(GetModuleIdentifier(), "version.current_version_released", + version.CurrentVersionReleased()); + UpsertRTValueTyped(GetModuleIdentifier(), + "version.current_a_withdrawn_version", + version.VersionWithdrawn()); MODULE_LOG_DEBUG("register software information to rt done"); } } // namespace GpgFrontend::Module::Integrated::VersionCheckingModule diff --git a/src/ui/dialog/help/AboutDialog.cpp b/src/ui/dialog/help/AboutDialog.cpp index acd76c97..77363bef 100644 --- a/src/ui/dialog/help/AboutDialog.cpp +++ b/src/ui/dialog/help/AboutDialog.cpp @@ -30,15 +30,14 @@ #include <openssl/opensslv.h> +#include <any> #include <string> #include "GpgFrontendBuildInfo.h" #include "core/function/GlobalSettingStation.h" +#include "core/module/Module.h" #include "core/module/ModuleManager.h" -#include "core/thread/TaskRunnerGetter.h" -#include "spdlog/spdlog.h" #include "ui/dialog/help/GnupgTab.h" -#include "ui/thread/VersionCheckTask.h" namespace GpgFrontend::UI { @@ -204,44 +203,57 @@ UpdateTab::UpdateTab(QWidget* parent) : QWidget(parent) { setLayout(layout); } +void UpdateTab::showEvent(QShowEvent* event) { + QWidget::showEvent(event); + SPDLOG_DEBUG("loading version loading info from rt"); + + auto is_loading_done = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.loading_done", false); + + if (!is_loading_done) { + Module::TriggerEvent("CHECK_APPLICATION_VERSION"); + } else { + slot_show_version_status(); + } +} + void UpdateTab::slot_show_version_status() { - this->pb_->setHidden(true); SPDLOG_DEBUG("loading version info from rt"); - auto is_loading_done = - std::any_cast<bool>(Module::ModuleManager::GetInstance()->RetrieveRTValue( - "__module_com.bktus.gpgfrontend.module.integrated." - "versionchecking", - "version.loading_done")); + auto is_loading_done = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.loading_done", false); if (!is_loading_done) { - SPDLOG_DEBUG("version info loading havn't been done yet"); + SPDLOG_DEBUG("version info loading havn't been done yet."); this->pb_->setHidden(false); + return; + } else { + this->pb_->setHidden(true); } - auto is_need_upgrade = - std::any_cast<bool>(Module::ModuleManager::GetInstance()->RetrieveRTValue( - "__module_com.bktus.gpgfrontend.module.integrated." - "versionchecking", - "version.need_upgrade")); - - auto is_current_a_withdrawn_version = - std::any_cast<bool>(Module::ModuleManager::GetInstance()->RetrieveRTValue( - "__module_com.bktus.gpgfrontend.module.integrated." - "versionchecking", - "version.current_a_withdrawn_version")); - - auto is_current_version_released = - std::any_cast<bool>(Module::ModuleManager::GetInstance()->RetrieveRTValue( - "__module_com.bktus.gpgfrontend.module.integrated." - "versionchecking", - "version.current_version_released")); - - auto latest_version = std::any_cast<std::string>( - Module::ModuleManager::GetInstance()->RetrieveRTValue( - "__module_com.bktus.gpgfrontend.module.integrated." - "versionchecking", - "version.latest_version")); + auto is_need_upgrade = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.need_upgrade", false); + + auto is_current_a_withdrawn_version = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.current_a_withdrawn_version", false); + + auto is_current_version_released = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.current_version_released", false); + + auto latest_version = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.latest_version", std::string{}); latest_version_label_->setText( "<center><b>" + QString(_("Latest Version From Github")) + ": " + diff --git a/src/ui/dialog/help/AboutDialog.h b/src/ui/dialog/help/AboutDialog.h index d8924011..b7871a29 100644 --- a/src/ui/dialog/help/AboutDialog.h +++ b/src/ui/dialog/help/AboutDialog.h @@ -28,10 +28,8 @@ #pragma once -#include "core/GpgContext.h" #include "ui/GpgFrontendUI.h" #include "ui/dialog/GeneralDialog.h" -#include "ui/struct/SoftwareVersion.h" namespace GpgFrontend::UI { @@ -88,6 +86,9 @@ class UpdateTab : public QWidget { */ explicit UpdateTab(QWidget* parent = nullptr); + protected: + void showEvent(QShowEvent* event) override; + private slots: /** * @brief diff --git a/src/ui/main_window/MainWindow.cpp b/src/ui/main_window/MainWindow.cpp index dbca1f55..96210219 100644 --- a/src/ui/main_window/MainWindow.cpp +++ b/src/ui/main_window/MainWindow.cpp @@ -38,7 +38,6 @@ #include "ui/SignalStation.h" #include "ui/UserInterfaceUtils.h" #include "ui/struct/SettingsObject.h" -#include "ui/thread/VersionCheckTask.h" #include "widgets/KeyList.h" namespace GpgFrontend::UI { diff --git a/src/ui/main_window/MainWindow.h b/src/ui/main_window/MainWindow.h index 2be70242..34cdf5b2 100644 --- a/src/ui/main_window/MainWindow.h +++ b/src/ui/main_window/MainWindow.h @@ -314,7 +314,7 @@ class MainWindow : public GeneralMainWindow { /** * @details called when need to upgrade. */ - void slot_version_upgrade(const SoftwareVersion& version); + void slot_version_upgrade(); /** * @details diff --git a/src/ui/main_window/MainWindowSlotFunction.cpp b/src/ui/main_window/MainWindowSlotFunction.cpp index 02088de1..35f7f5ed 100644 --- a/src/ui/main_window/MainWindowSlotFunction.cpp +++ b/src/ui/main_window/MainWindowSlotFunction.cpp @@ -40,6 +40,7 @@ #include "core/function/gpg/GpgKeyGetter.h" #include "core/function/gpg/GpgKeyImportExporter.h" #include "core/function/gpg/GpgKeyManager.h" +#include "core/module/ModuleManager.h" #include "core/thread/DataObject.h" #include "dialog/SignersPicker.h" #include "spdlog/spdlog.h" @@ -815,22 +816,47 @@ void MainWindow::upload_key_to_server() { void MainWindow::SlotOpenFile(QString& path) { edit_->SlotOpenFile(path); } -void MainWindow::slot_version_upgrade(const SoftwareVersion& version) { - if (!version.InfoValid()) { - SPDLOG_ERROR("invalid version info"); +void MainWindow::slot_version_upgrade() { + auto is_loading_done = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.loading_done", false); + + if (!is_loading_done) { + SPDLOG_ERROR("invalid version info from rt"); return; } + auto is_need_upgrade = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.need_upgrade", false); + + auto is_current_a_withdrawn_version = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.current_a_withdrawn_version", false); + + auto is_current_version_released = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.current_version_released", false); + + auto latest_version = Module::RetrieveRTValueTypedOrDefault<>( + Module::GetRealModuleIdentifier( + "com.bktus.gpgfrontend.module.integrated.versionchecking"), + "version.latest_version", std::string{}); + SPDLOG_DEBUG( "version info, need upgrade: {}, with drawn: {}, current version " "released: {}", - version.NeedUpgrade(), version.VersionWithDrawn(), - version.CurrentVersionReleased()); + is_need_upgrade, is_current_a_withdrawn_version, + is_current_version_released); - if (version.NeedUpgrade()) { + if (is_need_upgrade) { statusBar()->showMessage( QString(_("GpgFrontend Upgradeable (New Version: %1).")) - .arg(version.latest_version.c_str()), + .arg(latest_version.c_str()), 30000); auto update_button = new QPushButton("Update GpgFrontend", this); connect(update_button, &QPushButton::clicked, [=]() { @@ -838,23 +864,23 @@ void MainWindow::slot_version_upgrade(const SoftwareVersion& version) { about_dialog->show(); }); statusBar()->addPermanentWidget(update_button, 0); - } else if (version.VersionWithDrawn()) { + } else if (is_current_a_withdrawn_version) { QMessageBox::warning( this, _("Withdrawn Version"), QString( _("This version(%1) may have been withdrawn by the developer due " "to serious problems. Please stop using this version " "immediately and use the latest stable version.")) - .arg(version.current_version.c_str()) + + .arg(latest_version.c_str()) + "<br/>" + QString(_("You can download the latest stable version(%1) on " "Github Releases " "Page.<br/>")) - .arg(version.latest_version.c_str())); - } else if (!version.CurrentVersionReleased()) { + .arg(latest_version.c_str())); + } else if (!is_current_version_released) { statusBar()->showMessage( QString(_("This maybe a BETA Version (Latest Stable Version: %1).")) - .arg(version.latest_version.c_str()), + .arg(latest_version.c_str()), 30000); } } diff --git a/src/ui/struct/SoftwareVersion.cpp b/src/ui/struct/SoftwareVersion.cpp deleted file mode 100644 index dec76e82..00000000 --- a/src/ui/struct/SoftwareVersion.cpp +++ /dev/null @@ -1,101 +0,0 @@ -/** - * Copyright (C) 2021 Saturneric <[email protected]> - * - * This file is part of GpgFrontend. - * - * GpgFrontend is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * GpgFrontend is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with GpgFrontend. If not, see <https://www.gnu.org/licenses/>. - * - * The initial version of the source code is inherited from - * the gpg4usb project, which is under GPL-3.0-or-later. - * - * All the source code of GpgFrontend was modified and released by - * Saturneric <[email protected]> starting on May 12, 2021. - * - * SPDX-License-Identifier: GPL-3.0-or-later - * - */ - -#include "SoftwareVersion.h" - -int GpgFrontend::UI::SoftwareVersion::version_compare(const std::string& a, - const std::string& b) { - auto temp_a = a, temp_b = b; - - if (!temp_a.empty() && temp_a.front() == 'v') { - temp_a = temp_a.erase(0, 1); - SPDLOG_DEBUG("real version a: {}", temp_a); - } - - if (!temp_b.empty() && temp_b.front() == 'v') { - temp_b.erase(0, 1); - SPDLOG_DEBUG("real version b: {}", temp_b); - } - - // First, split the string. - std::vector<std::string> va, vb; - boost::split(va, temp_a, boost::is_any_of(".")); - boost::split(vb, temp_b, boost::is_any_of(".")); - - // Compare the numbers step by step, but only as deep as the version - // with the least elements allows. - const int depth = - std::min(static_cast<int>(va.size()), static_cast<int>(vb.size())); - int ia = 0, ib = 0; - for (int i = 0; i < depth; ++i) { - try { - ia = boost::lexical_cast<int>(va[i]); - ib = boost::lexical_cast<int>(vb[i]); - } catch (boost::bad_lexical_cast& ignored) { - break; - } - if (ia != ib) break; - } - - // Return the required number. - if (ia > ib) - return 1; - else if (ia < ib) - return -1; - else { - // In case of equal versions, assumes that the version - // with the most elements is the highest version. - if (va.size() > vb.size()) - return 1; - else if (va.size() < vb.size()) - return -1; - } - - // Everything is equal, return 0. - return 0; -} - -bool GpgFrontend::UI::SoftwareVersion::NeedUpgrade() const { - SPDLOG_DEBUG("compair version current {} latest {}, result {}", - current_version, latest_version, - version_compare(current_version, latest_version)); - - SPDLOG_DEBUG("load done: {}, pre-release: {}, draft: {}", load_info_done, - latest_prerelease, latest_draft); - return load_info_done && !latest_prerelease && !latest_draft && - version_compare(current_version, latest_version) < 0; -} - -bool GpgFrontend::UI::SoftwareVersion::VersionWithDrawn() const { - return load_info_done && !current_version_found && current_prerelease && - !current_draft; -} - -bool GpgFrontend::UI::SoftwareVersion::CurrentVersionReleased() const { - return load_info_done && current_version_found; -}
\ No newline at end of file diff --git a/src/ui/struct/SoftwareVersion.h b/src/ui/struct/SoftwareVersion.h deleted file mode 100644 index d4d9f729..00000000 --- a/src/ui/struct/SoftwareVersion.h +++ /dev/null @@ -1,85 +0,0 @@ -/** - * Copyright (C) 2021 Saturneric <[email protected]> - * - * This file is part of GpgFrontend. - * - * GpgFrontend is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * GpgFrontend is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with GpgFrontend. If not, see <https://www.gnu.org/licenses/>. - * - * The initial version of the source code is inherited from - * the gpg4usb project, which is under GPL-3.0-or-later. - * - * All the source code of GpgFrontend was modified and released by - * Saturneric <[email protected]> starting on May 12, 2021. - * - * SPDX-License-Identifier: GPL-3.0-or-later - * - */ - -#pragma once - -#include <boost/date_time.hpp> - -namespace GpgFrontend::UI { -/** - * @brief - * - */ -struct SoftwareVersion { - std::string latest_version; ///< - std::string current_version; ///< - bool latest_prerelease = false; ///< - bool latest_draft = false; ///< - bool current_prerelease = false; ///< - bool current_draft = false; ///< - bool load_info_done = false; ///< - bool current_version_found = false; ///< - std::string publish_date; ///< - std::string release_note; ///< - - /** - * @brief - * - * @return true - * @return false - */ - [[nodiscard]] bool InfoValid() const { return load_info_done; } - - /** - * @brief - * - * @return true - * @return false - */ - [[nodiscard]] bool NeedUpgrade() const; - - /** - * @brief - * - * @return true - * @return false - */ - [[nodiscard]] bool VersionWithDrawn() const; - - /** - * @brief - * - * @return true - * @return false - */ - [[nodiscard]] bool CurrentVersionReleased() const; - - private: - static int version_compare(const std::string& a, const std::string& b); -}; -} // namespace GpgFrontend::UI diff --git a/src/ui/thread/VersionCheckTask.cpp b/src/ui/thread/VersionCheckTask.cpp deleted file mode 100644 index 72857ae3..00000000 --- a/src/ui/thread/VersionCheckTask.cpp +++ /dev/null @@ -1,177 +0,0 @@ -/** - * Copyright (C) 2021 Saturneric <[email protected]> - * - * This file is part of GpgFrontend. - * - * GpgFrontend is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * GpgFrontend is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with GpgFrontend. If not, see <https://www.gnu.org/licenses/>. - * - * The initial version of the source code is inherited from - * the gpg4usb project, which is under GPL-3.0-or-later. - * - * All the source code of GpgFrontend was modified and released by - * Saturneric <[email protected]> starting on May 12, 2021. - * - * SPDX-License-Identifier: GPL-3.0-or-later - * - */ - -#include "VersionCheckTask.h" - -#include <nlohmann/json.hpp> - -#include "GpgFrontendBuildInfo.h" - -namespace GpgFrontend::UI { - -VersionCheckTask::VersionCheckTask() - : Task("version_check_task"), - network_manager_(new QNetworkAccessManager(this)), - current_version_(std::string("v") + std::to_string(VERSION_MAJOR) + "." + - std::to_string(VERSION_MINOR) + "." + - std::to_string(VERSION_PATCH)) { - qRegisterMetaType<SoftwareVersion>("SoftwareVersion"); - version_.current_version = current_version_; -} - -void VersionCheckTask::Run() { - HoldOnLifeCycle(true); - - try { - using namespace nlohmann; - SPDLOG_DEBUG("current version: {}", current_version_); - std::string latest_version_url = - "https://api.github.com/repos/saturneric/gpgfrontend/releases/latest"; - - QNetworkRequest latest_request; - latest_request.setUrl(QUrl(latest_version_url.c_str())); - latest_reply_ = network_manager_->get(latest_request); - connect(latest_reply_, &QNetworkReply::finished, this, - &VersionCheckTask::slot_parse_latest_version_info); - - // loading done - version_.load_info_done = true; - - } catch (...) { - SPDLOG_ERROR("unknown error occurred"); - emit SignalTaskShouldEnd(-1); - } -} - -void VersionCheckTask::slot_parse_latest_version_info() { - version_.current_version = current_version_; - - try { - if (latest_reply_ == nullptr || - latest_reply_->error() != QNetworkReply::NoError) { - SPDLOG_ERROR("latest version request error"); - version_.latest_version = current_version_; - } else { - latest_reply_bytes_ = latest_reply_->readAll(); - - auto latest_reply_json = - nlohmann::json::parse(latest_reply_bytes_.toStdString()); - - std::string latest_version = latest_reply_json["tag_name"]; - - SPDLOG_INFO("latest version from Github: {}", latest_version); - - QRegularExpression re(R"(^[vV](\d+\.)?(\d+\.)?(\*|\d+))"); - auto version_match = re.match(latest_version.c_str()); - if (version_match.hasMatch()) { - latest_version = version_match.captured(0).toStdString(); - SPDLOG_DEBUG("latest version matched: {}", latest_version); - } else { - latest_version = current_version_; - SPDLOG_WARN("latest version unknown"); - } - - bool prerelease = latest_reply_json["prerelease"], - draft = latest_reply_json["draft"]; - std::string publish_date = latest_reply_json["published_at"]; - std::string release_note = latest_reply_json["body"]; - version_.latest_version = latest_version; - version_.latest_prerelease = prerelease; - version_.latest_draft = draft; - version_.publish_date = publish_date; - version_.release_note = release_note; - } - } catch (...) { - SPDLOG_ERROR("unknown error occurred"); - version_.load_info_done = false; - } - - if (latest_reply_ != nullptr) { - latest_reply_->deleteLater(); - } - - try { - std::string current_version_url = - "https://api.github.com/repos/saturneric/gpgfrontend/releases/tags/" + - current_version_; - - QNetworkRequest current_request; - current_request.setUrl(QUrl(current_version_url.c_str())); - current_reply_ = network_manager_->get(current_request); - - connect(current_reply_, &QNetworkReply::finished, this, - &VersionCheckTask::slot_parse_current_version_info); - } catch (...) { - SPDLOG_ERROR("current version request create error"); - emit SignalTaskShouldEnd(-1); - } -} - -void VersionCheckTask::slot_parse_current_version_info() { - try { - if (current_reply_ == nullptr || - current_reply_->error() != QNetworkReply::NoError) { - if (current_reply_ != nullptr) { - SPDLOG_ERROR("current version request network error: {}", - current_reply_->errorString().toStdString()); - } else { - SPDLOG_ERROR( - "current version request network error, null reply object"); - } - - version_.current_version_found = false; - version_.load_info_done = false; - } else { - version_.current_version_found = true; - current_reply_bytes_ = current_reply_->readAll(); - SPDLOG_DEBUG("current version: {}", current_reply_bytes_.size()); - auto current_reply_json = - nlohmann::json::parse(current_reply_bytes_.toStdString()); - bool current_prerelease = current_reply_json["prerelease"], - current_draft = current_reply_json["draft"]; - version_.latest_prerelease = current_prerelease; - version_.latest_draft = current_draft; - version_.load_info_done = true; - } - } catch (...) { - SPDLOG_ERROR("unknown error occurred"); - version_.load_info_done = false; - } - - SPDLOG_DEBUG("current version parse done: {}", - version_.current_version_found); - - if (current_reply_ != nullptr) { - current_reply_->deleteLater(); - } - - emit SignalUpgradeVersion(version_); - emit SignalTaskShouldEnd(0); -} - -} // namespace GpgFrontend::UI diff --git a/src/ui/thread/VersionCheckTask.h b/src/ui/thread/VersionCheckTask.h deleted file mode 100644 index 74428c49..00000000 --- a/src/ui/thread/VersionCheckTask.h +++ /dev/null @@ -1,98 +0,0 @@ -/** - * Copyright (C) 2021 Saturneric <[email protected]> - * - * This file is part of GpgFrontend. - * - * GpgFrontend is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * GpgFrontend is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with GpgFrontend. If not, see <https://www.gnu.org/licenses/>. - * - * The initial version of the source code is inherited from - * the gpg4usb project, which is under GPL-3.0-or-later. - * - * All the source code of GpgFrontend was modified and released by - * Saturneric <[email protected]> starting on May 12, 2021. - * - * SPDX-License-Identifier: GPL-3.0-or-later - * - */ - -#pragma once - -#include <qnetworkaccessmanager.h> -#include <qnetworkreply.h> - -#include <memory> -#include <string> - -#include "core/thread/Task.h" -#include "ui/GpgFrontendUI.h" -#include "ui/struct/SoftwareVersion.h" - -namespace GpgFrontend::UI { - -/** - * @brief - * - */ -class VersionCheckTask : public Thread::Task { - Q_OBJECT - - public: - /** - * @brief Construct a new Version Check Thread object - * - */ - explicit VersionCheckTask(); - - signals: - - /** - * @brief - * - * @param version - */ - void SignalUpgradeVersion(SoftwareVersion version); - - protected: - /** - * @brief - - * - */ - void Run() override; - - private slots: - - /** - * @brief - * - */ - void slot_parse_latest_version_info(); - - /** - * @brief - * - */ - void slot_parse_current_version_info(); - - private: - QByteArray latest_reply_bytes_; ///< - QByteArray current_reply_bytes_; ///< - QNetworkReply* latest_reply_ = nullptr; ///< latest version info reply - QNetworkReply* current_reply_ = nullptr; ///< current version info reply - QNetworkAccessManager* network_manager_; ///< - std::string current_version_; - SoftwareVersion version_; -}; - -} // namespace GpgFrontend::UI |