mirror of
https://github.com/ebean-orm/ebean.git
synced 2026-10-23 10:03:59 +00:00
#1881 - Update Postgres init helper procedures for DB table partitions
This commit is contained in:
+18
-66
@@ -18,9 +18,7 @@ begin
|
||||
period_end timestamptz,
|
||||
period_name text,
|
||||
base_name text,
|
||||
part_name text,
|
||||
unique_column text,
|
||||
index_column text
|
||||
part_name text
|
||||
);
|
||||
end if;
|
||||
end$$;
|
||||
@@ -28,38 +26,15 @@ end$$;
|
||||
------------------------------------------------------------------------------------
|
||||
-- Function: _partition_create
|
||||
--
|
||||
-- Internal helper method to create a partition given meta data and
|
||||
-- optional extra function to call (typically to create additional indexes)
|
||||
-- Internal helper method to create a partition given meta data
|
||||
------------------------------------------------------------------------------------
|
||||
create or replace function _partition_create(meta partition_meta, extra text)
|
||||
create or replace function _partition_create(meta partition_meta)
|
||||
returns text
|
||||
language plpgsql
|
||||
set timezone to 'UTC'
|
||||
as $$
|
||||
declare
|
||||
idx_col text;
|
||||
idx_name text;
|
||||
begin
|
||||
|
||||
execute format('create table if not exists %I partition of %I for values from (''%s'') TO (''%s'')', meta.part_name, meta.base_name, meta.period_start, meta.period_end);
|
||||
|
||||
if (length(meta.unique_column) > 0) then
|
||||
execute format('create unique index if not exists uq_%I ON %I (%I)', meta.part_name, meta.part_name, meta.unique_column);
|
||||
end if;
|
||||
|
||||
if (length(meta.index_column) > 0) then
|
||||
-- delimited for multiple indexes
|
||||
foreach idx_col in array regexp_split_to_array(meta.index_column,';')
|
||||
loop
|
||||
idx_name = replace(idx_col, ',', '_');
|
||||
execute format('create index if not exists ix_%I_%s ON %I (%s)', meta.part_name, idx_name, meta.part_name, idx_col);
|
||||
end loop;
|
||||
end if;
|
||||
|
||||
if (length(extra) > 0) then
|
||||
execute 'select ' || extra || '($1)' using meta;
|
||||
end if;
|
||||
|
||||
return meta.part_name;
|
||||
end;
|
||||
$$;
|
||||
@@ -74,9 +49,7 @@ $$;
|
||||
create or replace function _partition_meta(
|
||||
mode text,
|
||||
asOf date,
|
||||
baseName text,
|
||||
uniqueColumn text,
|
||||
indexColumn text)
|
||||
baseName text)
|
||||
returns partition_meta
|
||||
language plpgsql
|
||||
set timezone to 'UTC'
|
||||
@@ -108,29 +81,13 @@ begin
|
||||
select asOfUtc, asOfUtc + interval '1 month' into meta.period_start, meta.period_end;
|
||||
end if;
|
||||
|
||||
select partName, baseName, format('%s_%s', baseName, partName), uniqueColumn, indexColumn
|
||||
into meta.period_name, meta.base_name, meta.part_name, meta.unique_column, meta.index_column;
|
||||
select partName, baseName, format('%s_%s', baseName, partName)
|
||||
into meta.period_name, meta.base_name, meta.part_name;
|
||||
|
||||
return meta;
|
||||
end;
|
||||
$$;
|
||||
|
||||
create or replace function _partition_meta_initdate(
|
||||
meta partition_meta,
|
||||
initDate date)
|
||||
returns partition_meta
|
||||
language plpgsql
|
||||
set timezone to 'UTC'
|
||||
as $$
|
||||
begin
|
||||
meta.period_start = initDate;
|
||||
return meta;
|
||||
end;
|
||||
$$;
|
||||
|
||||
|
||||
-- select _partition_over('week', current_date, 4);
|
||||
|
||||
------------------------------------------------------------------------------------
|
||||
-- Function: _partition_over
|
||||
--
|
||||
@@ -180,24 +137,21 @@ $$;
|
||||
--
|
||||
-- Examples:
|
||||
--
|
||||
-- select partition('week', 'trip', 'id', 'when_started', 4);
|
||||
-- select partition('month', 'event', 'id', 'event_timestamp', 1);
|
||||
-- select partition('week', 'trip', 4);
|
||||
-- select partition('month', 'event', 1);
|
||||
--
|
||||
------------------------------------------------------------------------------------
|
||||
create or replace function partition(
|
||||
mode text, -- one of 'day','week','month','year'
|
||||
baseName text, -- base table name
|
||||
uniqueColumn text, -- optional unique column
|
||||
indexColumn text, -- optional column to index
|
||||
partitionCount integer default 0, -- number of additional partitions
|
||||
fromDate date default current_date, -- date to create first partition for
|
||||
extra text default '') -- custom function to call per partition
|
||||
fromDate date default current_date) -- date to create first partition for
|
||||
returns text
|
||||
language plpgsql
|
||||
set timezone to 'UTC'
|
||||
as $$
|
||||
begin
|
||||
perform _partition_create(_partition_meta(mode, poDate, baseName, uniqueColumn, indexColumn), extra)
|
||||
perform _partition_create(_partition_meta(mode, poDate, baseName))
|
||||
from _partition_over(mode, fromDate, partitionCount) poDate;
|
||||
return 'done';
|
||||
end;
|
||||
@@ -212,18 +166,15 @@ $$;
|
||||
--
|
||||
-- Examples:
|
||||
--
|
||||
-- select partition_init(date '2001-01-01', 'week', 'event', 'id', 'event_timestamp', 4);
|
||||
-- select partition_init(date '2001-01-01', 'week', 'event');
|
||||
--
|
||||
------------------------------------------------------------------------------------
|
||||
create or replace function partition_init(
|
||||
initDate date, -- first partition period start date
|
||||
mode text, -- one of 'day','week','month','year'
|
||||
baseName text, -- base table name
|
||||
uniqueColumn text, -- optional unique column
|
||||
indexColumn text, -- optional column to index
|
||||
partitionCount integer default 0, -- number of additional partitions
|
||||
fromDate date default current_date, -- date to create first partition for
|
||||
extra text default '') -- custom function to call per partition
|
||||
fromDate date default current_date) -- date to create first partition for
|
||||
returns text
|
||||
language plpgsql
|
||||
set timezone to 'UTC'
|
||||
@@ -232,13 +183,14 @@ declare
|
||||
meta partition_meta;
|
||||
begin
|
||||
-- override the period start for the first partition
|
||||
meta = _partition_meta(mode, fromDate, baseName, uniqueColumn, indexColumn);
|
||||
meta = _partition_meta_initdate(meta, initDate);
|
||||
perform _partition_create(meta, extra);
|
||||
meta = _partition_meta(mode, fromDate, baseName);
|
||||
meta.period_start = initDate;
|
||||
perform _partition_create(meta);
|
||||
|
||||
if (partitionCount > 0) then
|
||||
-- create additional migrations normally
|
||||
perform _partition_create(_partition_meta(mode, poDate, baseName, uniqueColumn, indexColumn), extra)
|
||||
-- create additional partitions normally
|
||||
fromDate = fromDate + interval '1 day';
|
||||
perform _partition_create(_partition_meta(mode, poDate, baseName))
|
||||
from _partition_over(mode, fromDate, partitionCount) poDate;
|
||||
end if;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user