Merge pull request #156 from duckdb/jray/support-pivot
add support for pivot
This commit is contained in:
@@ -401,13 +401,63 @@ void HttpServer::DoHandleRun(const httplib::Request &req,
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
unique_ptr<SQLStatement> last_statement;
|
||||||
|
|
||||||
|
auto statements = connection->ExtractStatements(content);
|
||||||
|
auto statement_count = statements.size();
|
||||||
|
|
||||||
|
if (statement_count == 0) {
|
||||||
|
SetResponseErrorResult(res, "No statements");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If there's more than one statement, run all but the last.
|
||||||
|
if (statement_count > 1) {
|
||||||
|
for (auto i = 0; i < statement_count - 1; ++i) {
|
||||||
|
auto pending = connection->PendingQuery(std::move(statements[i]));
|
||||||
|
// Return any error found before execution.
|
||||||
|
if (pending->HasError()) {
|
||||||
|
SetResponseErrorResult(res, pending->GetError());
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
// Execute tasks until result is ready (or there's an error).
|
||||||
|
auto exec_result = PendingExecutionResult::RESULT_NOT_READY;
|
||||||
|
while (!PendingQueryResult::IsResultReady(exec_result)) {
|
||||||
|
exec_result = pending->ExecuteTask();
|
||||||
|
if (exec_result == PendingExecutionResult::BLOCKED ||
|
||||||
|
exec_result == PendingExecutionResult::NO_TASKS_AVAILABLE) {
|
||||||
|
std::this_thread::sleep_for(std::chrono::milliseconds(1));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Return any error found during execution.
|
||||||
|
switch (exec_result) {
|
||||||
|
case PendingExecutionResult::EXECUTION_ERROR:
|
||||||
|
SetResponseErrorResult(res, pending->GetError());
|
||||||
|
return;
|
||||||
|
case PendingExecutionResult::EXECUTION_FINISHED:
|
||||||
|
case PendingExecutionResult::RESULT_READY:
|
||||||
|
// ignore the result
|
||||||
|
pending->Execute();
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
SetResponseErrorResult(
|
||||||
|
res, StringUtil::Format("Unexpected PendingExecutionResult: %s",
|
||||||
|
exec_result));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the last statement.
|
||||||
|
auto &statement_to_run = statements[statement_count - 1];
|
||||||
|
|
||||||
// We use a pending query so we can execute tasks and fetch chunks
|
// We use a pending query so we can execute tasks and fetch chunks
|
||||||
// incrementally. This enables cancellation.
|
// incrementally. This enables cancellation.
|
||||||
unique_ptr<PendingQueryResult> pending;
|
unique_ptr<PendingQueryResult> pending;
|
||||||
|
|
||||||
// Create pending query, with request content as SQL.
|
// Create pending query, with request content as SQL.
|
||||||
if (parameter_values.size() > 0) {
|
if (parameter_values.size() > 0) {
|
||||||
auto prepared = connection->Prepare(content);
|
auto prepared = connection->Prepare(std::move(statement_to_run));
|
||||||
if (prepared->HasError()) {
|
if (prepared->HasError()) {
|
||||||
SetResponseErrorResult(res, prepared->GetError());
|
SetResponseErrorResult(res, prepared->GetError());
|
||||||
return;
|
return;
|
||||||
@@ -420,7 +470,7 @@ void HttpServer::DoHandleRun(const httplib::Request &req,
|
|||||||
}
|
}
|
||||||
pending = prepared->PendingQuery(values, true);
|
pending = prepared->PendingQuery(values, true);
|
||||||
} else {
|
} else {
|
||||||
pending = connection->PendingQuery(content, true);
|
pending = connection->PendingQuery(std::move(statement_to_run), true);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (pending->HasError()) {
|
if (pending->HasError()) {
|
||||||
@@ -468,7 +518,9 @@ void HttpServer::DoHandleRun(const httplib::Request &req,
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
SetResponseErrorResult(res, "Unexpected PendingExecutionResult");
|
SetResponseErrorResult(
|
||||||
|
res, StringUtil::Format("Unexpected PendingExecutionResult: %s",
|
||||||
|
exec_result));
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user