在这篇文章中提到:client端对于非INSERT语句,processOrdinaryQuery()方法的代码如下:
/// Process the query that doesn't require transferring data blocks to the server.
void processOrdinaryQuery()
{
//客户端sendQuery()后, SQL及其他信息封装成数据包发送到服务端, //数据包被发送到对应的端口, 由服务端*Handler进行具体的处理, run() -> runImpl() -> receivePacket()
connection->sendQuery(query, query_id, QueryProcessingStage::Complete, &context.getSettingsRef(), nullptr,
true);
sendExternalTables();
receiveResult();//客户端接收服务端的处理结果, 也是以数据包的形式发送过来的
}
主要包含三个步骤:1)将SQL从Client端发送到Server端;2)sendExternalTables();3)Client端等待Server端发送回来的结果。
receiveResult()方法如下:
/// Receives and processes packets coming from server. Also checks if query execution should be cancelled.
//接收处理服务器Server端发送的数据包, 同时检查SQL执行是否被取消
void receiveResult()
{
InterruptListener interrupt_listener;
bool cancelled = false;
// TODO: get the poll_interval from commandline.
const auto receive_timeout = connection->getTimeouts().receive_timeout;
constexpr size_t default_poll_interval = 1000000; /// in microseconds
constexpr size_t min_poll_interval = 5000; /// in microseconds
const size_t poll_interval
= std::max(min_poll_interval,
std::min<size_t>(receive_timeout.totalMicroseconds(), default_poll_interval));
while (true)
{
Stopwatch receive_watch(CLOCK_MONOTONIC_COARSE);
while (true)
{
/// Has the Ctrl+C been pressed and thus the query should be cancelled?
/// If this is the case, inform the server about it
/// and receive

本文深入解析ClickHouse客户端与服务器的交互过程,重点介绍processOrdinaryQuery()方法,包括SQL发送、外部表发送及结果接收流程。详细分析了receiveResult()方法内部的双重循环机制,阐述了数据包接收、处理及取消查询的实现细节。
最低0.47元/天 解锁文章
2220

被折叠的 条评论
为什么被折叠?



