在 PostgreSQL 中,我有一个表,其中包含用户可以进行的一些设置。在该表中,如果用户没有任何设置,则还会出现一个“全局”用户。
此查询返回用户的设置:
SELECT FIELD_1, FIELD_2, FIELD_3, FIELD_XML
FROM SETTINGS
WHERE FIELD_USR = :MY_USR AND FIELD_TYPE = :FIELD_TYPE
此返回“全局”用户的设置(实际上仅是 XML):
SELECT FIELD_XML AS GLOBAL_XML
FROM SETTINGS
WHERE FIELD_USR = :GLOBAL_USR AND FIELD_TYPE = :FIELD_TYPE
我想要的是一个返回带有
FIELD_1, FIELD_2, FIELD_3, FIELD_XML, GLOBAL_XML
的单行的查询。
问题是这些查询中的任何一个都可能返回 null,因此我尝试使用子查询失败了:
SELECT FIELD_1, FIELD_2, FIELD_3, FIELD_XML,
(SELECT FIELD_XML
FROM SETTINGS
WHERE FIELD_USR = :GLOBAL_USR AND FIELD_TYPE = :FIELD_TYPE) AS GLOBAL_XML
FROM SETTINGS
--Fails if the user doesn't have a setting. Swapping fails if there is no global user.
WHERE FIELD_USR = :MY_USR AND FIELD_TYPE = :FIELD_TYPE
我获得想要的结果的唯一方法是使用
FULL JOIN
和子查询:
SELECT A.FIELD_1, A.FIELD_2, A.FIELD_3, A.FIELD_XML, B.FIELD_XML AS GLOBAL_XML
FROM (SELECT FIELD_1, FIELD_2, FIELD_3, FIELD_XML
FROM SETTINGS
WHERE FIELD_USR = :MY_USR AND FIELD_TYPE = :FIELD_TYPE) A
FULL JOIN
(SELECT FIELD_XML
FROM SETTINGS
WHERE FIELD_USR = :GLOBAL_USR AND FIELD_TYPE = :FIELD_TYPE) B ON B.FIELD_TYPE = A.FIELD_TYPE
这会返回我
FIELD_1, FIELD_2, FIELD_3, FIELD_XML
(可能为空)和 GLOBAL_XML
(也可能为空)。但是有更好的方法吗?
select * from
(
SELECT '1' ordN,'User' src,FIELD_1, FIELD_2, FIELD_3, FIELD_XML
FROM SETTINGS
WHERE FIELD_USR = :MY_USR AND FIELD_TYPE = :FIELD_TYPE
union all
SELECT '1' ordN,'Global' src,FIELD_1, FIELD_2, FIELD_3, FIELD_XML
FROM SETTINGS
WHERE FIELD_USR = :GLOBAL_USR AND FIELD_TYPE = :FIELD_TYPE
) x
order by ordN
limit 1