文章目錄
- 環境
- 癥狀
- 問題原因
- 解決方案
環境
系統平臺:UOS(海光),UOS (飛騰),UOS(鯤鵬),UOS(龍芯),UOS (申威),銀河麒麟svs(X86_64),銀河麒麟(飛騰)svs,銀河麒麟(龍芯)svs,銀河麒麟 (X86_64),銀河麒麟 (飛騰),銀河麒麟 (鯤鵬),銀河麒麟 (海光),銀河麒麟 (龍芯),中科方德 (海光),中科方德 (X86_64),中科方德(海光)SVS,中科方德(兆芯),普華Linux(龍芯),銀河麒麟(龍芯)R系 V4,銀河麒麟(飛騰)U系 V4,中標麒麟 (鯤鵬),中標麒麟 (x86-64) 6
版本:9.0,6.0,5.1,5.6.5,14,13,12,11,10.4,5.6.4,5.6.3,5.6.1,4.5.9,4.5.8,4.5.7,4.5.6
癥狀
HGDB流復制環境,備庫與主庫數據不一致 數據庫報錯日志如下:
2024-05-28 14:17:18.707 CST,,,7820,,665576ee.1e8c,1,,2024-05-28 14:17:18 CST,,0,日志,00000,"在時間點: 0/BA000000 (時間安排6)啟動日志的流操作",,,,,,,,,""
2024-05-28 14:17:18.707 CST,,,7820,,665576ee.1e8c,2,,2024-05-28 14:17:18 CST,,0,致命錯誤,XX000,"無法從WAL流中獲得數據: 錯誤: 所要求的WAL段0000000600000000000000BA已經被刪除",,,,,,,,
問題原因
數據庫備節點所需wal日志已被刪除,導致備節點接收不到相應日志,流復制斷連
解決方案
流復制集群出現主備數據庫因斷檔導致數據不同步的問題,均可使用以下第一種方式解決,此解決方法若是數據量較大的情況下要選擇在夜間業務不繁忙時重做備庫,因為重做過程可能會對資源占用較大,對數據庫運行有一定影響。第二種方法適用于備庫所需wal日志已被刪除,但歸檔還在的情況,優先使用此種方式解決,兩種方案的具體解決步驟如下所示:
一、主節點沒有歸檔的情況
主備斷檔時間較久,備庫需要的wal日志,或者歸檔日志已經被刪除;
此情況只能選擇使用pg_basebackup重做備庫,示例步驟如下:
示例環境
IP | 數據目錄 | |
---|---|---|
主節點 | x.x.2.49 | /data/highgo/data |
備節點 | x.x.2.50 | /data/highgo/data |
- 停掉備節點數據庫
[root@HGDB-458 highgo]# pg_ctl stop
- 重命名備節點data目錄
[root@HGDB-458 highgo]# mv /data/highgo/data /data/highgo/databak
- 備節點使用pg_basebackup重新同步數據目錄
[root@HGDB-458 highgo]# pg_basebackup -h x.x.2.49 -p 5866 -U sysdba -D /data/highgo/data -Fp -P -Xs -R -v
- 創建復制槽
創建復制槽可以確保主從數據庫之間的數據一致性。主數據庫產生的 WAL 日志在從數據庫處理之前不會被刪除,但若出現備節點異常宕機或斷檔情況會導使主節點wal日志累積嚴重會導致磁盤爆滿,需要權衡其優缺點,并根據具體情況來選擇是否使用,具體配置步驟如下:
主節點:
[root@HGDB-458 highgo]# psql highgo sysdba
highgo=# select * from pg_create_physical_replication_slot('node_1');
highgo=# select * from pg_replication_slots; # 檢查是否創建成功
備節點:
修改postgresql.auto.conf配置文件,添加復制槽相關配置:
vim /data/highgo/data/postgresql.auto.conf
## 添加以下參數值
primary_slot_name = 'node_1'
- 啟動備節點數據庫,檢查流復制狀態
[root@HGDB-458 highgo]# pg_ctl start
[root@HGDB-458 highgo]# psql -d highgo -U sysdba
highgo=# select * from pg_stat_replication ;pid | usesysid | usename | application_name | client_addr | client_hostname | client_port | backend_start | backend_xmin | state | sent_lsn | write_lsn | fl
ush_lsn | replay_lsn | write_lag | flush_lag | replay_lag | sync_priority | sync_state | reply_time
------+----------+---------+------------------+--------------+-----------------+-------------+-------------------------------+--------------+-----------+------------+------------+---
---------+------------+-----------------+-----------------+-----------------+---------------+------------+-------------------------------1651 | 9999 | sysdba | walreceiver | x.x.2.50 | | 58026 | 2024-05-28 11:08:15.038853+08 | | streaming | 0/B9000000 | 0/B9000000 | 0/
B9000000 | 0/B9000000 | 00:00:00.101506 | 00:00:00.101506 | 00:00:00.101506 | 0 | async | 2024-05-28 11:08:14.512443+08
(1 行記錄)
二、主節點有歸檔的情況
主備流復制斷檔,由于未配置復制槽,wal已被刪除,查詢數據庫日志,某wal日志文件已被刪除,但在主節點歸檔目錄中查詢到此wal日志文件
此情況可通過拷貝歸檔日志到備節點恢復流復制
具體示例步驟如下:
示例環境:
IP | 數據目錄 | 歸檔目錄 | |
---|---|---|---|
主節點 | x.x.2.49 | /data/highgo/data | /data/highgo/hgdbbak/archive |
備節點 | x.x.2.50 | /data/highgo/data | /data/highgo/hgdbbak/archive |
1、通過數據庫日志查詢備節點所需wal日志# 相關文檔
vim /data/highgo/data/hgdb_log/highgodb_28.csv
## 相關日志如下所示
2024-05-28 14:17:18.707 CST,,,7820,,665576ee.1e8c,1,,2024-05-28 14:17:18 CST,,0,日志,00000,"在時間點: 0/BA000000 (時間安排6)啟動日志的流操作",,,,,,,,,""
2024-05-28 14:17:18.707 CST,,,7820,,665576ee.1e8c,2,,2024-05-28 14:17:18 CST,,0,致命錯誤,XX000,"無法從WAL流中獲得數據: 錯誤: 所要求的WAL段0000000600000000000000BA已經被刪除",,,,,,,,
2、在主節點歸檔目錄中找到查詢出的wal日志
[root@HGDB-458 pg_wal]# cd /data/highgo/hgdbbak/archive
[root@HGDB-458 pg_wal]# ls -l 0000000600000000000000BA
-rw------- 1 root root 16777216 5月 28 13:30 0000000600000000000000BA
3、將此歸檔日志及之后的所有歸檔打包并拷貝到備節點中
[root@HGDB-458 archive]# cd /data/highgo/hgdbbak/archive
[root@HGDB-458 archive]# find . -type f -newermt '2024-05-28 13:30' -exec tar -zcvf hgdb_archive_bak0528.tar.gz {} +
# 將當前目錄下修改時間在 '2024-05-28 13:30' 及之后的所有文件打包為hgdb_archive_bak0528.tar.gz
[root@HGDB-458 archive]# scp hgdb_archive_bak0528.tar.gz root@x.x.2.50:/data/highgo/
# 拷貝到備節點/data/highgo/目錄下,也可以用其他方式
4、恢復wal日志(備節點操作)
解壓歸檔日志到數據目錄pg_wal文件夾下
[root@HGDB-458 archive]# tar -zxvf hgdb_archive_bak0528.tar.gz -C /data/highgo/data/pg_wal/
5、檢查流復制是否恢復
主節點執行
[root@HGDB-458 opt]# psql highgo sysdba
highgo=# select * from pg_stat_replication ;pid | usesysid | usename | application_name | client_addr | client_hostname | client_port | backend_start | backend_xmin | state | sent_lsn | write_lsn | flush_ls
n | replay_lsn | write_lag | flush_lag | replay_lag | sync_priority | sync_state | reply_time
------+----------+---------+------------------+--------------+-----------------+-------------+-------------------------------+--------------+-----------+------------+------------+---------
---+------------+-----------+-----------+------------+---------------+------------+-------------------------------3716 | 9999 | sysdba | walreceiver | x.x.2.50 | | 58918 | 2024-05-28 14:17:24.354824+08 | | streaming | 0/C3000000 | 0/C3000000 | 0/C30000
00 | 0/C3000000 | | | | 0 | async | 2024-05-29 05:22:51.494491+08
(1 行記錄)
# 流復制已恢復正常
6、配置復制槽功能
創建復制槽可以確保主從數據庫之間的數據一致性。主數據庫產生的 WAL 日志在從數據庫處理之前不會被刪除,但若出現備節點異常宕機或斷檔情況會導使主節點wal日志累積嚴重會導致磁盤爆滿,需要權衡其優缺點,并根據具體情況來選擇是否使用,具體配置步驟如下:
主節點:
[root@HGDB-458 highgo]# psql highgo sysdba
highgo=# select * from pg_create_physical_replication_slot('node_1');
highgo=# select * from pg_replication_slots; # 檢查是否創建成功
備節點:
修改postgresql.auto.conf配置文件,添加復制槽相關配置:
vim /data/highgo/data/postgresql.auto.conf
## 添加以下參數值
primary_slot_name = 'node_1'
配置完成后重啟備節點數據庫使修改生效
[root@HGDB-458 highgo]# pg_ctl restart