有条件地从PostgreSQL中的单独表中选择一列

时间:2018-11-28 16:52:42

标签: sql postgresql

我有一张通知,事件和组织表。通知具有称为event-id的列,可以为空。我正在尝试选择带有事件的通知的organization.timezone通知,以及没有事件的无时区(或null)的通知。这是表的外观示例(已删除不相关的字段)

通知表

id | message | event-id

0  |  "a"    | 0

1  |  "b"    | nil

事件表

id | org-id 

0  |  0    

1  |  1

组织表

id | timezone

0  |  "Eastern"    

1  |  "Other" 

我的查询应该返回

id | message | timezone

0  |  "a"    | "eastern"

1  |  "b"    | nil

我的尝试如下(从clojure honeysql转换,如果出现错字,请您谅解):

Select notifications.id, notifications.message, (case when notifications.event-id then organizations.timezone end) 
where (or (= notifications.event-id nil) 
          (and (= notifications.event-id events.id)
               (= events.org-id organizations.id))
end

但我知道

我的查询应该返回

id | message | case

0  |  "a"    | "eastern"

1  |  "b"    | nil

1  |  "b"    | nil

我该如何解决此问题,以免获得事件ID为null的每个通知的重复值?

1 个答案:

答案 0 :(得分:0)

您翻译的SQL无效,因此很难说出为什么要重复,但是这里有一些有效的SQL将返回您想要的结果,并希望您可以将其转换为原始格式。

设置

CREATE TABLE notifications (
  "id" INTEGER,
  "message" VARCHAR(3),
  "event-id" INTEGER
);

INSERT INTO notifications
  ("id", "message", "event-id")
VALUES
  ('0', 'a', '0'),
  ('1', 'b', NULL);

CREATE TABLE events (
  "id" INTEGER,
  "org-id" INTEGER
);

INSERT INTO events
  ("id", "org-id")
VALUES
  ('0', '0'),
  ('1', '1');

CREATE TABLE organizations (
  "id" INTEGER,
  "timezone" VARCHAR(9)
);

INSERT INTO organizations
  ("id", "timezone")
VALUES
  ('0', 'Eastern'),
  ('1', 'Other');

查询

SELECT n.id, n.message, o.timezone
FROM notifications n
LEFT JOIN events e
    ON e.id = n."event-id"
LEFT JOIN organizations o
    ON o.id = e."org-id";

结果

| id  | message | timezone |
| --- | ------- | -------- |
| 0   | a       | Eastern  |
| 1   | b       |          |

DB Fiddle