Rewrite how MasterSlave handles --recursion-methods.

This commit is contained in:
Daniel Nichter
2012-08-02 10:57:36 -06:00
parent e29aa514e3
commit e6d31a666a
11 changed files with 961 additions and 801 deletions

View File

@@ -1872,66 +1872,6 @@ use warnings FATAL => 'all';
use English qw(-no_match_vars);
use constant PTDEBUG => $ENV{PTDEBUG} || 0;
sub new {
my ( $class, %args ) = @_;
my $self = {
%args,
replication_thread => {},
};
return bless $self, $class;
}
sub get_slaves {
my ($self, %args) = @_;
my @required_args = qw(make_cxn recursion_method recurse DSNParser Quoter);
foreach my $arg ( @required_args ) {
die "I need a $arg argument" unless exists $args{$arg};
}
my ($make_cxn, $methods, $recurse, $dp) = @args{@required_args};
my $slaves = [];
PTDEBUG && _d('Slave recursion method:', $methods);
if ( !@$methods || grep { m/processlist|hosts/i } @$methods ) {
my @required_args = qw(dbh dsn);
foreach my $arg ( @required_args ) {
die "I need a $arg argument" unless $args{$arg};
}
my ($dbh, $dsn) = @args{@required_args};
$self->recurse_to_slaves(
{ dbh => $dbh,
dsn => $dsn,
dsn_parser => $dp,
recurse => $recurse,
method => $methods,
callback => sub {
my ( $dsn, $dbh, $level, $parent ) = @_;
return unless $level;
PTDEBUG && _d('Found slave:', $dp->as_string($dsn));
push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh);
return;
},
}
);
}
elsif ( @$methods && $methods->[0] =~ m/^dsn=/i ) {
(my $dsn_table_dsn = join ",", @$methods) =~ s/^dsn=//i;
$slaves = $self->get_cxn_from_dsn_table(
%args,
dsn_table_dsn => $dsn_table_dsn,
);
}
elsif ( !@$methods || $methods->[0] =~ m/none/i ) {
PTDEBUG && _d('Not getting to slaves');
}
else {
die "Unexpected recursion methods: @$methods";
}
return $slaves;
}
sub check_recursion_method {
my ($methods) = @_;
@@ -1951,13 +1891,93 @@ sub check_recursion_method {
}
}
sub new {
my ( $class, %args ) = @_;
my @required_args = qw(OptionParser DSNParser Quoter);
foreach my $arg ( @required_args ) {
die "I need a $arg argument" unless $args{$arg};
}
my $self = {
%args,
replication_thread => {},
};
return bless $self, $class;
}
sub get_slaves {
my ($self, %args) = @_;
my @required_args = qw(make_cxn);
foreach my $arg ( @required_args ) {
die "I need a $arg argument" unless $args{$arg};
}
my ($make_cxn) = @args{@required_args};
my $slaves = [];
my $dp = $self->{DSNParser};
my $methods = $self->_resolve_recursion_methods($args{dsn});
if ( grep { m/processlist|hosts/i } @$methods ) {
my @required_args = qw(dbh dsn);
foreach my $arg ( @required_args ) {
die "I need a $arg argument" unless $args{$arg};
}
my ($dbh, $dsn) = @args{@required_args};
$self->recurse_to_slaves(
{ dbh => $dbh,
dsn => $dsn,
callback => sub {
my ( $dsn, $dbh, $level, $parent ) = @_;
return unless $level;
PTDEBUG && _d('Found slave:', $dp->as_string($dsn));
push @$slaves, $make_cxn->(dsn => $dsn, dbh => $dbh);
return;
},
}
);
}
elsif ( $methods->[0] =~ m/^dsn=/i ) {
(my $dsn_table_dsn = join ",", @$methods) =~ s/^dsn=//i;
$slaves = $self->get_cxn_from_dsn_table(
%args,
dsn_table_dsn => $dsn_table_dsn,
);
}
elsif ( $methods->[0] =~ m/none/i ) {
PTDEBUG && _d('Not getting to slaves');
}
else {
die "Unexpected recursion methods: @$methods";
}
return $slaves;
}
sub _resolve_recursion_methods {
my ($self, $dsn) = @_;
my $o = $self->{OptionParser};
if ( $o->got('recursion-method') ) {
return $o->get('recursion-method');
}
elsif ( $dsn && ($dsn->{P} || 3306) != 3306 ) {
PTDEBUG && _d('Port number is non-standard; using only hosts method');
return [qw(hosts)];
}
else {
return $o->get('recursion-method');
}
}
sub recurse_to_slaves {
my ( $self, $args, $level ) = @_;
$level ||= 0;
my $dp = $args->{dsn_parser};
my $dsn = $args->{dsn};
my $dp = $self->{DSNParser};
my $recurse = $args->{recurse} || $self->{OptionParser}->get('recurse');
my $dsn = $args->{dsn};
if ( $args->{method} && lc($args->{method}->[0] || '') eq 'none' ) {
my $methods = $self->_resolve_recursion_methods($dsn);
PTDEBUG && _d('Recursion methods:', @$methods);
if ( lc($methods->[0]) eq 'none' ) {
PTDEBUG && _d('Not recursing to slaves');
return;
}
@@ -1992,11 +2012,11 @@ sub recurse_to_slaves {
$args->{callback}->($dsn, $dbh, $level, $args->{parent});
if ( !defined $args->{recurse} || $level < $args->{recurse} ) {
if ( !defined $recurse || $level < $recurse ) {
my @slaves =
grep { !$_->{master_id} || $_->{master_id} == $id } # Only my slaves.
$self->find_slave_hosts($dp, $dbh, $dsn, $args->{method});
$self->find_slave_hosts($dp, $dbh, $dsn, $methods);
foreach my $slave ( @slaves ) {
PTDEBUG && _d('Recursing from',
@@ -2010,14 +2030,12 @@ sub recurse_to_slaves {
sub find_slave_hosts {
my ( $self, $dsn_parser, $dbh, $dsn, $methods ) = @_;
my @methods = $self->_resolve_recursion_methods($methods, $dsn);
PTDEBUG && _d('Looking for slaves on', $dsn_parser->as_string($dsn),
'using methods', @methods);
'using methods', @$methods);
my @slaves;
METHOD:
foreach my $method ( @methods ) {
foreach my $method ( @$methods ) {
my $find_slaves = "_find_slaves_by_$method";
PTDEBUG && _d('Finding slaves with', $find_slaves);
@slaves = $self->$find_slaves($dsn_parser, $dbh, $dsn);
@@ -2028,15 +2046,6 @@ sub find_slave_hosts {
return @slaves;
}
sub _resolve_recursion_methods {
my ($self, $methods, $dsn) = @_;
return @$methods if $methods && @$methods;
return qw( processlist hosts ) if (($dsn->{P} || 3306) == 3306);
PTDEBUG && _d('Port number is non-standard; using only hosts method');
return qw( hosts );
}
sub _find_slaves_by_processlist {
my ( $self, $dsn_parser, $dbh, $dsn ) = @_;
@@ -2529,13 +2538,16 @@ sub reset_known_replication_threads {
sub get_cxn_from_dsn_table {
my ($self, %args) = @_;
my @required_args = qw(dsn_table_dsn make_cxn DSNParser Quoter);
my @required_args = qw(dsn_table_dsn make_cxn);
foreach my $arg ( @required_args ) {
die "I need a $arg argument" unless $args{$arg};
}
my ($dsn_table_dsn, $make_cxn, $dp, $q) = @args{@required_args};
my ($dsn_table_dsn, $make_cxn) = @args{@required_args};
PTDEBUG && _d('DSN table DSN:', $dsn_table_dsn);
my $dp = $self->{DSNParser};
my $q = $self->{Quoter};
my $dsn = $dp->parse($dsn_table_dsn);
my $dsn_table;
if ( $dsn->{D} && $dsn->{t} ) {
@@ -3383,16 +3395,15 @@ sub main {
# Despite the name, recursing to slaves actually begins at the specified
# server, so the named server may also be included.
my $ms = new MasterSlave();
my $ms = new MasterSlave(
OptionParser => $o,
DSNParser => $dp,
Quoter => $q,
);
$ms->recurse_to_slaves(
{ dbh => $dbh,
dsn => $master_dsn,
dsn_parser => $dp,
recurse => $o->get('recurse'),
method => $o->got('recursion-method')
? $o->get('recursion-method')
: [],
callback => sub {
{ dbh => $dbh,
dsn => $master_dsn,
callback => sub {
my ( $dsn, $dbh, $level, $parent ) = @_;
if ( !$parent ) {
$root = $dsn;