MySQL 查询,插入时出现重复问题
MySQL Query, problems with with duplicates on insert into
所以我正在使用论坛软件 Xenforo,我需要有关 SQL 查询的帮助,该查询将定期执行。该论坛将拥有大约 300-500 名活跃用户。所以没什么太大的。
目标:
所有用户 xf_users
都需要订阅 node_id 71
,但属于某些 user_group_id
的用户除外。
现在用户可以取消订阅论坛或更改 notify_on
和 send_alert
& send_email
字段。我不要那个。所以如果用户 'unsubscribe' 需要重新添加。
唯一接受的更改是 notify_on
也可以是“消息”。
总结:
如果用户不在 table 和 node_id 71
,则将用户插入 xf_forum_watch
和 node_id 71
,notify_on
设置为“thread”,send_alert
& send_email
设置为“1”。
如果 user_id
和 node_id 71
的行存在,则将 send_alert
和 send_email
更新为“1”,如果其中之一是“ 0”。如果 notify_on
为空:更新为“thread”。
到目前为止我得到了什么:
我的想法#1 是一个导火索。问题是,我从来没有写过触发器,也不知道如何解决我的问题。
想法 #2 是在 phpMyAdmin 中编写一个“事件”,它会定期运行查询。
我得到了将所有正确用户插入列表一次的代码,但我在保持列表更新方面遇到了问题。
我已经尝试使用 ON DUPLICATE KEY UPDATE
...但我没有让它按预期工作。
我的快速解决方案是删除 node_id 71
的所有行并使用下面的查询重新添加所有行,但这不允许用户 select notify_on
“消息”。还有
帮忙? ♥
table:
Screenshot of the table
(!! table 还将包含不同的行 node_id
。这些必须保持不变!!)
代码:
insert into xf_forum_watch
select user_id,
"71" as node_id,
"thread" as notify_on,
"1" as send_alert,
"1" as send_email
from xf_user
where user_group_id NOT IN (1, 18, 40);
这会将正确的用户添加到列表中(见屏幕截图)。但是,如果用户已经订阅,它会抛出错误。
希望我没有遗漏任何细节。如果还有问题,请告诉我。
感谢各种帮助。
PS:我希望我没有破坏格式。我不习惯在这里发帖。
编辑:感谢@GMB 的解决方案。
我有一个后续问题。我想将工作查询放入存储过程,但它给了我一个错误:
DELIMITER $$
CREATE PROCEDURE forceSubscribeToNode(
IN node_id_var INT
)
BEGIN
insert into xf_forum_watch
(user_id, node_id, notify_on, send_alert, send_email)
select user_id,
node_id_var as node_id,
"thread" as notify_on,
1 as send_alert,
1 as send_email
from xf_user
where user_group_id NOT IN (1, 18, 40)
on duplicate key update
send_alert = 1,
send_email = 1,
notify_on = case when notify_on is null or notify_on = '' then 'thread' else notify_on end
END $$
DELIMITER ;
错误:
#1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'END' at line 18
(第 18 行是“send_email = 1,”)
我做错了什么?
您只需在查询中添加 on duplicate key
:
insert into xf_forum_watch
(user_id, node_id, notify_on, send_alert, send_email)
select user_id,
71 as node_id,
'thread' as on notify_on,
1 as send_alert,
1 as send_email
from xf_user
where user_group_id NOT IN (1, 18, 40)
on duplicate key update
send_alert = 1,
send_email = 1,
notify_on = 'thread'
这假设您设置了正确的主键唯一性,以便正确识别重复项。
如果你想在 on duplicate key
子句中使用条件逻辑,那也是可能的:
on duplicate key update
send_alert = case when send_alert = 0 then 1 else send_alert end,
send_email = case when send_email = 0 then 1 else send_email end,
notify_on = case when notify_on is null or notify_on = '' then 'thread' else notify_on end
所以我正在使用论坛软件 Xenforo,我需要有关 SQL 查询的帮助,该查询将定期执行。该论坛将拥有大约 300-500 名活跃用户。所以没什么太大的。
目标:
所有用户 xf_users
都需要订阅 node_id 71
,但属于某些 user_group_id
的用户除外。
现在用户可以取消订阅论坛或更改 notify_on
和 send_alert
& send_email
字段。我不要那个。所以如果用户 'unsubscribe' 需要重新添加。
唯一接受的更改是 notify_on
也可以是“消息”。
总结:
如果用户不在 table 和
node_id 71
,则将用户插入xf_forum_watch
和node_id 71
,notify_on
设置为“thread”,send_alert
&send_email
设置为“1”。如果
user_id
和node_id 71
的行存在,则将send_alert
和send_email
更新为“1”,如果其中之一是“ 0”。如果notify_on
为空:更新为“thread”。
到目前为止我得到了什么:
我的想法#1 是一个导火索。问题是,我从来没有写过触发器,也不知道如何解决我的问题。
想法 #2 是在 phpMyAdmin 中编写一个“事件”,它会定期运行查询。
我得到了将所有正确用户插入列表一次的代码,但我在保持列表更新方面遇到了问题。
我已经尝试使用 ON DUPLICATE KEY UPDATE
...但我没有让它按预期工作。
我的快速解决方案是删除 node_id 71
的所有行并使用下面的查询重新添加所有行,但这不允许用户 select notify_on
“消息”。还有
帮忙? ♥
table:
Screenshot of the table
(!! table 还将包含不同的行 node_id
。这些必须保持不变!!)
代码:
insert into xf_forum_watch
select user_id,
"71" as node_id,
"thread" as notify_on,
"1" as send_alert,
"1" as send_email
from xf_user
where user_group_id NOT IN (1, 18, 40);
这会将正确的用户添加到列表中(见屏幕截图)。但是,如果用户已经订阅,它会抛出错误。
希望我没有遗漏任何细节。如果还有问题,请告诉我。
感谢各种帮助。
PS:我希望我没有破坏格式。我不习惯在这里发帖。
编辑:感谢@GMB 的解决方案。
我有一个后续问题。我想将工作查询放入存储过程,但它给了我一个错误:
DELIMITER $$
CREATE PROCEDURE forceSubscribeToNode(
IN node_id_var INT
)
BEGIN
insert into xf_forum_watch
(user_id, node_id, notify_on, send_alert, send_email)
select user_id,
node_id_var as node_id,
"thread" as notify_on,
1 as send_alert,
1 as send_email
from xf_user
where user_group_id NOT IN (1, 18, 40)
on duplicate key update
send_alert = 1,
send_email = 1,
notify_on = case when notify_on is null or notify_on = '' then 'thread' else notify_on end
END $$
DELIMITER ;
错误:
#1064 - You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'END' at line 18
(第 18 行是“send_email = 1,”)
我做错了什么?
您只需在查询中添加 on duplicate key
:
insert into xf_forum_watch
(user_id, node_id, notify_on, send_alert, send_email)
select user_id,
71 as node_id,
'thread' as on notify_on,
1 as send_alert,
1 as send_email
from xf_user
where user_group_id NOT IN (1, 18, 40)
on duplicate key update
send_alert = 1,
send_email = 1,
notify_on = 'thread'
这假设您设置了正确的主键唯一性,以便正确识别重复项。
如果你想在 on duplicate key
子句中使用条件逻辑,那也是可能的:
on duplicate key update
send_alert = case when send_alert = 0 then 1 else send_alert end,
send_email = case when send_email = 0 then 1 else send_email end,
notify_on = case when notify_on is null or notify_on = '' then 'thread' else notify_on end