MariaDB/MySQL備份和恢復(一):mysqldump工具用法詳述


MariaDB/MySQL備份恢復系列:
備份和恢復(一):mysqldump工具用法詳述
備份和恢復(二):導入、導出表數據
備份和恢復(三):xtrabackup用法和原理詳述


1.備份分類

按照是否能夠繼續提供服務,將數據庫備份類型划分為:

  • 熱備份:在線備份,能讀能寫
  • 溫備份:能讀不能寫
  • 冷備份:離線備份

按照備份數據庫對象分類:

  • 物理備份:直接復制數據文件
  • 邏輯備份:將數據導出至文件中,必要時將其還原(也包括備份成sql語句的方式)

按照是否備份整個數據集分為:

  • 完全備份:備份從開始到某段時間的全部數據
  • 差異備份:備份自完全備份以來變化的數據
  • 增量備份:備份自上次增量備份以來變化的數據

分類方式不同,不同分類的備份沒有沖突的關系,它們可以任意組合。

2.備份內容和備份工具

需要備份的內容:文件、二進制日志、事務日志、配置文件、操作系統上和MySQL相關的配置(如sudo,定時任務)。

物理備份和邏輯備份的優缺點:

  • 物理備份:直接復制數據文件,速度較快。
  • 邏輯備份:將數據導出到文本文件中或其他格式的文件中。有MySQL服務進程參與,相比物理備份而言速度較慢;可能丟失浮點數精度;但可以使用文本工具二次處理;可以跨版本和跨數據庫系統進行移植。

備份策略:要考慮安全,也要考慮還原時長

  • 完全備份+增量
  • 完全備份+差異

備份工具:

  • mysqldump:邏輯備份工具。要求mysql服務在線。MyISAM(溫備),InnoDB(熱備)
  • mysqlhotcopy:物理備份工具,溫備份,實際上是冷備。加鎖、flush table並進行cp或scp。即將廢棄的工具
  • cp:冷備
  • lvm快照:幾乎熱備。注意點是:先flush table、lock table、創建快照、釋放鎖、復制數據。因為要先flush table和lock table,這對於MyISAM來說很簡單很容易實現。但對於InnoDB來說,因為事務的原因,鎖表后可能還有緩存中的數據在寫入文件中,所以應該監控緩存中的數據是真的已經完全寫入數據文件中,之后才能進行復制數據。
  • xtrabackup:開源。MyISAM(溫備),InnoDB(熱備),速度較快。

3.mysqldump用法詳述

官方手冊:https://dev.mysql.com/doc/refman/5.7/en/mysqldump.html

mysqldump默認會從配置文件中的mysqldump段讀取選項,配置文件讀取的順序為:

/etc/my.cnf --> /etc/mysql/my.cnf --> /usr/local/mysql/etc/my.cnf --> ~/.my.cnf

3.1 語法選項

mysqldump [OPTIONS] database [tables]
mysqldump [OPTIONS] --databases [OPTIONS] DB1 [DB2 DB3...]
mysqldump [OPTIONS] --all-databases [OPTIONS]

3.1.1 連接選項

-u, --user=name        指定用戶名
-S, --socket=name      指定套接字路徑 
-p, --password[=name]  指定密碼
-P, --port=#           指定端口
-h, --host=name        指定主機名 
-r, --result-file=name
將導出結果保存到指定的文件中,在Linux中等同於覆蓋重定向。在windows中因為回車符\r\n的原因,使用該選項比重定向更好

3.1.2 篩選選項

--all-databases, -A  
指定dump所有數據庫。等價於使用--databases選定所有庫
--databases, -B  
指定需要dump的庫。該選項后的所有內容都被當成數據庫名;在輸出文件中的每個數據庫前會加上建庫語句和use語句
--ignore-table=db_name.tbl_name  
導出時忽略指定數據庫中的指定表,同樣可用於忽略視圖,要忽略多個則多次寫該選項
-d, --no-data       
不導出表數據,可以用在僅導出表結構的情況。
--events, -E  
導出事件調度器
--routines, -R   
導出存儲過程和函數。但不會導出它們的屬性值,若要導出它們的屬性,可以導出mysql.proc表然后reload
--triggers  
導出觸發器,默認已開啟
--tables 
覆蓋--databases選項,導出指定的表。但這樣只能導出一個庫中的表。格式為--tables database_name tab_list
--where='where_condition', -w 'where_condition'  
指定篩選條件並導出表中符合篩選的數據,如--where="user='jim'"

