#!/usr/bin/env bats load $BATS_TEST_DIRNAME/helper/common.bash setup() { setup_common dolt sql <" ]] || false dolt sql -q "insert into test (pk,c0,c1,c2,c3,c4,c5) values (0,0,0,0,0,0,0)" run dolt diff [ "$status" -eq 0 ] [[ "$output" =~ "| c0" ]] || false [[ "$output" =~ "+ | 0" ]] || false dolt sql -q "alter table test drop column c0" dolt diff } @test "schema-changes: dolt diff on schema changes rename primary key" { dolt add test dolt commit -m "committed table so we can see diffs" dolt sql -q "alter table test rename column pk to pk1" run dolt diff [ "$status" -eq 0 ] [[ "$output" =~ "pk1" ]] || false } @test "schema-changes: adding and dropping column should produce no diff" { dolt add test dolt commit -m "committed table so we can see diffs" dolt sql -q "alter table test add c0 bigint" dolt sql -q "alter table test drop column c0" run dolt diff [ "$status" -eq 0 ] [ "$output" = "" ] } @test "schema-changes: schema diff should show primary keys in output" { dolt add test dolt commit -m "committed table so we can see diffs" dolt sql -q 'alter table test rename column c2 to column2' run dolt diff --schema [ "$status" -eq 0 ] [[ "$output" =~ "PRIMARY KEY" ]] || false } @test "schema-changes: changing column does not allow nulls in primary key" { dolt sql < | 1 | 1 | NULL | | < | 2 | 2 | 2 | | > | 2 | 2 | NULL | +---+-----+-----+------+ EOF ) [[ "$output" =~ "$EXPECTED" ]] || false } # We passed nil where a sql ctx was expected in merge. When we added # collations, the sql ctx became required and merge started to panic. @test "schema-changes: regression test for merging check constraints with TEXT type panicking due to a nil sql ctx" { dolt sql -q "create table t (pk int primary key, col1 text);" dolt commit -Am "initial" dolt branch right dolt sql -q "insert into t values (1, 'valid');" dolt commit -am "row" dolt checkout right dolt sql -q "alter table t add constraint col1_check CHECK (col1 = 'valid');" dolt commit -am "add check" dolt checkout main dolt merge -m "merge" right run dolt sql -q "show create table t;" [ $status -eq 0 ] [[ $output =~ "CHECK ((\`col1\` = 'valid'))" ]] || false } @test "schema-changes: assert that schema changes don't rewrite the table when they don't need to" { dolt sql -q "create table t (pk int primary key, e enum('a', 'b', 'c'), s set('a', 'b', 'c'), c char(10), vc varchar(10), b binary(10), vb varbinary(10));" dolt sql -q "insert into t values (1, 'a', 'a,b', 'c', 'vc', 'b', 'vb');" dolt commit -Am "initial" # First check that DOLT_TEST_ASSERT_NO_TABLE_REWRITE does prevent schema changes that *do* require a table rewrite. # Although some of these operations don't change any rows, determining this requires an attempted rewrite that scans the table. run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column e enum('a', 'b');" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column s set('a', 'b');" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column c char(5);" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vc varchar(5);" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false # Unlike the other string types, binary requires a rewrite even when making the length longer. run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column b binary(15);" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vb varbinary(5);" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false # Changing the character set requires a rewrite. run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vc varbinary(10);" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false # Changing the character set requires a rewrite. run env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vc varchar(10) collate latin1_german1_ci;" [ $status -ne 0 ] [[ $output =~ "attempted to rewrite table but DOLT_TEST_ASSERT_NO_TABLE_REWRITE was set" ]] || false # Now, assert that making these schema modifications has no effect on the table data. env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column e enum('a', 'b', 'c', 'd', 'e');" env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column s set('a', 'b', 'c', 'd', 'e');" env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column c char(15);" env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vc varchar(15);" env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vb varbinary(15);" # Changing the collation for a non-PK column doesn't require a table rewrite, but it does invalidate the secondary indexes. # The GMS API doesn't currently let us separate the two, so currently this causes a table rewrite, but it doesn't have to. # env DOLT_TEST_ASSERT_NO_TABLE_REWRITE=1 dolt sql -q "alter table t modify column vc varchar(15) collate utf8mb4_0900_ai_ci;" # After all these schema changes, the table hash remains the same. run dolt sql -r csv -q "select DOLT_HASHOF_TABLE('t') = (select DOLT_HASHOF_TABLE('t') from t as of HEAD);" [[ "$output" =~ "true" ]] || false }