--
-- failure_create_index_concurrently
-- test create index concurrently command
-- failure.
SELECT citus.mitmproxy('conn.allow()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

SET citus.shard_count = 4; -- two per worker
CREATE SCHEMA index_schema;
SET SEARCH_PATH=index_schema;
CREATE TABLE index_test(id int, value_1 int, value_2 int);
SELECT create_distributed_table('index_test', 'id');
 create_distributed_table
---------------------------------------------------------------------

(1 row)

-- kill the connection when create command is issued
SELECT citus.mitmproxy('conn.onQuery(query="CREATE").kill()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

CREATE INDEX CONCURRENTLY idx_index_test ON index_test(id, value_1);
WARNING:  Commands that are not transaction-safe may result in partial failure, potentially leading to an inconsistent state.
If the problematic command is a CREATE operation, consider using the 'IF EXISTS' syntax to drop the object,
if applicable, and then re-attempt the original command.
ERROR:  connection to the remote node postgres@localhost:xxxxx failed with the following error: connection not open
SELECT citus.mitmproxy('conn.allow()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

-- verify index is not created
SELECT * FROM run_command_on_workers($$SELECT count(*) FROM pg_indexes WHERE indexname LIKE 'idx_index_test_%' $$)
WHERE nodeport = :worker_2_proxy_port;
 nodename  | nodeport | success | result
---------------------------------------------------------------------
 localhost |     9060 | t       | 0
(1 row)

DROP TABLE index_test;
CREATE TABLE index_test(id int, value_1 int, value_2 int);
SELECT create_reference_table('index_test');
 create_reference_table
---------------------------------------------------------------------

(1 row)

-- kill the connection when create command is issued
SELECT citus.mitmproxy('conn.onQuery(query="CREATE").kill()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

CREATE INDEX CONCURRENTLY idx_index_test ON index_test(id, value_1);
WARNING:  Commands that are not transaction-safe may result in partial failure, potentially leading to an inconsistent state.
If the problematic command is a CREATE operation, consider using the 'IF EXISTS' syntax to drop the object,
if applicable, and then re-attempt the original command.
ERROR:  connection to the remote node postgres@localhost:xxxxx failed with the following error: connection not open
SELECT citus.mitmproxy('conn.allow()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

DROP TABLE index_test;
CREATE TABLE index_test(id int, value_1 int, value_2 int);
SELECT create_distributed_table('index_test', 'id');
 create_distributed_table
---------------------------------------------------------------------

(1 row)

-- cancel the connection when create command is issued
-- network traffic may differ between execution during cancellation
-- therefore dump_network_traffic() calls are not made
SELECT citus.mitmproxy('conn.onQuery(query="CREATE").cancel(' || pg_backend_pid() || ')');
 mitmproxy
---------------------------------------------------------------------

(1 row)

CREATE INDEX CONCURRENTLY idx_index_test ON index_test(id, value_1);
WARNING:  Commands that are not transaction-safe may result in partial failure, potentially leading to an inconsistent state.
If the problematic command is a CREATE operation, consider using the 'IF EXISTS' syntax to drop the object,
if applicable, and then re-attempt the original command.
ERROR:  canceling statement due to user request
SELECT citus.mitmproxy('conn.allow()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

DROP TABLE index_test;
CREATE TABLE index_test(id int, value_1 int, value_2 int);
SELECT create_reference_table('index_test');
 create_reference_table
---------------------------------------------------------------------

(1 row)

-- cancel the connection when create command is issued
SELECT citus.mitmproxy('conn.onQuery(query="CREATE").cancel(' || pg_backend_pid() || ')');
 mitmproxy
---------------------------------------------------------------------

(1 row)

CREATE INDEX CONCURRENTLY idx_index_test ON index_test(id, value_1);
WARNING:  Commands that are not transaction-safe may result in partial failure, potentially leading to an inconsistent state.
If the problematic command is a CREATE operation, consider using the 'IF EXISTS' syntax to drop the object,
if applicable, and then re-attempt the original command.
ERROR:  canceling statement due to user request
SELECT citus.mitmproxy('conn.allow()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

DROP TABLE index_test;
CREATE TABLE index_test(id int, value_1 int, value_2 int);
SELECT create_distributed_table('index_test', 'id');
 create_distributed_table
---------------------------------------------------------------------

(1 row)

CREATE INDEX CONCURRENTLY idx_index_test ON index_test(id, value_1);
-- kill the connection when create command is issued
SELECT citus.mitmproxy('conn.onQuery(query="DROP INDEX CONCURRENTLY").kill()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

DROP INDEX CONCURRENTLY IF EXISTS idx_index_test;
WARNING:  Commands that are not transaction-safe may result in partial failure, potentially leading to an inconsistent state.
If the problematic command is a CREATE operation, consider using the 'IF EXISTS' syntax to drop the object,
if applicable, and then re-attempt the original command.
ERROR:  connection to the remote node postgres@localhost:xxxxx failed with the following error: connection not open
SELECT citus.mitmproxy('conn.allow()');
 mitmproxy
---------------------------------------------------------------------

(1 row)

-- verify index is not dropped at worker 2
SELECT * FROM run_command_on_workers($$SELECT count(*) FROM pg_indexes WHERE indexname LIKE 'idx_index_test_%' $$)
WHERE nodeport = :worker_2_proxy_port;
 nodename  | nodeport | success | result
---------------------------------------------------------------------
 localhost |     9060 | t       | 4
(1 row)

-- test unique concurrent index creation failure when there are duplicates
CREATE TABLE index_test_2 (a int, b int);
SELECT create_distributed_table('index_test_2', 'a');
 create_distributed_table
---------------------------------------------------------------------

(1 row)

INSERT INTO index_test_2 VALUES (1, 1), (1, 2);
CREATE UNIQUE INDEX CONCURRENTLY index_test_2_a_idx ON index_test_2(a);
WARNING:  Commands that are not transaction-safe may result in partial failure, potentially leading to an inconsistent state.
If the problematic command is a CREATE operation, consider using the 'IF EXISTS' syntax to drop the object,
if applicable, and then re-attempt the original command.
ERROR:  could not create unique index "index_test_2_a_idx_1880019"
DETAIL:  Key (a)=(1) is duplicated.
CONTEXT:  while executing command on localhost:xxxxx
DROP INDEX CONCURRENTLY IF EXISTS index_test_2_a_idx;
-- verify that index creation doesn't fail when duplicates are removed
DELETE FROM index_test_2 WHERE a = 1 AND b = 2;
CREATE UNIQUE INDEX CONCURRENTLY index_test_2_a_idx ON index_test_2(a);
DROP INDEX CONCURRENTLY IF EXISTS index_test_2_a_idx;
RESET SEARCH_PATH;
DROP SCHEMA index_schema CASCADE;
NOTICE:  drop cascades to 2 other objects
DETAIL:  drop cascades to table index_schema.index_test
drop cascades to table index_schema.index_test_2
-- verify index is not at worker 2 upon cleanup
SELECT * FROM run_command_on_workers($$SELECT count(*) FROM pg_indexes WHERE indexname LIKE 'idx_index_test_%' $$)
WHERE nodeport = :worker_2_proxy_port;
 nodename  | nodeport | success | result
---------------------------------------------------------------------
 localhost |     9060 | t       | 0
(1 row)