3.1.3 DDL選項

--add-drop-database 
在輸出中的create database語句前加上drop database語句先刪除數據庫
--add-drop-table    
在輸出的create table語句前加上drop table語句先刪除表,默認是已開啟的
--add-drop-trigger  
在輸出中的create trigger語句前加上drop trigger語句先刪除觸發器
-n, --no-create-db   
指定了--databases或者--all-databases選項時默認會加上數據庫創建語句,該選項抑制建庫語句的輸出
-t, --no-create-info 
不在輸出中包含建表語句
--replace            
使用replace代替insert語句

3.1.4 字符集選項

--default-character-set=charset_name 
在導出數據的過程中,指定導出的字符集。很重要,客戶端服務端字符集不同導出時可能亂碼,默認使用utf8
--set-charset 
在導出結果中加上set names charset_name語句。默認啟用。

3.1.5 復制選項

--apply-slave-statements
--delete-master-logs
--dump-slave[=value]
--include-master-host-port
--master-data[=value]  
該選項主要用來建立一個replication,當值為1時,導出文件中記錄change master語句;
當值為2時,change master語句被寫成注釋語句,默認值為空。
該選項自動忽略--lock-tables,當沒有使用--single-transaction時自動啟用--lock-all-tables。

3.1.6 格式化選項

--compact                   
簡化輸出導出的內容,幾乎所有注釋都不會輸出
--complete-insert, -c 在insert語句中加上插入的列信息
--create-options 在導出的建表語句中,加上所有的建表選項
--tab=dir_name, -T dir_name 將每個表的結構定義和數據分別導出到指定目錄下文件名同表名的.sql和txt文件中,其中.txt
文件中的字段分隔符是制表符。要求mysqldump必須和MySQL Server在同一主機,且mysql用
戶對指定的目錄有寫權限,並且連接數據庫的用戶必須有file權限。且指定要dump的表,不能和
--databases或--all-databases一起使用。它的實質是執行select into outfile。
--fields-terminated-by=name 指定輸出文件中的字段分隔符
--fields-enclosed-by=name 指定輸出文件中的字段值的包圍符,如使用引號將字符串包圍起來引用
--fields-optionally-enclosed-by=name 指定輸出文件中可選字段引用符
--fields-escaped-by=name 指定輸出文件中的轉義符
--lines-terminated-by=name 指定輸出文件中的換行符
-Q,
--quote-names 引用表名和列名時使用的標識符,默認使用反引號"`" 

3.1.7 性能選項

--delayed-insert  
對於非事務表,在insert時支持delayed功能,但在MySQL5.6.6開始該選項已經廢棄
--disable-keys, -K  
在insert語句前后加上禁用和啟用索引語句,大量數據插入時該選項很適合。默認開啟
--insert-ignore  
使用insert ignore語句替代insert語句
--quick, -q 
快速導出數據,該選項對於導出大表非常好用。默認導出數據時會一次性檢索表中所有數據並加入
到內存中,而該選項是每次檢索一行並導出一行

3.1.8 加鎖和事務相關選項

