#At file:///D:/source/bzr/mysql-6.0-bug-39690/
2702 Chuck Bell 2008-10-08
BUG#39690 Backup logs need to split backup image file into path and filename columns
This patch adds the backup_file_path column to the backup_history log.
The logic has been changed to store the exact path to the backup
image file as calculated in the stream class.
modified:
mysql-test/suite/backup/r/backup_logs.result
mysql-test/suite/backup/t/backup_logs.test
scripts/mysql_system_tables.sql
scripts/mysql_system_tables_fix.sql
sql/backup/logger.h
sql/backup/stream.cc
sql/log.cc
sql/log.h
sql/si_logs.cc
sql/si_logs.h
per-file messages:
mysql-test/suite/backup/r/backup_logs.result
Updated result file with new masks for backup_file_path column.
mysql-test/suite/backup/t/backup_logs.test
Added mask for new column.
scripts/mysql_system_tables.sql
Added column in script to upgrade the table.
scripts/mysql_system_tables_fix.sql
Added column in script to upgrade the table.
sql/backup/logger.h
Added a report method for the backup_file and backup_file_path columns.
Removed the path from the constructor so that the report method can be
used instead.
sql/backup/stream.cc
Added reporting of calculated path.
sql/log.cc
Added saving of the backup_file_path in the history data to the logs (table or file).
sql/log.h
Added new enum for backup_file_path column.
sql/si_logs.cc
Removed saving of backup file from constructor.
Added new SET method to save backup_file and backup_file_path data.
sql/si_logs.h
Added backup_file_path to history data structure.
Added destructor to free memory used to store the path.
Added SET method to set the backup_file and backup_file_path data attributes.
=== modified file 'mysql-test/suite/backup/r/backup_logs.result'
--- a/mysql-test/suite/backup/r/backup_logs.result 2008-10-07 17:15:44 +0000
+++ b/mysql-test/suite/backup/r/backup_logs.result 2008-10-08 14:04:37 +0000
@@ -9,6 +9,7 @@ AND character_set_name LIKE 'utf8'
ORDER BY column_name;
column_name character_set_name
backup_file utf8
+backup_file_path utf8
backup_state utf8
binlog_file utf8
command utf8
@@ -115,6 +116,7 @@ stop_time #
host_or_server_name localhost
username root
backup_file #
+backup_file_path #
user_comment
command BACKUP DATABASE backup_logs to 'backup_logs_orig.bak'
drivers MyISAM, Default, Snapshot
@@ -175,6 +177,7 @@ stop_time #
host_or_server_name localhost
username root
backup_file #
+backup_file_path #
user_comment
command RESTORE FROM 'backup_logs_orig.bak'
drivers MyISAM, Default, Snapshot
=== modified file 'mysql-test/suite/backup/t/backup_logs.test'
--- a/mysql-test/suite/backup/t/backup_logs.test 2008-10-07 17:15:44 +0000
+++ b/mysql-test/suite/backup/t/backup_logs.test 2008-10-08 14:04:37 +0000
@@ -134,7 +134,7 @@ reap;
connection con1;
#Show results
---replace_column 1 # 2 # 3 # 4 # 10 # 11 # 12 # 15 #
+--replace_column 1 # 2 # 3 # 4 # 10 # 11 # 12 # 15 # 16 #
--query_vertical SELECT ob.* FROM mysql.backup_history AS ob JOIN backup_logs.t1_res AS t1 ON ob.backup_id = t1.id;
--replace_column 1 # 3 # 4 #
SELECT obp.* FROM mysql.backup_progress AS obp JOIN backup_logs.t1_res AS t1 ON obp.backup_id = t1.id;
@@ -185,7 +185,7 @@ SET DEBUG_SYNC= 'now WAIT_FOR complete';
DELETE FROM backup_logs.t1_res;
SELECT MAX(backup_id) INTO @bup_id FROM mysql.backup_history WHERE command LIKE "RESTORE FROM%";
INSERT INTO backup_logs.t1_res (id) VALUES (@bup_id);
---replace_column 1 # 2 # 3 # 4 # 10 # 11 # 12 # 15 #
+--replace_column 1 # 2 # 3 # 4 # 10 # 11 # 12 # 15 # 16 #
--query_vertical SELECT ob.* FROM mysql.backup_history AS ob JOIN backup_logs.t1_res AS t1 ON ob.backup_id = t1.id;
--replace_column 1 # 3 # 4 #
SELECT obp.* FROM mysql.backup_progress AS obp JOIN backup_logs.t1_res AS t1 ON obp.backup_id = t1.id;
=== modified file 'scripts/mysql_system_tables.sql'
--- a/scripts/mysql_system_tables.sql 2008-09-03 12:39:48 +0000
+++ b/scripts/mysql_system_tables.sql 2008-10-08 14:04:37 +0000
@@ -82,7 +82,7 @@ DROP PREPARE stmt;
CREATE TABLE IF NOT EXISTS event ( db char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL default '', name char(64) CHARACTER SET utf8 NOT NULL default '', body longblob NOT NULL, definer char(77) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL default '', execute_at DATETIME default NULL, interval_value int(11) default NULL, interval_field ENUM('YEAR','QUARTER','MONTH','DAY','HOUR','MINUTE','WEEK','SECOND','MICROSECOND','YEAR_MONTH','DAY_HOUR','DAY_MINUTE','DAY_SECOND','HOUR_MINUTE','HOUR_SECOND','MINUTE_SECOND','DAY_MICROSECOND','HOUR_MICROSECOND','MINUTE_MICROSECOND','SECOND_MICROSECOND') default NULL, created TIMESTAMP NOT NULL, modified TIMESTAMP NOT NULL, last_executed DATETIME default NULL, starts DATETIME default NULL, ends DATETIME default NULL, status ENUM('ENABLED','DISABLED','SLAVESIDE_DISABLED') NOT NULL default 'ENABLED', on_completion ENUM('DROP','PRESERVE') NOT NULL default 'DROP', sql_mode set('REAL_AS_FLOAT','PIPES_AS_CONCAT','ANSI_QUOTES','IGNORE_SPACE','!
NOT_USED','ONLY_FULL_GROUP_BY','NO_UNSIGNED_SUBTRACTION','NO_DIR_IN_CREATE','POSTGRESQL','ORACLE','MSSQL','DB2','MAXDB','NO_KEY_OPTIONS','NO_TABLE_OPTIONS','NO_FIELD_OPTIONS','MYSQL323','MYSQL40','ANSI','NO_AUTO_VALUE_ON_ZERO','NO_BACKSLASH_ESCAPES','STRICT_TRANS_TABLES','STRICT_ALL_TABLES','NO_ZERO_IN_DATE','NO_ZERO_DATE','INVALID_DATES','ERROR_FOR_DIVISION_BY_ZERO','TRADITIONAL','NO_AUTO_CREATE_USER','HIGH_NOT_PRECEDENCE','NO_ENGINE_SUBSTITUTION','PAD_CHAR_TO_FULL_LENGTH') DEFAULT '' NOT NULL, comment char(64) CHARACTER SET utf8 COLLATE utf8_bin NOT NULL default '', originator int(10) NOT NULL, time_zone char(64) CHARACTER SET latin1 NOT NULL DEFAULT 'SYSTEM', character_set_client char(32) collate utf8_bin, collation_connection char(32) collate utf8_bin, db_collation char(32) collate utf8_bin, body_utf8 longblob, PRIMARY KEY (db, name) ) ENGINE=MyISAM DEFAULT CHARSET=utf8 COMMENT 'Events';
-CREATE TABLE IF NOT EXISTS backup_history ( backup_id BIGINT UNSIGNED NOT NULL COMMENT 'Surrogate key for (near) duplicate entries', process_id INT UNSIGNED NOT NULL COMMENT 'The process id that operation ran as', binlog_pos INT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The recorded binlog position of backup/restore', binlog_file CHAR(64) NOT NULL DEFAULT '' COMMENT 'The recorded binlog filename at time of backup/restore', backup_state ENUM('complete', 'starting', 'validity point', 'running', 'error', 'cancel') NOT NULL COMMENT 'Status of current operation', operation ENUM('backup', 'restore') NOT NULL COMMENT 'Type of operation', error_num INT NOT NULL DEFAULT 0 COMMENT 'The error from this run 0 == none', num_objects INT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The number of objects in the backup', total_bytes BIGINT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The size of the backup repository in bytes', validity_point_time datetime NOT NULL DEFAULT 0 COMMENT 'The time of the validity !
point.', start_time datetime NOT NULL DEFAULT 0 COMMENT 'The date/time of start of operation', stop_time datetime NOT NULL DEFAULT 0 COMMENT 'The date/time of end of operation', host_or_server_name CHAR (30) NOT NULL DEFAULT '' COMMENT 'The server name where operation ran', username CHAR (30) NOT NULL DEFAULT '' COMMENT 'The user name who ran the operation', backup_file CHAR (100) NOT NULL DEFAULT '' COMMENT 'The name of the file', user_comment VARCHAR (200) NOT NULL DEFAULT '' COMMENT 'The comment from user entered at command line', command VARCHAR (512) NOT NULL DEFAULT '' COMMENT 'The command used to issue operation', drivers VARCHAR (100) NOT NULL DEFAULT '' COMMENT 'The name of the storage engines used in the operation') ENGINE=CSV DEFAULT CHARACTER SET utf8;
+CREATE TABLE IF NOT EXISTS backup_history ( backup_id BIGINT UNSIGNED NOT NULL COMMENT 'Surrogate key for (near) duplicate entries', process_id INT UNSIGNED NOT NULL COMMENT 'The process id that operation ran as', binlog_pos INT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The recorded binlog position of backup/restore', binlog_file CHAR(64) NOT NULL DEFAULT '' COMMENT 'The recorded binlog filename at time of backup/restore', backup_state ENUM('complete', 'starting', 'validity point', 'running', 'error', 'cancel') NOT NULL COMMENT 'Status of current operation', operation ENUM('backup', 'restore') NOT NULL COMMENT 'Type of operation', error_num INT NOT NULL DEFAULT 0 COMMENT 'The error from this run 0 == none', num_objects INT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The number of objects in the backup', total_bytes BIGINT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The size of the backup repository in bytes', validity_point_time datetime NOT NULL DEFAULT 0 COMMENT 'The time of the validity !
point.', start_time datetime NOT NULL DEFAULT 0 COMMENT 'The date/time of start of operation', stop_time datetime NOT NULL DEFAULT 0 COMMENT 'The date/time of end of operation', host_or_server_name CHAR (30) NOT NULL DEFAULT '' COMMENT 'The server name where operation ran', username CHAR (30) NOT NULL DEFAULT '' COMMENT 'The user name who ran the operation', backup_file CHAR (100) NOT NULL DEFAULT '' COMMENT 'The name of the file', backup_file_path VARCHAR (512) NOT NULL DEFAULT '' COMMENT 'The full path to the backup image file', user_comment VARCHAR (200) NOT NULL DEFAULT '' COMMENT 'The comment from user entered at command line', command VARCHAR (512) NOT NULL DEFAULT '' COMMENT 'The command used to issue operation', drivers VARCHAR (100) NOT NULL DEFAULT '' COMMENT 'The name of the storage engines used in the operation') ENGINE=CSV DEFAULT CHARACTER SET utf8;
CREATE TABLE IF NOT EXISTS backup_progress ( backup_id BIGINT UNSIGNED NOT NULL COMMENT 'Key for backup_history table entries', object CHAR (30) NOT NULL DEFAULT '' COMMENT 'The object being operated on', start_time datetime NOT NULL DEFAULT 0 COMMENT 'The date/time of start of operation', stop_time datetime NOT NULL DEFAULT 0 COMMENT 'The date/time of end of operation', total_bytes BIGINT NOT NULL DEFAULT 0 COMMENT 'The size of the object in bytes', progress BIGINT UNSIGNED NOT NULL DEFAULT 0 COMMENT 'The number of bytes processed', error_num INT NOT NULL DEFAULT 0 COMMENT 'The error from this run 0 == none', notes CHAR(100) NOT NULL DEFAULT '' COMMENT 'Commentary from the backup engine') ENGINE=CSV DEFAULT CHARACTER SET utf8;
=== modified file 'scripts/mysql_system_tables_fix.sql'
--- a/scripts/mysql_system_tables_fix.sql 2008-08-07 03:05:33 +0000
+++ b/scripts/mysql_system_tables_fix.sql 2008-10-08 14:04:37 +0000
@@ -604,3 +604,5 @@ UPDATE user SET Create_tablespace_priv =
# changes was correct
flush privileges;
+
+ALTER TABLE backup_history ADD COLUMN backup_file_path VARCHAR (512) NOT NULL DEFAULT '' COMMENT 'The full path to the backup image file' AFTER backup_file;
=== modified file 'sql/backup/logger.h'
--- a/sql/backup/logger.h 2008-09-30 07:51:48 +0000
+++ b/sql/backup/logger.h 2008-10-08 14:04:37 +0000
@@ -57,6 +57,7 @@ class Logger
void report_vp_time(time_t, bool);
void report_binlog_pos(const st_bstream_binlog_pos&);
void report_driver(const char *driver);
+ void report_backup_file(char * path);
void report_stats_pre(const Image_info&);
void report_stats_post(const Image_info&);
ulonglong get_op_id() const
@@ -277,6 +278,17 @@ void Logger::report_driver(const char *d
backup_log->add_driver(driver);
}
+/**
+ Report backup file and path.
+*/
+inline
+void Logger::report_backup_file(char *path)
+{
+ DBUG_ASSERT(m_state == RUNNING);
+ DBUG_ASSERT(backup_log);
+ backup_log->backup_file(path);
+}
+
/**
Initialize logger for backup or restore operation.
@@ -300,7 +312,7 @@ int Logger::init(enum_type type, const L
m_type= type;
m_state= READY;
- backup_log = new Backup_log(m_thd, (enum_backup_operation)type, path, query);
+ backup_log = new Backup_log(m_thd, (enum_backup_operation)type, query);
backup_log->state(BUP_STARTING);
DEBUG_SYNC(m_thd, "after_backup_log_init");
return 0;
=== modified file 'sql/backup/stream.cc'
--- a/sql/backup/stream.cc 2008-09-11 11:14:59 +0000
+++ b/sql/backup/stream.cc 2008-10-08 14:04:37 +0000
@@ -195,6 +195,7 @@ Stream::Stream(Logger &log, ::String *ba
:m_flags(flags), m_block_size(0), m_log(log)
{
prepare_path(backupdir, orig_loc);
+ log.report_backup_file(m_path.c_ptr());
bzero(&stream, sizeof(stream));
bzero(&buf, sizeof(buf));
bzero(&mem, sizeof(mem));
=== modified file 'sql/log.cc'
--- a/sql/log.cc 2008-09-29 18:41:59 +0000
+++ b/sql/log.cc 2008-10-08 14:04:37 +0000
@@ -897,6 +897,15 @@ bool Log_to_csv_event_handler::
table->field[ET_OBH_FIELD_BACKUP_FILE]->set_notnull();
}
+ if (history_data->backup_file_path)
+ {
+ if (table->field[ET_OBH_FIELD_BACKUP_FILE_PATH]->store(
+ history_data->backup_file_path,
+ strlen(history_data->backup_file_path), system_charset_info))
+ goto err;
+ table->field[ET_OBH_FIELD_BACKUP_FILE_PATH]->set_notnull();
+ }
+
if (history_data->user_comment)
{
if (table->field[ET_OBH_FIELD_COMMENT]->store(history_data->user_comment,
@@ -3144,7 +3153,7 @@ bool MYSQL_BACKUP_LOG::open(const char *
"\terror_num \tnum_objects \ttotal_bytes "
"\tvalidity_point_time \tstart_time \tstop_time "
"\thost_or_server_name \tusername \tbackup_file "
- "\tuser_comment \tcommand \tdrivers\n",
+ "\tbackup_file_path \tuser_comment \tcommand \tdrivers\n",
sizeof(buff) - len);
else
end= strnmov(buff + len, "\nbackup_id \tobject \tstart_time \tstop_time "
@@ -3339,6 +3348,8 @@ bool MYSQL_BACKUP_LOG::write(THD *thd, s
if (write_str(user))
goto err;
if (write_str(history_data->backup_file))
+ goto err;
+ if (write_str(history_data->backup_file_path))
goto err;
if (write_str(history_data->user_comment))
goto err;
=== modified file 'sql/log.h'
--- a/sql/log.h 2008-08-27 17:30:49 +0000
+++ b/sql/log.h 2008-10-08 14:04:37 +0000
@@ -38,6 +38,7 @@ enum enum_backup_history_log_field
ET_OBH_FIELD_HOST_OR_SERVER,
ET_OBH_FIELD_USERNAME,
ET_OBH_FIELD_BACKUP_FILE,
+ ET_OBH_FIELD_BACKUP_FILE_PATH,
ET_OBH_FIELD_COMMENT,
ET_OBH_FIELD_COMMAND,
ET_OBH_FIELD_DRIVERS,
=== modified file 'sql/si_logs.cc'
--- a/sql/si_logs.cc 2008-09-30 07:51:48 +0000
+++ b/sql/si_logs.cc 2008-10-08 14:04:37 +0000
@@ -28,7 +28,6 @@
*/
Backup_log::Backup_log(THD *thd,
enum_backup_operation type,
- const LEX_STRING path,
const char *query)
{
m_thd= thd;
@@ -38,9 +37,6 @@ Backup_log::Backup_log(THD *thd,
m_op_hist.state= BUP_STARTING;
m_op_hist.operation= type;
- if (path.length > 0)
- m_op_hist.backup_file= path.str;
-
if (strlen(query) > 0)
m_op_hist.command= (char *)query;
@@ -68,6 +64,28 @@ void Backup_log::add_driver(const char *
if (strlen(driver_name) > 0)
str.append(driver_name);
m_op_hist.driver_name.copy(str);
+}
+
+/**
+ Report name of a backup image file and path used in backup/restore.
+
+ This method updates the backup_file and backup_file_path information
+ in the history data.
+
+ @param[IN] char * full_path The full path and file name of the backup file.
+*/
+void Backup_log::backup_file(const char *full_path)
+{
+ String str;
+
+ if (strlen(full_path))
+ {
+ size_t i= 0;
+ size_t j= 0;
+ m_op_hist.backup_file_path= (char *)my_malloc(FN_REFLEN, MYF(MY_WME));
+ j= dirname_part(m_op_hist.backup_file_path, full_path, &i);
+ m_op_hist.backup_file = (char *)(full_path + i);
+ }
}
/**
=== modified file 'sql/si_logs.h'
--- a/sql/si_logs.h 2008-09-30 07:51:48 +0000
+++ b/sql/si_logs.h 2008-10-08 14:04:37 +0000
@@ -48,6 +48,7 @@ struct st_backup_history
int error_num; ///< error number
char *user_comment; ///< user comment from command
char *backup_file; ///< the backup image file
+ char *backup_file_path; ///< the backup image path
char *command; ///< the command used
int binlog_pos; ///< position in the binary log
char *binlog_file; ///< the name of the binary log file
@@ -94,8 +95,12 @@ class Backup_log
public:
Backup_log(THD *thd,
enum_backup_operation type,
- const LEX_STRING path,
const char *query);
+ ~Backup_log ()
+ {
+ if (m_op_hist.backup_file_path)
+ my_free(m_op_hist.backup_file_path, MYF(0));
+ }
/*
Write the backup history data to the backup_history log.
@@ -132,6 +137,7 @@ public:
void stop(time_t when);
void vp_time(time_t when, bool report);
void add_driver(const char* driver);
+ void backup_file(const char *full_path);
private:
st_backup_history m_op_hist; ///< history log information