zoukankan      html  css  js  c++  java
  • EventSource

    <!doctype html>
    <html>
    <head>
        <meta charset="UTF-8">
        <title>EventSource</title>
    </head>
    <body>
    <script>
        window.onload=function(){
            name();
            function name(){
                var username=prompt("请输入您的昵称");
                if(!username){
                    return false;
                }
                var xml=new XMLHttpRequest();
                xml.open("POST","/addUser");
                xml.send("name="+username);
                xml.onreadystatechange=function(){
                    if(xml.status=200&&xml.readyState==4){
                        var res=JSON.parse(xml.responseText)
                        if(res.success=="ok"){
                            alert("欢迎你的加入");
                            window.hiddenValue.value=res.name;
                            var es = new EventSource("/chat");
                            es.addEventListener("message", function(e){
                                var temp=document.createElement("li");
                                temp.innerHTML= e.data;
                                window.message.scrollIntoView();
                                window.content.appendChild(temp);
                            },false);
                        }else{
                            alert(res.msg+",如果你还想加入,行刷新重新输入用户名称");
                            //本来用的递归,但是体验不好,就改了
                            //name();
                        }
                    }
                }
            }
            var div=document.getElementsByTagName("div")[0]
            div.style.width=window.innerWidth+"px";
        }
        function sendMessage(){
            var message=window.message.value;
            if(message.trim()){
              var b=new XMLHttpRequest();
                b.open("POST","/chat");
                b.send("message="+window.message.value+"&name="+ window.hiddenValue.value);
            }
        }
    
    </script>
    <div>
        <ul id="content">
        </ul>
    </div>
    <input type="text" name="message" id="message" /><input type="button" value="发送" onclick="sendMessage()"/>
    <input type="hidden" id="hiddenValue">
    </body>
    </html>
    View Code
    var server=require("http");
    var url=require("url");
    var file=require("fs");
    var querystring=require("querystring");
    var clientName=[];
    var responseArray=[];
    
        server.createServer(function (request, response) {
            var message="";
            var name="";
           var urlContent=url.parse(request.url);
    
            //首页
            if(urlContent.pathname=="/"){
                response.writeHead(200,{"Content-Type":"text/html;charset=utf-8"});
                file.readFile("../views/Index.html",function(err,data){
                 response.end(data);
             })
                return false;
            }
           else if(urlContent.pathname=="/chat"){
    
                //发送消息
                if(request.method=="POST"){
    
                    //并不能根据response得到正确的name索引,所以前台传递name
                    request.on("data",function(data){
                        data= querystring.parse(data.toString());
                        message+=decodeURIComponent(data.message.trim());
                        name+=decodeURIComponent(data.name.trim());
                    })
                    request.on("end",function(){
                        responseArray.forEach(function(i){
                            i.write("data:"+name+"说:"+message+"
    
    ");
                        })
                    })
                    response.end();
                }else{
    
                    //建立长连接,保存相应
                    responseArray.push(response);
                    response.writeHead(200,{"Content-Type":"text/event-stream"});
                    response.write("data:已连接至服务器
    
    ");
                    request.connection.on("end",function(){
                        var index=responseArray.indexOf(response)
                        clientName.splice(index,1);
                        responseArray.splice(index,1);
                        response.end();
                    })
                }
            }else if(urlContent.pathname=="/addUser"){
    
                //添加用户名
                request.on("data",function(data){
                    data= querystring.parse(data.toString().trim());
                    name+=decodeURIComponent(data.name.trim());
                });
                request.on("end",function(){
                     response.writeHead(200,{"Content-Type":"text/json;charset=utf-8"});
                      if(clientName.some(function(i){
                              if(i==name) return true;
                          })){
                         response.write("{"success":"fail","msg":"用户名重复"}")
                     }else{
                         response.write("{"success":"ok","name":""+name+""}");
                         responseArray.forEach(function(i){
                             i.write("data:欢迎"+name+"的加入"+"
    
    ");
                         })
                         clientName.push(name);
                     }
                    response.end();
    
                })
            }
            else{
                response.writeHead(404,{"Content-Type":"text/json"});
                response.end();
            }
    }).listen(8012);
    View Code

    后台使用Node.js  博主是一个新人,会有很多不太适合的代码,希望大家能多多帮助。代码中注意路径问题。代码仍有缺陷,现在连接断开,不一定能够删除用户名称。以下的总结都是基于上面的代码的,如果有其他情况,麻烦您给我说一下,谢谢。

     
    可以跟服务器建立一个保持连接状态的连接,这样服务器能在服务端来对客户端推送信息。服务端在推送的时候要注意格式。write的内容必须是data:内容的,当write中的内容 有一个空行的时候就会推送消息,推送后,会触发EventSource的message事件,事件对象的data属性为推送的消息内容。
    当write的时候发现客户端不再保持连接的时候,就会断开连接,如果还在write,就会触发write after end错误。只有服务端第一次wirte的时候才算连接成功,第一次write即使没有空格不进行推送,客户端也会得到200的状态,正式建立连接。如果服务端没有进行及时的write,则客户端认为还在请求过程中,等待服务端响应,会有一个等待时间,在等待的时间内write会正确的建立200链接。如果超过等待时间还是没有write,则请求将会失败,将重新发起请求。如果服务端明确发回404,并且response结束,则不会再次发出请求,否则,长连接请求会一直等待正式建立连接,并过时,再请求。
    第一个长连接请求在进行请求的时候,一直没有建立正式的连接,超时后,会再次发送一个连接,在Chrome中观看的话,同一个network发了两次请求,但是这两次请求的是不同的请求
     
    open事件为服务器连接打开的时候触发
    error当发生错误的时候出发
     
    如果服务器一直不触发messag事件,则过了一段时间后,不管还以前的连接是否还在,都会重新发起一个请求。服务器与客户端针对一个EventSource的request和response只存在一个,用前面的response.write的时候,将不会推送到客户端(此response已经被客户端放弃),如果连接建立后,服务器停掉了,则客户端会一直发送长连接请求。当在客户端使用eventsource的close或者关闭网页的时候,触发自己和服务器对应的request.connection的end事件。
  • 相关阅读:
    java.lang.NoClassDefFoundError: org/jaxen/JaxenException解决方法
    解决Axis2在webservice中遇到特殊字符的无法传输的缺陷(<CDATA>数据类型)
    java使用POST发送soap报文请求webservice返回500错误解析
    HTTP直接请求webService
    Java占位符替换工具类
    sonarLint 插件配置sonarQube Server
    设计模式之十一:抽象工厂模式(Abstract Factory)
    oracle 序列重置
    windows快捷键之打开网络连接
    android中依据不同分辨率dp和px的相互转算
  • 原文地址:https://www.cnblogs.com/wofeiwofei/p/5006713.html
Copyright © 2011-2022 走看看