Replication這高可用技術,從SQL2005來幾乎沒有多大改變(參考自己以前寫的文章),
交易複寫我個人也很常用,不過,我對雙向複寫就很感冒了,因為以前我有一陣子時間,
每天上班都要花不少時間處理雙向replication問題,
這篇來看看搭配In-Memory OLTP有那些注意事項。
當天SQL PASS分享結束後,有幾位和我一樣待在相同產業的朋友問我複寫是否可以搭配In-Memory OLTP技術,
當時因為時間關係,我只有簡單說明幾點實務上使用的經驗,所以我用這篇來整理一下。
目前限制
只支援快照和交易發行集的訂閱者的資料表(不含點對點異動複寫)。
In-memory table無法發行和散發。
訂閱端可以複寫至In-Memory table,我覺得採取這樣的設計有以下好處
No latching
No locking
No blocking
Improve excessive logging
上訴這四點都是In-Memory table的優勢,我也都在SQL PASS說明實務上的效能改善幅度,但你也要注意我提到In-Memory所帶來的副作用。
Note:壓縮、索引、snapshot isolation、reinitialized。
設定注意事項
發行項要啟用memory optimized和convert clustered index to nonclustered
(因為memory table目前無法真正完全支援clustered index,而且subsecriber的DDL會失敗)
請選擇drop existing object and create a new one(truncate table並不支援),
雖然truncate table比較好,因為重新初始化後,不需要重新在搞一次所有索引及壓縮設定。
訂閱注意事項
啟用In-memory subscription
我簡單測試訂閱端使用In-Memory OLTP技術
訂閱端我有一條session會無止境執行該table的full scan
declare @max int=0
while (1=1)
begin
select @max=count(*) from testDatetime
end
發行端我先insert 一百萬後delete
insert into testDatetime with(tablock)
select top 100000 sdatetime,edatetime,sdate,content
from testDatetime_Mem
delete testDatetime
發行端執行完成後,大約不到3秒,訂閱端就完成同步,
但請別忘記我還有一條session無止盡的full scan該資料表,
這表示,訂閱端可說沒有locking,latching和blocking影響所造成的latency。
用下面scripts確認一下latency
USE distribution
go
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
SELECT ma2.publisher_db,
mh1.delivery_latency / ( 1000 * 60 ) AS delivery_latency_Minutes,
mh1.agent_id ,
mh1.time,
CAST(mh1.comments AS XML) AS comments,
CASE mh1.runstatus
WHEN 1 THEN 'Start'
WHEN 2 THEN 'Succeed.'
WHEN 3 THEN 'In progress.'
WHEN 4 THEN 'Idle.'
WHEN 5 THEN 'Retry.'
WHEN 6 THEN 'Fail'
END AS Status,
mh1.duration,
mh1.xact_seqno,
mh1.delivered_transactions,
mh1.delivered_commands,
mh1.average_commands,
mh1.delivery_time,
mh1.delivery_rate,
ma2.name as jobname
FROM mslogreader_history mh1
JOIN (
SELECT mh1.agent_id, MAX(mh1.time) as maxtime
FROM mslogreader_history mh1
JOIN MSlogreader_agents ma on ma.id = mh1.agent_id
GROUP BY mh1.agent_id) AS mh2 ON mh1.agent_id = mh2.agent_id and mh1.time = mh2.maxtime
JOIN MSlogreader_agents ma2 on ma2.id = mh2.agent_id
ORDER BY mh1.delivery_latency desc
個人搭配In-Memory OLTP實務考量 for SQL2016 SP1
DML目前只能選擇drop and create。
注意RTO(當你要restore subscriber database)。
不複寫nonclustered index,訂閱端手動處理索引(無法複寫索引壓縮)。
訂閱端有索引限制問題。
訂閱端手動建立SP來處理所有交易,當然有些人可能會選擇複寫sp序列化到訂閱端執行。
Out of Memory issue
Batch send failed
There is insufficient system memory to run this query. (Source: MSSQLServer, Error number: 701)
如果訂閱端還有相關process查詢old row versions,這就表示需要更多ram來保留(long row chain issue)。
Out of disk space issue
The transaction log for database XXX is full due to 'XTP_CHECKPOINT'.
Could not write a checkpoint record in database XXX because the log is out of space.
硬碟空間(ldf,hkckt file group)也成長快速,我們在壓測階段就遇到不少這錯誤。
Select db_name(database_id) as DatabaseName, * from sys.dm_exec_requests
where command = 'XTP_OFFLINE_CKPT'
Writelog waittype
如我這篇Let's clear the relationship Recovery model and In-Memory Table所說,
所有DML操作都將完整logged,這表示你可能會遇到嚴重的writelog latency,
MS有提供使用NVDIMM作為persistent log buffer並採取DAX模式,
降低transaction commit times (latency)。
最後,實務上我覺得複寫+In-Memory OLTP影響DB架構不小,
目前因為支援度沒那麼完整,但我又為了要大幅提高交易效能,
所以有很多細節需要人工介入調整,導致訂閱端的DB和其他DB架構及部屬方式都有些許差異,
老實說,這真的讓我.....很不方便。
參考
Transactional Articles - Specify How Changes Are Propagated
Replication to Memory-Optimized Table Subscribers
[SQL SERVER][HA]建置交易式複寫(2)-遠端散發者
How It Works (It Just Runs Faster): Non-Volatile Memory SQL Server Tail Of Log Caching on NVDIMM
Log not truncating due to xpt_checkpoint
Troubleshooting transactional replication latency issues in SQL Server
Monitor SQL Replication Log Reader Agent Latency
Publishing Stored Procedure Execution in Transactional Replication