diff --git a/src/backend/distributed/commands/view.c b/src/backend/distributed/commands/view.c index e57681656..53e89b7e0 100644 --- a/src/backend/distributed/commands/view.c +++ b/src/backend/distributed/commands/view.c @@ -36,10 +36,8 @@ #include "utils/syscache.h" static List * FilterNameListForDistributedViews(List *viewNamesList, bool missing_ok); -static void AppendAliasesToCreateViewCommandForExistingView(StringInfo createViewCommand, - Oid viewOid); -static void AddOptionsToCreateViewCommandForExistingView(StringInfo createViewCommand, - Oid viewOid); +static void AppendAliasesToCreateViewCommand(StringInfo createViewCommand, Oid viewOid); +static void AppendOptionsToCreateViewCommand(StringInfo createViewCommand, Oid viewOid); /* * PreprocessViewStmt is called during the planning phase for CREATE OR REPLACE VIEW @@ -67,7 +65,8 @@ PreprocessViewStmt(Node *node, const char *queryString, /* - * PostprocessViewStmt actually creates the plan we need to execute for view propagation. + * PostprocessViewStmt actually creates the commmands we need to run on workers to + * propagate views. * * If view depends on any undistributable object, Citus can not distribute it. In order to * not to prevent users from creating local views on the coordinator WARNING message will @@ -219,11 +218,6 @@ FilterNameListForDistributedViews(List *viewNamesList, bool missing_ok) List *qualifiedViewName = NULL; foreach_ptr(qualifiedViewName, viewNamesList) { - /* - * Name of the view must be qualified before calling this function - */ - Assert(list_length(qualifiedViewName) == 2); - char *schemaName = strVal(linitial(qualifiedViewName)); char *viewName = strVal(lsecond(qualifiedViewName)); @@ -264,10 +258,10 @@ CreateViewDDLCommandsIdempotent(const ObjectAddress *viewAddress) appendStringInfoString(createViewCommand, "CREATE OR REPLACE VIEW "); - AddQualifiedViewNameToCreateViewCommand(createViewCommand, viewOid); - AppendAliasesToCreateViewCommandForExistingView(createViewCommand, viewOid); - AddOptionsToCreateViewCommandForExistingView(createViewCommand, viewOid); - AddViewDefinitionToCreateViewCommand(createViewCommand, viewOid); + AppendQualifiedViewNameToCreateViewCommand(createViewCommand, viewOid); + AppendAliasesToCreateViewCommand(createViewCommand, viewOid); + AppendOptionsToCreateViewCommand(createViewCommand, viewOid); + AppendViewDefinitionToCreateViewCommand(createViewCommand, viewOid); /* Add alter owner commmand */ StringInfo alterOwnerCommand = makeStringInfo(); @@ -285,11 +279,11 @@ CreateViewDDLCommandsIdempotent(const ObjectAddress *viewAddress) /* - * AppendAliasesToCreateViewCommandForExistingView appends aliases to the create view + * AppendAliasesToCreateViewCommand appends aliases to the create view * command for the existing view. */ static void -AppendAliasesToCreateViewCommandForExistingView(StringInfo createViewCommand, Oid viewOid) +AppendAliasesToCreateViewCommand(StringInfo createViewCommand, Oid viewOid) { /* Get column name aliases from pg_attribute */ ScanKeyData key[1]; @@ -298,7 +292,6 @@ AppendAliasesToCreateViewCommandForExistingView(StringInfo createViewCommand, Oi BTEqualStrategyNumber, F_OIDEQ, ObjectIdGetDatum(viewOid)); - /* TODO: Check the lock */ Relation maprel = table_open(AttributeRelationId, AccessShareLock); Relation mapidx = index_open(AttributeRelidNumIndexId, AccessShareLock); SysScanDesc pgAttributeScan = systable_beginscan_ordered(maprel, mapidx, NULL, 1, @@ -340,17 +333,16 @@ AppendAliasesToCreateViewCommandForExistingView(StringInfo createViewCommand, Oi /* - * AddOptionsToCreateViewCommandForExistingView add relation options to create view command + * AppendOptionsToCreateViewCommand add relation options to create view command * for an existing view */ static void -AddOptionsToCreateViewCommandForExistingView(StringInfo createViewCommand, Oid viewOid) +AppendOptionsToCreateViewCommand(StringInfo createViewCommand, Oid viewOid) { /* Add rel options to create view command */ char *relOptions = flatten_reloptions(viewOid); if (relOptions != NULL) { appendStringInfo(createViewCommand, "WITH (%s) ", relOptions); - pfree(relOptions); } } diff --git a/src/backend/distributed/deparser/deparse_view_stmts.c b/src/backend/distributed/deparser/deparse_view_stmts.c index 19b51fdc2..a251f41c5 100644 --- a/src/backend/distributed/deparser/deparse_view_stmts.c +++ b/src/backend/distributed/deparser/deparse_view_stmts.c @@ -22,8 +22,8 @@ #include "utils/builtins.h" #include "utils/lsyscache.h" -static void AddAliasesToCreateViewCommand(StringInfo buf, ViewStmt *stmt); -static void AddOptionsToCreateViewCommand(StringInfo buf, ViewStmt *stmt); +static void AppendAliasesFromViewStmtToCreateViewCommand(StringInfo buf, ViewStmt *stmt); +static void AppendOptionsFromViewStmtToCreateViewCommand(StringInfo buf, ViewStmt *stmt); static void AppendDropViewStmt(StringInfo buf, DropStmt *stmt); static void AppendViewNameList(StringInfo buf, List *objects); @@ -36,8 +36,7 @@ DeparseViewStmt(Node *node) ViewStmt *stmt = castNode(ViewStmt, node); StringInfo viewString = makeStringInfo(); - Oid schemaOid = RangeVarGetCreationNamespace(stmt->view); - Oid viewOid = get_relname_relid(stmt->view->relname, schemaOid); + Oid viewOid = RangeVarGetRelid(stmt->view, NoLock, false); if (stmt->replace) { @@ -48,9 +47,9 @@ DeparseViewStmt(Node *node) appendStringInfoString(viewString, "CREATE VIEW "); } - AddQualifiedViewNameToCreateViewCommand(viewString, viewOid); - AddAliasesToCreateViewCommand(viewString, stmt); - AddOptionsToCreateViewCommand(viewString, stmt); + AppendQualifiedViewNameToCreateViewCommand(viewString, viewOid); + AppendAliasesFromViewStmtToCreateViewCommand(viewString, stmt); + AppendOptionsFromViewStmtToCreateViewCommand(viewString, stmt); /* * Note that Postgres converts CREATE RECURSIVE VIEW commands to @@ -58,18 +57,18 @@ DeparseViewStmt(Node *node) * So, we don't need to RECURSIVE views separately while obtaining the * view creation command */ - AddViewDefinitionToCreateViewCommand(viewString, viewOid); + AppendViewDefinitionToCreateViewCommand(viewString, viewOid); return viewString->data; } /* - * AddQualifiedViewNameToCreateViewCommand adds the qualified view of the given view + * AppendQualifiedViewNameToCreateViewCommand adds the qualified view of the given view * oid to the given create view command. */ void -AddQualifiedViewNameToCreateViewCommand(StringInfo buf, Oid viewOid) +AppendQualifiedViewNameToCreateViewCommand(StringInfo buf, Oid viewOid) { char *viewName = get_rel_name(viewOid); char *schemaName = get_namespace_name(get_rel_namespace(viewOid)); @@ -80,11 +79,11 @@ AddQualifiedViewNameToCreateViewCommand(StringInfo buf, Oid viewOid) /* - * AddAliasesToCreateViewCommand appends aliases (if exists) of the given view statement + * AppendAliasesFromViewStmtToCreateViewCommand appends aliases (if exists) of the given view statement * to the given create view command. */ static void -AddAliasesToCreateViewCommand(StringInfo buf, ViewStmt *stmt) +AppendAliasesFromViewStmtToCreateViewCommand(StringInfo buf, ViewStmt *stmt) { if (stmt->aliases == NIL) { @@ -95,7 +94,7 @@ AddAliasesToCreateViewCommand(StringInfo buf, ViewStmt *stmt) ListCell *aliasItem; foreach(aliasItem, stmt->aliases) { - char *columnAliasName = pstrdup(quote_identifier(strVal(lfirst(aliasItem)))); + const char *columnAliasName = quote_identifier(strVal(lfirst(aliasItem))); if (isFirstAlias) { @@ -115,12 +114,12 @@ AddAliasesToCreateViewCommand(StringInfo buf, ViewStmt *stmt) /* - * AddOptionsToCreateViewCommand appends options (if exists) of the given view statement + * AppendOptionsFromViewStmtToCreateViewCommand appends options (if exists) of the given view statement * to the given create view command. Note that this function also handles * WITH [CASCADED | LOCAL] CHECK OPTION part of the CREATE VIEW command. */ static void -AddOptionsToCreateViewCommand(StringInfo buf, ViewStmt *stmt) +AppendOptionsFromViewStmtToCreateViewCommand(StringInfo buf, ViewStmt *stmt) { if (list_length(stmt->options) == 0) { @@ -156,11 +155,11 @@ AddOptionsToCreateViewCommand(StringInfo buf, ViewStmt *stmt) /* - * AddViewDefinitionToCreateViewCommand adds the definition of the given view to the + * AppendViewDefinitionToCreateViewCommand adds the definition of the given view to the * given create view command. */ void -AddViewDefinitionToCreateViewCommand(StringInfo buf, Oid viewOid) +AppendViewDefinitionToCreateViewCommand(StringInfo buf, Oid viewOid) { /* * Set search_path to NIL so that all objects outside of pg_catalog will be diff --git a/src/include/distributed/deparser.h b/src/include/distributed/deparser.h index d992b1214..22c7fe005 100644 --- a/src/include/distributed/deparser.h +++ b/src/include/distributed/deparser.h @@ -146,8 +146,8 @@ extern ObjectAddress RenameAttributeStmtObjectAddress(Node *stmt, bool missing_o /* forward declarations for deparse_view_stmts.c */ extern void QualifyDropViewStmt(Node *node); -extern void AddViewDefinitionToCreateViewCommand(StringInfo buf, Oid viewOid); -extern void AddQualifiedViewNameToCreateViewCommand(StringInfo buf, Oid viewOid); +extern void AppendViewDefinitionToCreateViewCommand(StringInfo buf, Oid viewOid); +extern void AppendQualifiedViewNameToCreateViewCommand(StringInfo buf, Oid viewOid); /* forward declarations for deparse_function_stmts.c */ extern char * DeparseDropFunctionStmt(Node *stmt); diff --git a/src/test/regress/expected/function_propagation.out b/src/test/regress/expected/function_propagation.out index 3f39a2578..fdd476934 100644 --- a/src/test/regress/expected/function_propagation.out +++ b/src/test/regress/expected/function_propagation.out @@ -500,7 +500,7 @@ BEGIN; ALTER TABLE table_to_dist ADD COLUMN col_1 int default function_propagation_schema.non_dist_func(NULL::non_dist_table_for_function); ERROR: "table table_to_dist" has dependency to "table non_dist_table_for_function" that is not in Citus' metadata -HINT: Distribute "table non_dist_table_for_function" first to distribute "table table_to_dist" +HINT: Distribute "table non_dist_table_for_function" first to update "table table_to_dist" on worker nodes ROLLBACK; -- Adding multiple columns with default values should propagate the function BEGIN; diff --git a/src/test/regress/expected/view_propagation.out b/src/test/regress/expected/view_propagation.out index 0a03ef387..fb0caeac3 100644 --- a/src/test/regress/expected/view_propagation.out +++ b/src/test/regress/expected/view_propagation.out @@ -3,6 +3,8 @@ CREATE SCHEMA view_prop_schema; SET search_path to view_prop_schema; -- Check creating views depending on different types of tables -- and from multiple schemas +-- Check the most basic one +CREATE VIEW prop_view_basic AS SELECT 1; -- Try to create view depending local table, then try to recreate it after distributing the table CREATE TABLE view_table_1(id int, val_1 text); CREATE VIEW prop_view_1 AS @@ -43,14 +45,14 @@ CREATE VIEW prop_view_3 AS WARNING: "view prop_view_3" has dependency to "table view_table_3" that is not in Citus' metadata DETAIL: "view prop_view_3" will be created only locally HINT: Distribute "table view_table_3" first to distribute "view prop_view_3" +SET client_min_messages TO WARNING; SELECT 1 FROM citus_add_node('localhost', :master_port, groupid=>0); -NOTICE: Replicating reference table "view_table_2" to the node localhost:xxxxx -NOTICE: localhost:xxxxx is the coordinator and already contains metadata, skipping syncing the metadata ?column? --------------------------------------------------------------------- 1 (1 row) +RESET client_min_messages; ALTER TABLE view_table_3 ADD CONSTRAINT f_key_for_local_table FOREIGN KEY(id) @@ -95,7 +97,7 @@ CREATE OR REPLACE VIEW prop_view_6 AS SELECT vt1.id, vt4.val_1 FROM view_table_1 AS vt1 INNER JOIN view_prop_schema_inner.view_table_4 AS vt4 ON vt1.id = vt4.id; -- Show that all views are propagated as distributed object -SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_%'; +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_%' ORDER BY 1; obj_identifier --------------------------------------------------------------------- (view,"{view_prop_schema,prop_view_1}",{}) @@ -104,7 +106,8 @@ SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as (view,"{view_prop_schema,prop_view_4}",{}) (view,"{view_prop_schema,prop_view_5}",{}) (view,"{view_prop_schema,prop_view_6}",{}) -(6 rows) + (view,"{view_prop_schema,prop_view_basic}",{}) +(7 rows) -- Check creating views depending various kind of objects -- Tests will also check propagating dependent objects @@ -223,6 +226,27 @@ SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as (view,"{view_prop_schema,nums_1_100_prop_view}",{}) (1 row) +-- Sequences are supported as dependency +CREATE SEQUENCE sequence_to_prop; +CREATE VIEW seq_view_prop AS SELECT sequence_to_prop.is_called FROM sequence_to_prop; +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%sequence_to_prop%'; + obj_identifier +--------------------------------------------------------------------- + (sequence,"{view_prop_schema,sequence_to_prop}",{}) +(1 row) + +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%seq_view_prop%'; + obj_identifier +--------------------------------------------------------------------- + (view,"{view_prop_schema,seq_view_prop}",{}) +(1 row) + +-- Views depend on temp sequences will be created locally +CREATE TEMPORARY SEQUENCE temp_sequence_to_drop; +CREATE VIEW temp_seq_view_prop AS SELECT temp_sequence_to_drop.is_called FROM temp_sequence_to_drop; +NOTICE: view "temp_seq_view_prop" will be a temporary view +WARNING: "view temp_seq_view_prop" has dependency on unsupported object "schema pg_temp_xxx" +DETAIL: "view temp_seq_view_prop" will be created only locally -- Aliases are supported CREATE VIEW aliased_opt_prop_view(alias_1, alias_2) AS SELECT * FROM view_table_6; -- View options are supported @@ -232,7 +256,7 @@ CREATE VIEW opt_prop_view CREATE VIEW sep_opt_prop_view AS SELECT * FROM view_table_6 WITH LOCAL CHECK OPTION; -SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%opt_prop_view%'; +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%opt_prop_view%' ORDER BY 1; obj_identifier --------------------------------------------------------------------- (view,"{view_prop_schema,aliased_opt_prop_view}",{}) @@ -294,27 +318,66 @@ SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as --------------------------------------------------------------------- (0 rows) +-- Drop a column that view depends on +ALTER TABLE view_table_1 DROP COLUMN val_1 CASCADE; +NOTICE: drop cascades to 3 other objects +DETAIL: drop cascades to view prop_view_1 +drop cascades to view prop_view_3 +drop cascades to view prop_view_8 +-- Since prop_view_3 depends on the view_table_1's val_1 column, it should be dropped +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_3%'; + obj_identifier +--------------------------------------------------------------------- +(0 rows) + +-- Drop a table that view depends on +DROP TABLE view_table_2 CASCADE; +NOTICE: drop cascades to 2 other objects +DETAIL: drop cascades to view prop_view_2 +drop cascades to constraint f_key_for_local_table on table view_table_3 +NOTICE: drop cascades to constraint f_key_for_local_table_1410200 on table view_prop_schema.view_table_3_1410200 +CONTEXT: SQL statement "SELECT citus_drop_all_shards(v_obj.objid, v_obj.schema_name, v_obj.object_name, drop_shards_metadata_only := false)" +PL/pgSQL function citus_drop_trigger() line XX at PERFORM +NOTICE: removing table view_prop_schema.view_table_3 from metadata as it is not connected to any reference tables via foreign keys +-- Since prop_view_2 depends on the view_table_2, it should be dropped +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_2%'; + obj_identifier +--------------------------------------------------------------------- +(0 rows) + +-- Show that unsupported CREATE OR REPLACE VIEW commands are catched by PG on the coordinator +CREATE TABLE table_to_test_unsup_view(id int, val1 text); +SELECT create_distributed_table('table_to_test_unsup_view', 'id'); + create_distributed_table +--------------------------------------------------------------------- + +(1 row) + +CREATE VIEW view_for_unsup_commands AS SELECT * FROM table_to_test_unsup_view; +CREATE OR REPLACE VIEW view_for_unsup_commands(a,b) AS SELECT * FROM table_to_test_unsup_view; +ERROR: cannot change name of view column "id" to "a" +HINT: Use ALTER VIEW ... RENAME COLUMN ... to change name of view column instead. +CREATE OR REPLACE VIEW view_for_unsup_commands AS SELECT id FROM table_to_test_unsup_view; +ERROR: cannot drop columns from view DROP SCHEMA view_prop_schema_inner CASCADE; NOTICE: drop cascades to 3 other objects DETAIL: drop cascades to table view_prop_schema_inner.view_table_4 drop cascades to view prop_view_6 drop cascades to table view_prop_schema_inner.inner_view_table DROP SCHEMA view_prop_schema CASCADE; -NOTICE: drop cascades to 17 other objects -DETAIL: drop cascades to table view_table_1 -drop cascades to view prop_view_1 -drop cascades to table view_table_2 -drop cascades to view prop_view_2 -drop cascades to table view_table_3_1410200 -drop cascades to table view_table_2_1410199 -drop cascades to table view_table_3 -drop cascades to view prop_view_3 +NOTICE: drop cascades to 15 other objects +DETAIL: drop cascades to view prop_view_basic +drop cascades to table view_table_1 drop cascades to view prop_view_4 drop cascades to view prop_view_5 drop cascades to function func_1_for_view(integer) drop cascades to view prop_view_7 drop cascades to type type_for_view_prop -drop cascades to view prop_view_8 drop cascades to table view_table_5 drop cascades to table view_table_6 drop cascades to view nums_1_100_prop_view +drop cascades to sequence sequence_to_prop +drop cascades to view seq_view_prop +drop cascades to table view_table_3 +drop cascades to table table_to_test_unsup_view +drop cascades to view view_for_unsup_commands diff --git a/src/test/regress/sql/upgrade_post_11_after.sql b/src/test/regress/sql/upgrade_post_11_after.sql index a106b9fcf..eff18eba0 100644 --- a/src/test/regress/sql/upgrade_post_11_after.sql +++ b/src/test/regress/sql/upgrade_post_11_after.sql @@ -8,7 +8,7 @@ SELECT citus_finalize_upgrade_to_citus11(enforce_version_check:=false); SELECT pg_identify_object_as_address(classid, objid, objsubid) FROM pg_catalog.pg_dist_object WHERE objid IN ('post_11_upgrade'::regnamespace, 'post_11_upgrade.part_table'::regclass, 'post_11_upgrade.sensors'::regclass, 'post_11_upgrade.func_in_transaction_def'::regproc, 'post_11_upgrade.partial_index_test_config'::regconfig, 'post_11_upgrade.my_type'::regtype) ORDER BY 1; -- on all nodes -SELECT run_command_on_workers($$SELECT array_agg(pg_identify_object_as_address(classid, objid, objsubid)) FROM pg_catalog.pg_dist_object WHERE objid IN ('post_11_upgrade'::regnamespace, 'post_11_upgrade.part_table'::regclass, 'post_11_upgrade.sensors'::regclass, 'post_11_upgrade.func_in_transaction_def'::regproc, 'post_11_upgrade.partial_index_test_config'::regconfig, 'post_11_upgrade.my_type'::regtype) ORDER BY 1;$$) ORDER BY 1; +SELECT run_command_on_workers($$SELECT array_agg(pg_identify_object_as_address(classid, objid, objsubid)) FROM pg_catalog.pg_dist_object WHERE objid IN ('post_11_upgrade'::regnamespace, 'post_11_upgrade.part_table'::regclass, 'post_11_upgrade.view_for_upgrade_test'::regclass, 'post_11_upgrade.sensors'::regclass, 'post_11_upgrade.func_in_transaction_def'::regproc, 'post_11_upgrade.partial_index_test_config'::regconfig, 'post_11_upgrade.my_type'::regtype) ORDER BY 1;$$) ORDER BY 1; -- Create the necessary test utility function CREATE OR REPLACE FUNCTION activate_node_snapshot() diff --git a/src/test/regress/sql/upgrade_post_11_before.sql b/src/test/regress/sql/upgrade_post_11_before.sql index 959b026f8..3fa7f3926 100644 --- a/src/test/regress/sql/upgrade_post_11_before.sql +++ b/src/test/regress/sql/upgrade_post_11_before.sql @@ -130,6 +130,11 @@ $$;'); CREATE TYPE post_11_upgrade.my_type AS (a int); +CREATE VIEW post_11_upgrade.view_for_upgrade_test AS SELECT * FROM sensors; + +SELECT run_command_on_workers('SET citus.enable_ddl_propagation TO off; +CREATE VIEW post_11_upgrade.view_for_upgrade_test AS SELECT * FROM sensors;'); + RESET citus.enable_ddl_propagation; CREATE TABLE sensors_parser( diff --git a/src/test/regress/sql/view_propagation.sql b/src/test/regress/sql/view_propagation.sql index 1517704f9..094515b0b 100644 --- a/src/test/regress/sql/view_propagation.sql +++ b/src/test/regress/sql/view_propagation.sql @@ -5,6 +5,9 @@ SET search_path to view_prop_schema; -- Check creating views depending on different types of tables -- and from multiple schemas +-- Check the most basic one +CREATE VIEW prop_view_basic AS SELECT 1; + -- Try to create view depending local table, then try to recreate it after distributing the table CREATE TABLE view_table_1(id int, val_1 text); CREATE VIEW prop_view_1 AS @@ -31,7 +34,9 @@ CREATE VIEW prop_view_3 AS SELECT * FROM view_table_1 WHERE id IN (SELECT view_table_2.id FROM view_table_2 INNER JOIN view_table_3 ON view_table_2.id = view_table_3.id); +SET client_min_messages TO WARNING; SELECT 1 FROM citus_add_node('localhost', :master_port, groupid=>0); +RESET client_min_messages; ALTER TABLE view_table_3 ADD CONSTRAINT f_key_for_local_table @@ -74,7 +79,7 @@ CREATE OR REPLACE VIEW prop_view_6 AS INNER JOIN view_prop_schema_inner.view_table_4 AS vt4 ON vt1.id = vt4.id; -- Show that all views are propagated as distributed object -SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_%'; +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_%' ORDER BY 1; -- Check creating views depending various kind of objects -- Tests will also check propagating dependent objects @@ -142,6 +147,17 @@ UNION ALL SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%nums_1_100_prop_view%'; +-- Sequences are supported as dependency +CREATE SEQUENCE sequence_to_prop; +CREATE VIEW seq_view_prop AS SELECT sequence_to_prop.is_called FROM sequence_to_prop; + +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%sequence_to_prop%'; +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%seq_view_prop%'; + +-- Views depend on temp sequences will be created locally +CREATE TEMPORARY SEQUENCE temp_sequence_to_drop; +CREATE VIEW temp_seq_view_prop AS SELECT temp_sequence_to_drop.is_called FROM temp_sequence_to_drop; + -- Aliases are supported CREATE VIEW aliased_opt_prop_view(alias_1, alias_2) AS SELECT * FROM view_table_6; @@ -154,7 +170,7 @@ CREATE VIEW sep_opt_prop_view AS SELECT * FROM view_table_6 WITH LOCAL CHECK OPTION; -SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%opt_prop_view%'; +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%opt_prop_view%' ORDER BY 1; -- Check definitions of views are correct on workers \c - - - :worker_1_port @@ -173,5 +189,26 @@ DROP VIEW opt_prop_view, aliased_opt_prop_view, view_prop_schema_inner.inner_vie SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%inner_view_prop%'; SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%opt_prop_view%'; +-- Drop a column that view depends on +ALTER TABLE view_table_1 DROP COLUMN val_1 CASCADE; + +-- Since prop_view_3 depends on the view_table_1's val_1 column, it should be dropped +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_3%'; + +-- Drop a table that view depends on +DROP TABLE view_table_2 CASCADE; + +-- Since prop_view_2 depends on the view_table_2, it should be dropped +SELECT * FROM (SELECT pg_identify_object_as_address(classid, objid, objsubid) as obj_identifier from pg_catalog.pg_dist_object) as obj_identifiers where obj_identifier::text like '%prop_view_2%'; + +-- Show that unsupported CREATE OR REPLACE VIEW commands are catched by PG on the coordinator +CREATE TABLE table_to_test_unsup_view(id int, val1 text); +SELECT create_distributed_table('table_to_test_unsup_view', 'id'); + +CREATE VIEW view_for_unsup_commands AS SELECT * FROM table_to_test_unsup_view; + +CREATE OR REPLACE VIEW view_for_unsup_commands(a,b) AS SELECT * FROM table_to_test_unsup_view; +CREATE OR REPLACE VIEW view_for_unsup_commands AS SELECT id FROM table_to_test_unsup_view; + DROP SCHEMA view_prop_schema_inner CASCADE; DROP SCHEMA view_prop_schema CASCADE;