diff options
| author | Kargatum <dowlandtop@yandex.com> | 2022-02-05 06:37:11 +0700 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2022-02-05 00:37:11 +0100 |
| commit | de13bf426e162ee10cbd5470cec74122d1d4afa0 (patch) | |
| tree | 407c1051b09fea21f946c4ad3b3e4727fca5c400 /src/server/database/Database/Transaction.cpp | |
| parent | d6ead1d1e019bd7afd8230b305ae4dd98babd353 (diff) | |
feat(Core/DBLayer): replace `char const*` to `std::string_view` (#10211)
* feat(Core/DBLayer): replace `char const*` to `std::string_view`
* CString
* 1
* chore(Core/Misc): code cleanup
* cl
* db fix
* fmt style sql
* to fmt
* py
* del old
* 1
* 2
* 3
* 1
* 1
Diffstat (limited to 'src/server/database/Database/Transaction.cpp')
| -rw-r--r-- | src/server/database/Database/Transaction.cpp | 84 |
1 files changed, 57 insertions, 27 deletions
diff --git a/src/server/database/Database/Transaction.cpp b/src/server/database/Database/Transaction.cpp index 1b669c085f..38f2ab051e 100644 --- a/src/server/database/Database/Transaction.cpp +++ b/src/server/database/Database/Transaction.cpp @@ -16,6 +16,7 @@ */ #include "Transaction.h" +#include "Errors.h" #include "Log.h" #include "MySQLConnection.h" #include "PreparedStatement.h" @@ -26,24 +27,24 @@ std::mutex TransactionTask::_deadlockLock; -#define DEADLOCK_MAX_RETRY_TIME_MS 60000 +constexpr Milliseconds DEADLOCK_MAX_RETRY_TIME_MS = 1min; //- Append a raw ad-hoc query to the transaction -void TransactionBase::Append(char const* sql) +void TransactionBase::Append(std::string_view sql) { - SQLElementData data; + SQLElementData data = {}; data.type = SQL_ELEMENT_RAW; - data.element.query = strdup(sql); - m_queries.push_back(data); + data.element = std::string(sql); + m_queries.emplace_back(data); } //- Append a prepared statement to the transaction void TransactionBase::AppendPreparedStatement(PreparedStatementBase* stmt) { - SQLElementData data; + SQLElementData data = {}; data.type = SQL_ELEMENT_PREPARED; - data.element.stmt = stmt; - m_queries.push_back(data); + data.element = stmt; + m_queries.emplace_back(data); } void TransactionBase::Cleanup() @@ -52,15 +53,38 @@ void TransactionBase::Cleanup() if (_cleanedUp) return; - for (SQLElementData const& data : m_queries) + for (SQLElementData& data : m_queries) { switch (data.type) { case SQL_ELEMENT_PREPARED: - delete data.element.stmt; + { + try + { + PreparedStatementBase* stmt = std::get<PreparedStatementBase*>(data.element); + ASSERT(stmt); + + delete stmt; + } + catch (const std::bad_variant_access& ex) + { + LOG_FATAL("sql.sql", "> PreparedStatementBase not found in SQLElementData. {}", ex.what()); + ABORT(); + } + } break; case SQL_ELEMENT_RAW: - free((void*)(data.element.query)); + { + try + { + std::get<std::string>(data.element).clear(); + } + catch (const std::bad_variant_access& ex) + { + LOG_FATAL("sql.sql", "> std::string not found in SQLElementData. {}", ex.what()); + ABORT(); + } + } break; } } @@ -72,6 +96,7 @@ void TransactionBase::Cleanup() bool TransactionTask::Execute() { int errorCode = TryExecute(); + if (!errorCode) return true; @@ -81,15 +106,17 @@ bool TransactionTask::Execute() threadIdStream << std::this_thread::get_id(); std::string threadId = threadIdStream.str(); - // Make sure only 1 async thread retries a transaction so they don't keep dead-locking each other - std::lock_guard<std::mutex> lock(_deadlockLock); - - for (uint32 loopDuration = 0, startMSTime = getMSTime(); loopDuration <= DEADLOCK_MAX_RETRY_TIME_MS; loopDuration = GetMSTimeDiffToNow(startMSTime)) { - if (!TryExecute()) - return true; + // Make sure only 1 async thread retries a transaction so they don't keep dead-locking each other + std::lock_guard<std::mutex> lock(_deadlockLock); - LOG_WARN("sql.sql", "Deadlocked SQL Transaction, retrying. Loop timer: {} ms, Thread Id: {}", loopDuration, threadId); + for (Milliseconds loopDuration = 0s, startMSTime = GetTimeMS(); loopDuration <= DEADLOCK_MAX_RETRY_TIME_MS; loopDuration = GetMSTimeDiffToNow(startMSTime)) + { + if (!TryExecute()) + return true; + + LOG_WARN("sql.sql", "Deadlocked SQL Transaction, retrying. Loop timer: {} ms, Thread Id: {}", loopDuration.count(), threadId); + } } LOG_ERROR("sql.sql", "Fatal deadlocked SQL Transaction, it will not be retried anymore. Thread Id: {}", threadId); @@ -126,17 +153,20 @@ bool TransactionWithResultTask::Execute() threadIdStream << std::this_thread::get_id(); std::string threadId = threadIdStream.str(); - // Make sure only 1 async thread retries a transaction so they don't keep dead-locking each other - std::lock_guard<std::mutex> lock(_deadlockLock); - for (uint32 loopDuration = 0, startMSTime = getMSTime(); loopDuration <= DEADLOCK_MAX_RETRY_TIME_MS; loopDuration = GetMSTimeDiffToNow(startMSTime)) { - if (!TryExecute()) + // Make sure only 1 async thread retries a transaction so they don't keep dead-locking each other + std::lock_guard<std::mutex> lock(_deadlockLock); + + for (Milliseconds loopDuration = 0s, startMSTime = GetTimeMS(); loopDuration <= DEADLOCK_MAX_RETRY_TIME_MS; loopDuration = GetMSTimeDiffToNow(startMSTime)) { - m_result.set_value(true); - return true; - } + if (!TryExecute()) + { + m_result.set_value(true); + return true; + } - LOG_WARN("sql.sql", "Deadlocked SQL Transaction, retrying. Loop timer: {} ms, Thread Id: {}", loopDuration, threadId); + LOG_WARN("sql.sql", "Deadlocked SQL Transaction, retrying. Loop timer: {} ms, Thread Id: {}", loopDuration.count(), threadId); + } } LOG_ERROR("sql.sql", "Fatal deadlocked SQL Transaction, it will not be retried anymore. Thread Id: {}", threadId); @@ -151,7 +181,7 @@ bool TransactionWithResultTask::Execute() bool TransactionCallback::InvokeIfReady() { - if (m_future.valid() && m_future.wait_for(std::chrono::seconds(0)) == std::future_status::ready) + if (m_future.valid() && m_future.wait_for(0s) == std::future_status::ready) { m_callback(m_future.get()); return true; |
