我有一个存储用户订阅信息的表,现在我想添加一个约束,使用户在同一时间段内没有多次订阅该产品。我试图这样做:
CREATE INDEX user_sub_exclusion_index ON user_sub USING GIST (
user_id,
tsrange(sub_start_time, sub_end_time)
);
并创建约束:
ALTER TABLE user_sub ADD CONSTRAINT user_sub_exclusion_constraint EXCLUDE USING GIST (
user_id WITH =,
tsrange(sub_start_time, sub_end_time) WITH &&
);
似乎 tsrange 需要时间戳数据类型。我试过范围函数但没有用。我应该怎么做才能使要点索引工作并且不更改数据类型?这是表 DDL:
CREATE TABLE public.user_sub (
id int8 NOT NULL GENERATED ALWAYS AS IDENTITY,
app_id varchar NOT NULL,
product_id int4 NOT NULL,
iap_product_id varchar NOT NULL,
created_time int8 NOT NULL,
updated_time int8 NOT NULL,
user_id int8 NOT NULL,
sub_start_time int8 NOT NULL DEFAULT 0,
sub_end_time int8 NOT NULL DEFAULT 0,
enabled int2 NOT NULL DEFAULT 1,
order_id varchar NOT NULL,
CONSTRAINT user_sub_new_pk PRIMARY KEY (id),
CONSTRAINT user_sub_new_un UNIQUE (order_id)
);
我已经尝试将字段更改为 timestamptz 并像这样调整 sql:
CREATE INDEX user_sub_exclusion_index ON user_sub USING GIST (
user_id,
tstzrange(sub_start, sub_end)
);
显示错误:
SQL Error [42704]: ERROR: data type bigint has no default operator class for access method "gist"
Hint: You must specify an operator class for the index or define a default operator class for the data type.
我应该怎么做才能添加约束?
默认情况下,PostgreSQL 不包括 GiST 运算符类的基本类型,如
bigint
. 您必须创建一个提供所需运算符类的标准扩展:然后你可以创建你的约束。
请注意,添加排除约束会自动创建一个 GiST 索引。