PT-2340 - Support MySQL 8.4

- Added test for replica lag check for pt-archiver
- Re-added deprecated slave- options
- Added tests for deprecation warnings and for legacy options for pt-archiver
- Removed practically not supported options --replica-user and --replica-password from pt-archiver, pt-kill, pt-query-digest
- Added legacy source/replica options (master/slave) variants and tests for pt-heartbeat, pt-online-schema-change, pt-replica-find, pt-replica-restart, pt-table-checksum, pt-table-sync
- Updated modules after lib/MasterSlave.pm change
This commit is contained in:
Sveta Smirnova
2024-09-24 03:04:46 +03:00
parent 1de149116a
commit 33086769a1
29 changed files with 2122 additions and 139 deletions

View File

@@ -28,7 +28,7 @@ elsif ( !$replica_dbh ) {
} elsif ($sandbox_version lt '5.7') {
plan skip_all => 'Only on MySQL 5.7+';
} else {
plan tests => 5;
plan tests => 8;
}
my ($source1_dbh, $source1_dsn) = $sb->start_sandbox(
@@ -95,6 +95,32 @@ like (
'Message saying channel name must be specified'
) or diag($output);
# Legacy option --check-slave-lag
@args = ('--source', $source1_dsn.',D=test,t=t1', '--purge', '--where', sprintf('id >= %d', $num_rows / 2), "--check-slave-lag", $replica1_dsn);
$output = output(
sub { $exit_status = pt_archiver::main(@args) },
stderr => 1,
);
isnt(
$exit_status,
0,
'Must specify a channel name',
);
like (
$output,
qr/"channel" was not specified/,
'Message saying channel name must be specified'
) or diag($output);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed'
) or diag($output);
push @args, ('--channel', 'sourcechan1');
output(

261
t/pt-archiver/replica_lag.t Normal file
View File

@@ -0,0 +1,261 @@
#!/usr/bin/env perl
BEGIN {
die "The PERCONA_TOOLKIT_BRANCH environment variable is not set.\n"
unless $ENV{PERCONA_TOOLKIT_BRANCH} && -d $ENV{PERCONA_TOOLKIT_BRANCH};
unshift @INC, "$ENV{PERCONA_TOOLKIT_BRANCH}/lib";
};
use strict;
use warnings FATAL => 'all';
use English qw(-no_match_vars);
use Test::More;
use Time::HiRes qw(time);
use PerconaTest;
use Sandbox;
use Data::Dumper;
require "$trunk/bin/pt-archiver";
my $dp = new DSNParser(opts=>$dsn_opts);
my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
my $source_dbh = $sb->get_dbh_for('source');
my $replica1_dbh = $sb->get_dbh_for('replica1');
if ( !$source_dbh ) {
plan skip_all => 'Cannot connect to sandbox source';
}
elsif ( !$replica1_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica1';
}
my $output;
my $cnf = "/tmp/12345/my.sandbox.cnf";
my @args = qw(--no-delete --where 1=1 --progress 1 --no-check-charset);
my $delay = 10;
# Prepare tables and replica lag
sub prepare {
$replica1_dbh->do("STOP ${replica_name}");
$source_dbh->do("RESET ${source_reset}");
$replica1_dbh->do("RESET ${replica_name}");
$replica1_dbh->do("START ${replica_name}");
$source_dbh->do("DROP DATABASE IF EXISTS test");
$source_dbh->do("CREATE DATABASE test");
$source_dbh->do("CREATE TABLE test.test(id INT)");
$source_dbh->do("CREATE TABLE test.actor LIKE sakila.actor");
$replica1_dbh->do("STOP ${replica_name}");
$replica1_dbh->do("CHANGE ${source_change} TO ${source_name}_DELAY=${delay}");
$replica1_dbh->do("START ${replica_name}");
$source_dbh->do("INSERT INTO test.test VALUES(1)");
# Sleeping to ensure that replica is lagging when pt-archiver starts
sleep(3);
}
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-replica-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Lag check works'
) or diag($output);
unlike(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning not printed for option --check-replica-lag'
) or diag($output);
# Option --check-replica-lag specified two times
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-replica-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox',
'--check-replica-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Lag check works when --check-replica-lag provided two times'
) or diag($output);
unlike(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --check-replica-lag provided two times'
) or diag($output);
# Option --check-replica-lag specified two times
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-replica-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox',
'--check-replica-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Test 2: Lag check works when --check-replica-lag provided two times'
) or diag($output);
unlike(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Test 2: Deprecation warning not printed when option --check-replica-lag provided two times'
) or diag($output);
# Warning printed for --check-slave-lag but the option works
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-slave-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Lag check works for deprecated option'
) or diag($output);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed for --check-slave-lag'
) or diag($output);
# Option --check-slave-lag specified two times
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-slave-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox',
'--check-slave-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Lag check works when option --check-slave-lag provided two times'
) or diag($output);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --check-slave-lag provided two times'
) or diag($output);
# Mix of --check-slave-lag amd --check-replica-lag options
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-replica-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox',
'--check-slave-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Lag check works for --check-replica-lag when --check-slave-lag also provided'
) or diag($output);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --check-slave-lag'
) or diag($output);
# Mix of --check-slave-lag amd --check-replica-lag options
prepare();
$output = output(
sub {
pt_archiver::main(@args,
'--source', "D=sakila,t=actor,F=$cnf",
'--dest', "D=test,t=actor,F=$cnf",
'--check-slave-lag', 'h=127.0.0.1,P=12346,u=msandbox,p=msandbox',
'--check-replica-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox'
)
},
stderr => 1
);
like(
$output,
qr/Sleeping: slave lag for server/,
'Lag check works for --check-slave-lag when --check-replica-lag also provided'
) or diag($output);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --check-slave-lag'
) or diag($output);
# #############################################################################
# Done.
# #############################################################################
$replica1_dbh->do("STOP ${replica_name}");
$source_dbh->do("RESET ${source_reset}");
$replica1_dbh->do("RESET ${replica_name}");
$replica1_dbh->do("START ${replica_name}");
$sb->wipe_clean($source_dbh);
ok($sb->ok(), "Sandbox servers") or BAIL_OUT(__FILE__ . " broke the sandbox");
done_testing;

View File