--add-locks         
在insert語句前后加上lock tables和unlock tables語句,默認已開啟。
--flush-logs, -F 在開始dump前先flush logs,如果同時使用了--all-databases則依次在每個數據庫dump前flush,
如果同時使用了--lock-all-tables,--master-data或者--single-transaction,則僅flush
一次,等價於使用flush tables with read lock鎖定所有表,這樣可以讓dump和flush在完全精
確的同一時刻執行。
--flush-privileges 在dump完所有數據庫后在數據文件的結尾加上flush privileges語句,在導出的數據涉及mysql庫或
者依賴於mysql庫時都應該使用該選項
--lock-all-tables, -x 為所有表加上一個持續到dump結束的全局讀鎖。該選項在dump階段僅加一次鎖,一鎖鎖永久且鎖所有。
該選項自動禁用--lock-tables和--single-transaction選項
--lock-tables, -l 在dump每個數據庫前依次對該數據庫中所有表加read local鎖(多次加鎖,lock tables...read local),
這樣就允許對myisam表進行並發插入。對於innodb存儲引擎,使用--single-transaction比
--lock-tables更好,因為它不完全鎖定表。因為該選項是分別對數據庫加鎖的,所以只能保證每個數
據庫的一致性而不能保證所有數據庫之間的一致性。該選項主要用於myisam表,如果既有myisam又有
innodb,則只能使用--lock-tables,或者分開dump更好
--single-transaction 該選項在dump前將設置事務隔離級別為repeatable read並發送一個start transaction語句給
服務端。該選項對於導出事務表如innodb表很有用,因為它在發出start transaction后能保證導
出的數據庫的一致性時而不阻塞任何的程序。該選項只能保證innodb表的一致性,無法保證myisam表
的一致性。在使用該選項的時候,一定要保證沒有任何其他連接在使用ALTER TABLE,CREATE TABLE,
DROP TABLE,RENAME TABLE,TRUNCATE TABLE語句,因為一致性讀無法隔離這些語句。
--single-transaction選項和--lock-tables選項互斥,因為lock tables會隱式提交事務。
要導出大的innodb表,該選項結合--quick選項更好
--no-autocommit 在insert語句前后加上SET autocommit = 0,並在需要提交的地方加上COMMIT語句
--order-by-primary 如果表中存在主鍵或者唯一索引,則排序后按序導出。對於myisam表遷移到innobd表時比較有用,但是
這樣會讓事務變得很長很慢

3.2 mysqldump導出示例

3.2.1 簡單備份示例

創建示例數據庫和表。

# 創建第一個數據庫
CREATE DATABASE backuptest;
USE backuptest;
# 創建innodb表
CREATE TABLE `student` (
    `studentid` INT (11) NOT NULL,
    `sname` CHAR (30) NOT NULL,
    `gender` enum ('male', 'female') DEFAULT NULL,
    `birth` date DEFAULT NULL,
    PRIMARY KEY (`studentid`)
) ENGINE = INNODB DEFAULT CHARSET = latin1

INSERT INTO student
VALUES
    (1,'malongshuai','male',curdate()),
    (2,'gaoxiaofang','female',date_add(curdate(), INTERVAL - 2 YEAR)),
    (3,'longshuai','male',date_add(curdate(), INTERVAL - 5 YEAR)),
    (4,'meishaonv','female',date_add(curdate(), INTERVAL - 3 YEAR)),
    (5,'tun\'er','female',date_add(curdate(), INTERVAL - 4 YEAR));

# 創建myisam表,並且字符集設置為UTF8
CREATE TABLE teacher (
    tid INT NOT NULL PRIMARY KEY,
    tname VARCHAR (30),
    gender enum ('male', 'female'),
    classname CHAR (10)
) ENGINE = myisam DEFAULT charset = utf8;

INSERT INTO teacher
VALUES
    (1,'wugui','male','計算機網絡'),
    (2,'woniu','female','C語言'),
    (3,'xiaowowo','female','oracle');

# 創建第二個數據庫
CREATE DATABASE backuptest1;
USE backuptest1;
create table student1 as select * from backuptest.student;
create table teacher1 charset=utf8 engine=myisam as select * from backuptest.teacher;

mysqldump三種備份方式如下:

mysqldump [OPTIONS] database [tables]
mysqldump [OPTIONS] --databases [OPTIONS] DB1 [DB2 DB3...]
mysqldump [OPTIONS] --all-databases [OPTIONS]

備份單個庫,此處備份mysql庫。重定向符號可以在Linux中等價於mysqldump的-r選項,所以下面的語句是等價的。

