20
20
#include < ydb/core/tx/data_events/shards_splitter.h>
21
21
#include < ydb/core/tx/scheme_cache/scheme_cache.h>
22
22
#include < ydb/core/tx/tx.h>
23
+ #include < ydb/core/persqueue/events/global.h>
23
24
#include < ydb/library/actors/core/actorsystem.h>
24
25
#include < ydb/library/actors/core/interconnect.h>
25
26
#include < ydb/library/wilson_ids/wilson.h>
@@ -1356,6 +1357,7 @@ struct TEvBufferWriteResult : public TEventLocal<TEvBufferWriteResult, TKqpEvent
1356
1357
1357
1358
class TKqpBufferWriteActor :public TActorBootstrapped <TKqpBufferWriteActor>, public IKqpTableWriterCallbacks {
1358
1359
using TBase = TActorBootstrapped<TKqpBufferWriteActor>;
1360
+ using TTopicTabletTxs = NTopic::TTopicOperationTransactions;
1359
1361
1360
1362
public:
1361
1363
enum class EState {
@@ -1384,6 +1386,7 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
1384
1386
State = EState::WRITING;
1385
1387
Alloc->Release ();
1386
1388
Counters->BufferActorsCount ->Inc ();
1389
+ TxManager->AddTopicsToShards ();
1387
1390
}
1388
1391
1389
1392
void Bootstrap () {
@@ -1404,6 +1407,7 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
1404
1407
hFunc (TEvBufferWrite, Handle);
1405
1408
1406
1409
hFunc (TEvTxProxy::TEvProposeTransactionStatus, Handle);
1410
+ hFunc (TEvPersQueue::TEvProposeTransactionResult, Handle);
1407
1411
hFunc (NKikimr::NEvents::TDataEvents::TEvWriteResult, Handle);
1408
1412
hFunc (TEvPipeCache::TEvDeliveryProblem, Handle);
1409
1413
default :
@@ -1590,6 +1594,7 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
1590
1594
Close ();
1591
1595
Process ();
1592
1596
SendToExternalShards (false );
1597
+ SendToTopics ();
1593
1598
}
1594
1599
1595
1600
void ImmediateCommit () {
@@ -1687,6 +1692,63 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
1687
1692
}
1688
1693
}
1689
1694
1695
+ void SendToTopics () {
1696
+ if (!TxManager->HasTopics ()) {
1697
+ return ;
1698
+ }
1699
+
1700
+ TTopicTabletTxs topicTxs;
1701
+ TxManager->BuildTopicTxs (topicTxs);
1702
+
1703
+ TMaybe<ui64> writeId;
1704
+ if (TxManager->GetTopicOperations ().HasWriteId ()) {
1705
+ writeId = TxManager->GetTopicOperations ().GetWriteId ();
1706
+ }
1707
+
1708
+ for (auto & [tabletId, t] : topicTxs) {
1709
+ auto & transaction = t.tx ;
1710
+ transaction.SetOp (NKikimrPQ::TDataTransaction::Commit);
1711
+
1712
+ const auto prepareSettings = TxManager->GetPrepareTransactionInfo ();
1713
+ if (!prepareSettings.ArbiterColumnShard ) {
1714
+ for (const ui64 sendingShardId : prepareSettings.SendingShards ) {
1715
+ transaction.AddSendingShards (sendingShardId);
1716
+ }
1717
+ for (const ui64 receivingShardId : prepareSettings.ReceivingShards ) {
1718
+ transaction.AddReceivingShards (receivingShardId);
1719
+ }
1720
+ } else {
1721
+ transaction.AddSendingShards (*prepareSettings.ArbiterColumnShard );
1722
+ transaction.AddReceivingShards (*prepareSettings.ArbiterColumnShard );
1723
+ }
1724
+
1725
+ auto ev = std::make_unique<TEvPersQueue::TEvProposeTransactionBuilder>();
1726
+
1727
+ if (t.hasWrite && writeId.Defined ()) {
1728
+ auto * w = transaction.MutableWriteId ();
1729
+ w->SetNodeId (SelfId ().NodeId ());
1730
+ w->SetKeyId (*writeId);
1731
+ }
1732
+ transaction.SetImmediate (false );
1733
+
1734
+ ActorIdToProto (SelfId (), ev->Record .MutableSourceActor ());
1735
+ ev->Record .MutableData ()->Swap (&transaction);
1736
+ ev->Record .SetTxId (*TxId);
1737
+
1738
+ SendTime[tabletId] = TInstant::Now ();
1739
+ auto traceId = BufferWriteActor.GetTraceId ();
1740
+
1741
+ CA_LOG_D (" Preparing KQP transaction on topic tablet: " << tabletId << " , writeId: " << writeId);
1742
+
1743
+ Send (
1744
+ MakePipePerNodeCacheID (false ),
1745
+ new TEvPipeCache::TEvForward (ev.release (), tabletId, /* subscribe */ true ),
1746
+ IEventHandle::FlagTrackDelivery,
1747
+ 0 ,
1748
+ std::move (traceId));
1749
+ }
1750
+ }
1751
+
1690
1752
void SendCommitToCoordinator () {
1691
1753
const auto commitInfo = TxManager->GetCommitInfo ();
1692
1754
@@ -1810,6 +1872,69 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
1810
1872
}
1811
1873
}
1812
1874
1875
+ void Handle (TEvPersQueue::TEvProposeTransactionResult::TPtr& ev) {
1876
+ auto & event = ev->Get ()->Record ;
1877
+ const ui64 tabletId = event.GetOrigin ();
1878
+
1879
+ CA_LOG_D (" Got ProposeTransactionResult" <<
1880
+ " , PQ tablet: " << tabletId <<
1881
+ " , status: " << NKikimrPQ::TEvProposeTransactionResult_EStatus_Name (event.GetStatus ()));
1882
+
1883
+ switch (event.GetStatus ()) {
1884
+ case NKikimrPQ::TEvProposeTransactionResult::PREPARED:
1885
+ ProcessPreparedTopic (ev);
1886
+ return ;
1887
+ case NKikimrPQ::TEvProposeTransactionResult::COMPLETE:
1888
+ ProcessCompletedTopic (ev);
1889
+ return ;
1890
+ case NKikimrPQ::TEvProposeTransactionResult::ABORTED:
1891
+ CA_LOG_E (" Got ABORTED ProposeTransactionResult for PQ."
1892
+ << " ShardID=" << ev->Get ()->Record .GetOrigin () << " ,"
1893
+ << " Sink=" << this ->SelfId () << " ." );
1894
+ ReplyErrorAndDie (
1895
+ TStringBuilder () << " Aborted proposal status for PQ. " ,
1896
+ NYql::NDqProto::StatusIds::ABORTED,
1897
+ {});
1898
+ return ;
1899
+ case NKikimrPQ::TEvProposeTransactionResult::BAD_REQUEST:
1900
+ CA_LOG_E (" Got BAD REQUEST ProposeTransactionResult for PQ."
1901
+ << " ShardID=" << ev->Get ()->Record .GetOrigin () << " ,"
1902
+ << " Sink=" << this ->SelfId () << " ." );
1903
+ ReplyErrorAndDie (
1904
+ TStringBuilder () << " Bad request proposal status for PQ. " ,
1905
+ NYql::NDqProto::StatusIds::BAD_REQUEST,
1906
+ {});
1907
+ return ;
1908
+ case NKikimrPQ::TEvProposeTransactionResult::OVERLOADED:
1909
+ CA_LOG_E (" Got OVERLOADED ProposeTransactionResult for PQ."
1910
+ << " ShardID=" << ev->Get ()->Record .GetOrigin () << " ,"
1911
+ << " Sink=" << this ->SelfId () << " ." );
1912
+ ReplyErrorAndDie (
1913
+ TStringBuilder () << " Overloaded proposal status for PQ. " ,
1914
+ NYql::NDqProto::StatusIds::OVERLOADED,
1915
+ {});
1916
+ return ;
1917
+ case NKikimrPQ::TEvProposeTransactionResult::CANCELLED:
1918
+ CA_LOG_E (" Got CANCELLED ProposeTransactionResult for PQ."
1919
+ << " ShardID=" << ev->Get ()->Record .GetOrigin () << " ,"
1920
+ << " Sink=" << this ->SelfId () << " ." );
1921
+ ReplyErrorAndDie (
1922
+ TStringBuilder () << " Cancelled proposal status for PQ. " ,
1923
+ NYql::NDqProto::StatusIds::CANCELLED,
1924
+ {});
1925
+ return ;
1926
+ default :
1927
+ CA_LOG_E (" Got undefined ProposeTransactionResult for PQ."
1928
+ << " ShardID=" << ev->Get ()->Record .GetOrigin () << " ,"
1929
+ << " Sink=" << this ->SelfId () << " ." );
1930
+ ReplyErrorAndDie (
1931
+ TStringBuilder () << " Undefined proposal status for PQ. " ,
1932
+ NYql::NDqProto::StatusIds::INTERNAL_ERROR,
1933
+ {});
1934
+ return ;
1935
+ }
1936
+ }
1937
+
1813
1938
void Handle (TEvPipeCache::TEvDeliveryProblem::TPtr& ev) {
1814
1939
CA_LOG_W (" TEvDeliveryProblem was received from tablet: " << ev->Get ()->TabletId );
1815
1940
ReplyErrorAndDie (TStringBuilder () << " Failed to deviler message." , NYql::NDqProto::StatusIds::UNAVAILABLE, {});
@@ -1837,7 +1962,7 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
1837
1962
Rollback ();
1838
1963
State = EState::FINISHED;
1839
1964
Send (ExecuterActorId, new TEvKqpBuffer::TEvResult{});
1840
- } else if (TxManager->IsSingleShard () && !TxManager->HasOlapTable () && !WriteInfos.empty ()) {
1965
+ } else if (TxManager->IsSingleShard () && !TxManager->HasOlapTable () && !WriteInfos.empty () && !TxManager-> HasTopics () ) {
1841
1966
TxManager->StartExecute ();
1842
1967
ImmediateCommit ();
1843
1968
} else {
@@ -2016,6 +2141,47 @@ class TKqpBufferWriteActor :public TActorBootstrapped<TKqpBufferWriteActor>, pub
2016
2141
}
2017
2142
}
2018
2143
2144
+ void ProcessPreparedTopic (TEvPersQueue::TEvProposeTransactionResult::TPtr& ev) {
2145
+ if (State != EState::PREPARING) {
2146
+ CA_LOG_D (" Ignored topic prepared event." );
2147
+ return ;
2148
+ }
2149
+ OnMessageReceived (ev->Get ()->Record .GetOrigin ());
2150
+ CA_LOG_D (" Got propose prepared result TxId=" << ev->Get ()->Record .GetTxId ()
2151
+ << " , TabletId=" << ev->Get ()->Record .GetOrigin ()
2152
+ << " , Cookie=" << ev->Cookie );
2153
+
2154
+ const auto & record = ev->Get ()->Record ;
2155
+ IKqpTransactionManager::TPrepareResult preparedInfo;
2156
+ preparedInfo.ShardId = record.GetOrigin ();
2157
+ preparedInfo.MinStep = record.GetMinStep ();
2158
+ preparedInfo.MaxStep = record.GetMaxStep ();
2159
+
2160
+ preparedInfo.Coordinator = 0 ;
2161
+ if (record.DomainCoordinatorsSize ()) {
2162
+ auto domainCoordinators = TCoordinators (TVector<ui64>(record.GetDomainCoordinators ().begin (),
2163
+ record.GetDomainCoordinators ().end ()));
2164
+ preparedInfo.Coordinator = domainCoordinators.Select (*TxId);
2165
+ }
2166
+
2167
+ OnPrepared (std::move (preparedInfo), 0 );
2168
+ }
2169
+
2170
+ void ProcessCompletedTopic (TEvPersQueue::TEvProposeTransactionResult::TPtr& ev) {
2171
+ NKikimrPQ::TEvProposeTransactionResult& event = ev->Get ()->Record ;
2172
+
2173
+ if (State != EState::COMMITTING) {
2174
+ CA_LOG_D (" Ignored completed event." );
2175
+ return ;
2176
+ }
2177
+ OnMessageReceived (event.GetOrigin ());
2178
+ CA_LOG_D (" Got propose completed result" <<
2179
+ " , topic tablet: " << event.GetOrigin () <<
2180
+ " , status: " << NKikimrPQ::TEvProposeTransactionResult_EStatus_Name (event.GetStatus ()));
2181
+
2182
+ OnCommitted (event.GetOrigin (), 0 );
2183
+ }
2184
+
2019
2185
void ProcessWritePreparedShard (NKikimr::NEvents::TDataEvents::TEvWriteResult::TPtr& ev) {
2020
2186
if (State != EState::PREPARING) {
2021
2187
CA_LOG_D (" Ignored write prepared event." );
0 commit comments