【问题标题】:Coding technique efficiency question: chatbox design编码技术效率问题:聊天框设计
【发布时间】:2011-05-24 17:06:13
【问题描述】:

我有一个问题想问任何有处理 PHP、Jquery 和 SQL 复杂编码经验的人。我意识到我写了很多,但我想详细一点。我有一个我能想到的 1 解决方案的问题,但它似乎效率不高,尤其是在有大量交通。我有一个存储来自用户的消息的表。我正在设计一个聊天平台,用户可以在其中打开聊天框并向其他朋友发送即时消息。

我需要拥有它的能力,所以当用户从他的在线朋友那里打开一个框并发送一条消息时,该朋友将弹出一个带有消息或消息的聊天框,并且该框将从那里更新。我希望该框还可以在用户导航站点直到他关闭该框之前,从一个页面到另一个页面维护先前发送的消息。发生这种情况时,我创建了一个查看列,我可以将当​​时该框中的所有消息标记为 1。从那时起,这些消息将不会弹出。只有新的会。所以关闭盒子基本上会重置它。

我有一个简单的 JSON 函数,用于发送信息,一个 php 处理程序运行查询并返回所有消息。然后将它们分类到各自的盒子中。

我认为一种解决方案是在 json 代码上设置一个刷新时间间隔,并不断检查viewed=0 的消息。如果有并且该框尚未弹出,它会将消息以 html 格式放入框中。这样做的问题是查询将选择用户收到的所有消息,并且他们将不断覆盖不会在视觉上显示但似乎对系统征税的框。我试图想出一种方法,该方法涉及一个查询,该查询检查时间戳是否大于 jquery 函数中发送的时间戳。 如果有人有任何建议或有用的文章或信息,我将不胜感激。

$.getJSON("../collabrr/chatbox.php?action=view&load=initial&receiver="+username+ "&token="+ token, function(json) {  
  for(i=0; i < json.length; i++) {
    openchat({ data : { user : json[i].user }}); //makes chatbox open up with name of sender

    $('#chatbox[data-name="'+json[i].user+'"]>#messagebox').prepend('<div id="chatbox-response">'+json[i].user+':'+json[i].message+'</div>').find('li').fadeIn(1500);
  }

});

$sql = 'SELECT timestamp, user, message, receiver
  FROM chatbox WHERE receiver=? AND viewed=? ORDER BY timestamp DESC';
$stmt = $conn->prepare($sql);
$result=$stmt->execute(array($_GET['receiver'],0));
        }

Field     Type          Null      Key   Default     Extra
id            int(6)    NO    PRI   NULL            auto_increment
convo_id  varchar(35)   NO      NULL     
timestamp int(11)   NO      NULL     
user      varchar(25)   NO      NULL     
receiver  varchar(25)   NO      NULL     
message   varchar(150)  NO      NULL     
viewed    int(1)    NO      NULL    

【问题讨论】:

    标签: php jquery sql


    【解决方案1】:

    轮询服务器以获取更新是一种解决方案。我可以再给你一个,但是我不知道你是否有可用的资源/时间来实施它。

    简而言之,这就是我在实现类似的东西时所做的:基本思想是使用 Websockets 并保持一个对后端开放的套接字。最好使用node.js 使用socket.io,因为它具有非阻塞性质。然后您将使用redis 及其pub/sub 功能从客户端A 接收更新并将它们推送到客户端B。

    当客户端 A 加载您的网站时,它通过 Websocket 连接到正在运行的 node.js 进程,称为 PUBLISHER。 Publisher 为该客户端订阅 redis 中的特定频道。客户端 B 加载您的网站,它还连接到 Publisher 等,就像客户端 A 一样。现在客户端 A 写入一些内容并将其发送到 Publisher。 Publisher 将此事件发布到其 redis 通道。客户 B 受到关注,因为他不仅订阅了他的频道,还订阅了 A 的频道(如果您有的话,可能是因为他们是您社交网站上的朋友)。

    这听起来可能相当复杂,实现起来也不是那么容易,但也许这可以让您对如何实现这样的 pub/sub 系统有一个基本的了解。轮询应该只作为一种后备解决方案,因为在高流量网站上,每隔 100 毫秒左右使用 ajax 请求不断轮询您的网络服务器会导致极端负载。

    【讨论】:

    • 我需要多少台服务器?这个过程听起来相当复杂。我在运行 linux 的虚拟服务器上运行我的站点,因为它仍在开发中并且没有收到高流量。鉴于我的情况,您是否仍建议实施此解决方案?
    • 还有,redis是怎么工作的?它说你可以存储信息,它是用 C 编写的,但它是什么,一个在服务器上运行的程序?
    • 另外,你的系统甚至使用数据库吗?
    • @Scarface 您需要多少台服务器取决于您对高可用性的需求。实际上,您只需要一个即可开始。网络服务器侦听端口 80,node.js 可能在 8010 上,redis 作为恶魔进程在端​​口 6379 上运行。Redis 是一个高性能数据结构服务器(基本上是 steroids 上的 memcache),作为一个额外的好东西,它内置了 pub/sub . 正如我所说,这并不容易实现,但恕我直言,这是实现它的正确方法。这实际上取决于您有多少时间用于您的项目,以及您是否愿意实施这样的解决方案。
    • 我们搭建的系统以mysql为主存储后端,同时也将数据存储在redis中,供node.js后端使用。
    【解决方案2】:

    听起来您想要的是一个 Ajax 推送解决方案(也称为“彗星”,原因不明)。

    这是一个解释如何使用 PHP/Javascript 进行操作的网站:http://www.zeitoun.net/articles/comet_and_php/start

    另见维基百科页面:http://en.wikipedia.org/wiki/Comet_%28programming%29 (呵呵,我注意到其中还包括对“彗星”名称的解释)

    【讨论】:

    • 这很有趣,而且肯定是我很快就会研究的东西。谢谢斯普德利!但是,由于时间原因,我不介意来回发送请求,因为彗星在实现方面看起来非常复杂,而且我对原型不熟悉。就我思考做事的方式而言,忽略不使用彗星的低效率,你怎么看?
    猜你喜欢
    • 2021-05-16
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-06-23
    • 1970-01-01
    • 1970-01-01
    • 2023-03-05
    相关资源
    最近更新 更多