mirror of
https://github.com/timescale/timescaledb.git
synced 2025-05-16 10:33:27 +08:00
Allow EXPLAIN in read-only mode
Using `EXPLAIN` when `transaction_read_only` is set to `on` fails with an error. This is fixed by explicitly setting the `check_read_only` flag.
This commit is contained in:
parent
65b8151af3
commit
39049feba6
2
.unreleased/pr_7637
Normal file
2
.unreleased/pr_7637
Normal file
@ -0,0 +1,2 @@
|
||||
Fixes: #7637 Allow EXPLAIN in read-only mode
|
||||
Thanks: @ikalafat for reporting the error
|
@ -4859,6 +4859,7 @@ process_ddl_command_start(ProcessUtilityArgs *args)
|
||||
handler = preprocess_execute;
|
||||
break;
|
||||
case T_ExplainStmt:
|
||||
check_read_only = false;
|
||||
handler = process_explain_start;
|
||||
break;
|
||||
|
||||
|
@ -8,7 +8,84 @@
|
||||
-- create_hypertable()
|
||||
--
|
||||
CREATE TABLE test_table(time bigint NOT NULL, device int);
|
||||
-- EXPLAIN should work in read-only mode, when enabling in transaction.
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_table;
|
||||
QUERY PLAN
|
||||
------------------------
|
||||
Seq Scan on test_table
|
||||
(1 row)
|
||||
|
||||
ROLLBACK;
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) SELECT * FROM test_table;
|
||||
QUERY PLAN
|
||||
------------------------------------------------
|
||||
Seq Scan on test_table (actual rows=0 loops=1)
|
||||
(1 row)
|
||||
|
||||
ROLLBACK;
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (COSTS OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
QUERY PLAN
|
||||
----------------------
|
||||
Insert on test_table
|
||||
-> Result
|
||||
(2 rows)
|
||||
|
||||
ROLLBACK;
|
||||
-- This should give an error since we are using ANALYZE and a DML. The
|
||||
-- read-only is checked when executing the actual INSERT statement,
|
||||
-- not inside our code.
|
||||
\set ON_ERROR_STOP 0
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
ERROR: cannot execute INSERT in a read-only transaction
|
||||
ROLLBACK;
|
||||
\set ON_ERROR_STOP 1
|
||||
SET default_transaction_read_only TO on;
|
||||
-- EXPLAIN should work in read-only mode, even when using the default.
|
||||
START TRANSACTION;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_table;
|
||||
QUERY PLAN
|
||||
------------------------
|
||||
Seq Scan on test_table
|
||||
(1 row)
|
||||
|
||||
ROLLBACK;
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) SELECT * FROM test_table;
|
||||
QUERY PLAN
|
||||
------------------------------------------------
|
||||
Seq Scan on test_table (actual rows=0 loops=1)
|
||||
(1 row)
|
||||
|
||||
ROLLBACK;
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (COSTS OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
QUERY PLAN
|
||||
----------------------
|
||||
Insert on test_table
|
||||
-> Result
|
||||
(2 rows)
|
||||
|
||||
ROLLBACK;
|
||||
-- This should give an error since we are using ANALYZE and a DML. The
|
||||
-- read-only is checked when executing the actual INSERT statement,
|
||||
-- not inside our code.
|
||||
\set ON_ERROR_STOP 0
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
ERROR: cannot execute INSERT in a read-only transaction
|
||||
ROLLBACK;
|
||||
\set ON_ERROR_STOP 1
|
||||
\set ON_ERROR_STOP 0
|
||||
SELECT * FROM create_hypertable('test_table', 'time');
|
||||
ERROR: cannot execute create_hypertable() in a read-only transaction
|
||||
|
@ -12,8 +12,59 @@
|
||||
--
|
||||
CREATE TABLE test_table(time bigint NOT NULL, device int);
|
||||
|
||||
-- EXPLAIN should work in read-only mode, when enabling in transaction.
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_table;
|
||||
ROLLBACK;
|
||||
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) SELECT * FROM test_table;
|
||||
ROLLBACK;
|
||||
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (COSTS OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
ROLLBACK;
|
||||
|
||||
-- This should give an error since we are using ANALYZE and a DML. The
|
||||
-- read-only is checked when executing the actual INSERT statement,
|
||||
-- not inside our code.
|
||||
\set ON_ERROR_STOP 0
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
ROLLBACK;
|
||||
\set ON_ERROR_STOP 1
|
||||
|
||||
SET default_transaction_read_only TO on;
|
||||
|
||||
-- EXPLAIN should work in read-only mode, even when using the default.
|
||||
START TRANSACTION;
|
||||
EXPLAIN (COSTS OFF) SELECT * FROM test_table;
|
||||
ROLLBACK;
|
||||
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) SELECT * FROM test_table;
|
||||
ROLLBACK;
|
||||
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (COSTS OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
ROLLBACK;
|
||||
|
||||
-- This should give an error since we are using ANALYZE and a DML. The
|
||||
-- read-only is checked when executing the actual INSERT statement,
|
||||
-- not inside our code.
|
||||
\set ON_ERROR_STOP 0
|
||||
START TRANSACTION;
|
||||
SET transaction_read_only TO on;
|
||||
EXPLAIN (ANALYZE ON, COSTS OFF, TIMING OFF, SUMMARY OFF) INSERT INTO test_table VALUES (1, 1);
|
||||
ROLLBACK;
|
||||
\set ON_ERROR_STOP 1
|
||||
|
||||
\set ON_ERROR_STOP 0
|
||||
SELECT * FROM create_hypertable('test_table', 'time');
|
||||
\set ON_ERROR_STOP 1
|
||||
@ -213,3 +264,4 @@ SELECT remove_retention_policy('test_table');
|
||||
SELECT add_job('now','12h');
|
||||
SELECT alter_job(1,scheduled:=false);
|
||||
SELECT delete_job(1);
|
||||
|
||||
|
Loading…
x
Reference in New Issue
Block a user