1. 程式人生 > >MySQL備份工具XtraBackup的使用

MySQL備份工具XtraBackup的使用

xtrabackup

MySQL備份工具XtraBackup的使用

xtrabackup簡介

Xtrabackup是由percona提供的mysql數據庫備份工具,據官方介紹,這也是世界上惟一一款開源的能夠對innodb和xtradb數據庫進行熱備的工具。特點:

(1)備份過程快速、可靠;

(2)備份過程不會打斷正在執行的事務;

(3)能夠基於壓縮等功能節約磁盤空間和流量;

(4)自動實現備份檢驗;

(5)還原速度快;

官方下載地址:地址,你可以通過此鏈接下載最新版。

#wget https://www.percona.com/downloads/XtraBackup/Percona-XtraBackup-2.4.8/binary/redhat/7/x86_64/percona-xtrabackup-24-2.4.8-1.el7.x86_64.rpm

# yum install ./percona-xtrabackup-24-2.4.8-1.el7.x86_64.rpm 使用yum的本地安裝方式解決其依賴關系

xtrabackup包含兩個主要的工具,即xtrabackup和innobackupex,二者區別如下:

(1)xtrabackup只能備份innodb和xtradb兩種引擎的表,而不能備份myisam引擎的表;

(2)innobackupex是一個封裝了xtrabackup的Perl腳本,支持同時備份innodb和myisam,但在對myisam備份時需要加一個全局的讀鎖。還有就是myisam不支持增量備份。

權衡兩者區別,建議使用innobackupex工具進行備份。

備份恢復過程

全量備份

其備份過程如下圖所示(該圖來源於網絡):

技術分享圖片

備份開始時首先會開啟一個後臺檢測進程,實時檢測mysql redo的變化,一旦發現redo中有新的日誌寫入,立刻將日誌記入後臺日誌文件xtrabackup_log中。之後復制innodb的數據文件和系統表空間文件ibdata1,待復制結束後,執行flush tables with read lock操作,復制.frm,MYI,MYD,等文件(執行flush tableswith read lock的目的是為了防止數據表發生DDL操作,並且在這一時刻獲得binlog的位置)最後會發出unlock tables,把表設置為可讀可寫狀態,最終停止xtrabackup_log。

全備恢復

這一階段會啟動xtrabackup內嵌的innodb實例,回放xtrabackup日誌xtrabackup_log,將提交的事務信息變更應用到innodb數據/表空間,同時回滾未提交的事務(這一過程類似innodb的實例恢復)。恢復過程如下圖:

技術分享圖片

增量備份

innobackupex增量備份過程中的"增量"處理,其實主要是相對innodb而言,對myisam和其他存儲引擎而言,它仍然是全拷貝(全備份)。

"增量"備份的過程主要是通過拷貝innodb中有變更的"頁"(這些變更的數據頁指的是"頁"的LSN大於xtrabackup_checkpoints中給定的LSN)。增量備份是基於全備的,第一次增備的數據必須要基於上一次的全備,之後的每次增備都是基於上一次的增備,最終達到一致性的增備。增量備份的過程如下,和全備的過程很類似,區別僅在第2步。

技術分享圖片

增備恢復

和全備恢復類似,也需要兩步,一是數據文件的恢復,如下第一幅圖,這裏的數據來源由3部分組成:全備份,增量備份和xtrabackup log。二是對未提交事務的回滾,如下第二幅圖所示:

技術分享圖片

技術分享圖片

XtraBackup使用示例

創建備份用戶

如果要使用一個最小權限的用戶進行備份,則可基於如下命令創建此類用戶:

MariaDB [(none)]> CREATE USER 'bkpuser'@'localhost' IDENTIFIED BY 'bkppass';

MariaDB [(none)]> GRANT RELOAD,PROCESS,LOCK TABLES, REPLICATION CLIENT ON *.* TO 'bkpuser'@'localhost';

MariaDB [(none)]> FLUSH PRIVILEGES;

#創建一個測試數據庫並添加內容

[root@node1 ~]# mysql -p <test.sql

test.sql腳本如下:

[root@node1 ~]# cat test.sql

create database zachary;

create table zachary.test(

id int primary key,

name varchar(20));

insert into zachary.test(id,name) values(1,'yangzhiheng');

創建一個備份目錄

[root@node1 ~]# mkdir /backup

創建一個全量備份:

[root@node1 ~]# innobackupex --user=bkpuser --password=bkppass /backup

技術分享圖片

出現上圖字樣表示備份完成。使用innobakupex備份時,其會調用xtrabackup備份所有的InnoDB表,復制所有關於表結構定義的相關文件(.frm)、以及MyISAM、MERGE、CSV和ARCHIVE表的相關文件,同時還會備份觸發器和數據庫配置信息相關的文件。這些文件會被保存至備份目錄下一個以當前時間戳時間的目錄中。

在備份的同時,innobackupex還會在備份目錄中創建如下文件:

(1)xtrabackup_checkpoints 備份類型(如完全或增量)、備份狀態(如是否已經為prepared狀態)和LSN(日誌序列號)範圍信息;

每個InnoDB頁(通常為16k大小)都會包含一個日誌序列號,即LSN。LSN是整個數據庫系統的系統版本號,每個頁面相關的LSN能夠表明此頁面最近是如何發生改變的。

(2)xtrabackup_binlog_info mysql服務器當前正在使用的二進制日誌文件及至備份這一刻為止二進制日誌事件的位置。

