--source include/have_ndb.inc

--echo # Init for ndb_show_tables result
CREATE TEMPORARY TABLE IF NOT EXISTS ndb_show_tables_results (
  id INT,
  type VARCHAR(20),
  state VARCHAR(20),
  logging VARCHAR(20),
  _database VARCHAR(255),
  _schema VARCHAR(20),
  name VARCHAR(255)
);

--echo #
--echo # Create child tables before parents
--echo # by turning off foreign_key_checks for this session
--echo #
select @@foreign_key_checks;
set @@foreign_key_checks=0;

create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references t2(pk1)
) engine=ndb;

create table t3 (
  pk int not null primary key,
  b int, c int,
  d int, e int, f int,
  g int, h int, i int, j int,
  foreign key (b, c) references t4(pk1, pk2),
  foreign key (d, e, f) references t5(uk1, uk2, uk3),
  foreign key (g, h, i, j) references t6(oi1, oi2, oi3, oi4)
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be 4 mock tables created
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

let $id_t1 = `select id from ndb_show_tables_results where name = "'t1'"`;
--echo # There should be 1 mock table created for t1
--replace_result $id_t1 <id>
eval select type, name from ndb_show_tables_results
  where name like "'NDB\$FKM_$id_t1%'";

let $id_t3 = `select id from ndb_show_tables_results where name = "'t3'"`;
--echo # There should be 3 mock tables created for t3
--replace_result $id_t3 <id>
eval select type, name from ndb_show_tables_results
  where name like "'NDB\$FKM_$id_t3%'" order by name;

drop table t3;

--source ndb_show_tables_result.inc

--echo # There should be 1 mock table
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Only t1 should have 1 mock table
--replace_result $id_t1 <id>
eval select type, name from ndb_show_tables_results
  where name like "'NDB\$FKM_$id_t1%'";

drop table t1;

--echo # There should be 0 mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo #
--echo # Create child table before parent
--echo # by turning off foreign_key_checks for this session
--echo #

create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references t2(pk1)
) engine=ndb;

create table t2 (
  pk1 int not null primary key,
  c int
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be 0 mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Verify that fk is working now when parent has been resolved
set foreign_key_checks=1;
--error ER_NO_REFERENCED_ROW_2
insert into t1 values(1, 2);
set foreign_key_checks=0;

drop table t1, t2;


--echo #
--echo # Exceed table name when creating the mock table by referencing
--echo # a not yet created table with really long name
--echo #

--echo # 1) By blowing the mock_tabname buffer(currently 512 bytes)
let $parent_tabname = `select repeat('abcdefghijklmnopqrstuvxyz_', 20)`;
--error ER_CANNOT_ADD_FOREIGN
eval create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references $parent_tabname(pk1)
) engine=ndb;
show warnings;

#
# Disabled for now, NdbApi fails to fetch the table from NDB and
# claims "283 table is being dropped". This looks like some problem in NdbApi
# (search for DBUG_PRINT with text "dropped by another thread")
#--echo # 2) By blowing the max tabname length in NDB
#let $parent_tabname = `select repeat('abcdefghijklmnopqrstuvxyz_', 15)`;
#--error ER_CANNOT_ADD_FOREIGN
#eval create table t1 (
#  pk int not null primary key,
#  b int,
#  foreign key (b) references $parent_tabname(pk1)
#) engine=ndb;
#show warnings;


--echo #
--echo # show create of table with mock table references
--echo #
create table t1 (
  a int not null,
  b int not null,
  c int not null,
  primary key (a),
  unique key (b) using hash,
  key (c),
  constraint fk1 foreign key(a) references t2 (a),
  constraint fk2 foreign key(b) references t3 (a),
  constraint fk3 foreign key(c) references t4 (a),
  constraint fk4 foreign key(a) references t2 (b),
  constraint fk5 foreign key(b) references t3 (b),
  constraint fk6 foreign key(c) references t4 (b)
) engine=ndbcluster;

