From 2c1db036b58ccd27f7c123b5dbf510906bd0fd11 Mon Sep 17 00:00:00 2001 From: Carlos Salguero Date: Wed, 6 Jul 2016 19:04:21 -0300 Subject: [PATCH 1/2] BUG-1595678 Added --slave-user, --slave-password params --- bin/pt-online-schema-change | 28 ++++++++++++++++- lib/MasterSlave.pm | 14 +++++++-- t/pt-online-schema-change/basics.t | 50 +++++++++++++++++++++--------- 3 files changed, 75 insertions(+), 17 deletions(-) diff --git a/bin/pt-online-schema-change b/bin/pt-online-schema-change index e13e3ab9..b0fb1a15 100755 --- a/bin/pt-online-schema-change +++ b/bin/pt-online-schema-change @@ -4110,6 +4110,7 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; + my $o = $self->{OptionParser}; $self->recurse_to_slaves( { dbh => $dbh, @@ -4118,7 +4119,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -11956,6 +11966,22 @@ replication lag, insert the values C and C into the table. Currently, the DSNs are ordered by id, but id and parent_id are otherwise ignored. +=item --slave-user + +type: string + +Sets the user to be used to connect to the slaves. +This parameter allows you to have a different user with less privileges on the +slaves but that user must exist on all slaves. + +=item --slave-password + +type: string + +Sets the password to be used to connect to the slaves. +It can be used with --slave-user and the password for the user must be the same +on all slaves. + =item --set-vars type: Array diff --git a/lib/MasterSlave.pm b/lib/MasterSlave.pm index 6b9eec75..5f51a456 100644 --- a/lib/MasterSlave.pm +++ b/lib/MasterSlave.pm @@ -80,7 +80,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -88,7 +89,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } diff --git a/t/pt-online-schema-change/basics.t b/t/pt-online-schema-change/basics.t index dac8b73f..86d80cc8 100644 --- a/t/pt-online-schema-change/basics.t +++ b/t/pt-online-schema-change/basics.t @@ -837,33 +837,55 @@ test_alter_table( ); test_alter_table( - name => "--preserve-triggers --no-swap-table", - table => "pt_osc.account", - pk_col => "id", + name => "--preserve-triggers --no-swap-tables", + table => "pt_osc.t", + file => "basic_no_fks_innodb.sql", + max_id => 20, test_type => "add_col", new_col => "foo", + no_change => 1, cmds => [ - qw(--execute --preserve-triggers --no-swap-table), '--alter', 'ADD COLUMN foo2 INT', + qw(--execute --no-swap-tables --preserve-triggers), '--alter', 'ADD COLUMN foo INT' ], ); test_alter_table( - name => "FK rebuild_constraints --preserve-triggers", - table => "sakila.film", - pk_col => "film_id", - test_type => "add_col", - file => "sakila_triggers.sql", - new_col => "foo", - check_fks => "rebuild_constraints", - cmds => [ - qw(--execute --preserve-triggers --alter-foreign-keys-method rebuild_constraints), '--alter', 'ADD COLUMN foo INT', + name => "Basic FK auto --execute", + table => "pt_osc.country", + pk_col => "country_id", + file => "basic_with_fks.sql", + test_type => "drop_col", + drop_col => "last_update", + check_fks => "rebuild_constraints", + cmds => [ + qw( + --execute + --alter-foreign-keys-method rebuild_constraints + --preserve-triggers + ), + '--alter', 'DROP COLUMN last_update', ], ); +$sb->do_as_root("master", q/GRANT REPLICATION SLAVE ON *.* TO 'slave_user'@'%' IDENTIFIED BY 'slave_password'/); +$sb->do_as_root("master", q/set sql_log_bin=0/); +$sb->do_as_root("master", q/DROP USER 'slave_user'/); +$sb->do_as_root("master", q/set sql_log_bin=1/); + +test_alter_table( + name => "--slave-user --slave-password", + file => "basic_no_fks_innodb.sql", + table => "pt_osc.t", + test_type => "add_col", + new_col => "bar", + cmds => [ + qw(--execute --slave-user slave_user --slave-password slave_password), '--alter', 'ADD COLUMN bar INT', + ], +); # ############################################################################# # Done. # ############################################################################# $sb->wipe_clean($master_dbh); ok($sb->ok(), "Sandbox servers") or BAIL_OUT(__FILE__ . " broke the sandbox"); - # +# done_testing; From 26cf65015ca9ffad7fdda471983cdb9eb2ac1750 Mon Sep 17 00:00:00 2001 From: Carlos Salguero Date: Wed, 6 Jul 2016 20:41:42 -0300 Subject: [PATCH 2/2] BUG-1595678 Updated MasterSlave lib into binaries Also updated a 'SHOW PROCESSLIST' to 'SHOW FULL PROCESSLIST' because pt-kill needs more than 100 chars in the info field. --- bin/pt-archiver | 45 ++++++++++++++++++++++--------------- bin/pt-heartbeat | 45 ++++++++++++++++++++++--------------- bin/pt-kill | 43 +++++++++++++++++++++-------------- bin/pt-online-schema-change | 4 ++-- bin/pt-query-digest | 16 ++++++++++--- bin/pt-slave-find | 45 ++++++++++++++++++++++--------------- bin/pt-slave-restart | 45 ++++++++++++++++++++++--------------- bin/pt-table-checksum | 45 ++++++++++++++++++++++--------------- bin/pt-table-sync | 45 ++++++++++++++++++++++--------------- lib/MasterSlave.pm | 2 +- 10 files changed, 204 insertions(+), 131 deletions(-) diff --git a/bin/pt-archiver b/bin/pt-archiver index 445e44bc..7a1832c7 100755 --- a/bin/pt-archiver +++ b/bin/pt-archiver @@ -3505,23 +3505,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -3557,7 +3556,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -3565,7 +3565,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -3763,7 +3772,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-heartbeat b/bin/pt-heartbeat index 393aaf14..b1991b44 100755 --- a/bin/pt-heartbeat +++ b/bin/pt-heartbeat @@ -112,23 +112,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -164,7 +163,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -172,7 +172,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -370,7 +379,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-kill b/bin/pt-kill index 2915feb6..2879cb0a 100755 --- a/bin/pt-kill +++ b/bin/pt-kill @@ -3775,23 +3775,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -3827,7 +3826,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -3835,7 +3835,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } diff --git a/bin/pt-online-schema-change b/bin/pt-online-schema-change index b0fb1a15..5363d016 100755 --- a/bin/pt-online-schema-change +++ b/bin/pt-online-schema-change @@ -4111,7 +4111,7 @@ sub get_slaves { } my ($dbh, $dsn) = @args{@required_args}; my $o = $self->{OptionParser}; - + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -4326,7 +4326,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-query-digest b/bin/pt-query-digest index 39f52b79..ae33df39 100755 --- a/bin/pt-query-digest +++ b/bin/pt-query-digest @@ -10436,7 +10436,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -10444,7 +10445,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -10642,7 +10652,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-slave-find b/bin/pt-slave-find index e80a4cff..02e15dfe 100755 --- a/bin/pt-slave-find +++ b/bin/pt-slave-find @@ -2212,23 +2212,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -2264,7 +2263,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -2272,7 +2272,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -2470,7 +2479,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-slave-restart b/bin/pt-slave-restart index 3de9e51b..a0406caa 100755 --- a/bin/pt-slave-restart +++ b/bin/pt-slave-restart @@ -2623,23 +2623,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -2675,7 +2674,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -2683,7 +2683,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -2881,7 +2890,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-table-checksum b/bin/pt-table-checksum index b5892ec0..2162e508 100755 --- a/bin/pt-table-checksum +++ b/bin/pt-table-checksum @@ -5003,23 +5003,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -5055,7 +5054,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -5063,7 +5063,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -5261,7 +5270,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/bin/pt-table-sync b/bin/pt-table-sync index 9f2d1196..177c34ed 100755 --- a/bin/pt-table-sync +++ b/bin/pt-table-sync @@ -6585,23 +6585,22 @@ use warnings FATAL => 'all'; use English qw(-no_match_vars); use constant PTDEBUG => $ENV{PTDEBUG} || 0; -sub check_recursion_method { +sub check_recursion_method { my ($methods) = @_; - - if ( @$methods != 1 ) { - if ( grep({ !m/processlist|hosts/i } @$methods) - && $methods->[0] !~ /^dsn=/i ) - { - die "Invalid combination of recursion methods: " - . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " - . "Only hosts and processlist may be combined.\n" - } - } - else { + if ( @$methods != 1 ) { + if ( grep({ !m/processlist|hosts/i } @$methods) + && $methods->[0] !~ /^dsn=/i ) + { + die "Invalid combination of recursion methods: " + . join(", ", map { defined($_) ? $_ : 'undef' } @$methods) . ". " + . "Only hosts and processlist may be combined.\n" + } + } + else { my ($method) = @$methods; - die "Invalid recursion method: " . ( $method || 'undef' ) - unless $method && $method =~ m/^(?:processlist$|hosts$|none$|dsn=)/i; - } + die "Invalid recursion method: " . ( $method || 'undef' ) + unless $method && $method =~ m/^(?:processlist$|hosts$|none$|cluster$|dsn=)/i; + } } sub new { @@ -6637,7 +6636,8 @@ sub get_slaves { die "I need a $arg argument" unless $args{$arg}; } my ($dbh, $dsn) = @args{@required_args}; - + my $o = $self->{OptionParser}; + $self->recurse_to_slaves( { dbh => $dbh, dsn => $dsn, @@ -6645,7 +6645,16 @@ sub get_slaves { my ( $dsn, $dbh, $level, $parent ) = @_; return unless $level; PTDEBUG && _d('Found slave:', $dp->as_string($dsn)); - push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh); + my $slave_dsn = $dsn; + if ($o->got('slave-user')) { + $slave_dsn->{u} = $o->get('slave-user'); + PTDEBUG && _d("Using slave user ".$o->get('slave-user')." on ".$slave_dsn->{h}.":".$slave_dsn->{P}); + } + if ($o->got('slave-password')) { + $slave_dsn->{p} = $o->get('slave-password'); + PTDEBUG && _d("Slave password set"); + } + push @$slaves, $make_cxn->(dsn => $slave_dsn, dbh => $dbh); return; }, } @@ -6843,7 +6852,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); grep { $_->{command} =~ m/Binlog Dump/i } map { # Lowercase the column names diff --git a/lib/MasterSlave.pm b/lib/MasterSlave.pm index 5f51a456..406c5259 100644 --- a/lib/MasterSlave.pm +++ b/lib/MasterSlave.pm @@ -352,7 +352,7 @@ sub get_connected_slaves { die "You do not have the PROCESS privilege"; } - $sql = 'SHOW PROCESSLIST'; + $sql = 'SHOW FULL PROCESSLIST'; PTDEBUG && _d($dbh, $sql); # It's probably a slave if it's doing a binlog dump. grep { $_->{command} =~ m/Binlog Dump/i }