(3)xtrabackup_binlog_pos_innodb 二進制日誌文件及用於InnoDB或XtraDB表的二進制日誌文件的當前position。

(4)xtrabackup_binary 備份中用到的xtrabackup的可執行文件;

(5)backup-my.cnf 備份命令用到的配置選項信息;

在使用innobackupex進行備份時,還可以使用--no-timestamp選項來阻止命令自動創建一個以時間命名的目錄;如此一來,innobackupex命令將會創建一個BACKUP-DIR目錄來存儲備份數據。

Prepare一個完全備份

一般情況下,在備份完成後,數據尚且不能用於恢復操作,因為備份的數據中可能會包含尚未提交的事務或已經提交但尚未同步至數據文件中的事務。因此,此時數據文件仍處理不一致狀態。“準備”的主要作用正是通過回滾未提交的事務及同步已經提交的事務至數據文件也使得數據文件處於一致性狀態。

使用—apply-log選項可以實現上述功能,如下所示:

[root@node1 ~]# innobackupex --apply-log /backup/2017-11-27_04-40-55

技術分享圖片

當出現complete OK字樣表示prepare完成。

從一個全量備份中恢復數據

註意:恢復時不用啟動MySQL,其數據目錄為空目錄

innobackupex命令的--copy-back選項用於執行恢復操作,其通過復制所有數據相關的文件至mysql服務器DATADIR目錄中來執行恢復過程。innobackupex通過backup-my.cnf來獲取DATADIR目錄的相關信息。

為了實驗效果更加明顯,我把該備份恢復至另一臺服務器。

[root@node1 ~]# scp -r /backup/2017-11-27_04-40-55 node3:

[root@node3 ~]# yum install mariadb-server

[root@node3 ~]# rm -rf /var/lib/mysql/*

[root@node3 ~]# innobackupex --copy-back 2017-11-27_04-40-55/

技術分享圖片

請確保如上信息的最行一行出現“innobackupex: completed OK!”。

當數據恢復至DATADIR目錄以後,還需要確保所有數據文件的屬主和屬組均為正確的用戶,如mysql,否則,在啟動mysqld之前還需要事先修改數據文件的屬主和屬組。如:

[root@node3 ~]# chown -R mysql.mysql /var/lib/mysql/*

啟動服務,驗證數據是否恢復:

[root@node3 ~]# systemctl start mariadb

[root@node3 ~]# mysql –p

MariaDB [(none)]> show databases;

+--------------------+

| Database |

+--------------------+

| information_schema |

| mysql |

| performance_schema |

| zachary |

+--------------------+

4 rows in set (0.02 sec)

MariaDB [(none)]> select * from zachary.test;

+----+-------------+

| id | name |

+----+-------------+

| 1 | yangzhiheng |

+----+-------------+

1 row in set (0.01 sec)

數據已恢復

使用XtraBackup進行增量備份

每個InnoDB的頁面都會包含一個LSN信息,每當相關的數據發生改變,相關的頁面的LSN就會自動增長。這正是InnoDB表可以進行增量備份的基礎,即innobackupex通過備份上次完全備份之後發生改變的頁面來實現。

準備一個數據變化

[root@node1 ~]# mysql -p < test2.sql

[root@node1 ~]# cat test2.sql

insert into zachary.test(id,name) values(2,'zachary');

insert into zachary.test(id,name) values(3,'tom');

insert into zachary.test(id,name) values(4,'jarry');

備份:

[root@node1 ~]# innobackupex --user=bkpuser --password=bkppass --incremental /backup --incremental-basedir=/backup/2017-11-27_04-40-55/

技術分享圖片

其中,--incremental-basedir參數指的是完全備份所在的目錄,此命令執行結束後,innobackupex命令會在/backup目錄中創建一個新的以時間命名的目錄以存放所有的增量備份數據。另外,在執行過增量備份之後再一次進行增量備份時,其--incremental-basedir應該指向上一次的增量備份所在的目錄。

需要註意的是,前文已講述過,增量備份僅能應用於InnoDB或XtraDB表,對於MyISAM表而言,執行增量備份時其實進行的是完全備份。

Prepare一個增量備份

“準備”(prepare)增量備份與整理完全備份有著一些不同,尤其要註意的是:

(1)需要在每個備份(包括完全和各個增量備份)上,將已經提交的事務進行“重放”。“重放”之後,所有的備份數據將合並到完全備份上。

(2)基於所有的備份將未提交的事務進行“回滾”。

於是,操作就變成了:

[root@node1 ~]# innobackupex --apply-log --redo-only /backup/2017-11-27_04-40-55/

接著執行:

[root@node1 ~]# innobackupex --apply-log --redo-only /backup/2017-11-27_04-40-55/ --incremental-dir=/backup/2017-11-27_05-23-52

如果後面有其他增量的話,可以按時間順序執行其他增量操作

# innobackupex --apply-log --redo-only BASE-DIR --incremental-dir=INCREMENTAL-DIR-2

其中BASE-DIR指的是完全備份所在的目錄,而INCREMENTAL-DIR-1指的是第一次增量備份的目錄,INCREMENTAL-DIR-2指的是第二次增量備份的目錄,其它依次類推,即如果有多次增量備份,每一次都要執行如上操作

Prepare之後按照之前全量備份恢復所使用的操作來進行恢復,這裏不再詳述。

本篇文章還未寫完,後期會補上。


MySQL備份工具XtraBackup的使用