删除分区
使用
DROP_PARTITIONS
函数删除给定表的一个或多个分区键。可以指定单个分区键或分区键范围。
例如,对新表进行分区中显示的表按列 order_date
进行分区:
=> CREATE TABLE public.store_orders
(
order_no int,
order_date timestamp NOT NULL,
shipper varchar(20),
ship_date date
)
PARTITION BY YEAR(order_date);
鉴于此表定义,Vertica 会为每个唯一的 order_date
年份(在本例中为 2017、2016、2015 和 2014 年)创建一个分区键,并相应地将数据划分到不同的 ROS 容器中。
以下 DROP_PARTITIONS
语句从表 store_orders
中删除与分区键 2014 关联的所有订单记录:
=> SELECT DROP_PARTITIONS ('store_orders', 2014, 2014);
Partition dropped
拆分分区组
如果表 partition 子句包括 GROUP BY
子句,则分区将按其分区组键在 ROS 中合并。 DROP_PARTITIONS
随后可以指定给定分区组内或跨多个分区组的分区键范围。无论哪种情况,删除操作都要求 Vertica 拆分存储这些分区的 ROS 容器。为此,该函数的 force_split
参数必须设置为 true。
例如,上面显示的 store_orders
表可以使用 GROUP BY
子句重新分区,如下所示:
=> ALTER TABLE store_orders
PARTITION BY order_date::DATE GROUP BY DATE_TRUNC('year', (order_date)::DATE) REORGANIZE;
由于之前删除了 2014 年的所有订单记录,order_date
值现在跨越三个年份(2017 年、2016 年和 2015 年)。因此,Tuple Mover 为每年创建三个分区组键,并为每个组指定一个或多个 ROS 容器。然后,它将 store_orders
分区合并到相应的组中。
以下 DROP_PARTITIONS
语句指定删除跨越两个年份(2014 年和 2015 年)的订单日期:
=> SELECT DROP_PARTITIONS('store_orders', '2015-05-30', '2016-01-16', 'true');
Partition dropped
删除操作要求 Vertica 从两个分区组(2015 和 2016)删除分区。这些组至少跨越两个 ROS 容器,必须拆分这些容器才能移除目标分区。因此,将函数的 force_split
参数设置为 true。
调度分区删除
如果硬件具有固定的磁盘空间,则可能需要配置一个定期执行的进程,以便通过删除分区来迁出旧数据。
例如,如果空间只够将数据存储固定的天数,请将 Vertica 配置为删除最旧的分区键。为此,请创建一个基于时间的作业调度程序(例如 cron
),以计划在低负载期间删除分区键。
如果数据输入速率具有峰值和谷值,则可以使用以下两种技术来管理分区键删除方式:
-
设置一个定期(每天)检查磁盘空间的进程。如果已用磁盘空间百分比超出特定阈值(例如 80%),则删除最旧的分区键。
-
在分区中添加一个可根据行计数等指标递增的假列。例如,每次行计数增加 100 行时,该列可能会递增。设置一个定期(每天)查询此列的进程。如果新列中的值超出特定阈值(例如 100),请删除最旧的分区键,并将该列的值设置回 0。
表锁定
DROP_PARTITIONS
会在目标表上获取一个独占的 O 锁,以阻止可能会影响表数据的任何 DML 操作(DELETE
、UPDATE
、INSERT
或 COPY
)。该锁还会阻止在 SERIALIZABLE 隔离级别发出的 SELECT
语句。
如果操作无法在目标表上获取 O lock,Vertica 将尝试关闭该表上运行的任何内部 tuple mover 会话。如果成功,则可以继续操作。在用户会话中运行的显式 Tuple Mover 操作不会关闭。如果显式 Tuple Mover 操作在表上运行,则该操作仅在 Tuple Mover 操作完成后继续。