Use do-while control loops for waiting on log processing

This allows to use the same functions with very short timeouts while
ensuring that the actual state is checked at least once instead of
timing out before even looking at at ZK at least once.
This commit is contained in:
Nicolae Vartolomei 2021-09-16 16:38:27 +01:00
parent db516e8c91
commit c428f433c3
No known key found for this signature in database
GPG Key ID: 6A71A31C4A463CF6
2 changed files with 11 additions and 7 deletions

View File

@ -730,7 +730,10 @@ bool ZooKeeper::waitForDisappear(const std::string & path, const WaitCondition &
}
};
while (!condition || !condition())
/// do-while control structure to allow using this function in non-blocking
/// fashion with a wait condition which returns false by the time this
/// method is called.
do
{
/// Use getData insteand of exists to avoid watch leak.
impl->get(path, callback, watch);
@ -746,7 +749,8 @@ bool ZooKeeper::waitForDisappear(const std::string & path, const WaitCondition &
if (state->event_type == Coordination::DELETED)
return true;
}
} while (!condition || !condition());
return false;
}

View File

@ -5105,8 +5105,7 @@ bool StorageReplicatedMergeTree::tryWaitForReplicaToProcessLogEntry(
/// Don't recheck ZooKeeper too often
constexpr auto event_wait_timeout_ms = 3000;
if (!startsWith(entry.znode_name, "log-"))
throw Exception("Logical error: unexpected name of log node: " + entry.znode_name, ErrorCodes::LOGICAL_ERROR);
LOG_DEBUG(log, "Waiting for {} to process log entry", replica);
{
/// Take the number from the node name `log-xxxxxxxxxx`.
@ -5117,7 +5116,7 @@ bool StorageReplicatedMergeTree::tryWaitForReplicaToProcessLogEntry(
/// Let's wait until entry gets into the replica queue.
bool pulled_to_queue = false;
while (!stop_waiting())
do
{
zkutil::EventPtr event = std::make_shared<Poco::Event>();
@ -5132,8 +5131,9 @@ bool StorageReplicatedMergeTree::tryWaitForReplicaToProcessLogEntry(
/// So log_pointer node will exist, but we will never update it because all background threads already stopped.
/// It can lead to query hung because table drop query can wait for some query (alter, optimize, etc) which called this method,
/// but the query will never finish because the drop already shut down the table.
event->tryWait(event_wait_timeout_ms);
}
if (!stop_waiting())
event->tryWait(event_wait_timeout_ms);
} while (!stop_waiting());
if (!pulled_to_queue)
return false;