我为创建了一个表来存储用户的休假数据.之后,为多列设置唯一索引,但当EXEC插入SQL时,它会再次复制数据

这是我的DDL:

create table day_off_movements
(
    id                 bigserial
        primary key,
    user_id            bigint
        constraint fk_day_off_movements_user
            references users,
    proxy_user_id      bigint
        constraint fk_day_off_movements_proxy_users
            references users,
    reason             text,
    day_off_start_date timestamp with time zone,
    day_off_end_date   timestamp with time zone,
    used_days          bigint,
    created_at         timestamp with time zone,
    updated_at         timestamp with time zone
);

索引:

create unique index idx_day_off_all
    on day_off_movements (user_id, proxy_user_id, day_off_start_date, day_off_end_date);

控制查询:

SELECT user_id,proxy_user_id,day_off_end_date,day_off_start_date,count(*)
                 FROM public.day_off_movements t
GROUP BY user_id, proxy_user_id, day_off_end_date, day_off_start_date

输出为json:

[
  {
    "user_id": 961,
    "proxy_user_id": null,
    "day_off_end_date": "2020-07-29 00:00:00.000000 +00:00",
    "day_off_start_date": "2020-07-27 00:00:00.000000 +00:00",
    "count": 3
  }
]

我哪里不对劲? 谢谢你的帮助.

推荐答案

您似乎已经在列user_idproxy_user_idday_off_start_dateday_off_end_date上创建了唯一索引.这意味着这four列的组合在您的表中应该是唯一的.然而,在您的JSON中,proxy_user_id的值是106.

在SQL中,104不被视为值,并且它不像其他值那样参与唯一性约束.这意味着,即使其他字段(user_idday_off_start_dateday_off_end_date)相同,proxy_user_id字段中包含104的多行也不会违反唯一索引.

如果您想要防止这种情况,您有几个 Select :

  • 不允许proxy_user_id字段中的空值
  • 在JSON中使用占位符值而不是100
  • 使用部分索引

以下是如何创建部分索引的示例:

CREATE UNIQUE INDEX idx_day_off_all
ON day_off_movements (
    user_id, 
    proxy_user_id, 
    day_off_start_date,
    day_off_end_date
)
WHERE proxy_user_id IS NOT NULL;

这将对proxy_user_id不为空的所有行强制唯一性约束,但如果proxy_user_id为空,则允许具有相同user_idday_off_start_dateday_off_end_date的多个行.

Postgresql相关问答推荐

横向联接返回的行数太多

错误:用户需要系统密码:postgres

使用Helm设置PostgreSQL配置

Postgres >= 和 <= 具有特殊字符的行为

如何在typeorm和嵌套js中将运行时变量设置为postgresql

转换数组类型

PostgreSQL 错误:42P01:relation "[Table]" does not exist

INSERT RETURNING 是否保证以 right的顺序返回?

SQL:当谈到 NOT IN 和 NOT EQUAL TO 时,哪个更有效,为什么?

在 Postgresql 中获取星期几

没有查询要创建的in ... error

在 postgreSQL 中更改序列名称

为 postgresql 存储过程设置隔离级别

仅在存在时重命名列

PostgreSQL 获取过go 12 小时的元素

如何在 postgresql 交叉表中用零替换空值

如何更改 PostgreSQL 中的日期样式?

如何在我的 Mac 上卸载 postgresql(运行 Snow Leopard)

在 Flask-sqlalchemy 和 Postgresql 中使用 JSON 类型

错误:无法在只读事务中执行 CREATE TABLE