PT-1852 Added --no-check-foreing-keys to pt-osc

This commit is contained in:
Carlos Salguero
2020-06-21 18:53:47 -03:00
parent 89440c1ad1
commit c6b4bd747e
3 changed files with 131 additions and 0 deletions

View File

@@ -9102,6 +9102,15 @@ sub main {
$child_table->{name},
$child_table->{row_est} || '?';
}
# TODO: Fix self referencing foreign keys handling.
# See: https://jira.percona.com/browse/PT-1802
# https://jira.percona.com/browse/PT-1853
if (has_self_ref_fks($orig_tbl->{db}, $orig_tbl->{tbl}, $child_tables) and $o->get('check-foreign-keys')) {
print "The table has self referencing foreign keys and that might lead to errors.\n";
print "Use --no-check-foreign-keys to disable this check.\n";
return 1
}
if ( $alter_fk_method ) {
# Let the user know how we're going to update the child table
@@ -10396,6 +10405,20 @@ sub check_alter {
return;
}
sub has_self_ref_fks {
my ($orig_db, $orig_table, $child_tables) = @_;
my $db_tbl = sprintf("`%s`.`%s`", $orig_db, $orig_table);
foreach my $child_table ( @$child_tables ) {
if ($db_tbl eq $child_table->{name}) {
return 1;
}
};
return undef;
}
# This function tries to detect if the --alter param is adding unique indexes.
# It returns an array of arrays, having a list of fields for each unique index
# found.
@@ -12168,6 +12191,15 @@ L<"--print"> and verify that the triggers are correct.
=back
=item --[no]check-foreign-keys
default: yes
Check for self referencing foreing keys. Currently self referencing FKs are
not fully supported so to prevent errors, this program wont't run if the table
has self referen foreign keys. Use this parameter to disable self referencing
FK checks.
=item --check-interval
type: time; default: 1

View File

@@ -0,0 +1,80 @@
#!/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 threads;
use threads::shared;
use Thread::Semaphore;
use English qw(-no_match_vars);
use Test::More;
use Data::Dumper;
use PerconaTest;
use Sandbox;
use SqlModes;
use File::Temp qw/ tempdir /;
require "$trunk/bin/pt-online-schema-change";
plan tests => 3;
my $dp = new DSNParser(opts=>$dsn_opts);
my $sb = new Sandbox(basedir => '/tmp', DSNParser => $dp);
my $master_dbh = $sb->get_dbh_for("master");
my $master_dsn = $sb->dsn_for("master");
# 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.
my @args = (qw(--set-vars innodb_lock_wait_timeout=3));
my $output;
my $exit_status;
$sb->load_file('master', "t/pt-online-schema-change/samples/pt-1853.sql");
($output, $exit_status) = full_output(
sub { pt_online_schema_change::main(@args, "$master_dsn,D=test,t=jointit",
'--execute',
'--alter', "engine=innodb",
'--alter-foreign-keys-method', 'rebuild_constraints'
),
},
stderr => 1,
);
isnt(
$exit_status,
0,
"PT-1853, there are self referencing FKs -> exit status != 0",
);
($output, $exit_status) = full_output(
sub { pt_online_schema_change::main(@args, "$master_dsn,D=test,t=jointit",
'--execute',
'--alter', "engine=innodb",
'--alter-foreign-keys-method', 'rebuild_constraints',
'--no-check-foreign-keys'
),
},
stderr => 1,
);
isnt(
$exit_status,
0,
"PT-1853, there are self referencing FKs but --no-check-foreign-keys was specifid -> exit status = 0",
);
# #############################################################################
# Done.
# #############################################################################
$sb->wipe_clean($master_dbh);
ok($sb->ok(), "Sandbox servers") or BAIL_OUT(__FILE__ . " broke the sandbox");
done_testing;

View File

@@ -0,0 +1,19 @@
DROP DATABASE IF EXISTS test;
CREATE DATABASE test;
USE test;
CREATE TABLE t1 (
id int,
f1 int
);
CREATE TABLE `joinit` (
`i` int(11) NOT NULL AUTO_INCREMENT,
`s` varchar(64) DEFAULT NULL,
`t` time NOT NULL,
`g` int(11) NOT NULL,
`j` int(11) NOT NULL DEFAULT 1,
PRIMARY KEY (`i`))
ENGINE=InnoDB;
ALTER TABLE joinit ADD FOREIGN KEY i_fk (j) REFERENCES joinit (i) ON UPDATE cascade ON DELETE restrict;