账号密码登录
微信安全登录
微信扫描二维码登录

登录后绑定QQ、微信即可实现信息互通

手机验证码登录
找回密码返回
邮箱找回 手机找回
注册账号返回
其他登录方式
分享
  • 收藏
    X
    ajax长轮询时php被阻塞
    25
    0

    刚接触实时通讯这块,知道用websocket更高效,但我想了解轮询的实现过程,循序渐进

    短轮询用定时器setInterval已经实现了,但长轮询时后台进入死循环模块导致整个网站的php网页无响应,比如刷新页面、提交消息都没法进行。具体代码如下:

    chat.php:

    <div class="chat_content_input">
                <div>
                    <textarea name="chat_input" class="chat_input"
                              style="width: 570px;height: 120px;margin: 5px;resize: none"></textarea>
                </div>
                <div style="text-align: right">
                    <button class="chat_post">发送</button>
                </div>
    </div>

    chat.js:

    //拉取新消息
                var setting = {
                    type: "POST",
                    dataType: "html",
                    url: "./util/action.php?action=message_pull",
                    data: {uid_get: $('#chat_content').attr('uid')},//传递目标用户uid
                    success: function (msg) {
                        if (msg.length > 0) {
                            $('.chat_content_list_table').append(msg);//追加消息列表
                        }
                        $.ajax(setting);//立即继续请求
                    }
                };
                $.ajax(setting);

    action.php中的对应函数:

    function message_pull($conn)
    {
        session_start();
        session_write_close();//关闭session锁并没有效果,仍被阻塞
        $uid_post = $_SESSION['userinfo'][0]['id'];//发送者,即当前登录用户uid
        $uid_get = $_POST['uid_get'];//消息目标用户uid
        $message_list = '';
    
        //建立长连接,直到拉取到新消息后断开连接
        while (true) {
            //查询新消息
            foreach (select($conn, 'message', "(uid_get=$uid_post AND uid_post=$uid_get AND read_flag<>1)") as $message) {
                update($conn, 'message', 'read_flag=1', "id={$message['id']}");//每读取一条则将其置为已读状态
                $message_list .= "<tr class='content_list_post' style='text-align: right;font-size: 18px'><td>" . $message['content'] . "</td></tr><tr><td style='text-align: right;font-size: 8px'>" . $message['post_time'] . "</td></tr>";
            }
            if (strlen($message_list) > 0) {
                echo $message_list;//输出新消息
                break;//断开连接
            }else 
                sleep(1);//挂起1s后继续查询
        }
        mysqli_close($conn);
    }

    之后测试一下,发现一旦php后台进入while循环,就会导致被阻塞,但我看到网上很多demo都这样写,于是感觉很疑惑,谢谢大大们指教

    参考链接:https://www.cnblogs.com/zhenb...

    1
    打赏
    收藏
    点击回答
    您的回答被采纳后将获得:提问者悬赏的 10 元积分
        全部回答
    • 0
    • 爱只为她 普通会员 1楼
      502 Bad Gateway

      502 Bad Gateway


      nginx
    更多回答
    扫一扫访问手机版
    • 回到顶部
    • 回到顶部