mysqlbinlog基于datetime和position的恢复

最近项目上线,因为测试的时候没有测试到,结果生产环境下多跑了50多条update SQL state,所以mysql实例需要恢复到update以前的状态,因为不知道怎么查看mysql的ibdata1二进制日志中的undo记录,所以只好使用mysqlbinlog工具进行全库恢复到某个时间点,以下是我在虚拟环境下模拟的场景,生产环境模仿请慎重:


show master logs;--显示当前服务器中的所有二进制日志文件
--show binary logs;
flush logs;--生成新的二进制文件
show master logs;
select database();
show databases;
drop database if exists xxx;--将库删除
create database xxx default character set utf8 collate utf8_general_ci;--创建新库
show databases;
use xxx;
select database();
source /home/mysql/infiles/xxx-20141208-040001.sql--使用全库备份恢复
show master logs;
show master status\G--显示最新的二进制日志和最近的position
select now();--2014-12-09 21:48:48/Linux OS: date--显示当前恢复好的时间节点
查找初始位置
show binlog events in 'mysql-bin.000027' limit 10\G--查看新的二进制日志的初始节点和状态
--show binlog events in 'mysql-bin.000027' from 4 limit 10,50\G
###############################################################################
*************************** 1. row ***************************
   Log_name: mysql-bin.000027
        Pos: 4
 Event_type: Format_desc
  Server_id: 2
End_log_pos: 107
       Info: Server ver: 5.5.38-r5436-log, Binlog ver: 4
*************************** 2. row ***************************
   Log_name: mysql-bin.000027
        Pos: 107
 Event_type: Query
  Server_id: 2
End_log_pos: 196
       Info: drop database if exists xxx
*************************** 3. row ***************************
   Log_name: mysql-bin.000027
        Pos: 196
 Event_type: Query
  Server_id: 2
End_log_pos: 328
       Info: create database xxx default character set utf8 collate utf8_general_ci
*************************** 4. row ***************************
   Log_name: mysql-bin.000027
        Pos: 328
 Event_type: Query
  Server_id: 2
End_log_pos: 446
       Info: use `xxx`; DROP TABLE IF EXISTS `account` /* generated by server */
###############################################################################
查找需要回复位置
select now();--2014-12-09 21:59:48--查看执行正确SQL之后的时间点
show binlog events in 'mysql-bin.000031' from 61687468 limit 50\G--查找执行正确SQL之后的position
show binlog events in 'mysql-bin.000031' from 120069891 limit 50\G
###############################################################################
*************************** 1. row ***************************
   Log_name: mysql-bin.000027
        Pos: 120069891
 Event_type: Delete_rows
  Server_id: 2
End_log_pos: 120069997
       Info: table_id: 191 flags: STMT_END_F
*************************** 2. row ***************************
   Log_name: mysql-bin.000027
        Pos: 120069997
 Event_type: Xid
  Server_id: 2
End_log_pos: 120070024
       Info: COMMIT /* xid=1398 */
*************************** 3. row ***************************
   Log_name: mysql-bin.000027
        Pos: 120070024
 Event_type: Query
  Server_id: 2
End_log_pos: 120070091
       Info: BEGIN
*************************** 4. row ***************************
   Log_name: mysql-bin.000027
        Pos: 120070091
 Event_type: Table_map
  Server_id: 2
End_log_pos: 120070164
       Info: table_id: 192 (xxx.modular)
*************************** 5. row ***************************
   Log_name: mysql-bin.000027
        Pos: 120070164
 Event_type: Update_rows
  Server_id: 2
End_log_pos: 120071024
       Info: table_id: 192

###############################################################################    
--通过以上的日志,可以知道删除操作Delete_rows的开始pos在“120069891”,结束pos在“120070024”,也就是COMMIT处的pos,接下来是
--更新表xxx.modular的记录操作,BEGIN位置是“120070024”,第一条Update_rows位置在“120070164”,最后查看更新操作的结束位置

show binlog events in 'mysql-bin.000027' from 121784504 limit 50\G--查看update结束时的节点
*************************** 1. row ***************************
   Log_name: mysql-bin.000027
        Pos: 121784504
 Event_type: Table_map
  Server_id: 2
End_log_pos: 121784576
       Info: table_id: 194 (wgj.carousel_diagram)
*************************** 2. row ***************************
   Log_name: mysql-bin.000027
        Pos: 121784576
 Event_type: Update_rows
  Server_id: 2
End_log_pos: 121785439
       Info: table_id: 194
*************************** 3. row ***************************
   Log_name: mysql-bin.000027
        Pos: 121785439
 Event_type: Update_rows
  Server_id: 2
End_log_pos: 121786302
       Info: table_id: 194
*************************** 4. row ***************************
   Log_name: mysql-bin.000027
        Pos: 121786302
 Event_type: Update_rows
  Server_id: 2
