我正在开发一个简单的网络聊天服务器。我有两张 table :
聊天消息:
- 行 ID
- 用户名
- 时间
- 行动
- 目标
- 留言
在线用户:
- 用户名
- 行动
- 上次事件
我如何从 onlineUsers 中删除 online.LastActive < %t%-120 的任何行,对于从 onlineUsers 中删除的任何项目,我想向 chatMsgs 添加一个新行,其中
Username=onlineUsers.username,
LastAction='logout',
Time=%t%,
Message='Timed out after 2min'
%t% 只是一个占位符,它将被 php 的 time() 返回值替换。如果可能的话,我想通过一次调用 mysqli_query 处理程序来完成此操作,尽管查询字符串可以包含 mysql 服务器的多个指令
以下工作据我所知(尚未经过彻底测试),但我想知道是否有更好的方法:
<?php
// $db is an mysqli database link.
$t = time()
$e = $t - 120,
$q = "SELECT Username FROM onlineUsers WHERE LastActive<={$e};",
$r = $db->query($q);
if (!$r)
die('db error');
elseif ($r->num_rows > 0) {
$q = '';
$r = $r->fetch_all(MYSQLI_NUM);
for ($n in $r)
$q .= "INSERT INTO chatMsg(Username,Time,Action,Message) VALUES('{$n}',{$t},'Logout','Timed out after 2min');";
$q .= "DELETE FROM onlineUsers WHERE LastActive<={$e};";
$r = $db->query($q);
if (!$r)
die('db error');
}
?>
最佳答案
如果您想在单个 SQL 语句中完成所有这些操作,那么以下内容就足够了(使用上面的 $t 和 $e 变量):
INSERT INTO chatMsg(Username, Time, Action, Message)
SELECT Username, {$t}, 'logout', 'Timed out after 2 mins'
FROM onlineUsers
WHERE LastActive <= {$e};
DELETE FROM onlineUsers WHERE LastActive <= {$e};
请注意,可能会出现竞争条件 - 如果用户在 INSERT 和 DELETE 语句之间执行某些事件,它们仍将从 onlineUsers 表中删除。您可以解决此问题,加载所有“要删除”的条目,首先调用删除,然后添加注销消息,但这与您最初的要求相反。
关于php - MySQL先插入后删除,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10959948/