[root@xuexi ~]# mysqldump -uroot -p123456 -S /mydata/data/mysql.sock mysql >/tmp/mysql.bak
[root@xuexi ~]# mysqldump -uroot -p123456 -S /mydata/data/mysql.sock -r /tmp/mysql1.bak mysql

查看備份文件,會發現dump單個庫的時候不會在輸出文件中記錄建庫語句和use語句

[root@xuexi ~]# less /tmp/mysql.bak 
-- MySQL dump 10.13  Distrib 5.6.35, for linux-glibc2.5 (x86_64)
--
-- Host: localhost    Database: mysql
-- ------------------------------------------------------
-- Server version       5.6.35-log

/*!40101 SET @OLD_CHARACTER_SET_CLIENT=@@CHARACTER_SET_CLIENT */;
/*!40101 SET @OLD_CHARACTER_SET_RESULTS=@@CHARACTER_SET_RESULTS */;
/*!40101 SET @OLD_COLLATION_CONNECTION=@@COLLATION_CONNECTION */;
/*!40101 SET NAMES utf8 */;
/*!40103 SET @OLD_TIME_ZONE=@@TIME_ZONE */;
/*!40103 SET TIME_ZONE='+00:00' */;
/*!40014 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0 */;
/*!40014 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0 */;
/*!40101 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='NO_AUTO_VALUE_ON_ZERO' */;
/*!40111 SET @OLD_SQL_NOTES=@@SQL_NOTES, SQL_NOTES=0 */;

--
-- Table structure for table `columns_priv`
--

DROP TABLE IF EXISTS `columns_priv`;
/*!40101 SET @saved_cs_client     = @@character_set_client */;
/*!40101 SET character_set_client = utf8 */;
......

備份多個庫。

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --databases backuptest backuptest1 >/tmp/mutil_db.bak

備份所有庫。

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --all-databases >/tmp/all_db.bak

備份多個庫或所有庫時,會在dump文件中加入建庫語句和use語句。實際上,只要使用--databases選項,即使只備份一個庫也會加上建庫語句和use語句。

[root@xuexi ~]# grep -C 2 -i 'use' /tmp/mutil_db.bak  
CREATE DATABASE /*!32312 IF NOT EXISTS*/ `backuptest` /*!40100 DEFAULT CHARACTER SET latin1 */;

USE `backuptest`;

--
--
CREATE DATABASE /*!32312 IF NOT EXISTS*/ `backuptest1` /*!40100 DEFAULT CHARACTER SET latin1 */;

USE `backuptest1`;

--

所以使用mysqldump備份的時候,無論何時都建議--databases或者--all-databases選項二選一,這樣就免去了連進數據庫的過程。

3.2.2 使用DDL選項備份示例

DDL選項如下:

--add-drop-database
--add-drop-table   
--add-drop-trigger 
-n, --no-create-db  
-t, --no-create-info
--replace     

--no-create-db將抑制建庫語句,所以不建議使用。

--no-create-info將抑制建表語句。使用和不使用的對比如下:

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --databases backuptest >/tmp/backuptest.bak
mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --no-create-info --databases backuptest >/tmp/backuptest1.bak
vimdiff /tmp/backuptest.bak /tmp/backuptest1.bak

--replace將會把insert語句替換為replace語句。

shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --replace --databases backuptest >/tmp/backuptest2.bak
shell> grep -i 'replace' /tmp/backuptest2.bak                                                                     
REPLACE INTO `student` VALUES (1,'malongshuai','male','2017-03-31'),(2,'gaoxiaofang','female','2015-03-31'),(3,'longshuai','male','2012-03-31'),(4,'meishaonv','female','2014-03-31'),(5,'tun\'er','female','2013-03-31');
REPLACE INTO `teacher` VALUES (1,'wugui','male','計算機網絡'),(2,'woniu','female','C語言'),(3,'xiaowowo','female','oracle');

3.2.3 使用字符集選項示例

dump數據的時候,客戶端和數據庫的字符集不一致的話會進行字符集轉換,轉換的過程是不可逆的,所以有可能會導致亂碼。

