From 3949ba30e13837ceb47bcfae4b41a6a5324b5145 Mon Sep 17 00:00:00 2001 From: "Scott E. Graves" Date: Sat, 18 Feb 2017 10:15:01 -0600 Subject: [PATCH] Refactoring --- SiaDrive.Api/AutoThread.cpp | 43 +++++++++++ SiaDrive.Api/AutoThread.h | 28 +++++++ SiaDrive.Api/SiaApi.h | 94 ++++++++++++++--------- SiaDrive.Api/SiaCommon.h | 12 +++ SiaDrive.Api/SiaConsensus.cpp | 51 ++++-------- SiaDrive.Api/SiaDrive.Api.vcxproj | 2 + SiaDrive.Api/SiaDrive.Api.vcxproj.filters | 6 ++ SiaDrive.Api/SiaFile.cpp | 4 +- SiaDrive.Api/SiaFileTree.cpp | 18 +---- SiaDrive.Api/SiaRenter.cpp | 19 ++++- SiaDrive.Api/SiaWallet.cpp | 18 ++--- 11 files changed, 193 insertions(+), 102 deletions(-) create mode 100644 SiaDrive.Api/AutoThread.cpp create mode 100644 SiaDrive.Api/AutoThread.h diff --git a/SiaDrive.Api/AutoThread.cpp b/SiaDrive.Api/AutoThread.cpp new file mode 100644 index 0000000..f45d252 --- /dev/null +++ b/SiaDrive.Api/AutoThread.cpp @@ -0,0 +1,43 @@ +#include "stdafx.h" +#include "AutoThread.h" + +using namespace Sia::Api; + +CAutoThread::CAutoThread(const CSiaCurl& siaCurl) : + _siaCurl(siaCurl.GetHostConfig()), + _stopEvent(::CreateEvent(nullptr, FALSE, FALSE, nullptr)) +{ +} + +CAutoThread::~CAutoThread() +{ + StopAutoThread(); + ::CloseHandle(_stopEvent); +} + +void CAutoThread::StartAutoThread() +{ + std::lock_guard l(_startStopMutex); + if (!_thread) + { + _thread.reset(new std::thread([this]() { + do + { + AutoThreadCallback(_siaCurl); + } while (::WaitForSingleObject(_stopEvent, 2000) == WAIT_TIMEOUT); + })); + } +} + +void CAutoThread::StopAutoThread() +{ + std::lock_guard l(_startStopMutex); + if (_thread) + { + ::SetEvent(_stopEvent); + _thread->join(); + _thread.reset(nullptr); + } +} + + diff --git a/SiaDrive.Api/AutoThread.h b/SiaDrive.Api/AutoThread.h new file mode 100644 index 0000000..b42328b --- /dev/null +++ b/SiaDrive.Api/AutoThread.h @@ -0,0 +1,28 @@ +#pragma once +#include +#include + +NS_BEGIN(Sia) +NS_BEGIN(Api) + +class AFX_EXT_CLASS CAutoThread +{ +public: + CAutoThread(const CSiaCurl& siaCurl); + +public: + virtual ~CAutoThread(); + +private: + CSiaCurl _siaCurl; + HANDLE _stopEvent; + std::unique_ptr _thread; + std::mutex _startStopMutex; + +protected: + void StartAutoThread(); + void StopAutoThread(); + virtual void AutoThreadCallback(const CSiaCurl& siaCurl) = 0; +}; + +NS_END(2) \ No newline at end of file diff --git a/SiaDrive.Api/SiaApi.h b/SiaDrive.Api/SiaApi.h index e574258..e628d4d 100644 --- a/SiaDrive.Api/SiaApi.h +++ b/SiaDrive.Api/SiaApi.h @@ -1,10 +1,36 @@ #pragma once #include "SiaCommon.h" #include "SiaCurl.h" +#include "AutoThread.h" NS_BEGIN(Sia) NS_BEGIN(Api) + +class AFX_EXT_CLASS CSiaBase +{ +public: + explicit CSiaBase(const CSiaCurl& siaCurl) : + _siaCurl(siaCurl) + { + } + +public: + virtual ~CSiaBase() = 0 + { + } + +private: + const CSiaCurl& _siaCurl; + +protected: + inline const CSiaCurl& GetSiaCurl() const + { + return _siaCurl; + } +}; + + class AFX_EXT_CLASS CSiaApi { public: @@ -27,19 +53,17 @@ public: }; class _CSiaFileTree; - class AFX_EXT_CLASS _CSiaFile + class AFX_EXT_CLASS _CSiaFile : + public virtual CSiaBase { friend CSiaApi; friend _CSiaFileTree; private: - _CSiaFile(CSiaCurl& siaCurl, const json& fileJson); + explicit _CSiaFile(const CSiaCurl& siaCurl, const json& fileJson); public: - ~_CSiaFile(); - - private: - CSiaCurl& _siaCurl; + virtual ~_CSiaFile(); // Properties Property(String, SiaPath, public, private) @@ -51,17 +75,15 @@ public: Property(std::uint32_t, Expiration, public, private) }; - class AFX_EXT_CLASS _CSiaFileTree + class AFX_EXT_CLASS _CSiaFileTree : + public virtual CSiaBase { friend CSiaApi; public: - _CSiaFileTree(CSiaCurl& siaCurl); + explicit _CSiaFileTree(const CSiaCurl& siaCurl); public: - ~_CSiaFileTree(); - - private: - CSiaCurl& _siaCurl; + virtual ~_CSiaFileTree(); private: std::vector> _fileList; @@ -78,17 +100,15 @@ public: bool FileExists(const String& siaPath) const; }; - class AFX_EXT_CLASS _CSiaWallet + class AFX_EXT_CLASS _CSiaWallet : + public virtual CSiaBase { friend CSiaApi; private: - _CSiaWallet(CSiaCurl& siaCurl); + explicit _CSiaWallet(const CSiaCurl& siaCurl); public: - ~_CSiaWallet(); - - private: - CSiaCurl& _siaCurl; + virtual ~_CSiaWallet(); // Properties Property(bool, Created, public, private) @@ -105,18 +125,21 @@ public: _SiaApiError GetAddress(String& address) const; }; - class AFX_EXT_CLASS _CSiaRenter + class AFX_EXT_CLASS _CSiaRenter : + public virtual CSiaBase, + public virtual CAutoThread { friend CSiaApi; + private: - _CSiaRenter(CSiaCurl& siaCurl); + explicit _CSiaRenter(const CSiaCurl& siaCurl); public: - ~_CSiaRenter(); - - private: - CSiaCurl& _siaCurl; + virtual ~_CSiaRenter(); + protected: + virtual void AutoThreadCallback(const CSiaCurl& siaCurl) override; + public: _SiaApiError FileExists(const String& siaPath, bool& exists) const; _SiaApiError DeleteFile(const String& siaPath); @@ -125,34 +148,29 @@ public: _SiaApiError GetFileTree(std::shared_ptr<_CSiaFileTree>& siaFileTree) const; }; - class AFX_EXT_CLASS _CSiaConsensus + class AFX_EXT_CLASS _CSiaConsensus : + public virtual CSiaBase, + public virtual CAutoThread { friend CSiaApi; + private: - _CSiaConsensus(CSiaCurl& siaCurl); + explicit _CSiaConsensus(const CSiaCurl& siaCurl); public: - ~_CSiaConsensus(); - - private: - CSiaCurl _siaCurl; - - private: - HANDLE _stopEvent; - std::unique_ptr _refreshThread; + virtual ~_CSiaConsensus(); // Properties Property(std::uint64_t, Height, public, private) Property(bool, Synced, public, private) Property(String, CurrentBlock, public, private) - private: - void StartRefreshThread(); - void StopRefreshThread(); + protected: + virtual void AutoThreadCallback(const CSiaCurl& siaCurl) override; }; public: - CSiaApi(const SiaHostConfig& hostConfig); + explicit CSiaApi(const SiaHostConfig& hostConfig); public: ~CSiaApi(); diff --git a/SiaDrive.Api/SiaCommon.h b/SiaDrive.Api/SiaCommon.h index f470bab..7f5e1be 100644 --- a/SiaDrive.Api/SiaCommon.h +++ b/SiaDrive.Api/SiaCommon.h @@ -112,4 +112,16 @@ inline Hastings CalculateAverageUploadPrice(const std::vector& hosts) return CalculateAveragePrice(hosts, [](const IHost& host)->Hastings { return host.GetUploadPrice(); }); } +static String& ReplaceStringInPlace(String& subject, const String& search, const String& replace) +{ + size_t pos = 0; + while ((pos = subject.find(search, pos)) != std::string::npos) + { + subject.replace(pos, search.length(), replace); + pos += replace.length(); + } + + return subject; +} + NS_END(2) \ No newline at end of file diff --git a/SiaDrive.Api/SiaConsensus.cpp b/SiaDrive.Api/SiaConsensus.cpp index b511944..03c846b 100644 --- a/SiaDrive.Api/SiaConsensus.cpp +++ b/SiaDrive.Api/SiaConsensus.cpp @@ -3,50 +3,33 @@ using namespace Sia::Api; -CSiaApi::_CSiaConsensus::_CSiaConsensus(CSiaCurl& siaCurl) : - _siaCurl(siaCurl.GetHostConfig()), // IMPORTANT: Need a copy of CSiaCurl for use in thread - _stopEvent(::CreateEvent(nullptr, FALSE, FALSE, nullptr)) +CSiaApi::_CSiaConsensus::_CSiaConsensus(const CSiaCurl& siaCurl) : + CSiaBase(siaCurl), + CAutoThread(siaCurl), + _Height(0), + _Synced(false) { - StartRefreshThread(); + StartAutoThread(); } CSiaApi::_CSiaConsensus::~_CSiaConsensus() { - StopRefreshThread(); - ::CloseHandle(_stopEvent); + StopAutoThread(); } -void CSiaApi::_CSiaConsensus::StartRefreshThread() +void CSiaApi::_CSiaConsensus::AutoThreadCallback(const CSiaCurl& siaCurl) { - if (!_refreshThread) + json result; + if (ApiSuccess(siaCurl.Get(L"/consensus", result))) { - _refreshThread.reset(new std::thread([this]() { - do - { - json result; - if (ApiSuccess(_siaCurl.Get(L"/consensus", result))) - { - SetHeight(result["height"].get()); - SetSynced(result["synced"].get()); - SetCurrentBlock(CA2W(result["currentblock"].get().c_str()).m_psz); - } - else - { - SetHeight(0); - SetSynced(false); - SetCurrentBlock(L""); - } - } while (::WaitForSingleObject(_stopEvent, 2000) == WAIT_TIMEOUT); - })); + SetHeight(result["height"].get()); + SetSynced(result["synced"].get()); + SetCurrentBlock(CA2W(result["currentblock"].get().c_str()).m_psz); } -} - -void CSiaApi::_CSiaConsensus::StopRefreshThread() -{ - if (_refreshThread) + else { - SetEvent(_stopEvent); - _refreshThread->join(); - _refreshThread.reset(nullptr); + SetHeight(0); + SetSynced(false); + SetCurrentBlock(L""); } } \ No newline at end of file diff --git a/SiaDrive.Api/SiaDrive.Api.vcxproj b/SiaDrive.Api/SiaDrive.Api.vcxproj index 8310302..beb5b04 100644 --- a/SiaDrive.Api/SiaDrive.Api.vcxproj +++ b/SiaDrive.Api/SiaDrive.Api.vcxproj @@ -189,6 +189,7 @@ + false @@ -225,6 +226,7 @@ + diff --git a/SiaDrive.Api/SiaDrive.Api.vcxproj.filters b/SiaDrive.Api/SiaDrive.Api.vcxproj.filters index cce6bec..555ed53 100644 --- a/SiaDrive.Api/SiaDrive.Api.vcxproj.filters +++ b/SiaDrive.Api/SiaDrive.Api.vcxproj.filters @@ -54,6 +54,9 @@ Source Files + + Source Files + @@ -88,6 +91,9 @@ Header Files + + Header Files + diff --git a/SiaDrive.Api/SiaFile.cpp b/SiaDrive.Api/SiaFile.cpp index a7295ca..19cb0cc 100644 --- a/SiaDrive.Api/SiaFile.cpp +++ b/SiaDrive.Api/SiaFile.cpp @@ -3,8 +3,8 @@ using namespace Sia::Api; -CSiaApi::_CSiaFile::_CSiaFile(CSiaCurl& siaCurl, const json& fileJson) : - _siaCurl(siaCurl), +CSiaApi::_CSiaFile::_CSiaFile(const CSiaCurl& siaCurl, const json& fileJson) : + CSiaBase(siaCurl), _SiaPath(CA2W(fileJson["siapath"].get().c_str())), _FileSize(fileJson["filesize"].get()), _Available(fileJson["available"].get()), diff --git a/SiaDrive.Api/SiaFileTree.cpp b/SiaDrive.Api/SiaFileTree.cpp index 74d1d69..079e2ab 100644 --- a/SiaDrive.Api/SiaFileTree.cpp +++ b/SiaDrive.Api/SiaFileTree.cpp @@ -4,20 +4,8 @@ using namespace Sia::Api; -static String& ReplaceStringInPlace(String& subject, const String& search, const String& replace) -{ - size_t pos = 0; - while ((pos = subject.find(search, pos)) != std::string::npos) - { - subject.replace(pos, search.length(), replace); - pos += replace.length(); - } - - return subject; -} - -CSiaApi::_CSiaFileTree::_CSiaFileTree(CSiaCurl& siaCurl) : - _siaCurl(siaCurl) +CSiaApi::_CSiaFileTree::_CSiaFileTree(const CSiaCurl& siaCurl) : + CSiaBase(siaCurl) { } @@ -32,7 +20,7 @@ void CSiaApi::_CSiaFileTree::BuildTree(const json& result) _fileList.clear(); for (const auto& file : result["files"]) { - _fileList.push_back(CSiaFilePtr(new CSiaFile(_siaCurl, file))); + _fileList.push_back(CSiaFilePtr(new CSiaFile(GetSiaCurl(), file))); } } diff --git a/SiaDrive.Api/SiaRenter.cpp b/SiaDrive.Api/SiaRenter.cpp index 2d2f357..ceeb4b7 100644 --- a/SiaDrive.Api/SiaRenter.cpp +++ b/SiaDrive.Api/SiaRenter.cpp @@ -3,14 +3,25 @@ using namespace Sia::Api; -CSiaApi::_CSiaRenter::_CSiaRenter(CSiaCurl& siaCurl) : - _siaCurl(siaCurl) +CSiaApi::_CSiaRenter::_CSiaRenter(const CSiaCurl& siaCurl) : + CSiaBase(siaCurl), + CAutoThread(siaCurl) { + StartAutoThread(); } CSiaApi::_CSiaRenter::~_CSiaRenter() { + StopAutoThread(); +} +void CSiaApi::_CSiaRenter::AutoThreadCallback(const CSiaCurl& siaCurl) +{ + json result; + if (ApiSuccess(siaCurl.Get(L"/renter", result))) + { + + } } SiaApiError CSiaApi::_CSiaRenter::FileExists(const String& siaPath, bool& exists) const @@ -42,9 +53,9 @@ SiaApiError CSiaApi::_CSiaRenter::QueueUploadFile(const String& siaPath, const S SiaApiError CSiaApi::_CSiaRenter::GetFileTree(CSiaFileTreePtr& siaFileTree) const { SiaApiError ret = SiaApiError::RequestError; - siaFileTree.reset(new CSiaFileTree(_siaCurl)); + siaFileTree.reset(new CSiaFileTree(GetSiaCurl())); json result; - if (ApiSuccess(_siaCurl.Get(L"/renter/files", result))) + if (ApiSuccess(GetSiaCurl().Get(L"/renter/files", result))) { siaFileTree->BuildTree(result); ret = SiaApiError::Success; diff --git a/SiaDrive.Api/SiaWallet.cpp b/SiaDrive.Api/SiaWallet.cpp index 5f4fd2e..4b8c053 100644 --- a/SiaDrive.Api/SiaWallet.cpp +++ b/SiaDrive.Api/SiaWallet.cpp @@ -21,8 +21,8 @@ static String SeedLangToString(const SiaSeedLanguage& lang) } } -CSiaApi::_CSiaWallet::_CSiaWallet(CSiaCurl& siaCurl) : - _siaCurl(siaCurl), +CSiaApi::_CSiaWallet::_CSiaWallet(const CSiaCurl& siaCurl) : + CSiaBase(siaCurl), _Created(false), _Locked(false) { @@ -37,7 +37,7 @@ CSiaApi::_CSiaWallet::~_CSiaWallet() bool CSiaApi::_CSiaWallet::Refresh() { json result; - SiaCurlError error = _siaCurl.Get(L"/wallet", result); + SiaCurlError error = GetSiaCurl().Get(L"/wallet", result); if (ApiSuccess(error)) { SetCreated(result["encrypted"].get()); @@ -59,7 +59,7 @@ SiaApiError CSiaApi::_CSiaWallet::Create(const SiaSeedLanguage& seedLanguage, St { error = SiaApiError::RequestError; json result; - SiaCurlError cerror = _siaCurl.Post(L"/wallet/init", { {L"dictionary", SeedLangToString(seedLanguage)} }, result); + SiaCurlError cerror = GetSiaCurl().Post(L"/wallet/init", { {L"dictionary", SeedLangToString(seedLanguage)} }, result); if (ApiSuccess(cerror)) { error = SiaApiError::Success; @@ -87,7 +87,7 @@ SiaApiError CSiaApi::_CSiaWallet::Lock() error = SiaApiError::RequestError; json result; - SiaCurlError cerror = _siaCurl.Post(L"/wallet/lock", {}, result); + SiaCurlError cerror = GetSiaCurl().Post(L"/wallet/lock", {}, result); if (ApiSuccess(cerror)) { Refresh(); @@ -106,7 +106,7 @@ SiaApiError CSiaApi::_CSiaWallet::Unlock(const String& password) error = SiaApiError::RequestError; json result; - SiaCurlError cerror = _siaCurl.Post(L"/wallet/unlock", { {L"encryptionpassword", password} }, result); + SiaCurlError cerror = GetSiaCurl().Post(L"/wallet/unlock", { {L"encryptionpassword", password} }, result); if (ApiSuccess(cerror)) { Refresh(); @@ -134,7 +134,7 @@ SiaApiError CSiaApi::_CSiaWallet::GetConfirmedBalance(SiaCurrency& balance) cons balance = 0; json result; - SiaCurlError cerror = _siaCurl.Get(L"/wallet", result); + SiaCurlError cerror = GetSiaCurl().Get(L"/wallet", result); if (ApiSuccess(cerror)) { balance = HastingsStringToSiaCurrency(String(CA2W(result["confirmedsiacoinbalance"].get().c_str()))); @@ -150,7 +150,7 @@ SiaApiError CSiaApi::_CSiaWallet::GetUnonfirmedBalance(SiaCurrency& balance) con balance = 0; json result; - SiaCurlError cerror = _siaCurl.Get(L"/wallet", result); + SiaCurlError cerror = GetSiaCurl().Get(L"/wallet", result); if (ApiSuccess(cerror)) { balance = HastingsStringToSiaCurrency(String(CA2W(result["unconfirmedincomingsiacoins"].get().c_str()))); @@ -166,7 +166,7 @@ SiaApiError CSiaApi::_CSiaWallet::GetAddress(String& address) const address = L""; json result; - SiaCurlError cerror = _siaCurl.Get(L"/wallet/address", result); + SiaCurlError cerror = GetSiaCurl().Get(L"/wallet/address", result); if (ApiSuccess(cerror)) { address = CA2W(result["address"].get().c_str());