@@ -32,7 +32,7 @@ elsif ( !$replica2_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica2';
}
else {
plan tests => 29;
plan tests => 35;
}
diag(`rm -rf /tmp/pt-heartbeat-sentinel >/dev/null 2>&1`);
@@ -196,9 +196,28 @@ like(
"--check 12347, automatic source server_id"
) or diag($output);
$output = output(
sub { pt_heartbeat::main(qw(-h 127.1 -P 12347 -u msandbox -p msandbox),
qw(-D test --check --print-master-server-id)) },
stderr => 1
);
like(
$output,
qr/0\.\d\d\s+12346\n/,
"--check 12347, automatic source server_id with legacy option"
) or diag($output);
like(
$output,
qr/Option --print-master-server-id is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --print-master-server-id'
) or diag($output);
$output = output(
sub { pt_heartbeat::main(qw(-h 127.1 -P 12347 -u msandbox -p msandbox),
qw(-D test --check --print-source-server-id --source-server-id 12346)) },
stderr => 1
);
like(
@@ -207,6 +226,43 @@ like(
"--check 12347 from --source-server-id 12346"
);
$output = output(
sub { pt_heartbeat::main(qw(-h 127.1 -P 12347 -u msandbox -p msandbox),
qw(-D test --check --print-source-server-id --master-server-id 12346)) },
stderr => 1
);
like(
$output,
qr/0\.\d\d\s+12346\n/,
"--check 12347 from --master-server-id 12346"
) or diag($output);
like(
$output,
qr/Option --master-server-id is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --master-server-id'
) or diag($output);
$output = output(
sub { pt_heartbeat::main(qw(-h 127.1 -P 12347 -u msandbox -p msandbox),
qw(-D test --check --print-source-server-id --master-server-id 12346),
qw( --source-server-id 12345)) },
stderr => 1
);
like(
$output,
qr/0\.\d\d\s+12345\n/,
"--check 12347 from --source-server-id 12345 regardless of --master-server-id 12346"
);
like(
$output,
qr/Option --master-server-id is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --master-server-id'
) or diag($output);
$output = output(
sub { pt_heartbeat::main(qw(-h 127.1 -P 12347 -u msandbox -p msandbox),
qw(-D test --check --print-source-server-id --source-server-id 12345)) },

View File

@@ -0,0 +1,162 @@
#!/usr/bin/env perl
BEGIN {
die "The PERCONA_TOOLKIT_BRANCH environment variable is not set.\n"
unless $ENV{PERCONA_TOOLKIT_BRANCH} && -d $ENV{PERCONA_TOOLKIT_BRANCH};
unshift @INC, "$ENV{PERCONA_TOOLKIT_BRANCH}/lib";
};
use strict;
use warnings FATAL => 'all';
use English qw(-no_match_vars);
use Test::More;
use PerconaTest;
use Sandbox;
use SqlModes;
require "$trunk/bin/pt-heartbeat";
my $dp = new DSNParser(opts=>$dsn_opts);
my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
my $source_dbh = $sb->get_dbh_for('source');
my $replica1_dbh = $sb->get_dbh_for('replica1');
if ( !$source_dbh ) {
plan skip_all => 'Cannot connect to sandbox source';
}
elsif ( !$replica1_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica1';
}
my $cnf = "/tmp/12345/my.sandbox.cnf";
my ($output, $exit_code);
my $rows;
$source_dbh->do('CREATE DATABASE IF NOT EXISTS test');
# Create a new user that is going to be replicated on replicas.
if ($sandbox_version eq '8.0') {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED WITH mysql_native_password BY 'replica_password'/);
} else {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED BY 'replica_password'/);
}
$sb->do_as_root("replica1", q/GRANT REPLICATION CLIENT ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->wait_for_replicas();
# Ensure we cannot connect to replicas using standard credentials
# Since replica2 is a replica of replica1, removing the user from the replica1 will remove
# the user also from replica2
$sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
($output, $exit_code) = full_output(
sub {
pt_heartbeat::main(
qw(-h 127.1 -u msandbox -p msandbox -P 12345 --database test),
qw(--table heartbeat --create-table --update --interval 0.5 --run-time 2),
qw(--replica-user replica_user --replica-password replica_password)
)
},
stderr => 1,
);
is(
$exit_code,
0,
"pt-heartbeat finished correctly"
) or diag($output);
$rows = `/tmp/12346/use -u root -s -e "select server_id from test.heartbeat"`;
chomp $rows;
is(
$rows,
12345,
"Replica1 has source heartbeat",
);
unlike(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-user provided'
) or diag($output);
unlike(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-password provided'
) or diag($output);
$source_dbh->do('TRUNCATE TABLE test.heartbeat');
$rows = `/tmp/12346/use -u root -s -e "select count(*) from test.heartbeat"`;
chomp $rows;
is(
$rows,
0,
'Heartbeat table truncated on replica'
);
($output, $exit_code) = full_output(
sub {
pt_heartbeat::main(
qw(-h 127.1 -u msandbox -p msandbox -P 12345 --database test),
qw(--table heartbeat --create-table --update --interval 0.5 --run-time 2),
qw(--slave-user replica_user --slave-password replica_password)
)
},
stderr => 1,
);
is(
$exit_code,
0,
"pt-heartbeat finished correctly"
) or diag($output);
$rows = `/tmp/12346/use -u root -s -e "select server_id from test.heartbeat"`;
chomp $rows;
is(
$rows,
12345,
"Replica1 has source heartbeat",
);
like(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-user provided'
) or diag($output);
like(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-password provided'
) or diag($output);
# #############################################################################
# Done.
# #############################################################################
# Drop test user
$sb->do_as_root("replica1", q/DROP USER 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
# Restore privilegs for the other test files
$sb->do_as_root("replica1", q/RENAME USER 'msandbox_old'@'%' TO 'msandbox'@'%'/);
$sb->do_as_root("source", q/FLUSH PRIVILEGES/);
$sb->do_as_root("source", q/FLUSH TABLES/);
$sb->wipe_clean($source_dbh);
ok($sb->ok(), "Sandbox servers") or BAIL_OUT(__FILE__ . " broke the sandbox");
done_testing;
exit;

View File

@@ -36,7 +36,7 @@ my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
if ($sb->is_cluster_mode) {
plan skip_all => 'Not for PXC';
} else {
plan tests => 6;
plan tests => 18;
}
my $source_dbh = $sb->get_dbh_for('source');
my $replica_dbh = $sb->get_dbh_for('replica1');
@@ -97,7 +97,7 @@ like(
$output,
qr/Replica lag is \d+ seconds on .* Waiting/s,
"Base test waits on the correct replica",
);
) or diag($output);
# Repeat the test now using --check-replica-lag
$args = "$source_dsn,D=test,t=pt178 --execute --chunk-size 1 --max-lag $max_lag --alter 'ENGINE=InnoDB' "
@@ -120,6 +120,39 @@ like(
"--check-replica-lag waits on the correct replica",
);
unlike(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --check-replica-lag provided'
) or diag($output);
# Repeat the test now using deprecated --check-slave-lag
$args = "$source_dsn,D=test,t=pt178 --execute --chunk-size 1 --max-lag $max_lag --alter 'ENGINE=InnoDB' "
. "--check-slave-lag h=127.0.0.1,P=12346,u=msandbox,p=msandbox,D=test,t=sbtest --pid $tmp_file_name --progress time,5";
# Run a full table scan query to ensure the replica is behind the source
reset_query_cache($source_dbh, $source_dbh);
# Update one row so replica is delayed
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 LIMIT 1');
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 WHERE f1 = ""');
# We need to sleep, otherwise pt-osc can finish before replica is delayed
sleep($max_lag);
diag("Starting deprecated --check-slave-lag test. This is going to take some time due to the delay in the replica");
$output = `$trunk/bin/pt-online-schema-change $args 2>&1`;
like(
$output,
qr/Replica lag is \d+ seconds on .* Waiting/s,
"--check-slave-lag waits on the correct replica",
);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --check-slave-lag provided'
) or diag($output);
# Repeat the test new adding and removing a replica during the process
$args = "$source_dsn,D=test,t=pt178 --execute --chunk-size 1 --max-lag $max_lag --alter 'ENGINE=InnoDB' "
. "--recursion-method=dsn=D=test,t=dynamic_replicas --recurse 0 --pid $tmp_file_name --progress time,5";
@@ -188,6 +221,137 @@ unlike(
"--skip-check-replica-lag is really skipping the replica",
);
unlike(
$output,
qr/Option --skip-check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --skip-check-replica-lag provided'
) or diag($output);
# Repeat the test now using deprecated --skip-check-slave-lag
# Run a full table scan query to ensure the replica is behind the source
reset_query_cache($source_dbh, $source_dbh);
# Update one row so replica is delayed
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 LIMIT 1');
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 WHERE f1 = ""');
# We need to sleep, otherwise pt-osc can finish before replica is delayed
sleep($max_lag);
$args = "$source_dsn,D=test,t=pt178 --execute --chunk-size 1 --max-lag $max_lag --alter 'ENGINE=InnoDB' "
. "--skip-check-slave-lag h=127.0.0.1,P=12346,u=msandbox,p=msandbox,D=test,t=sbtest --pid $tmp_file_name --progress time,5";
diag("Starting deprecated --skip-check-slave-lag test. This is going to take some time due to the delay in the replica");
$output = `$trunk/bin/pt-online-schema-change $args 2>&1`;
unlike(
$output,
qr/Replica lag is \d+ seconds on .*:12346. Waiting/s,
"--skip-check-slave-lag is really skipping the replica",
);
like(
$output,
qr/Option --skip-check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --skip-check-slave-lag provided'
) or diag($output);
# Test --replica-user and --replica-password
# Create a new user that is going to be replicated on replicas.
if ($sandbox_version eq '8.0') {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED WITH mysql_native_password BY 'replica_password'/);
} else {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED BY 'replica_password'/);
}
$sb->do_as_root("replica1", q/GRANT REPLICATION CLIENT ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/GRANT REPLICATION SLAVE ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->wait_for_replicas();
# Ensure we cannot connect to replicas using standard credentials
# Since replica2 is a replica of replica1, removing the user from the replica1 will remove
# the user also from replica2
$sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
# Repeat the basic test with --replica-user and --replica-password
# Run a full table scan query to ensure the replica is behind the source
reset_query_cache($source_dbh, $source_dbh);
# Update one row so replica is delayed
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 LIMIT 1');
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 WHERE f1 = ""');
# We need to sleep, otherwise pt-osc can finish before replica is delayed
sleep($max_lag);
$args = "$source_dsn,D=test,t=pt178 --execute --chunk-size 10 --max-lag $max_lag --alter 'ENGINE=InnoDB' "
. "--pid $tmp_file_name --progress time,5 "
. "--replica-user replica_user --replica-password replica_password";
diag("Starting basic test with --replica-user and --replica-password. This is going to take some time due to the delay in the replica");
$output = `$trunk/bin/pt-online-schema-change $args 2>&1`;
like(
$output,
qr/Replica lag is \d+ seconds on .*:12346. Waiting/s,
"Basic test waits on the correct replica with --replica-user and --replica-password",
) or diag($output);
unlike(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning not printed for option --replica-user'
) or diag($output);
unlike(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning not printed for option --replica-password'
) or diag($output);
# Repeat the basic test with deprecated --slave-user and --slave-password
# Run a full table scan query to ensure the replica is behind the source
reset_query_cache($source_dbh, $source_dbh);
# Update one row so replica is delayed
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 LIMIT 1');
$source_dbh->do('UPDATE `test`.`pt178` SET f2 = f2 + 1 WHERE f1 = ""');
# We need to sleep, otherwise pt-osc can finish before replica is delayed
sleep($max_lag);
$args = "$source_dsn,D=test,t=pt178 --execute --chunk-size 10 --max-lag $max_lag --alter 'ENGINE=InnoDB' "
. "--pid $tmp_file_name --progress time,5 "
. "--slave-user replica_user --slave-password replica_password";
diag("Starting basic test with deprecated --slave-user and --slave-password. This is going to take some time due to the delay in the replica");
$output = `$trunk/bin/pt-online-schema-change $args 2>&1`;
like(
$output,
qr/Replica lag is \d+ seconds on .*:12346. Waiting/s,
"Basic test waits on the correct replica with --slave-user and --slave-password",
) or diag($output);
like(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --slave-user'
) or diag($output);
like(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --slave-password'
) or diag($output);
# Drop test user
$sb->do_as_root("replica1", q/DROP USER 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
# Restore privilegs for the other tests
$sb->do_as_root("replica1", q/RENAME USER 'msandbox_old'@'%' TO 'msandbox'@'%'/);
$sb->do_as_root("source", q/FLUSH PRIVILEGES/);
$sb->do_as_root("source", q/FLUSH TABLES/);
diag("Setting replica delay to 0 seconds");
$replica_dbh->do("STOP ${replica_name}");
$source_dbh->do("RESET ${source_reset}");

View File

@@ -44,7 +44,7 @@ elsif ( !$replica2_dbh ) {
plan skip_all => 'Cannot connect to second sandbox replica';
}
else {
plan tests => 10;
plan tests => 13;
}
my @args = ('h=127.0.0.1,P=12345,u=msandbox,p=msandbox,s=1');
@@ -68,6 +68,63 @@ my $expected = <<EOF;
EOF
is($output, $expected, 'Source with replica and replica of replica');
###############################################################################
# Test --replica-user and --replica-password options
###############################################################################
# Create a new user that is going to be replicated on replicas.
if ($sandbox_version eq '8.0') {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED WITH mysql_native_password BY 'replica_password'/);
} else {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED BY 'replica_password'/);
}
$sb->do_as_root("replica1", q/GRANT REPLICATION CLIENT ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/GRANT REPLICATION SLAVE ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->wait_for_replicas();
# Ensure we cannot connect to replicas using standard credentials
# Since replica2 is a replica of replica1, removing the user from the replica1 will remove
# the user also from replica2
$sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
$output = `$trunk/bin/pt-replica-find -h 127.0.0.1 -P 12345 -u msandbox -p msandbox s=1 --report-format hostname --replica-user replica_user --replica-password replica_password`;
$expected = <<EOF;
127.0.0.1:12345
+- 127.0.0.1:12346
+- 127.0.0.1:12347
EOF
is(
$output,
$expected,
'Source with replica and replica of replica with --replica-user/--replica-password'
) or diag($output);
unlike(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning not printed for option --replica-user'
) or diag($output);
unlike(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning not printed for option --replica-password'
) or diag($output);
# Drop test user
$sb->do_as_root("replica1", q/DROP USER 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
# Restore privilegs for the other tests
$sb->do_as_root("replica1", q/RENAME USER 'msandbox_old'@'%' TO 'msandbox'@'%'/);
$sb->do_as_root("source", q/FLUSH PRIVILEGES/);
$sb->do_as_root("source", q/FLUSH TABLES/);
###############################################################################
# Test --resolve-hostname option (we don't know the hostname of the test
# machine so we settle for any non null string)
@@ -79,20 +136,6 @@ like (
"--resolve-address option"
) or diag($output);
# #############################################################################
# Until MasterSlave::find_replica_hosts() is improved to overcome the problems
# with SHOW REPLICA HOSTS, this test won't work.
# #############################################################################
# Make replica2 replica of source.
#diag(`../../mk-slave-move/mk-slave-move --sibling-of-master h=127.1,P=12347`);
#$output = `perl ../mk-slave-find -h 127.0.0.1 -P 12345 -u msandbox -p msandbox`;
#$expected = <<EOF;
#127.0.0.1:12345
#+- 127.0.0.1:12346
#+- 127.0.0.1:12347
#EOF
#is($output, $expected, 'Source with two replicas');
# #########################################################################
# Issue 391: Add --pid option to all scripts
# #########################################################################

View File

@@ -44,7 +44,7 @@ elsif ( !$replica2_dbh ) {
plan skip_all => 'Cannot connect to second sandbox replica';
}
else {
plan tests => 10;
plan tests => 14;
}
my @args = ('h=127.0.0.1,P=12345,u=msandbox,p=msandbox,s=1');
@@ -68,6 +68,71 @@ my $expected = <<EOF;
EOF
is($output, $expected, 'Source with replica and replica of replica');
###############################################################################
# Test --slave-user and --slave-password options
###############################################################################
# Create a new user that is going to be replicated on replicas.
if ($sandbox_version eq '8.0') {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED WITH mysql_native_password BY 'replica_password'/);
} else {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED BY 'replica_password'/);
}
$sb->do_as_root("replica1", q/GRANT REPLICATION CLIENT ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/GRANT REPLICATION SLAVE ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->wait_for_replicas();
# Ensure we cannot connect to replicas using standard credentials
# Since replica2 is a replica of replica1, removing the user from the replica1 will remove
# the user also from replica2
$sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
$output = `$trunk/bin/pt-replica-find -h 127.0.0.1 -P 12345 -u msandbox -p msandbox s=1 --report-format hostname --slave-user replica_user --slave-password replica_password 2>/dev/null`;
$expected = <<EOF;
127.0.0.1:12345
+- 127.0.0.1:12346
+- 127.0.0.1:12347
EOF
is(
$output,
$expected,
'Source with replica and replica of replica with --slave-user/--slave-password'
) or diag($output);
$output = `$trunk/bin/pt-replica-find -h 127.0.0.1 -P 12345 -u msandbox -p msandbox s=1 --report-format hostname --slave-user replica_user --slave-password replica_password 2>&1`;
like(
$output,
qr/\+- 127.0.0.1:12347/,
'Test 2: Source with replica and replica of replica with --slave-user/--slave-password'
) or diag($output);
like(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --slave-user'
) or diag($output);
like(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning printed for option --slave-password'
) or diag($output);
# Repeat the basic test with deprecated --slave-user and --slave-password
# Drop test user
$sb->do_as_root("replica1", q/DROP USER 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
# Restore privilegs for the other tests
$sb->do_as_root("replica1", q/RENAME USER 'msandbox_old'@'%' TO 'msandbox'@'%'/);
$sb->do_as_root("source", q/FLUSH PRIVILEGES/);
$sb->do_as_root("source", q/FLUSH TABLES/);
###############################################################################
# Test --resolve-hostname option (we don't know the hostname of the test
# machine so we settle for any non null string)
@@ -79,20 +144,6 @@ like (
"--resolve-address option"
) or diag($output);
# #############################################################################
# Until MasterSlave::find_replica_hosts() is improved to overcome the problems
# with SHOW REPLICA HOSTS, this test won't work.
# #############################################################################
# Make replica2 replica of source.
#diag(`../../mk-slave-move/mk-slave-move --sibling-of-master h=127.1,P=12347`);
#$output = `perl ../mk-slave-find -h 127.0.0.1 -P 12345 -u msandbox -p msandbox`;
#$expected = <<EOF;
#127.0.0.1:12345
#+- 127.0.0.1:12346
#+- 127.0.0.1:12347
#EOF
#is($output, $expected, 'Source with two replicas');
# #########################################################################
# Issue 391: Add --pid option to all scripts
# #########################################################################

View File

@@ -11,6 +11,7 @@ use warnings FATAL => 'all';
use English qw(-no_match_vars);
use Test::More;
use Data::Dumper;
use File::Temp qw(tempfile);
use PerconaTest;
use Sandbox;
@@ -162,6 +163,51 @@ like(
stop() or die "Failed to stop pt-replica-restart";
# #############################################################################
# Test the replica of the source with deprecated option syntax.
# #############################################################################
$source_dbh->do('DROP DATABASE IF EXISTS test');
$source_dbh->do('CREATE DATABASE test');
$source_dbh->do('CREATE TABLE test.t (a INT)');
$sb->wait_for_replicas;
# Bust replication
$replica2_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
wait_repl_broke($replica2_dbh) or die "Failed to break replication";
# fetch the source uuid, which is the machine we need to skip an event from
$r = $source_dbh->selectrow_hashref('select @@GLOBAL.server_uuid as uuid');
$uuid = $r->{uuid};
$r = $replica2_dbh->selectrow_hashref("show ${replica_name} status");
like(
$r->{last_error},
qr/Table 'test.t' doesn't exist'/,
'replicaofreplica - deprecated option: Replication broke');
# Start an instance
my (undef, $tempfile) = tempfile();
start("--master-uuid=$uuid $replica2_dsn > $tempfile 2>&1") or die;
wait_repl_ok($replica2_dbh);
like(
slurp_file($tempfile),
qr/Option --master-uuid is deprecated and will be removed in future versions./,
'Deprecation warning printed for legacy option --master-uuid'
);
$r = $replica2_dbh->selectrow_hashref("show ${replica_name} status");
like(
$r->{last_errno},
qr/^0$/,
'Skips event from source on replica2 for deprecated --master-uuid'
) or BAIL_OUT("Replication is broken");
stop() or die "Failed to stop pt-replica-restart";
diag(`rm $tempfile >/dev/null`);
# #############################################################################
# Test skipping 2 events in a row.
# #############################################################################

View File

@@ -105,6 +105,108 @@ unlike(
'--error-text works (issue 459)'
);
$replica_dbh->do('CREATE TABLE test.t (a INT)');
$replica_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# #############################################################################
# Testing --recurse option
# #############################################################################
# Bust replication again.
$source_dbh->do('DROP TABLE IF EXISTS test.t');
$source_dbh->do('CREATE TABLE test.t (a INT)');
sleep 1;
$replica_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
$output = `/tmp/12346/use -e "show ${replica_name} status"`;
like(
$output,
qr/Table 'test.t' doesn't exist'/,
'It is busted again'
);
# Start an instance
$output = `$trunk/bin/pt-replica-restart --max-sleep 0.25 -h 127.0.0.1 -P 12345 -u msandbox -p msandbox --error-text "doesn't exist" --run-time 1s --recurse 1 2>&1`;
like(
$output,
qr/P=12346/,
'Replica discovered'
);
$replica_dbh->do('CREATE TABLE test.t (a INT)');
$replica_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# #############################################################################
# Testing --recurse option with --replica-user/--replica-password
# #############################################################################
# Create a new user that is going to be replicated on replicas.
if ($sandbox_version eq '8.0') {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED WITH mysql_native_password BY 'replica_password'/);
} else {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED BY 'replica_password'/);
}
$sb->do_as_root("replica1", q/GRANT REPLICATION CLIENT ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/GRANT REPLICATION SLAVE ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->wait_for_replicas();
# Bust replication again.
$source_dbh->do('DROP TABLE IF EXISTS test.t');
$source_dbh->do('CREATE TABLE test.t (a INT)');
sleep 1;
$replica_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
$output = `/tmp/12346/use -e "show ${replica_name} status"`;
like(
$output,
qr/Table 'test.t' doesn't exist'/,
'It is busted again'
);
# Ensure we cannot connect to replicas using standard credentials
# Since replica2 is a replica of replica1, removing the user from the replica1 will remove
# the user also from replica2
$sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
# Start an instance
$output = `$trunk/bin/pt-replica-restart --max-sleep 0.25 -h 127.0.0.1 -P 12345 -u msandbox -p msandbox --error-text "doesn't exist" --run-time 1s --recurse 1 --replica-user replica_user --replica-password replica_password 2>&1`;
like(
$output,
qr/P=12346/,
'Replica discovered with --replica-user/--replica-password'
);
unlike(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-user provided'
) or diag($output);
unlike(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-password provided'
) or diag($output);
# Drop test user
$sb->do_as_root("replica1", q/DROP USER 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
# Restore privilegs for the other tests
$sb->do_as_root("replica1", q/RENAME USER 'msandbox_old'@'%' TO 'msandbox'@'%'/);
$sb->do_as_root("source", q/FLUSH PRIVILEGES/);
$sb->do_as_root("source", q/FLUSH TABLES/);
$replica_dbh->do('CREATE TABLE test.t (a INT)');
$replica_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# ###########################################################################
# Issue 391: Add --pid option to all scripts
# ###########################################################################

View File

@@ -105,6 +105,104 @@ unlike(
'--error-text works (issue 459)'
);
# #############################################################################
# Testing --recurse option
# #############################################################################
# Bust replication again.
$source_dbh->do('DROP TABLE IF EXISTS test.t');
$source_dbh->do('CREATE TABLE test.t (a INT)');
sleep 1;
$replica_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
$output = `/tmp/12346/use -e "show ${replica_name} status"`;
like(
$output,
qr/Table 'test.t' doesn't exist'/,
'It is busted again'
);
# Start an instance
$output = `$trunk/bin/pt-slave-restart --max-sleep 0.25 -h 127.0.0.1 -P 12345 -u msandbox -p msandbox --error-text "doesn't exist" --run-time 1s --recurse 1 2>&1`;
like(
$output,
qr/P=12346/,
'Replica discovered'
);
$replica_dbh->do('CREATE TABLE test.t (a INT)');
$replica_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# #############################################################################
# Testing --recurse option with --slave-user/--slave-password
# #############################################################################
# Create a new user that is going to be replicated on replicas.
if ($sandbox_version eq '8.0') {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED WITH mysql_native_password BY 'replica_password'/);
} else {
$sb->do_as_root("replica1", q/CREATE USER 'replica_user'@'localhost' IDENTIFIED BY 'replica_password'/);
}
$sb->do_as_root("replica1", q/GRANT REPLICATION CLIENT ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/GRANT REPLICATION SLAVE ON *.* TO 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->wait_for_replicas();
# Bust replication again.
$source_dbh->do('DROP TABLE IF EXISTS test.t');
$source_dbh->do('CREATE TABLE test.t (a INT)');
sleep 1;
$replica_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
$output = `/tmp/12346/use -e "show ${replica_name} status"`;
like(
$output,
qr/Table 'test.t' doesn't exist'/,
'It is busted again'
);
# Ensure we cannot connect to replicas using standard credentials
# Since replica2 is a replica of replica1, removing the user from the replica1 will remove
# the user also from replica2
$sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
# Start an instance
$output = `$trunk/bin/pt-slave-restart --max-sleep 0.25 -h 127.0.0.1 -P 12345 -u msandbox -p msandbox --error-text "doesn't exist" --run-time 1s --recurse 1 --slave-user replica_user --slave-password replica_password 2>&1`;
like(
$output,
qr/P=12346/,
'Replica discovered with --slave-user/--slave-password'
);
like(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-user provided'
) or diag($output);
like(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-password provided'
) or diag($output);
# Drop test user
$sb->do_as_root("replica1", q/DROP USER 'replica_user'@'localhost'/);
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
# Restore privilegs for the other tests
$sb->do_as_root("replica1", q/RENAME USER 'msandbox_old'@'%' TO 'msandbox'@'%'/);
$sb->do_as_root("source", q/FLUSH PRIVILEGES/);
$sb->do_as_root("source", q/FLUSH TABLES/);
$replica_dbh->do('CREATE TABLE test.t (a INT)');
$replica_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# ###########################################################################
# Issue 391: Add --pid option to all scripts
# ###########################################################################

View File

@@ -0,0 +1,286 @@
#!/usr/bin/env perl
BEGIN {
die "The PERCONA_TOOLKIT_BRANCH environment variable is not set.\n"
unless $ENV{PERCONA_TOOLKIT_BRANCH} && -d $ENV{PERCONA_TOOLKIT_BRANCH};
unshift @INC, "$ENV{PERCONA_TOOLKIT_BRANCH}/lib";
};
use strict;
use warnings FATAL => 'all';
use English qw(-no_match_vars);
use Test::More;
use Data::Dumper;
use File::Temp qw(tempfile);
use PerconaTest;
use Sandbox;
require "$trunk/bin/pt-replica-restart";
diag('Restarting the sandbox');
diag(`SAKILA=0 REPLICATION_THREADS=0 $trunk/sandbox/test-env restart`);
diag("Sandbox restarted");
my $dp = new DSNParser(opts=>$dsn_opts);
my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
my $source_dbh = $sb->get_dbh_for('source');
my $replica1_dbh = $sb->get_dbh_for('replica1');
my $replica2_dbh = $sb->get_dbh_for('replica2');
if ( !$source_dbh ) {
plan skip_all => 'Cannot connect to sandbox source';
}
elsif ( !$replica1_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica1';
}
elsif ( !$replica2_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica2';
}
my $replica1_dsn = $sb->dsn_for("replica1");
my $replica2_dsn = $sb->dsn_for("replica2");
my $pid_file = "/tmp/pt-replica-restart-test-$PID.pid";
my $log_file = "/tmp/pt-replica-restart-test-$PID.log";
my $cmd = "$trunk/bin/pt-replica-restart --daemonize --run-time 5 --max-sleep 0.25 --pid $pid_file --log $log_file";
sub start {
my ( $extra ) = @_;
stop() or return;
system "$cmd $extra";
PerconaTest::wait_for_files($pid_file);
}
sub stop() {
return 1 if !is_running();
diag(`$trunk/bin/pt-replica-restart --stop -q >/dev/null 2>&1 &`);
wait_until(sub { !-f $pid_file }, 0.3, 2);
diag(`rm -f /tmp/pt-replica-restart-sentinel`);
return is_running() ? 0 : 1;
}
sub is_running {
chomp(my $running = `ps -eaf | grep -v grep | grep '$cmd'`);
if (!-f $pid_file && !$running) {
return 0;
} elsif (-f $pid_file && !$running) {
diag(`rm -f $pid_file`);
return 0;
}
return 1;
}
sub wait_repl_broke {
my $dbh = shift;
return wait_until(
sub {
my $row = $dbh->selectrow_hashref("show ${replica_name} status");
return $row->{last_sql_errno};
}
);
}
sub wait_repl_ok {
my $dbh = shift;
wait_until(
sub {
my $row = $dbh->selectrow_hashref("show ${replica_name} status");
return $row->{last_sql_errno} == 0;
},
0.30,
5,
);
}
# #############################################################################
# Testing --until-source option
# #############################################################################
$source_dbh->do('DROP DATABASE IF EXISTS test');
$source_dbh->do('CREATE DATABASE test');
$source_dbh->do('CREATE TABLE test.t (a INT)');
$sb->wait_for_replicas;
# Bust replication
$replica1_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
wait_repl_broke($replica1_dbh) or die "Failed to break replication";
my $r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
like($r->{last_error}, qr/Table 'test.t' doesn't exist'/, 'replica: Replication broke');
$source_dbh->do('INSERT INTO test.t SELECT 2');
$r = $source_dbh->selectrow_hashref("show ${source_status} status");
my $until_file = $r->{file};
my $until_pos = $r->{position};
$source_dbh->do('INSERT INTO test.t SELECT 3');
my (undef, $tempfile) = tempfile();
# Start pt-replica-restart and wait up to 5s for it to fix replication
# (it should take < 1s but tests can be really slow sometimes).
start("--until-source=${until_file},${until_pos} $replica1_dsn > $tempfile 2>&1") or die "Failed to start pt-replica-restart";
wait_repl_ok($replica1_dbh);
# Check if replication is fixed.
$r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
like(
$r->{last_errno},
qr/^0$/,
'Event is skipped',
) or BAIL_OUT("Replication is broken: " . Dumper($r) . `cat $log_file`);
is(
$r->{"relay_${source_name}_log_file"},
$until_file,
'Started until specified source binary log file'
) or diag(Dumper($r));
is(
$r->{"exec_${source_name}_log_pos"},
$until_pos,
'Started until specified source binary log pos'
) or diag(Dumper($r));
unlike(
slurp_file($tempfile),
qr/Option --until-master is deprecated and will be removed in future versions./,
'Deprecation warning not printed for option --unitl-source'
) or diag(slurp_file($tempfile));
# Stop pt-replica-restart.
stop() or die "Failed to stop pt-replica-restart";
diag(`rm $tempfile >/dev/null`);
$replica1_dbh->do('CREATE TABLE test.t (a INT)');
$replica1_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# #############################################################################
# Testing legacy --until-master option
# #############################################################################
$source_dbh->do('DROP DATABASE IF EXISTS test');
$source_dbh->do('CREATE DATABASE test');
$source_dbh->do('CREATE TABLE test.t (a INT)');
$sb->wait_for_replicas;
# Bust replication
$replica1_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
wait_repl_broke($replica1_dbh) or die "Failed to break replication";
$r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
like($r->{last_error}, qr/Table 'test.t' doesn't exist'/, 'replica: Replication broke');
$source_dbh->do('INSERT INTO test.t SELECT 2');
$r = $source_dbh->selectrow_hashref("show ${source_status} status");
$until_file = $r->{file};
$until_pos = $r->{position};
$source_dbh->do('INSERT INTO test.t SELECT 3');
(undef, $tempfile) = tempfile();
# Start pt-replica-restart and wait up to 5s for it to fix replication
# (it should take < 1s but tests can be really slow sometimes).
start("--until-master=${until_file},${until_pos} $replica1_dsn > $tempfile 2>&1") or die "Failed to start pt-replica-restart";
wait_repl_ok($replica1_dbh);
# Check if replication is fixed.
$r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
like(
$r->{last_errno},
qr/^0$/,
'Event is skipped',
) or BAIL_OUT("Replication is broken: " . Dumper($r) . `cat $log_file`);
is(
$r->{"relay_${source_name}_log_file"},
$until_file,
'Started until specified source binary log file'
) or diag(Dumper($r));
is(
$r->{"exec_${source_name}_log_pos"},
$until_pos,
'Started until specified source binary log pos'
) or diag(Dumper($r));
like(
slurp_file($tempfile),
qr/Option --until-master is deprecated and will be removed in future versions./,
'Deprecation warning printed for legacy option --unitl-master'
) or diag(slurp_file($tempfile));
# Stop pt-replica-restart.
stop() or die "Failed to stop pt-replica-restart";
diag(`rm $tempfile >/dev/null`);
$replica1_dbh->do('CREATE TABLE test.t (a INT)');
$replica1_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# #############################################################################
# Testing --until-relay option
# #############################################################################
$source_dbh->do('DROP DATABASE IF EXISTS test');
$source_dbh->do('CREATE DATABASE test');
$source_dbh->do('CREATE TABLE test.t (a INT)');
$sb->wait_for_replicas;
# Bust replication
$replica1_dbh->do('DROP TABLE test.t');
$source_dbh->do('INSERT INTO test.t SELECT 1');
wait_repl_broke($replica1_dbh) or die "Failed to break replication";
$r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
like($r->{last_error}, qr/Table 'test.t' doesn't exist'/, 'replica: Replication broke');
$r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
$until_file = $r->{relay_log_file};
my $rm1 = $source_dbh->selectrow_hashref("show ${source_status} status");
$source_dbh->do('INSERT INTO test.t SELECT 2');
my $rm2 = $source_dbh->selectrow_hashref("show ${source_status} status");
$until_pos = $r->{relay_log_pos} + $rm2->{position} - $rm1->{position};
$source_dbh->do('INSERT INTO test.t SELECT 3');
(undef, $tempfile) = tempfile();
# Start pt-replica-restart and wait up to 5s for it to fix replication
# (it should take < 1s but tests can be really slow sometimes).
start("--until-relay=${until_file},${until_pos} $replica1_dsn > $tempfile 2>&1") or die "Failed to start pt-replica-restart";
wait_repl_ok($replica1_dbh);
# Check if replication is fixed.
$r = $replica1_dbh->selectrow_hashref("show ${replica_name} status");
like(
$r->{last_errno},
qr/^0$/,
'Event is skipped',
) or BAIL_OUT("Replication is broken: " . Dumper($r) . `cat $log_file`);
is(
$r->{"relay_log_file"},
$until_file,
'Started until specified relay log file'
) or diag(Dumper($r));
is(
$r->{"relay_log_pos"},
$until_pos,
'Started until specified relay log pos'
) or diag(Dumper($r));
# Stop pt-replica-restart.
stop() or die "Failed to stop pt-replica-restart";
diag(`rm $tempfile >/dev/null`);
$replica1_dbh->do('CREATE TABLE test.t (a INT)');
$replica1_dbh->do("start ${replica_name}");
$sb->wait_for_replicas;
# #############################################################################
# Done.
# #############################################################################
diag(`rm -f $pid_file $log_file >/dev/null`);
diag(`$trunk/sandbox/test-env restart`);
ok($sb->ok(), "Sandbox servers") or BAIL_OUT(__FILE__ . " broke the sandbox");
done_testing;

View File

@@ -38,7 +38,7 @@ elsif ( !$replica1_dbh ) {
elsif ( !@{$source_dbh->selectall_arrayref("show databases like 'sakila'")} ) {
plan skip_all => 'sakila database is not loaded';
} else {
plan tests => 40;
plan tests => 46;
}
# The sandbox servers run with lock_wait_timeout=3 and it's not dynamic
@@ -208,6 +208,80 @@ is_deeply(
"--emptry-replicate-table on by default"
) or print STDERR Dumper($row);
# ############################################################################
# --[no]check-replica-tables
# ############################################################################
$sb->wipe_clean($source_dbh);
$sb->load_file('source', 't/pt-table-checksum/samples/issue_21.sql');
$replica2_dbh->do('ALTER TABLE test.issue_21 DROP COLUMN b');
($output, $exit_status) = full_output(
sub {
pt_table_checksum::main(@args,
qw(-t test.issue_21),
qw(--chunk-time 0 --chunk-size 2 --no-check-replica-tables --no-replicate-check),
'--skip-check-replica-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox'
)
},
stderr => 1
);
is(
$exit_status,
0,
'no error with --no-check-replica-tables'
);
like(
$output,
qr/Skipping replica h=127.0.0.1,P=12347/,
'Broken replica skipped with --no-check-replica-tables and --skip-check-replica-lag'
);
unlike(
$output,
qr/Option --\[no\]check-slave-tables is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --no-check-replica-tables provided'
) or diag($output);
($output, $exit_status) = full_output(
sub {
pt_table_checksum::main(@args,
qw(-t test.issue_21),
qw(--chunk-time 0 --chunk-size 2 --no-check-slave-tables --no-replicate-check),
'--skip-check-replica-lag', 'h=127.0.0.1,P=12347,u=msandbox,p=msandbox'
)
},
stderr => 1
);
is(
$exit_status,
0,
'no error with --no-check-slave-tables'
);
like(
$output,
qr/Skipping replica h=127.0.0.1,P=12347/,
'Broken replica skipped with -no-check-slave-tables and --skip-check-replica-lag'
);
like(
$output,
qr/Option --\[no\]check-slave-tables is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --no-check-slave-tables provided'
) or diag($output);
$sb->load_file(
'replica2',
't/pt-table-checksum/samples/issue_21.sql',
undef,
no_wait => 1
);
$replica2_dbh->do("START ${replica_name}");
# ############################################################################
# --[no]recheck
# ############################################################################

View File

@@ -206,7 +206,6 @@ like(
"Bug 1016131: ptc should skip tables where all columns are excluded"
);
# Test #12
{
$output = output(
sub { pt_table_checksum::main(@args,
@@ -222,6 +221,36 @@ like(
"--skip-check-replica-lag",
);
unlike(
$output,
qr/Option --skip-check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --skip-check-replica-lag provided'
) or diag($output);
# Deprecatted option --skip-check-slave-lag
$output = output(
sub {
pt_table_checksum::main(@args,
'--skip-check-slave-lag', "h=127.0.0.1,P=".$sb->port_for('replica1'),
),
},
stderr => 1,
);
$skipping_str = "Skipping.*".$sb->port_for('replica1');
like(
$output,
qr/$skipping_str/s,
"--skip-check-slave-lag",
);
like(
$output,
qr/Option --skip-check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --skip-check-slave-lag provided'
) or diag($output);
# Test #12
# Test for skip-check-replica-lag and empty replica port
$output = output(
sub { pt_table_checksum::main(@args,

View File

@@ -24,7 +24,7 @@ if ( !$dbh ) {
plan skip_all => 'Cannot connect to sandbox source';
}
else {
plan tests => 2;
plan tests => 7;
}
# The sandbox servers run with lock_wait_timeout=3 and it's not dynamic
@@ -57,17 +57,56 @@ $sb->do_as_root("replica1", q/RENAME USER 'msandbox'@'%' TO 'msandbox_old'@'%'/)
$sb->do_as_root("replica1", q/FLUSH PRIVILEGES/);
$sb->do_as_root("replica1", q/FLUSH TABLES/);
$output = output(
sub { pt_table_checksum::main(@args) },
stderr => 1,
);
is(
PerconaTest::count_checksum_results($output, 'rows'),
6,
"Large BLOB/TEXT/BINARY Checksum"
) or diag($output);
unlike(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-user provided'
) or diag($output);
unlike(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-password provided'
) or diag($output);
#Legacy variant
@args = ($source_dsn, qw(--replicate test.checksums -d test --slave-user replica_user --slave-password replica_password --ignore-databases mysql));
$output = output(
sub { pt_table_checksum::main(@args) },
stderr => 1,
);
is(
PerconaTest::count_checksum_results($output, 'rows'),
6,
"Large BLOB/TEXT/BINARY Checksum"
) or diag($output);
like(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-user provided'
) or diag($output);
like(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-password provided'
) or diag($output);
# #############################################################################
# Done.
# #############################################################################

View File

@@ -63,7 +63,7 @@ my @args = ($source1_dsn,
# The sandbox servers run with lock_wait_timeout=3 and it's not dynamic
# so we need to specify --set-vars innodb_lock_wait_timeout=3 else the tool will die.
$sb->do_as_root("chan_replica1", 'stop ${replica_name} IO_thread;');
$sb->do_as_root("chan_replica1", "stop ${replica_name} IO_thread;");
my $output;
my $exit_status;
@@ -79,7 +79,7 @@ is(
"PT-1637 exist status 128 if replication is stopped and --fail-on-replication-stopped",
);
$sb->do_as_root("chan_replica1", 'start ${replica_name} IO_thread;');
$sb->do_as_root("chan_replica1", "start ${replica_name} IO_thread;");
sleep(2);
$sb->stop_sandbox(qw(chan_source1 chan_replica2 chan_replica1));

View File

@@ -37,7 +37,7 @@ elsif ( !$replica2_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica2';
}
else {
plan tests => 4;
plan tests => 8;
}
# The sandbox servers run with lock_wait_timeout=3 and it's not dynamic
@@ -90,6 +90,43 @@ is(
"Ignores replica1 when --check-replica-lag=replica2"
);
unlike(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --check-replica-lag provided'
) or diag($output);
$row = $source_dbh->selectall_arrayref("select * from percona.checksums where db='sakila' and tbl='city'");
is(
scalar @$row,
1,
"Checksummed table"
);
$source_dbh->do("delete from percona.checksums where db='sakila' and tbl='city'");
# Checksum but only use replica2 to check for lag with deprecated --check-slave-lag.
($output, $exit_status) = full_output(
sub {
pt_table_checksum::main(@args,
qw(-t sakila.city --quiet),
qw(--no-replicate-check), '--check-slave-lag', 'P=12347')
},
stderr => 1,
);
is(
$exit_status,
0,
"Ignores replica1 when --check-slave-lag=replica2"
);
like(
$output,
qr/Option --check-slave-lag is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --check-slave-lag provided'
) or diag($output);
$row = $source_dbh->selectall_arrayref("select * from percona.checksums where db='sakila' and tbl='city'");
is(
scalar @$row,

View File

@@ -29,7 +29,7 @@ elsif ( !$replica_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica';
}
else {
plan tests => 24;
plan tests => 30;
}
$sb->create_dbs($source_dbh, [qw(test)]);
@@ -131,6 +131,45 @@ is_deeply(
'Synced OK with --replica-user'
);
unlike(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-user provided'
) or diag($output);
unlike(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --replica-password provided'
) or diag($output);
$sb->load_file('source', 't/pt-table-sync/samples/before.sql');
$output = run('test1', 'test2', '--algorithms Chunk,GroupBy --no-bin-log --slave-user replica_user --slave-password replica_password');
like(
$output,
qr/INSERT INTO `test`.`test2`\(`a`, `b`\) VALUES \('1', 'en'\);\nINSERT INTO `test`.`test2`\(`a`, `b`\) VALUES \('2', 'ca'\);/,
'Basic Chunk sync with --slave-user/--slave-password'
);
is_deeply(
query_replica('select * from test.test2'),
[ { a => 1, b => 'en' }, { a => 2, b => 'ca' } ],
'Synced OK with --slave-user'
);
like(
$output,
qr/Option --slave-user is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-user provided'
) or diag($output);
like(
$output,
qr/Option --slave-password is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --slave-password provided'
) or diag($output);
$sb->load_file('source', 't/pt-table-sync/samples/before.sql');
$output = run('test1', 'test2', '--algorithms Nibble --no-bin-log');
is($output, "INSERT INTO `test`.`test2`(`a`, `b`) VALUES ('1', 'en');

View File

@@ -18,7 +18,7 @@ require "$trunk/bin/pt-table-sync";
my $dp = new DSNParser(opts=>$dsn_opts);
my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
plan tests => 4;
plan tests => 11;
# #############################################################################
# Ensure that syncing source-source works OK
@@ -26,13 +26,11 @@ plan tests => 4;
# Start up 12348 <-> 12349
diag('Starting source-source servers...');
#diag(`$trunk/sandbox/start-sandbox source-source 12348 12349 >/dev/null`);
diag(`$trunk/sandbox/start-sandbox source-source 12348 12349`);
my $source1_dbh = $sb->get_dbh_for('source1');
my $source2_dbh = $sb->get_dbh_for('source2');
# Load some tables and data (on both, since they're source-source).
$source1_dbh->do("CREATE DATABASE test");
$sb->load_file("source1", "t/pt-table-sync/samples/before.sql");
$sb->wait_for_replicas();
$sb->wait_for_replicas(
@@ -57,6 +55,7 @@ my $output = output(
qw(--no-check-replica --sync-to-source --print --execute),
"h=127.0.0.1,P=12348,u=msandbox,p=msandbox,D=test,t=test1")
},
stderr => 1
);
# 0 = ok no diffs
@@ -74,6 +73,18 @@ like(
"SQL to sync diff"
);
unlike(
$output,
qr/Option --sync-to-master is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --sync-to-source provided'
) or diag($output);
unlike(
$output,
qr/Option --\[no\]check-slave is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --no-check-replica provided'
) or diag($output);
PerconaTest::wait_for_table($source1_dbh, "test.test1", "a=1 and b='mm'");
my $rows = $source1_dbh->selectall_arrayref("SELECT * FROM test.test1");
@@ -83,6 +94,81 @@ is_deeply(
"Diff row synced on source1"
);
diag('Stopping source-source servers...');
diag(`$trunk/sandbox/stop-sandbox 12348 12349 >/dev/null`);
# #############################################################################
# Repeat the test with deprecated options.
# #############################################################################
# Start up 12348 <-> 12349
diag('Starting source-source servers...');
diag(`$trunk/sandbox/start-sandbox source-source 12348 12349`);
$source1_dbh = $sb->get_dbh_for('source1');
$source2_dbh = $sb->get_dbh_for('source2');
$sb->load_file("source1", "t/pt-table-sync/samples/before.sql");
$sb->wait_for_replicas();
$sb->wait_for_replicas(
source => 'source1',
replica => 'source2',
);
# Make source2 different from source1. So source2 has the _correct_ data,
# and the sync below will make source1 have that data too.
$source2_dbh->do("set sql_log_bin=0");
$source2_dbh->do("update test.test1 set b='mm' where a=1");
$source2_dbh->do("set sql_log_bin=1");
# This will make source1's data match the changed, correcct data on source2
# (that is _not_ a typo). The sync direction is therefore source2 -> source1
# because, given the command below, the given host source1 and with
# --sync-to-source that makes source2 "the" source with the correct data.
$exit_status = 0;
$output = output(
sub {
$exit_status = pt_table_sync::main(
qw(--no-check-slave --sync-to-master --print --execute),
"h=127.0.0.1,P=12348,u=msandbox,p=msandbox,D=test,t=test1")
},
stderr =>1
);
# 0 = ok no diffs
# 1 = error
# >1 = sum(@status{@ChangeHandler::ACTIONS})
is(
$exit_status,
2,
"Exit status 2"
);
like(
$output,
qr/REPLACE INTO `test`\.`test1`\s*\(`a`, `b`\) VALUES\s*\('1', 'mm'\)/,
"SQL to sync diff"
);
like(
$output,
qr/Option --sync-to-master is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --sync-to-master provided'
) or diag($output);
like(
$output,
qr/Option --\[no\]check-slave is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --no-check-slave provided'
) or diag($output);
PerconaTest::wait_for_table($source1_dbh, "test.test1", "a=1 and b='mm'");
$rows = $source1_dbh->selectall_arrayref("SELECT * FROM test.test1");
is_deeply(
$rows,
[ [1, 'mm'], [2, 'ca'] ],
"Diff row synced on source1"
);
diag('Stopping source-source servers...');
diag(`$trunk/sandbox/stop-sandbox 12348 12349 >/dev/null`);

View File

@@ -20,12 +20,13 @@ my $output;
my $dp = new DSNParser(opts=>$dsn_opts);
my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
my $source_dbh = $sb->get_dbh_for('source');
my $replica_dbh = $sb->get_dbh_for('replica1');
my $replica1_dbh = $sb->get_dbh_for('replica1');
my $replica2_dbh = $sb->get_dbh_for('replica2');
if ( !$source_dbh ) {
plan skip_all => 'Cannot connect to sandbox source';
}
elsif ( !$replica_dbh ) {
elsif ( !$replica1_dbh ) {
plan skip_all => 'Cannot connect to sandbox replica';
}
@@ -59,7 +60,7 @@ like(
"check-child-tables: error message"
);
my $rows = $replica_dbh->selectall_arrayref("select * from on_del_cas.child2");
my $rows = $replica1_dbh->selectall_arrayref("select * from on_del_cas.child2");
is_deeply(
$rows,
[ [1,1] ],
@@ -80,6 +81,76 @@ unlike(
"check-child-tables: no error message with --print"
);
# #############################################################################
# --[no]check-source
# #############################################################################
# Connecting replica with wrong user name
$replica1_dbh->do("STOP ${replica_name}");
$replica1_dbh->do("CHANGE ${source_change} TO ${source_name}_port=12347, ${source_name}_user='does_not_exist'");
$replica1_dbh->do("START ${replica_name}");
$output = output(
sub {
pt_table_sync::main($replica1_dsn, qw(--sync-to-source),
qw(--execute -d on_del_cas --wait 0))
},
stderr => 1,
);
like(
$output,
qr/The server specified as a source has no connected replicas/,
"Error when --check-source is enabled (default)"
) or diag($output);
$output = output(
sub {
pt_table_sync::main($replica1_dsn, qw(--sync-to-source),
qw(--execute -d on_del_cas --wait 0 --no-check-source))
},
stderr => 1,
);
unlike(
$output,
qr/The server specified as a source has no connected replicas/,
"No wrong source error when --check-source is disabled"
) or diag($output);
unlike(
$output,
qr/Option --\[no\]check-master is deprecated and will be removed in future versions./,
'Deprecation warning not printed when option --no-check-source provided'
) or diag($output);
# Legacy option
$output = output(
sub {
pt_table_sync::main($replica1_dsn, qw(--sync-to-source),
qw(--execute -d on_del_cas --wait 0 --no-check-master))
},
stderr => 1,
);
unlike(
$output,
qr/The server specified as a source has no connected replicas/,
"No wrong source error when --check-master is disabled"
) or diag($output);
like(
$output,
qr/Option --\[no\]check-master is deprecated and will be removed in future versions./,
'Deprecation warning printed when option --no-check-master provided'
) or diag($output);
$replica1_dbh->do("STOP ${replica_name}");
$replica1_dbh->do("CHANGE ${source_change} TO ${source_name}_port=12345, ${source_name}_user='msandbox'");
$replica1_dbh->do("START ${replica_name}");
$replica1_dbh->do("STOP ${replica_name}");
$replica1_dbh->do("CHANGE ${source_change} TO ${source_name}_port=12345, ${source_name}_user='msandbox'");
$replica1_dbh->do("START ${replica_name}");
# #############################################################################
# Done.
# #############################################################################