Skip to content

Commit

Permalink
Block merging of frozen chunks
Browse files Browse the repository at this point in the history
It should not be possible to merge a frozen chunk since it is used to
tier chunks. If the chunk is merged, it might no longer exist when the
tiering happens.
  • Loading branch information
erimatnor committed Feb 10, 2025
1 parent 41b141f commit dccd04c
Show file tree
Hide file tree
Showing 6 changed files with 34 additions and 3 deletions.
1 change: 1 addition & 0 deletions .unreleased/pr_7665
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
Fixes: #7665 Block merging of frozen chunks
2 changes: 1 addition & 1 deletion src/chunk.c
Original file line number Diff line number Diff line change
Expand Up @@ -3406,7 +3406,7 @@ ts_chunk_unset_frozen(Chunk *chunk)
}

bool
ts_chunk_is_frozen(Chunk *chunk)
ts_chunk_is_frozen(const Chunk *chunk)
{
return ts_flags_are_set_32(chunk->fd.status, CHUNK_STATUS_FROZEN);
}
Expand Down
2 changes: 1 addition & 1 deletion src/chunk.h
Original file line number Diff line number Diff line change
Expand Up @@ -200,7 +200,7 @@ extern TSDLLEXPORT bool ts_chunk_set_partial(Chunk *chunk);
extern TSDLLEXPORT bool ts_chunk_set_unordered(Chunk *chunk);
extern TSDLLEXPORT bool ts_chunk_set_frozen(Chunk *chunk);
extern TSDLLEXPORT bool ts_chunk_unset_frozen(Chunk *chunk);
extern TSDLLEXPORT bool ts_chunk_is_frozen(Chunk *chunk);
extern TSDLLEXPORT bool ts_chunk_is_frozen(const Chunk *chunk);
extern TSDLLEXPORT bool ts_chunk_set_compressed_chunk(Chunk *chunk, int32 compressed_chunk_id);
extern TSDLLEXPORT bool ts_chunk_clear_compressed_chunk(Chunk *chunk);
extern TSDLLEXPORT void ts_chunk_drop(const Chunk *chunk, DropBehavior behavior, int32 log_level);
Expand Down
9 changes: 8 additions & 1 deletion tsl/src/chunk.c
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,6 @@
#include <access/tableam.h>
#include <access/transam.h>
#include <access/xact.h>
#include <c.h>
#include <catalog/catalog.h>
#include <catalog/dependency.h>
#include <catalog/heap.h>
Expand Down Expand Up @@ -893,6 +892,14 @@ chunk_merge_chunks(PG_FUNCTION_ARGS)
errmsg("merging compressed chunks is not yet supported"),
errhint("Decompress the chunks before merging.")));

if (ts_chunk_is_frozen(chunk))
ereport(ERROR,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("cannot merge frozen chunk \"%s.%s\" scheduled for tiering",
NameStr(chunk->fd.schema_name),
NameStr(chunk->fd.table_name)),
errhint("Untier the chunk before merging.")));

if (hypertable_id == INVALID_HYPERTABLE_ID)
hypertable_id = chunk->fd.hypertable_id;
else if (hypertable_id != chunk->fd.hypertable_id)
Expand Down
17 changes: 17 additions & 0 deletions tsl/test/expected/merge_chunks.out
Original file line number Diff line number Diff line change
Expand Up @@ -353,6 +353,23 @@ ERROR: cannot merge OSM chunks
reset role;
update _timescaledb_catalog.chunk ch set osm_chunk = false where table_name = '_hyper_1_1_chunk';
set role :ROLE_DEFAULT_PERM_USER;
-- Merge frozen chunks
select _timescaledb_functions.freeze_chunk('_timescaledb_internal._hyper_1_1_chunk');
freeze_chunk
--------------
t
(1 row)

call merge_chunks('_timescaledb_internal._hyper_1_1_chunk', '_timescaledb_internal._hyper_1_2_chunk');
ERROR: cannot merge frozen chunk "_timescaledb_internal._hyper_1_1_chunk" scheduled for tiering
call merge_chunks('_timescaledb_internal._hyper_1_2_chunk', '_timescaledb_internal._hyper_1_1_chunk');
ERROR: cannot merge frozen chunk "_timescaledb_internal._hyper_1_1_chunk" scheduled for tiering
select _timescaledb_functions.unfreeze_chunk('_timescaledb_internal._hyper_1_1_chunk');
unfreeze_chunk
----------------
t
(1 row)

\set ON_ERROR_STOP 1
-- Set seed to consistently generate same data and same set of chunks
select setseed(0.2);
Expand Down
6 changes: 6 additions & 0 deletions tsl/test/sql/merge_chunks.sql
Original file line number Diff line number Diff line change
Expand Up @@ -218,6 +218,12 @@ reset role;
update _timescaledb_catalog.chunk ch set osm_chunk = false where table_name = '_hyper_1_1_chunk';
set role :ROLE_DEFAULT_PERM_USER;

-- Merge frozen chunks
select _timescaledb_functions.freeze_chunk('_timescaledb_internal._hyper_1_1_chunk');
call merge_chunks('_timescaledb_internal._hyper_1_1_chunk', '_timescaledb_internal._hyper_1_2_chunk');
call merge_chunks('_timescaledb_internal._hyper_1_2_chunk', '_timescaledb_internal._hyper_1_1_chunk');
select _timescaledb_functions.unfreeze_chunk('_timescaledb_internal._hyper_1_1_chunk');

\set ON_ERROR_STOP 1


Expand Down

0 comments on commit dccd04c

Please sign in to comment.