End_log_pos: 121787117
       Info: table_id: 194
*************************** 5. row ***************************
   Log_name: mysql-bin.000027
        Pos: 121787117
 Event_type: Update_rows
  Server_id: 2
End_log_pos: 121787737
       Info: table_id: 194 flags: STMT_END_F
*************************** 6. row ***************************
   Log_name: mysql-bin.000027
        Pos: 121787737
 Event_type: Xid
  Server_id: 2
End_log_pos: 121787764
       Info: COMMIT /* xid=1449 */
       
--通过以上的日志,可以知道操作Update_rows的COMMIT结束位置在“121787764”,所以二进制日志“mysql-bin.000027”需要执行的是从pos
“4”---“120070024”,而需要取消执行的是从pos“120070024”---“121787764”,即需要恢复的更新操作。

或者通过OS导出从什么时候开始至什么时候结束的二进制日志
mysqlbinlog --no-defaults --start-datetime='2014-12-09 14:30:00' --stop-datetime='2014-12-09 15:30:00' /opt/mysql/binlogs/mysql-bin.000027 > /home/mysql/infiles/xxx20141209_1430_1530.sql
然后导出使用notepad++打开查看
BEGIN
/*!*/;
# at 120069813
# at 120069891
#141209 14:33:48 server id 2  end_log_pos 120069891     Table_map: `xxx`.`member_enactment` mapped to number 191
#141209 14:33:48 server id 2  end_log_pos 120069997     Delete_rows: table id 191 flags: STMT_END_F

BINLOG '
zJeGVBMCAAAATgAAAAMfKAcAAL8AAAAAAAEAA3dnagAQbWVtYmVyX2VuYWN0bWVudAANCAgPDw8P
DwMD/AMMDAvAAAADMAAwABgABP4D
zJeGVBkCAAAAagAAAG0fKAcAAL8AAAAAAAEADf//COKhAAAAAAAAANwAAAAAAAAACeS8muWRmOWN
oQcjZmZmZmZmByNmZmZmZmYDQlNEAQAAAP//AAABAAAAoNcmbFESAACg1yZsURIAAA==
'/*!*/;
# at 120069997
#141209 14:33:48 server id 2  end_log_pos 120070024     Xid = 1398
COMMIT/*!*/;
# at 120070024
#141209 14:34:16 server id 2  end_log_pos 120070091     Query    thread_id=5    exec_time=0    error_code=0
SET TIMESTAMP=1418106856/*!*/;
BEGIN
/*!*/;
# at 120070091
        |
        |
        |
# at 120157030
#141209 14:34:16 server id 2  end_log_pos 120070164     Table_map: `xxx`.`modular` mapped to number 192
#141209 14:34:16 server id 2  end_log_pos 120071024     Update_rows: table id 192

--查看二进制日志,找出删除操作Delete_rows的开始pos在“120069891”,结束pos在“120070024”,也就是COMMIT处的pos,接下来是
--更新表xxx.modular的记录操作,BEGIN位置是“120070091”,第一条Update_rows位置在“120070164”,最后查看更新操作的结束位置

# at 121787737
#141209 14:34:19 server id 2  end_log_pos 121787764     Xid = 1449
COMMIT/*!*/;
DELIMITER ;
# End of log file
ROLLBACK /* added by mysqlbinlog */;
/*!50003 SET COMPLETION_TYPE=@OLD_COMPLETION_TYPE*/;
/*!50530 SET @@SESSION.PSEUDO_SLAVE_MODE=0*/;

--通过以上的日志,可以知道操作Update_rows的COMMIT结束位置在“121787764”,所以二进制日志“mysql-bin.000027”需要执行的是从pos
“4”---“120070024”,而需要取消执行的是从pos“120070024”---“121787764”,即跳过这些更新操作,然后直接执行pos“121787764”之后的
二进制日志至最新位置

以下是需要执行数据库恢复的语句:
1、通过position进行恢复
mysqlbinlog --no-defaults --stop-position='120070024' /opt/mysql/binlogs/mysql-bin.000027 | mysql -h127.0.0.1 -uroot -P3306 -p        --全库恢复到正确的SQL执行点
mysqlbinlog --no-defaults --start-position='121787764' /opt/mysql/binlogs/mysql-bin.000027 | mysql -h127.0.0.1 -uroot -P3306 -p        --跳过错误的update语句执行后续的SQL操作
2、通过datetime进行恢复
mysqlbinlog --no-defaults --stop-datetime='2014-12-09 14:34:16' /opt/mysql/binlogs/mysql-bin.000027 | mysql -h127.0.0.1 -uroot -P3306 -p
mysqlbinlog --no-defaults --start-datetime='2014-12-09 14:34:19' /opt/mysql/binlogs/mysql-bin.000027 | mysql -h127.0.0.1 -uroot -P3306 -p


你可能感兴趣的:(mysql,mysqlbinlog备份恢复)