日期范围的唯一性约束

spi*_*ike 15 postgresql database-design exclusion-constraint postgresql-9.4

考虑一个prices包含这些列的表:

id         integer primary key
product_id integer -- foreign key
start_date date not null
end_date   date not null
quantity   integer
price      numeric
Run Code Online (Sandbox Code Playgroud)

我希望数据库强制执行这样的规则,即产品在日期范围内(通过where <date> BETWEEN start_date AND end_date)的特定数量只能有一个价格。

这种基于范围的约束可行吗?

ype*_*eᵀᴹ 29

是的,您可以使用EXCLUDE约束,这是UNIQUE约束的概括:

ALTER TABLE prices 
  ADD CONSTRAINT unique_price_per_product_quantity_daterange
    EXCLUDE  USING gist
    ( product_id WITH =, 
      quantity WITH =, 
      daterange(start_date, end_date, '[]') WITH &&   -- this is the crucial
    );
Run Code Online (Sandbox Code Playgroud)

约束可以解释为:

不允许有相同product_id、相同quantity和重叠 ( &&) 日期范围的两行。

'[]'是为希望全包的日期范围(默认是[)用于范围类型)。

请参阅有关范围类型约束的文档。您可能还需要通过运行来添加扩展(一次,对于要安装它的每个数据库):

CREATE EXTENSION btree_gist;
Run Code Online (Sandbox Code Playgroud)