show create table t1;

create table t2 (
  a int primary key,
  b int not null,
  c int not null,
  unique(b) using hash,
  index(c)
) engine = ndb;

show create table t1;

set @@ndb_show_foreign_key_mock_tables= 1;
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
show create table t1;
set @@ndb_show_foreign_key_mock_tables= 0;

drop table t1, t2;


--echo #
--echo # Create child table and then the parent
--echo # which does not match the fk
--echo #

# Suppress the warning this test case generates
--disable_query_log ONCE
call mtr.add_suppression("NDB FK: .* have all the referenced columns");

create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references t2(pk1)
) engine=ndb;

create table t2 (
  pk2 int not null primary key,
  c int
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be 1 mock table still
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t1, t2;

--echo #
--echo # Create child table and then the parent
--echo # which does not match any index
--echo #

# Suppress the warning this test case generates
--disable_query_log ONCE
call mtr.add_suppression("NDB FK: .* no matching index could be found");

create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references t2(c)
) engine=ndb;

create table t2 (
  pk1 int not null primary key,
  c int
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be 1 mock table still
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t1, t2;

# Turn on ndb_show_foreign_key_mock_tables to get more info about
# when creating and dropping mock tables
set @@ndb_show_foreign_key_mock_tables= 1;

--echo #
--echo # Test where FK goes from t1->t2->t3->t4 and tables are created in that order

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t1 (
  pk11 int not null primary key,
  b int,
  foreign key (b) references t2(pk21)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table t2 (
  pk21 int not null primary key,
  b int, c int,
  foreign key (b, c) references t3(pk31, pk32)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table t3 (
  pk31 int not null,
  pk32 int not null,
  primary key(pk31, pk32),
  d int, e int,f int,
  foreign key (d,e,f) references t4(pk41, pk42, pk43)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t4 (
  pk41 int not null,
  pk42 int not null,
  pk43 int not null,
  primary key(pk41, pk42, pk43),
  m varchar(55)
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t1, t2, t3, t4;


--echo #
--echo # Test where FK 'fans out' t1->t2 t1->t3 t1->t4, create t1 first

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table t1 (
  pk11 int not null primary key,
  b int,
  foreign key (b) references t2(c),
  d int, e int,
  foreign key (d, e) references t3(f, g),
  h varchar(55), i int, j datetime,
  foreign key (h, i, j) references t4(k, l, m)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t2 (
  pk21 int not null primary key,
  c int,
  unique(c)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t3 (
  pk31 int not null,
  pk32 int not null,
  primary key(pk31, pk32),
  g int, f int,
  unique(f, g)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t4 (
  pk41 int not null,
  pk42 int not null,
  pk43 int not null,
  primary key(pk41, pk42, pk43),
  m varchar(55), l int, k datetime,
  unique(k, l, m)
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t1, t2, t3, t4;

--echo #
--echo # Test where FK refers to 2+ different indices in parent t1->t2(1) t1->t2(2)

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table t1 (
  pk11 int not null primary key,
  foreign key (pk11) references t2(pk21),
  b int,
  foreign key (b) references t2(c),
  d int, e int,
  foreign key (d, e) references t2(f, g),
  h varchar(55), i int, j datetime,
  foreign key (h, i, j) references t2(k, l, m)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table t2 (
  pk21 int not null primary key,
  c int,
  unique(c),
  g int, f int,
  unique(f, g),
  m varchar(55), l int, k datetime,
  unique(k, l, m)
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t1, t2;


--echo #
--echo # Test drop of referenced table(mock table should be created)
--echo #

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t1 (
  pk1 int not null primary key,
  foreign key (pk1) references t2(pk2),
  a varchar(255)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table t2 (
  pk2 int not null primary key,
  b datetime
) engine=ndb;

--source ndb_show_tables_result.inc

--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
drop table t2;

--source ndb_show_tables_result.inc

let $id_t1 = `select id from ndb_show_tables_results where name = "'t1'"`;
--echo # There should be 1 mock table created for t1
--replace_result $id_t1 <id>
eval select type, name from ndb_show_tables_results
  where name like "'NDB\$FKM_$id_t1%'";

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
drop table t1;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

# Turn off ndb_show_foreign_key_mock_tables again
set @@ndb_show_foreign_key_mock_tables= 0;


--echo #
--echo # Test mock tables in different databases, mock table
--echo # should be created in same database as the real parent would.
--echo #

set @@ndb_show_foreign_key_mock_tables= 1;

create database mydb0;
create database mydb1;

# Create child referencing parent in different db
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table mydb1.t1 (
  a int primary key,
  constraint fk1 foreign key(a) references mydb0.t2(a)
) engine = ndb;

--source ndb_show_tables_result.inc
let $id_t1 = `select id from ndb_show_tables_results
  where _database = "'mydb1'" and name = "'t1'"`;
--echo # There should be 1 mock table created for t1
--replace_result $id_t1 <id>
eval select type, _database, name from ndb_show_tables_results
  where name like "'NDB\$FKM_$id_t1%'";

# Drop child table, should also remove the mock table
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
drop table mydb1.t1;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

# Create child again
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table mydb1.t1 (
  a int primary key,
  constraint fk1 foreign key(a) references mydb0.t2(a)
) engine = ndb;

# And the parent
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table mydb0.t2 (
  a int primary key
) engine = ndb;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Drop child then parent
drop table mydb1.t1;
drop table mydb0.t2;

# Create child again
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table mydb1.t1 (
  a int primary key,
  constraint fk1 foreign key(a) references mydb0.t2(a)
) engine = ndb;

# And the parent
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table mydb0.t2 (
  a int primary key
) engine = ndb;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Drop parent then child(creates mock which is then dropped)
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
drop table mydb0.t2;
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
drop table mydb1.t1;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo #
--echo # Create spagetthi foreign keys between tables in three different databases
--echo #
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references mydb1.t2(pk1),
  c int,
  unique(c),
  j int,
  foreign key (j) references mydb0.t3(pk2),
  k int,
  foreign key (k) references mydb0.t1(pk5),
  l int,
  foreign key (l) references mydb1.t1(pk6),
  y int,
  foreign key (y) references mydb1.t1(z)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table mydb1.t2 (
  pk1 int not null primary key,
  d int,
  foreign key (d) references mydb0.t3(pk2)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table mydb0.t3 (
  pk2 int not null primary key,
  e int,
  foreign key (e) references test.t1(c)
) engine=ndb;

create table mydb0.t4 (
  pk3 int not null primary key,
  f int,
  foreign key (f) references t3(pk2)
) engine=ndb;

create table mydb0.t5 (
  pk4 int not null primary key,
  g int,
  foreign key (g) references test.t1(pk),
  h int,
  foreign key (h) references mydb1.t2(pk1),
  i int,
  foreign key (i) references mydb0.t3(pk2)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
create table mydb0.t1 (
  pk5 int not null primary key,
  m int,
  foreign key (m) references test.t1(pk),
  n int,
  foreign key (n) references mydb1.t2(pk1),
  o int,
  foreign key (o) references mydb0.t3(pk2)
) engine=ndb;

--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
--sorted_result
create table mydb1.t1 (
  pk6 int not null primary key,
  p int,
  foreign key (p) references test.t1(pk),
  q int,
  foreign key (q) references mydb1.t2(pk1),
  x int,
  foreign key (x) references mydb0.t3(pk2),
  z int,
  unique(z)
) engine=ndb;

set @@ndb_show_foreign_key_mock_tables= 0;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Drop the database mydb0 with all tables still there
drop database mydb0;

--source ndb_show_tables_result.inc
--echo # There should be 4 mock tables created by dropping mydb0
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Drop also database mydb1
drop database mydb1;

--source ndb_show_tables_result.inc
--echo # There should be 5 mock tables all referenced by test.t1
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo # Drop t1 and the 5 remaining mocks
drop table t1;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";


--echo #
--echo # ALTER a table which references mock parent
--echo #

create table t1 (
  pk int not null primary key,
  b int,
  foreign key (b) references t2(pk1)
) engine=ndb;

--source ndb_show_tables_result.inc
--echo # There should be one mock table in place of t2
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
select name from ndb_show_tables_results where name like "'NDB\$FKM%'";

alter table t1 add column c int;

--source ndb_show_tables_result.inc
--echo # There should be one mock table still
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
select name from ndb_show_tables_results where name like "'NDB\$FKM%'";

alter table t1 algorithm = copy, add column d int not null;

--source ndb_show_tables_result.inc
--echo # There should be one mock table still
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
select name from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t1;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";


--echo #
--echo # Alter table to add foreign keys referencing non existing parents. One
--echo # new mock should be created per fk
--echo #

create table child (
  a int primary key auto_increment,
  b int not null,
  c int not null,
  unique(b) using hash,
  index(c)
) engine = ndb;

alter table child algorithm=inplace, add constraint fk1 foreign key (a) references parent(a);
alter table child algorithm=inplace, add constraint fk2 foreign key (b) references parent(col1);
alter table child algorithm=inplace, add constraint fk3 foreign key (c) references parent(col2);
alter table child algorithm=inplace,
  add constraint fk4 foreign key (c) references parent(col3),
  add constraint fk5 foreign key (c) references parent(col4),
  add constraint fk6 foreign key (c) references parent(col5);

--source ndb_show_tables_result.inc
--echo # There should be 6 mock tables
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
select name from ndb_show_tables_results where name like "'NDB\$FKM%'";

alter table child algorithm=inplace, drop foreign key fk1;

--source ndb_show_tables_result.inc
--echo # There should be 5 mock tables
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
select name from ndb_show_tables_results where name like "'NDB\$FKM%'";

alter table child algorithm=inplace,
  drop foreign key fk3,
  drop foreign key fk4,
  drop foreign key fk6;

--source ndb_show_tables_result.inc
--echo # There should be 2 mock tables left
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
select name from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table child;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

--echo #
--echo # Alter table into place(i.e rename) as new parent, should remove
--echo # the mock table
--echo #

create table t1 (
  pk1 int not null primary key,
  b int,
  foreign key (b) references t2(pk2)
) engine=ndb;

create table t3 (
  pk2 int not null primary key,
  b int
) engine=ndb;

--source ndb_show_tables_result.inc
--echo # There should be one mock table for t1
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

set @@ndb_show_foreign_key_mock_tables= 1;
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
alter table t3 rename t2;
set @@ndb_show_foreign_key_mock_tables= 0;

# Rename table referenced by foreign key -> t1 references t3
alter table t2 rename t3;
--replace_regex /(FK|fk)_[0-9]+_[0-9]+/FK_<child_id>_<id>/
show create table t1;

drop table t3;
create table t2 (
  pk2 int not null primary key,
  b int
) engine=ndb;

--source ndb_show_tables_result.inc
--echo # There should be one mock table for t1
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

set @@ndb_show_foreign_key_mock_tables= 1;
--replace_regex /FKM_[0-9]+_[0-9]+_/FKM_<child_id>_<id>_/
alter table t2 algorithm=inplace, rename t3;
set @@ndb_show_foreign_key_mock_tables= 0;

--source ndb_show_tables_result.inc
--echo # There should be no mock tables
select count(*) from ndb_show_tables_results where name like "'NDB\$FKM%'";

drop table t3, t1;


--echo #
--echo # Truncating table which references mock table
--echo #
create table t1 (
  pk1 int not null primary key,
  b int,
  foreign key fk1 (b) references t2(pk2)
) engine=ndb;

set foreign_key_checks=1;
truncate table t1;
set foreign_key_checks=0;

set @@ndb_show_foreign_key_mock_tables= 1;
truncate table t1;
set @@ndb_show_foreign_key_mock_tables= 0;

show create table t1;

drop table t1;


--echo #
--echo # Truncating referenced table -> not allowed
--echo #
create table t2 (
  pk2 int not null primary key,
  c int
) engine=ndb;
create table t1 (
  pk1 int not null primary key,
  b int,
  foreign key (b) references t2(pk2)
) engine=ndb;

set foreign_key_checks=1;
--error ER_TRUNCATE_ILLEGAL_FK
truncate table t2;
set foreign_key_checks=0;

--error ER_TRUNCATE_ILLEGAL_FK
truncate table t2;

drop table t1, t2;


--echo #
--echo # Truncating referenced table which references
--echo # another table -> not allowed
--echo #
create table t3 (
  pk3 int not null primary key,
  d int
) engine=ndb;
create table t2 (
  pk2 int not null primary key,
  c int,
  foreign key (c) references t3(pk3)
) engine=ndb;
create table t1 (
  pk1 int not null primary key,
  b int,
  foreign key (b) references t2(pk2)
) engine=ndb;

set foreign_key_checks=1;
--error ER_TRUNCATE_ILLEGAL_FK
truncate table t2;
set foreign_key_checks=0;

--error ER_TRUNCATE_ILLEGAL_FK
truncate table t2;

drop table t1, t2, t3;


--echo #
--echo # Truncating referencing table
--echo #
create table t2 (
  pk2 int not null primary key,
  c int
) engine=ndb;
create table t1 (
  pk1 int not null primary key,
  b int,
  foreign key fk1 (b) references t2(pk2)
) engine=ndb;

set @@ndb_show_foreign_key_mock_tables= 1;
set foreign_key_checks=1;
truncate table t1;
set foreign_key_checks=0;

truncate table t1;
set @@ndb_show_foreign_key_mock_tables= 0;

show create table t1;

drop table t1, t2;

--echo #
--echo # Truncate with multiple foreign keys
--echo #
create table t2 (
  pk2 int not null primary key,
  c int
) engine=ndb;
create table t1 (
  pk1 int not null primary key,
  b int,
  c int,
  d int,
  e int,
  foreign key fk1 (b) references t2(pk2),
  foreign key fk2 (c) references t3(pk3),
  foreign key fk3 (d) references t3(pk4),
  foreign key fk4 (e) references t4(pk5)
) engine=ndb;

set @@ndb_show_foreign_key_mock_tables= 1;
set foreign_key_checks=1;
truncate table t1;
set foreign_key_checks=0;

truncate table t1;
set @@ndb_show_foreign_key_mock_tables= 0;

show create table t1;

drop table t1, t2;

--echo #
--echo # Create child table referencing mock parent, insert data and
--echo # then create the real parent (like mysqldump does it)
--echo #
CREATE TABLE `address` (
  `no` int(11) NOT NULL AUTO_INCREMENT,
  `type` int(11) NOT NULL DEFAULT '37',
  `customer_id` int(11) NOT NULL,
  `street` varchar(255) DEFAULT NULL,
  `country` int(11) DEFAULT NULL,
  PRIMARY KEY (`no`),
  KEY `ca_fk1` (`customer_id`),
  CONSTRAINT `ca_fk1` FOREIGN KEY(`customer_id`) REFERENCES `customer` (`id`)
    ON DELETE CASCADE ON UPDATE RESTRICT
) ENGINE=ndbcluster AUTO_INCREMENT=2 DEFAULT CHARSET=latin1;

INSERT INTO `address` VALUES (1,37,1,'Main st. 1215',48);

CREATE TABLE `customer` (
  `id` int(11) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=ndbcluster DEFAULT CHARSET=latin1;

--echo # Check DML
insert into address (type, customer_id, street, country)
  values (38,2,'Second st. 2326',49 );
insert into address (type, customer_id, street, country)
  values (39,1,'Third st. 3437',50 );
update address set country=50 where no=2;
# Add a valid customer for first address
insert into customer values(1);

--echo # Check DML with foreign_key_checks on
set foreign_key_checks=1;

# Try to point first address to another customer which does not exists
--error ER_NO_REFERENCED_ROW_2
update address set customer_id = 3 where no = 1;

# Delete first customer, should delete two rows from address -> one remaining
delete from customer where id = 1;
select no, type, customer_id from address;

set foreign_key_checks=0;

drop table address, customer;


--echo #
--echo # Create child table referencing real parent, insert data
--echo # and then create fk(like mysqldump does not do it)
--echo #
CREATE TABLE `customer` (
  `id` int(11) NOT NULL,
  PRIMARY KEY (`id`)
) ENGINE=ndbcluster DEFAULT CHARSET=latin1;

INSERT INTO `customer` VALUES (1);

CREATE TABLE `address` (
  `no` int(11) NOT NULL AUTO_INCREMENT,
  `type` int(11) NOT NULL DEFAULT '37',
  `customer_id` int(11) NOT NULL,
  `street` varchar(255) DEFAULT NULL,
  `country` int(11) DEFAULT NULL,
  PRIMARY KEY (`no`),
  KEY `ca_fk1` (`customer_id`)
) ENGINE=ndbcluster AUTO_INCREMENT=2 DEFAULT CHARSET=latin1;

# Insert record pointing at existing customer
INSERT INTO `address` VALUES (1,37,1,'Main st. 1215',48);

# Insert record pointing at _non_ existing customer
INSERT INTO `address` VALUES (2,22,2,'Second st. 2222',2);

--echo # Add fk inplace
# Adding foreign key with foreign_key_checks=1, fails since data is inconsistent
set foreign_key_checks=1;
--error ER_NO_REFERENCED_ROW_2
ALTER TABLE address ALGORITHM=inplace,
  ADD CONSTRAINT `ca_fk1` FOREIGN KEY(`customer_id`) REFERENCES `customer` (`id`)
    ON DELETE CASCADE ON UPDATE RESTRICT;
set foreign_key_checks=0;

# Turn off foreign_key_checks and create the fk anyway
ALTER TABLE address ALGORITHM=inplace,
  ADD CONSTRAINT `ca_fk1` FOREIGN KEY(`customer_id`) REFERENCES `customer` (`id`)
    ON DELETE CASCADE ON UPDATE RESTRICT;

--echo # Add another fk copying
# Adding foreign key with foreign_key_checks=1, fails since data is inconcistent
set foreign_key_checks=1;
--error ER_NO_REFERENCED_ROW_2
ALTER TABLE address ALGORITHM=copy,
  ADD CONSTRAINT `ca_fk2` FOREIGN KEY(`customer_id`) REFERENCES `customer` (`id`)
    ON DELETE CASCADE ON UPDATE RESTRICT;
set foreign_key_checks=0;

# Turn off foreign_key_checks and create the fk anyway.
ALTER TABLE address ALGORITHM=copy,
  ADD CONSTRAINT `ca_fk2` FOREIGN KEY(`customer_id`) REFERENCES `customer` (`id`)
    ON DELETE CASCADE ON UPDATE RESTRICT;

# Some more alters to exercise the "copy fk functions"
ALTER TABLE address ALGORITHM=inplace,
  ADD COLUMN a int COLUMN_FORMAT DYNAMIC;
ALTER TABLE address ALGORITHM=copy,
  ADD COLUMN b int not null;

--echo # Check DML with foreign_key_checks on
set foreign_key_checks=1;

# Try to point first address to another customer which does not exists
--error ER_NO_REFERENCED_ROW_2
update address set customer_id = 3 where no = 1;

# Point second address to first customer
update address set customer_id = 1 where no = 2;

# Delete customer, should delete two rows from address -> table empty
delete from customer where id = 1;
select count(*) from address;

set foreign_key_checks=0;

drop table address, customer;

