| 677 | } |
| 678 | |
| 679 | static TransactionCnchPtr prepareCnchTransaction(ContextMutablePtr context, [[maybe_unused]] ASTPtr & ast) |
| 680 | { |
| 681 | auto server_type = context->getServerType(); |
| 682 | |
| 683 | if (server_type != ServerType::cnch_server && server_type != ServerType::cnch_worker) |
| 684 | return {}; |
| 685 | if (auto txn = context->getCurrentTransaction(); txn) |
| 686 | { |
| 687 | LOG_DEBUG(&Poco::Logger::get("executeQuery"), "Cnch query is already in a transaction " + txn->getTransactionRecord().toString()); |
| 688 | return txn; |
| 689 | } |
| 690 | |
| 691 | if (server_type == ServerType::cnch_server) |
| 692 | { |
| 693 | bool read_only = isReadOnlyTransaction(ast.get()); |
| 694 | auto session_txn = isQueryInInteractiveSession(context, ast) |
| 695 | ? context->getSessionContext()->getCurrentTransaction()->as<CnchExplicitTransaction>() |
| 696 | : nullptr; |
| 697 | TxnTimestamp primary_txn_id = session_txn ? session_txn->getTransactionID() : TxnTimestamp{0}; |
| 698 | auto txn = context->getCnchTransactionCoordinator().createTransaction( |
| 699 | CreateTransactionOption() |
| 700 | .setContext(context) |
| 701 | .setReadOnly(read_only) |
| 702 | .setForceCleanByDM(context->getSettingsRef().force_clean_transaction_by_dm) |
| 703 | .setAsyncPostCommit(context->getSettingsRef().async_post_commit) |
| 704 | .setPrimaryTransactionId(primary_txn_id)); |
| 705 | context->setCurrentTransaction(txn); |
| 706 | if (session_txn && !read_only) |
| 707 | session_txn->addStatement(queryToString(ast)); |
| 708 | return txn; |
| 709 | } |
| 710 | else if (server_type == ServerType::cnch_worker) |
| 711 | { |
| 712 | /// TODO: test it |
| 713 | bool is_initial_query = (context->getClientInfo().query_kind == ClientInfo::QueryKind::INITIAL_QUERY); |
| 714 | |
| 715 | String database; |
| 716 | String table; |
| 717 | if (auto * insert = ast->as<ASTInsertQuery>()) |
| 718 | { |
| 719 | database = insert->table_id.database_name; |
| 720 | table = insert->table_id.table_name; |
| 721 | } |
| 722 | else if (auto * system = ast->as<ASTSystemQuery>(); system && system->type == ASTSystemQuery::Type::DEDUP) |
| 723 | { |
| 724 | database = system->database; |
| 725 | table = system->table; |
| 726 | } |
| 727 | |
| 728 | if (is_initial_query && !table.empty()) |
| 729 | { |
| 730 | if (database.empty()) |
| 731 | database = context->getCurrentDatabase(); |
| 732 | |
| 733 | auto storage = DatabaseCatalog::instance().getTable(StorageID(database, table), context); |
| 734 | if (!dynamic_cast<StorageCnchMergeTree *>(storage.get()) && !dynamic_cast<StorageCloudMergeTree *>(storage.get())) |
| 735 | return {}; |
| 736 |
no test coverage detected