[英]postgresql insert in update
INSERT INTO analytic_filter_log_device(guest_device_id,query_filter_id,created_time) VALUES (UPDATE guest_device gd
SET status = false
FROM(
SELECT
gl.guest_device_id AS device_id
FROM guest_login gl
JOIN guest_device gd ON gd.id = gl.guest_device_id AND gd.status = TRUE
JOIN guest_login_ap gla ON gla.guest_login_id = gl.id
JOIN config_ap ca ON ca.id = gla.ap_id AND ca.company_id = 1
WHERE ('2018-06-26 00:00:00' IS NULL OR '2018-07-26 23:59:59' IS NULL OR (gla.start_time, gla.end_time) OVERLAPS ('2018-06-26 00:00:00', '2018-07-26 23:59:59')) AND
get_duration_in_interval(gla.start_time, gla.duration::bigint, '2018-06-26 00:00:00', '2018-07-26 23:59:59') >= 5
GROUP BY gl.guest_device_id
HAVING COUNT(DISTINCT gl.id) >= 5
) as t1
WHERE gd.id = t1.device_id
RETURNING 1,1,now());
you can use a select
inside a values
clause like that. 您可以像这样在values
子句中使用select
。 You either specify constants using insert into .. values (1,2,3)
or you use a select query directly as the source for the insert: insert into ... select ... from
您可以使用insert into .. values (1,2,3)
指定常量,也可以直接使用select查询作为insert的源: insert into ... select ... from
You can rewrite your query in two ways: 您可以通过两种方式重写查询:
You need to use a data modifying CTE 您需要使用修改CTE的数据
with updated (guest_device_id) as (
UPDATE guest_device gd
SET status = false
FROM(
SELECT gl.guest_device_id AS device_id
FROM guest_login gl
JOIN guest_device gd ON gd.id = gl.guest_device_id AND gd.status = TRUE
JOIN guest_login_ap gla ON gla.guest_login_id = gl.id
JOIN config_ap ca ON ca.id = gla.ap_id AND ca.company_id = 1
WHERE (gla.start_time, gla.end_time) OVERLAPS ('2018-06-26 00:00:00', '2018-07-26 23:59:59'))
AND get_duration_in_interval(gla.start_time, gla.duration::bigint, '2018-06-26 00:00:00', '2018-07-26 23:59:59') >= 5
GROUP BY gl.guest_device_id
HAVING COUNT(DISTINCT gl.id) >= 5
) as t1
WHERE gd.id = t1.device_id
RETURNING gd.id
)
INSERT INTO analytic_filter_log_device(guest_device_id,query_filter_id,created_time)
select guest_device_id, 1, now()
from updated;
Alternatively use the update returning
directly in the select
query: 或者,直接在select
查询中使用update returning
的update returning
:
INSERT INTO analytic_filter_log_device(guest_device_id,query_filter_id,created_time)
select id, 1, now()
from (
UPDATE guest_device gd
SET status = false
FROM(
SELECT gl.guest_device_id AS device_id
FROM guest_login gl
JOIN guest_device gd ON gd.id = gl.guest_device_id AND gd.status = TRUE
JOIN guest_login_ap gla ON gla.guest_login_id = gl.id
JOIN config_ap ca ON ca.id = gla.ap_id AND ca.company_id = 1
WHERE (gla.start_time, gla.end_time) OVERLAPS ('2018-06-26 00:00:00', '2018-07-26 23:59:59'))
AND get_duration_in_interval(gla.start_time, gla.duration::bigint, '2018-06-26 00:00:00', '2018-07-26 23:59:59') >= 5
GROUP BY gl.guest_device_id
HAVING COUNT(DISTINCT gl.id) >= 5
) as t1
WHERE gd.id = t1.device_id
RETURNING gd.id
) t;
Note that I replaced the hard-coded returning 1
with returning gd.id
and removed the useless '2018-06-26 00:00:00' IS NULL
part (as that is always true) 请注意,我用returning gd.id
替换了硬编码的returning 1
并删除了无用的'2018-06-26 00:00:00' IS NULL
returning gd.id
'2018-06-26 00:00:00' IS NULL
部分(因为这始终是事实)
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.