例如,插入一個帶有中文字符的記錄到字符集為latin1的表student中。

insert INTO backuptest.`student` VALUES (6,'','male','2017-03-31');

如果提示無法插入,則設置客戶端字符集和連接字符集為latin1,character_set_client、character_set_connection、character_set_results,使用set names latin1即可,它會設置它們3個。

插入成功之后,其他會話連接數據庫查詢將會是亂碼的。dump的時候也是亂碼的,因為dump默認會使用utf8字符集,在latin1轉碼為utf8的過程中出現了亂碼。

shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --databases backuptest >/tmp/backuptest.bak
shell> grep -i 'insert' /tmp/backuptest.bak
INSERT INTO `student` VALUES (1,'malongshuai','male','2017-03-31'),(2,'gaoxiaofang','female','2015-03-31'),(3,'longshuai','male','2012-03-31'),(4,'meishaonv','female','2014-03-31'),(5,'tun\'er','female','2013-03-31'),(6,'马','male','2017-03-31');
INSERT INTO `teacher` VALUES (1,'wugui','male','計算機網絡'),(2,'woniu','female','C語言'),(3,'xiaowowo','female','oracle');

再使用亂碼的文件來恢復的話,肯定是亂碼的結果。

這時可以指定dump時的字符集為latin1來使得dump數據時無需轉換字符集。

shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --default-character-set=latin1 --databases backuptest >/tmp/backuptest.bak
shell> grep -i 'insert' /tmp/backuptest.bak
INSERT INTO `student` VALUES (1,'malongshuai','male','2017-03-31'),(2,'gaoxiaofang','female','2015-03-31'),(3,'longshuai','male','2012-03-31'),(4,'meishaonv','female','2014-03-31'),(5,'tun\'er','female','2013-03-31'),(6,'','male','2017-03-31');

測試完成之后,將新插入的含有中文字符的記錄刪除。

delete from backuptest.student where studentid=6;

3.2.4 使用格式化選項示例

格式化選項如下:

--compact                   
--complete-insert, -c       
--create-options            
--tab=dir_name, -T dir_name 
--fields-terminated-by=name            
--fields-enclosed-by=name              
--fields-optionally-enclosed-by=name   
--fields-escaped-by=name               
--lines-terminated-by=name            
-Q, --quote-names                       

選項--compact可以極大的簡化輸出,讓輸出變得更加簡單明晰。但是卻不安全,因為它不止會簡化注釋語句,還會簡化部分非注釋語句,如insert前后的lock語句。所以該選項僅用來調試使用。

shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --compact --databases backuptest >/tmp/backuptest.bak
shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --databases backuptest >/tmp/backuptest1.bak
shell> vimdiff /tmp/backuptest.bak /tmp/backuptest1.bak

"--complete-insert, -c"選項會在每個insert語句中列出插入列列表,而默認情況下mysqldump備份時是不加的。

shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --databases backuptest >/tmp/backuptest.bak
shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock -c --databases backuptest >/tmp/backuptest1.bak
shell> vimdiff /tmp/backuptest.bak /tmp/backuptest1.bak  

--tab選項是將表的結構定義和數據分開dump,結構定義語句dump到表的同名.sql文件中,數據dump到表的同名.txt文件中。--tab指定這些文件的輸出目錄。但要求mysqldump和MySQL服務器必須在同一台服務器上,且mysql系統用戶對指定的輸出目錄有寫權限,連接數據庫的用戶還需要有file權限。而且該選項不能和--databases或--all-databases一起使用。因為它只能定義表的結構。

一般和該選項一起使用的有:該部分內容見select ... into outfile

--fields-terminated-by=name            
--fields-enclosed-by=name              
--fields-optionally-enclosed-by=name   
--fields-escaped-by=name               
--lines-terminated-by=name  

3.2.5 使用篩選選項示例

--all-databases, -A  
--databases, -B  
--ignore-table=db_name.tbl_name  
-d, --no-data       
--events, -E  
--routines, -R   
--triggers  
--tables 
--where='where_condition', -w 'where_condition'  

