diff --git a/Makefile b/Makefile index b4fd3f2f4..84a5e5e01 100644 --- a/Makefile +++ b/Makefile @@ -35,7 +35,8 @@ SRCS = \ src/process_utility.c \ src/sort_transform.c \ src/insert_chunk_state.c \ - src/insert_statement_state.c + src/insert_statement_state.c \ + src/ddl_utils.c OBJS = $(SRCS:.c=.o) DEPS = $(SRCS:.c=.d) diff --git a/sql/common/ddl_utils.sql b/sql/common/ddl_utils.sql new file mode 100644 index 000000000..5247cb258 --- /dev/null +++ b/sql/common/ddl_utils.sql @@ -0,0 +1,9 @@ + +CREATE OR REPLACE FUNCTION ddl_is_add_column(pg_ddl_command) + RETURNS bool IMMUTABLE STRICT + AS '$libdir/timescaledb' LANGUAGE C; + +CREATE OR REPLACE FUNCTION ddl_is_drop_column(pg_ddl_command) + RETURNS bool IMMUTABLE STRICT + AS '$libdir/timescaledb' LANGUAGE C; + diff --git a/sql/load_order.txt b/sql/load_order.txt index b84c6166b..404799879 100644 --- a/sql/load_order.txt +++ b/sql/load_order.txt @@ -47,3 +47,4 @@ sql/main/ddl.sql sql/main/ddl_triggers.sql sql/main/setup_main.sql sql/common/permissions.sql +sql/common/ddl_utils.sql diff --git a/sql/main/ddl_triggers.sql b/sql/main/ddl_triggers.sql index 171babcec..a9e4c90d7 100644 --- a/sql/main/ddl_triggers.sql +++ b/sql/main/ddl_triggers.sql @@ -158,28 +158,34 @@ BEGIN found_action = FALSE; --was a column added? - FOR att_row IN - SELECT * - FROM pg_attribute att - WHERE attrelid = info.objid AND + + IF ddl_is_add_column(info.command) THEN + FOR att_row IN + SELECT * + FROM pg_attribute att + WHERE attrelid = info.objid AND attnum > 0 AND NOT attisdropped AND att.attnum NOT IN (SELECT c.attnum FROM _timescaledb_catalog.hypertable_column c WHERE hypertable_id = hypertable_row.id) LOOP PERFORM _timescaledb_internal.create_column_from_attribute(hypertable_row.id, att_row); - found_action = TRUE; END LOOP; + found_action = TRUE; + END IF; + --was a column deleted - FOR rec IN - SELECT name - FROM _timescaledb_catalog.hypertable_column c - INNER JOIN pg_attribute att ON (attrelid = info.objid AND att.attnum = c.attnum AND attisdropped) --do not match on att.attname here. it gets mangled - WHERE hypertable_id = hypertable_row.id - LOOP - PERFORM _timescaledb_meta_api.drop_column(hypertable_row.id, rec.name); - found_action = TRUE; - END LOOP; + IF ddl_is_drop_column(info.command) THEN + FOR rec IN + SELECT name + FROM _timescaledb_catalog.hypertable_column c + INNER JOIN pg_attribute att ON (attrelid = info.objid AND att.attnum = c.attnum AND attisdropped) --do not match on att.attname here. it gets mangled + WHERE hypertable_id = hypertable_row.id + LOOP + PERFORM _timescaledb_meta_api.drop_column(hypertable_row.id, rec.name); + END LOOP; + found_action = TRUE; + END IF; --was a column renamed FOR rec IN diff --git a/src/ddl_utils.c b/src/ddl_utils.c new file mode 100644 index 000000000..e0945e04d --- /dev/null +++ b/src/ddl_utils.c @@ -0,0 +1,62 @@ +#include +#include + +enum ddl_cmd_type +{ + DDL_DROP_COLUMN, DDL_ADD_COLUMN, DDL_OTHER +}; + +static enum ddl_cmd_type +ddl_type_from_cmd(CollectedCommand *cmd) +{ + ListCell *cell; + + if (cmd->type == SCT_AlterTable) + { + foreach(cell, cmd->d.alterTable.subcmds) + { + CollectedATSubcmd *sub = lfirst(cell); + AlterTableCmd *subcmd = (AlterTableCmd *) sub->parsetree; + + Assert(IsA(subcmd, AlterTableCmd)); + + switch (subcmd->subtype) + { + case AT_AddColumn: + case AT_AddColumnRecurse: + return DDL_ADD_COLUMN; + case AT_DropColumn: + case AT_DropColumnRecurse: + return DDL_DROP_COLUMN; + default: + break; + } + } + } + + return DDL_OTHER; +} + +/* + * Test if ddl command is an alter table add column + */ +PG_FUNCTION_INFO_V1(ddl_is_add_column); +Datum +ddl_is_add_column(PG_FUNCTION_ARGS) +{ + bool is_add_column = DDL_ADD_COLUMN == ddl_type_from_cmd((CollectedCommand *) PG_GETARG_POINTER(0)); + + PG_RETURN_BOOL(is_add_column); +} + +/* + * Test if ddl command is an alter table drop column + */ +PG_FUNCTION_INFO_V1(ddl_is_drop_column); +Datum +ddl_is_drop_column(PG_FUNCTION_ARGS) +{ + bool is_drop_column = DDL_DROP_COLUMN == ddl_type_from_cmd((CollectedCommand *) PG_GETARG_POINTER(0)); + + PG_RETURN_BOOL(is_drop_column); +} diff --git a/test/expected/alternate_users.out b/test/expected/alternate_users.out index 6da549a33..6e3b14223 100644 --- a/test/expected/alternate_users.out +++ b/test/expected/alternate_users.out @@ -185,6 +185,91 @@ psql:include/ddl_ops_1.sql:61: ERROR: UPDATE ONLY not supported on hypertables DELETE FROM ONLY PUBLIC."Hypertable_1" WHERE "Device_id" = 'dev1'; psql:include/ddl_ops_1.sql:62: ERROR: DELETE ONLY not currently supported on hypertables \set ON_ERROR_STOP 1 +CREATE TABLE my_ht (time bigint, val integer); +SELECT * FROM create_hypertable('my_ht', 'time'); + create_hypertable +------------------- + +(1 row) + +ALTER TABLE my_ht ADD COLUMN val2 integer; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should error when adding again +\set ON_ERROR_STOP 0 +ALTER TABLE my_ht ADD COLUMN val2 integer; +psql:include/ddl_ops_1.sql:73: ERROR: column "val2" of relation "my_ht" already exists +\set ON_ERROR_STOP 1 +-- Should create +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | + val3 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should skip and not error +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +psql:include/ddl_ops_1.sql:81: NOTICE: column "val3" of relation "my_ht" already exists, skipping +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | + val3 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should drop +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should skip and not error +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +psql:include/ddl_ops_1.sql:89: NOTICE: column "val3" of relation "my_ht" does not exist, skipping +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + \ir include/ddl_ops_2.sql ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN temp_f INTEGER NOT NULL DEFAULT 31; ALTER TABLE PUBLIC."Hypertable_1" DROP COLUMN temp_c; @@ -217,3 +302,4 @@ psql:include/ddl_ops_2.sql:26: ERROR: CREATE TRIGGER not supported on hypertabl ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_3 BIGINT NOT NULL DEFAULT 131; --create column with same name as previously dropped one ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_4 BIGINT NOT NULL DEFAULT 131; + diff --git a/test/expected/ddl.out b/test/expected/ddl.out index 35f5cb4da..ba77e96ab 100644 --- a/test/expected/ddl.out +++ b/test/expected/ddl.out @@ -100,6 +100,91 @@ psql:include/ddl_ops_1.sql:61: ERROR: UPDATE ONLY not supported on hypertables DELETE FROM ONLY PUBLIC."Hypertable_1" WHERE "Device_id" = 'dev1'; psql:include/ddl_ops_1.sql:62: ERROR: DELETE ONLY not currently supported on hypertables \set ON_ERROR_STOP 1 +CREATE TABLE my_ht (time bigint, val integer); +SELECT * FROM create_hypertable('my_ht', 'time'); + create_hypertable +------------------- + +(1 row) + +ALTER TABLE my_ht ADD COLUMN val2 integer; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should error when adding again +\set ON_ERROR_STOP 0 +ALTER TABLE my_ht ADD COLUMN val2 integer; +psql:include/ddl_ops_1.sql:73: ERROR: column "val2" of relation "my_ht" already exists +\set ON_ERROR_STOP 1 +-- Should create +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | + val3 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should skip and not error +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +psql:include/ddl_ops_1.sql:81: NOTICE: column "val3" of relation "my_ht" already exists, skipping +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | + val3 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should drop +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should skip and not error +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +psql:include/ddl_ops_1.sql:89: NOTICE: column "val3" of relation "my_ht" does not exist, skipping +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + SELECT * FROM PUBLIC."Hypertable_1"; time | Device_id | temp_c | humidity | sensor_1 | sensor_2 | sensor_3 | sensor_4 ---------------------+-----------+--------+----------+----------+----------+----------+---------- @@ -191,7 +276,8 @@ SELECT * FROM _timescaledb_catalog.default_replica_node; ---------------+---------------+------------ single | 1 | 0 single | 2 | 0 -(2 rows) + single | 3 | 0 +(3 rows) \ir include/ddl_ops_2.sql ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN temp_f INTEGER NOT NULL DEFAULT 31; @@ -225,6 +311,7 @@ psql:include/ddl_ops_2.sql:26: ERROR: CREATE TRIGGER not supported on hypertabl ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_3 BIGINT NOT NULL DEFAULT 131; --create column with same name as previously dropped one ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_4 BIGINT NOT NULL DEFAULT 131; + \d+ PUBLIC."Hypertable_1" Table "public.Hypertable_1" Column | Type | Modifiers | Storage | Stats target | Description diff --git a/test/expected/ddl_single.out b/test/expected/ddl_single.out index eb519c988..6ce563de8 100644 --- a/test/expected/ddl_single.out +++ b/test/expected/ddl_single.out @@ -100,6 +100,91 @@ psql:include/ddl_ops_1.sql:61: ERROR: UPDATE ONLY not supported on hypertables DELETE FROM ONLY PUBLIC."Hypertable_1" WHERE "Device_id" = 'dev1'; psql:include/ddl_ops_1.sql:62: ERROR: DELETE ONLY not currently supported on hypertables \set ON_ERROR_STOP 1 +CREATE TABLE my_ht (time bigint, val integer); +SELECT * FROM create_hypertable('my_ht', 'time'); + create_hypertable +------------------- + +(1 row) + +ALTER TABLE my_ht ADD COLUMN val2 integer; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should error when adding again +\set ON_ERROR_STOP 0 +ALTER TABLE my_ht ADD COLUMN val2 integer; +psql:include/ddl_ops_1.sql:73: ERROR: column "val2" of relation "my_ht" already exists +\set ON_ERROR_STOP 1 +-- Should create +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | + val3 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should skip and not error +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +psql:include/ddl_ops_1.sql:81: NOTICE: column "val3" of relation "my_ht" already exists, skipping +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | + val3 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should drop +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + +-- Should skip and not error +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +psql:include/ddl_ops_1.sql:89: NOTICE: column "val3" of relation "my_ht" does not exist, skipping +\d my_ht + Table "public.my_ht" + Column | Type | Modifiers +--------+---------+----------- + time | bigint | + val | integer | + val2 | integer | +Triggers: + _timescaledb_main_after_insert_trigger AFTER INSERT ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.main_table_after_insert_trigger() + _timescaledb_main_insert_trigger BEFORE INSERT ON my_ht FOR EACH ROW EXECUTE PROCEDURE _timescaledb_internal.main_table_insert_trigger() + _timescaledb_modify_trigger BEFORE DELETE OR UPDATE ON my_ht FOR EACH STATEMENT EXECUTE PROCEDURE _timescaledb_internal.on_unsupported_main_table() + SELECT * FROM PUBLIC."Hypertable_1"; time | Device_id | temp_c | humidity | sensor_1 | sensor_2 | sensor_3 | sensor_4 ---------------------+-----------+--------+----------+----------+----------+----------+---------- @@ -120,7 +205,8 @@ SELECT * FROM _timescaledb_catalog.default_replica_node; ---------------+---------------+------------ single | 1 | 0 single | 2 | 0 -(2 rows) + single | 3 | 0 +(3 rows) \ir include/ddl_ops_2.sql ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN temp_f INTEGER NOT NULL DEFAULT 31; @@ -154,6 +240,7 @@ psql:include/ddl_ops_2.sql:26: ERROR: CREATE TRIGGER not supported on hypertabl ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_3 BIGINT NOT NULL DEFAULT 131; --create column with same name as previously dropped one ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_4 BIGINT NOT NULL DEFAULT 131; + \d+ PUBLIC."Hypertable_1" Table "public.Hypertable_1" Column | Type | Modifiers | Storage | Stats target | Description diff --git a/test/sql/include/ddl_ops_1.sql b/test/sql/include/ddl_ops_1.sql index 8f86149c6..1fd840464 100644 --- a/test/sql/include/ddl_ops_1.sql +++ b/test/sql/include/ddl_ops_1.sql @@ -61,3 +61,30 @@ CREATE UNIQUE INDEX "Unique2" ON PUBLIC."Hypertable_1" (sensor_1); UPDATE ONLY PUBLIC."Hypertable_1" SET time = 0 WHERE TRUE; DELETE FROM ONLY PUBLIC."Hypertable_1" WHERE "Device_id" = 'dev1'; \set ON_ERROR_STOP 1 + + +CREATE TABLE my_ht (time bigint, val integer); +SELECT * FROM create_hypertable('my_ht', 'time'); +ALTER TABLE my_ht ADD COLUMN val2 integer; +\d my_ht + +-- Should error when adding again +\set ON_ERROR_STOP 0 +ALTER TABLE my_ht ADD COLUMN val2 integer; +\set ON_ERROR_STOP 1 + +-- Should create +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +\d my_ht + +-- Should skip and not error +ALTER TABLE my_ht ADD COLUMN IF NOT EXISTS val3 integer; +\d my_ht + +-- Should drop +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +\d my_ht + +-- Should skip and not error +ALTER TABLE my_ht DROP COLUMN IF EXISTS val3; +\d my_ht diff --git a/test/sql/include/ddl_ops_2.sql b/test/sql/include/ddl_ops_2.sql index 6d6d41b84..c7dcfe15b 100644 --- a/test/sql/include/ddl_ops_2.sql +++ b/test/sql/include/ddl_ops_2.sql @@ -30,5 +30,4 @@ FOR EACH STATEMENT EXECUTE PROCEDURE empty_trigger_func(); ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_3 BIGINT NOT NULL DEFAULT 131; --create column with same name as previously dropped one ALTER TABLE PUBLIC."Hypertable_1" ADD COLUMN sensor_4 BIGINT NOT NULL DEFAULT 131; - - +