# 数据推送

# socket,websocket,socketio 之间的关系

  • socket(套接字): 套接字是通信的基石,是支持 TCP/IP 协议的路通信的基本操作单元。从所处的地位来说,套接字上联应用进程,下联网络协议栈,是应用程序通过网络协议进行通信的接口,是应用程序与网络协议根进行交互的接口。
  • websocket: websocket 是基于 TCP 传输层协议实现的一种标准协议,用于在客户端和服务端双向传输数据。
  • sockio: socket.io 是将 Websocket、ajax 和其它的通信方式全部封装了统一的通信接口。兼容所有浏览器,解决浏览器不兼容问题。socketio 包含 websocket。

# Comet

环境 xampp

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>datapush</title>
  </head>
  <body>
    <script
      type="text/javascript"
      src="http://libs.baidu.com/jquery/2.0.0/jquery.min.js"
    ></script>
    <script type="text/javascript">
      function conn() {
        $.ajax({
          url: "./data.php",
          dataType: "json",
          success: function(data) {
            console.log(data);
            conn();
          },
        });
      }
      conn();
    </script>
    <!-- <script type="text/javascript">
      var getXmlHttpRequest = function () {
        if (window.XMLHttpRequest) {
          return new XMLHttpRequest();
        } else if (window.ActiveXObject) {
          return new ActiveXObject("Microsoft.XMLHTTP");
        }
      };
      var xhr = getXmlHttpRequest();
      xhr.onreadystatechange = function () {
        console.log(xhr.readyState);
        // readState 3 正在结束数据
        if (xhr.readyState === 3 && xhr.status == 200) {
          console.log(xhr.responseText);
        }
      };
      xhr.open("get", "data.php", true);
      xhr.send("");
    </script> -->
  </body>
</html>
<?php
  header("Content-type:  application/json;charset=utf-8");
  header("Cache-Control:max-age=0");
  $i=0;
  while(true){
    $res=array("success"=>"ok","text"=>$random);
    echo json_encode($res);
    exit();
  }
  // while($i<90000){
  //   sleep(2);
  //   $i++;
  //   $random = rand(1, 999);
  //   echo($random);
  //   echo("<br/>");
  //   // $res=array("success"=>"ok","text"=>$random);
  //   // echo json_encode($res);
  //   ob_flush();
  //   flush();
  // }
?>

# WebSocket

<script type="text/javascript">
  $(function() {
    var i = 0;
    var socket = io.connect("http://localhost:3000");
    socket.on("open", function() {
      console.log("已连接");
      socket.send("连接成功");
    });
    socket.on("test", function(json) {
      console.log("test", json);
    });
  });
</script>
var http = require("http");
var server = http.createServer(app);
var io = require("socket.io")(server);

io.on("connection", function(socket) {
  socket.emit("open");
  // 对message事件的监听
  socket.on("message", function(msg) {
    console.log("服务端收到客户端的信息", msg);
    // 返回信息
    socket.emit("test", "server ready");
    // 广播向其他用户
    socket.broadcast.emit("text", "server ready");
  });
  socket.on("disconnect", function() {});
});
app.get("/", function(req, res) {
  res.sendfile("views/index.html");
});

# SSE(Server-Sent Events)

SSE 用于 web 应用程序刷新数据,不需要用户做任何动作。
SSE 工作于存在 HTTP/HTTPS 协议,支持代理服务器与认证技术。SSE 是文本协议,你能轻易的调试它。如果你需要发送大部二进制数据从服务端到客户端,websocket 是更好的选择。

<!-- index.html -->
<meta charset="UTF-8" />
<script type="text/javascript">
  var source;
  function init(argument) {
    source = new EventSource("http://localhost/sse/data.php");
    source.onopen = function() {
      console.log("连接已建立", this.readyState);
    };
    source.onmessage = function(event) {
      console.log("从服务器时时获取的数据", event);
    };
    source.onerror = function() {};
  }
  init();
</script>
<?php
  header("Content-Type:text/event-stream;charset=utf-8");
  header("Access-Control-Allow-Origin:http://127.0.0.1/");
  echo "data: 现在北京时间是".date("H:i:s")."\r\n\r\n";
?>