Postgresql

pg_repack 減慢 PostgreSQL 複製

  • January 4, 2022

我有一個主 PostgreSQL 9.5 伺服器和一個備用伺服器。對於我使用的複制repmgr(WAL 流)。通常主備之間的延遲<5s:

$ psql -t -c "SELECT extract(epoch from now() - pg_last_xact_replay_timestamp());"
 0.044554

定期pg_repack在 master 上呼叫以優化索引和表。重新打包表會導致 WAL 流發生大量變化並顯著減慢複製速度,因此主備之間的差異可能超過 1 小時。

有沒有辦法減少這種延遲?是否可以以比重新打包更改更高的優​​先級同步新傳入的數據?

我正要問一個類似的問題,但它與流/複製實際數據寫入磁碟的複制流(“物理”/塊相關)有關。隨著vacuum full(reindexes),截斷/恢復,現在pg_repack,表被重寫到磁碟,導致大量數據寫入需要流式傳輸到另一端……

因此,不,我不相信您將能夠進行“優先化”,因為當重建表“交換”到活動表時,主控上的新更新/寫入將進入重建表,而不是舊表,然後副本需要該表“可用”!

我已經養成了殺死複製的習慣,進行主要的數據更改(也許在數據更改之前將其作為“備份”可用),然後重新啟動新的完整 pg_basebackup/replication

希望這有助於解釋您所處的情況以及到目前為止我是如何解決它的:)

也就是說,請閱讀:https ://www.depesz.com/2013/06/21/bloat-removal-by-tuples-moving/

Depesz 解釋了一種機制,該機制幫助他“即時”將數據移動到表的開頭,並且使用類似於以下程式碼的數據始終可用:

with x as (
delete from test where id in (999997,999998,999999) returning *
)
insert into test
   select * from x;

然後分批執行,與 $ vacuum $ 語句一起執行以清理空間。以慢速/託管方法執行此操作,您可以在不落後於副本太遠的情況下進行“重新打包”。

請注意 update/insert/delete 上的觸發器!

WAL是一個順序日誌,所以WAL中的一個segment只有在前面所有的segment都被應用的情況下才能被應用。因此,將某些 WAL 段優先於其他段是沒有邏輯意義的。

當您使用時,pg_repack您正在對數據庫數據進行更改,因此將其寫入 WAL。當您說“這會減慢複製速度”時,我可能會將其細化為“它會延遲複製”,因為所需的複制量而不是減慢速度。

我能看到的唯一解決方案是將 延遲pg_repack到不太關鍵的時間(如果有的話),或者修改優化表和索引的方法以最小化 WAL 寫入量(例如 @Hvisage 所指出的)。

引用自:https://dba.stackexchange.com/questions/162719