postgresql删除分区表

时间:2014-11-21 03:11:15

标签: function postgresql partition

我是Postgresql的新手,并且不知道如何管理分区表 我有基于日的分区表。在插入数据之前,触发器检查日期并放入相应的子表中 例如,
11.15.2014 - 插入名为11-15-2014_log的表中 11.16.2014 - 插入名为11-16-2014_log的表中 现在我想创建将删除旧子表的函数,例如,超过90天的表。 我应该根据其tablename查找并删除子表(因为它包含创建日期)或者我应该在主表中找到超过90天的记录吗? 任何建议或提示将不胜感激。感谢。

3 个答案:

答案 0 :(得分:1)

关于删除分区,下面的示例删除sales表的分区。使用以下命令创建销售表:

CREATE TABLE sales
(
  dept_no     number,   
  part_no     varchar2,
  country     varchar2(20),
  date    date,
  amount  number
)
PARTITION BY LIST(country)
(
  PARTITION europe VALUES('FRANCE', 'ITALY'),
  PARTITION asia VALUES('INDIA', 'PAKISTAN'),
  PARTITION americas VALUES('US', 'CANADA')
);

查询ALL_TAB_PARTITIONS视图将显示分区名称:

acctg=# SELECT partition_name, server_name, high_value FROM ALL_TAB_PARTITIONS;
 partition_name | server_name |     high_value      
----------------+-------------+---------------------
 europe         | seattle     | 'FRANCE', 'ITALY'
 asia           | chicago     | 'INDIA', 'PAKISTAN'
 americas       | boston      | 'US', 'CANADA'
(3 rows)

要从sales表中删除Americas分区,请调用以下命令:

ALTER TABLE sales DROP PARTITION americas;

查询ALL_TAB_PARTITIONS视图表明该分区已成功删除:

acctg=# SELECT partition_name, server_name, high_value FROM ALL_TAB_PARTITIONS;
 partition_name |     high_value      
----------------+---------------------
 asia           | 'INDIA', 'PAKISTAN'
 europe         | 'FRANCE', 'ITALY'
(2 rows)

答案 1 :(得分:0)

我将删除主表中较旧的记录,例如:

DELETE FROM master_table WHERE creation_date < 'today' - INTERVAL '90 days';

但是,我的建议是将此查询计时为服务器的 sleepy time 运行,比如说凌晨5点

答案 2 :(得分:0)

对于那些最终在这里寻找如何删除PostgreSQL中的表分区的人来说,这是现代的答案。

解决方案不是使用DELETE语句,因为这将删除数据而不删除保存数据的相应表分区。 OP询问管理分区表,而不是删除记录,因此使用DELETE语句的任何解决方案都会增加删除记录的不必要的数据库开销,使空分区表保留在原位,并完全忽略使用分区的主要好处之一;当表不再有用时将其删除。

在这种情况下,解决方案必须是DROP不再需要的分区表。我已经在我的生产环境中编写了解决此问题的解决方案,答案是here

要解决OP的问题,我编写的函数可以用两个小修改来修改 fullTablename 变量和日期格式。必须从

更改fullTablename变量行
fullTablename := base_table_name || '_' || to_char(startTime, dateFormat);

到这样的YYYY-MM-DD_log格式

fullTablename := to_char(startTime, dateFormat) || '_' || base_table_name;

然后需要从

稍微修改日期格式
WHEN partition_plan='day'   THEN 'YYYYDDD'

到声明的表命名约定

WHEN partition_plan='day'   THEN 'YYYY-MM-DD'

然后可以从日常维护脚本中调用调用该函数来执行清理的SQL查询,如下所示:

SELECT public.drop_partitions(current_date-180, 'public', 'log', 5, 'day');

哪个会删除早于 180 天前 5 天的YYYY-MM-DD_log表。对于删除数十个或数百个旧表分区的初始运行,可以将 5 设置为更高的值,以达到所需的效果。