篩選數據庫此處不再贅述。

--ignore-table表示忽略數據庫中的某張表不被dump。要忽略多張表的時候多次寫該選項即可。例如忽略backuptest.student和backuptest1.student1。

shell> mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --ignore-table backuptest.student --ignore-table backuptest1.student1 --databases backuptest backuptest1 >/tmp/backuptest.bak
shell> grep -i 'student' /tmp/backuptest.bak |wc -l
0

--no-data表示只dump表的結構,不dump數據。

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --no-data -d backuptest>/tmp/backuptest.bak

grep -i 'insert' /tmp/backuptest.bak | wc -l
0

--tables指定數據庫來導出其中的某些表。只支持指定一個數據庫。該選項會覆蓋--databases選項,所以不會建庫語句和use語句。該選項可以用在分開備份innodb表和myisam表。

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --tables backuptest student teacher>/tmp/backuptest.bak

--where指定某個表的篩選條件,格式為--where="condition"。如果指定了篩選列,則要導出的表中必須要含有該列。另外,顯式指定表時,格式為"db_name tab_list"。以下格式都正確。

# 導出某數據庫下的一個表中的篩選數據
mysqldump -uroot -p123456  -S /mydata/data/mysql.sock --where="gender='male'" backuptest student>/tmp/backuptest.bak
# 導出某數據庫下多個表中的篩選數據
mysqldump -uroot -p123456  -S /mydata/data/mysql.sock --where="gender='male'" backuptest student teacher>/tmp/backuptest.bak
# 導出多個數據庫中的篩選數據
mysqldump -uroot -p123456 -S /mydata/data/mysql.sock --where="gender='male'" --databases backuptest backuptest1>/tmp/backuptest.bak

3.2.6 使用事務選項示例

--add-locks選項是在insert語句前后加上lock tables和unlock tables語句。

--no-autocommit選項是在insert語句前后加上set autocommit=0,並在事務結束的地方加上commit語句。這樣插入數據時只需一次提交,可以大幅提升大量插入時的性能。

--flush-logs, -F

在開始dump前先flush logs,如果同時使用了--all-databases,則依次在每個數據庫dump前flush;如果同時使用了--lock-all-tables,--master-data或者--single-transaction,則僅flush一次,因為這幾個選項是dump前開啟一個長事務或者全局鎖定。等價於使用flush tables with read lock鎖定所有表,這樣可以讓dump和flush在完全精確的同一時刻執行。

--flush-privileges  

在dump完所有數據庫后在數據文件的結尾加上flush privileges語句,在導出的數據涉及mysql數據庫或者依賴於mysql數據庫時都應該使用該選項。

--lock-all-tables, -x 

為所有表加上一個持續到dump結束的全局讀鎖。該選項在dump階段僅加一次鎖,一鎖鎖永久且鎖所有。該選項自動禁用--lock-tables和--single-transaction選項。

--lock-tables, -l 

在dump每個數據庫前依次對該數據庫中所有表加上read local鎖(多次加鎖,lock tables ... read local),這樣就允許對myisam表進行並發插入。對於innodb存儲引擎,使用--single-transaction比--lock-tables更好,因為它不完全需要鎖定表。因為該選項是分別對數據庫加鎖的,所以只能保證每個數據庫之間的一致性而不能保證在所有數據庫之間的一致性。 該選項主要用於myisam表,如果既有myisam又有innodb,則只能使用--lock-tables了,或者分開dump更好。

--single-transaction

該選項在dump前將設置事務隔離級別為repeatable read並發送一個start transaction語句給服務端該選項對於導出事務表如innodb表很有用,因為它在發出start transaction后能保證導出的數據庫的一致性時而不阻塞任何的程序。當使用該選項只能保證innodb表的一致性,對於myisam表是無法保證的。但是在使用該選項的時候,一定要保證沒有任何其他數據庫的連接在使用ALTER TABLE, CREATE TABLE, DROP TABLE, RENAME TABLE, TRUNCATE TABLE語句,因為一致性讀無法隔離這些語句。--single-transaction選項和--lock-tables選項互斥,因為lock tables會隱式提交事務,要導出大的innodb表,該選項結合--quick選項更好。

