Skip to content

Commit 3459b44

Browse files
committed
Change: execute DDL only when required to avoid requesting
metadata locks. There is a race condition when executing xtrabackup concurrently in multiple PXC nodes with Page Tracking enabled: a node will issue CREATE DATABASE IF NOT EXISTS... and a second node will hang while trying to apply this in TOI.
1 parent e7872bb commit 3459b44

1 file changed

Lines changed: 61 additions & 30 deletions

File tree

storage/innobase/xtrabackup/src/backup_mysql.cc

Lines changed: 61 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1808,6 +1808,9 @@ bool write_xtrabackup_info(MYSQL *connection) {
18081808
const char *uuid = NULL;
18091809
char *server_version = NULL;
18101810
char *xtrabackup_info_data = NULL;
1811+
char *schema_exists = NULL;
1812+
char *table_exists = NULL;
1813+
char *column_is_changed = NULL;
18111814
int idx;
18121815
bool null = true;
18131816

@@ -1837,37 +1840,62 @@ bool write_xtrabackup_info(MYSQL *connection) {
18371840
uuid = get_backup_uuid(connection);
18381841
server_version = read_mysql_one_value(connection, "SELECT VERSION()");
18391842

1840-
xb_mysql_query(connection, "CREATE DATABASE IF NOT EXISTS PERCONA_SCHEMA",
1841-
false);
1842-
xb_mysql_query(connection,
1843-
"CREATE TABLE IF NOT EXISTS PERCONA_SCHEMA.xtrabackup_history("
1844-
"uuid VARCHAR(40) NOT NULL PRIMARY KEY,"
1845-
"name VARCHAR(255) DEFAULT NULL,"
1846-
"tool_name VARCHAR(255) DEFAULT NULL,"
1847-
"tool_command TEXT DEFAULT NULL,"
1848-
"tool_version VARCHAR(255) DEFAULT NULL,"
1849-
"ibbackup_version VARCHAR(255) DEFAULT NULL,"
1850-
"server_version VARCHAR(255) DEFAULT NULL,"
1851-
"start_time TIMESTAMP NULL DEFAULT NULL,"
1852-
"end_time TIMESTAMP NULL DEFAULT NULL,"
1853-
"lock_time BIGINT UNSIGNED DEFAULT NULL,"
1854-
"binlog_pos TEXT DEFAULT NULL,"
1855-
"innodb_from_lsn BIGINT UNSIGNED DEFAULT NULL,"
1856-
"innodb_to_lsn BIGINT UNSIGNED DEFAULT NULL,"
1857-
"partial ENUM('Y', 'N') DEFAULT NULL,"
1858-
"incremental ENUM('Y', 'N') DEFAULT NULL,"
1859-
"format ENUM('file', 'tar', 'xbstream') DEFAULT NULL,"
1860-
"compact ENUM('Y', 'N') DEFAULT NULL,"
1861-
"compressed ENUM('Y', 'N') DEFAULT NULL,"
1862-
"encrypted ENUM('Y', 'N') DEFAULT NULL"
1863-
") CHARACTER SET utf8 ENGINE=innodb",
1864-
false);
1843+
schema_exists = read_mysql_one_value(connection, "SELECT COUNT(*) "
1844+
"FROM INFORMATION_SCHEMA.SCHEMATA "
1845+
"WHERE SCHEMA_NAME = 'PERCONA_SCHEMA'");
1846+
if (strcmp(schema_exists, "0") == 0) {
1847+
// Only create the schema if it doesn't exist to avoid requesting a metadata lock
1848+
xb_mysql_query(connection, "CREATE DATABASE IF NOT EXISTS PERCONA_SCHEMA",
1849+
false);
1850+
1851+
table_exists = read_mysql_one_value(connection, "SELECT COUNT(*) "
1852+
"FROM INFORMATION_SCHEMA.TABLES "
1853+
"WHERE TABLE_SCHEMA = 'PERCONA_SCHEMA' "
1854+
"AND TABLE_NAME = 'xtrabackup_history'");
1855+
if (strcmp(table_exists, "0") == 0)
1856+
{
1857+
// Only create the table if it doesn't exist to avoid requesting a metadata lock
1858+
xb_mysql_query(connection,
1859+
"CREATE TABLE IF NOT EXISTS PERCONA_SCHEMA.xtrabackup_history("
1860+
"uuid VARCHAR(40) NOT NULL PRIMARY KEY,"
1861+
"name VARCHAR(255) DEFAULT NULL,"
1862+
"tool_name VARCHAR(255) DEFAULT NULL,"
1863+
"tool_command TEXT DEFAULT NULL,"
1864+
"tool_version VARCHAR(255) DEFAULT NULL,"
1865+
"ibbackup_version VARCHAR(255) DEFAULT NULL,"
1866+
"server_version VARCHAR(255) DEFAULT NULL,"
1867+
"start_time TIMESTAMP NULL DEFAULT NULL,"
1868+
"end_time TIMESTAMP NULL DEFAULT NULL,"
1869+
"lock_time BIGINT UNSIGNED DEFAULT NULL,"
1870+
"binlog_pos TEXT DEFAULT NULL,"
1871+
"innodb_from_lsn BIGINT UNSIGNED DEFAULT NULL,"
1872+
"innodb_to_lsn BIGINT UNSIGNED DEFAULT NULL,"
1873+
"partial ENUM('Y', 'N') DEFAULT NULL,"
1874+
"incremental ENUM('Y', 'N') DEFAULT NULL,"
1875+
"format ENUM('file', 'tar', 'xbstream') DEFAULT NULL,"
1876+
"compact ENUM('Y', 'N') DEFAULT NULL,"
1877+
"compressed ENUM('Y', 'N') DEFAULT NULL,"
1878+
"encrypted ENUM('Y', 'N') DEFAULT NULL"
1879+
") CHARACTER SET utf8 ENGINE=innodb",
1880+
false);
1881+
}
1882+
}
18651883

1866-
/* Upgrade from previous versions */
1867-
xb_mysql_query(connection,
1868-
"ALTER TABLE PERCONA_SCHEMA.xtrabackup_history MODIFY COLUMN "
1869-
"binlog_pos TEXT DEFAULT NULL",
1870-
false);
1884+
column_is_changed = read_mysql_one_value(connection, "SELECT COUNT(*) "
1885+
"FROM INFORMATION_SCHEMA.COLUMNS "
1886+
"WHERE TABLE_SCHEMA = 'PERCONA_SCHEMA' "
1887+
"AND TABLE_NAME = 'xtrabackup_history' "
1888+
"AND COLUMN_NAME = 'binlog_pos' "
1889+
"AND DATA_TYPE = 'TEXT'");
1890+
1891+
if (strcmp(column_is_changed, "0") == 0) {
1892+
// Only alter table if it's required to avoid requesting metadata lock
1893+
/* Upgrade from previous versions */
1894+
xb_mysql_query(connection,
1895+
"ALTER TABLE PERCONA_SCHEMA.xtrabackup_history MODIFY COLUMN "
1896+
"binlog_pos TEXT DEFAULT NULL",
1897+
false);
1898+
}
18711899

18721900
stmt = mysql_stmt_init(connection);
18731901

@@ -2012,6 +2040,9 @@ bool write_xtrabackup_info(MYSQL *connection) {
20122040

20132041
free(xtrabackup_info_data);
20142042
free(server_version);
2043+
free(schema_exists);
2044+
free(table_exists);
2045+
free(column_is_changed);
20152046

20162047
return (true);
20172048
}

0 commit comments

Comments
 (0)