我們都知道事務的特性有:
1)原子性(Atomicity)原子性是指事務是一個不可分割的工作機關,事務中的操作要麼都發生,要麼都不發生。
2)一緻性(Consistency)一個事務中,事務前後資料的完整性必須保持一緻。
3)隔離性(Isolation)多個事務,事務的隔離性是指多個使用者并發通路資料庫時, 一個使用者的 事務不能被其它使用者的事務所幹擾,多個并發事務之間資料要互相隔離。
4)持久性(Durability)持久性是指一個事務一旦被送出,它對資料庫中資料的改變 就是永久性的,接下來即使資料庫發生故障也不應該對其有任何影響。
那Tdsql 在執行事務時遇到死鎖時是如何處理的 呢 ,如何保證事務的原子性和資料的一緻性的呢?
首先我們看下面這個場景:

假設t2表的結構為:create table t2(aa int(10) primarykey,bb int(11)) shardkey= aa ;
如果第一個事務等待第二個事務的鎖的時候,第二個事務又發起一個SQL導緻等待第一個事務的鎖的時候,這個時候就會産生死鎖。這個TDSQL會如何處理呢 ?
為此proxy增加分布式死鎖檢測機制,原理如下:
Tdsql 在sql 引擎即proxy增加了死鎖檢測機制,在proxy 将SQL請求發往set之後就會開啟計時,一旦收到SQL請求的響應就會取消計時。如果計時逾時,則網關向後端各個set發送如下sql:
SELECT a.trx_xid, a.trx_mysql_thread_id as thread_id, a.trx_started, a.trx_rows_modified, b.trx_xid as blocking_trx
FROM information_schema.innodb_lock_waits as lock_info JOIN information_schema.innodb_trx as a JOIN information_schema.innodb_trx as b ON lock_info.requesting_trx_id = a.trx_id AND lock_info.blocking_trx_id = b.trx_id AND a.trx_xa_type = 'external' and b.trx_xa_type = 'external';
來檢測是否有死鎖形成,如果判斷有交叉等待的鎖形成死鎖,就會開啟死鎖處理機制,終止其中一個會話,被終止的會話就會進行復原。然後業務就會繼續進行下去。
上面語句中涉及字段解釋如下:
TRX_ID: 事務Id
TRX_STARTED:交易開始時間。
TRX_ROWS_MODIFIED:此事務中已修改和插入的行數。
TRX_MYSQL_THREAD_ID: MySQL線程ID,與show processlist中的ID值相對應
REQUESTING_TRX_ID:請求(阻止)事務的ID。
BLOCKING_TRX_ID: 阻止事務的ID。
是以在tdsql 遇到死鎖時不會長時間進行等待,而是根據死鎖檢測機制進行處理,在快速處理死鎖時同時保證事務的原子性和一緻性。