3.3 mysqldump使用建議

1.從性能考慮:在需要導出大量數據的時候,使用--quick選項可以加速導出,但導入速度不變。如果是innodb表,則可以同時加上--no-autocommit選項,這樣大量數據量導入時將極大提升性能。

2.一致性考慮:對於innodb表,幾乎沒有理由不用--single-transaction選項。對於myisam表,使用--lock-all-tables選項要好於--lock-tables。既有innodb又有myisam表時,可以分開導出,又能保證一致性,還能保證效率。

3.方便管理和維護性考慮:在導出時flush log很有必要。加上--flush-logs選項即可。而且一般要配合--lock-all-tables選項或者--single-transaction選項一起使用,因為同時使用時,只需刷新一次日志即可,並且也能保證一致性。同時,還可以配合--master-data=2,這樣就可以方便地知道二進制日志中備份結束點的位置。

4.字符集考慮:如果有表涉及到了中文數據,在dump時,一定要將dump的字符集設置的和該表的字符集一樣。

5.雜項考慮:備份過程中會產生二進制日志,但是這是沒有必要的。所以在備份前可以關掉,備份完后開啟。set sql_log_bin=0關閉,set sql_log_bin=1開啟。

以下是備份不同存儲引擎類型表的示例:

備份myisam表:需要時加上--default-character-set

set sql_log_bin=0

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock -q --lock-all-tables --flush-logs --master-data=2 --tables backuptest teacher >/tmp/myisam.sql ;

set sql_log_bin=1

備份innodb表:需要時加上--default-character-set

set sql_log_bin=0

mysqldump -uroot -p123456 -S /mydata/data/mysql.sock -q --no-autocommit --flush-logs --single-transaction --master-data=2 --tables backuptest student >/tmp/innodb.sql;

set sql_log_bin=1

3.4 mysqldump + 二進制日志備份

mysqldump可以實現全備份,在mysqldump之后再二進制日志備份就相當於增量備份,這樣就可以實現全備份之后的定時點還原。

假設要備份的是一張innodb表。使用下面的語句:

mysqldump  -uroot -p123456 -S /mydata/data/mysql.sock -q --no-autocommit --flush-logs --single-transaction --master-data=2 --tables backuptest student >/tmp/innodb.sql;

因為dump前會flush二進制日志,所以之后對該表的操作會記錄到新的滾動日志中。然后只需備份新的二進制日志即可。

然后在該表中插入一行記錄。

insert into student select 10,'xiaolonglong','male','2015-01-02';

備份新的二進制日志。

mysqlbinlog mysql-bin.000002 >/tmp/new_binlog.sql

設計剛才備份的表誤操作,如刪除該表。

drop table student;

使用該表的完全備份和二進制日志恢復。因為備份時使用的是--tables選項,所以要恢復需要進入數據庫指定數據庫,然后使用source來加載sql文件。

use backuptest;
source /tmp/innodb.sql;
source /tmp/new_binlog.sql;

3.5 mysqldump工具的評價

mysqldump備份的文件是邏輯SQL語句,總體來說,簡單,便捷,在有些時候遷移數據的時候比較有用。另外,它的功能也很多,例如導出數據,導出表結構等。

但是缺點是恢復速度太慢,因為恢復數據時是通過insert不斷插入記錄的,它的恢復速度遠不及load data infile導入數據。

在備份方式上,mysqldump備份myisam表時因為要加--lock-all-tables,這時要備份的數據庫全部被上鎖,可讀不可寫,所以實現的是溫備。mysqldump備份innodb表時因為要加--single-transaction,會自動將隔離級別設置為repeatable read並開啟一個事務,這時mysqldump將獲取dump執行前一刻的行版本,並處於一個長事務中直到dump結束。所以不影響目標數據庫的使用,可讀也可寫,即實現的是熱備。


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM