<head>
<script type="text/javascript">
var ws = new WebSocket("ws://localhost:7272")
//申请一个WebSocket对象,参数是服务端地址,同http协议使用http://开头一样,WebSocket协议的url使用ws://开头,另外安全的WebSocket协议使用wss://开头
ws.onopen = function(){
//当WebSocket创建成功时,触发onopen事件
console.log("open")
ws.send("hello")//将消息发送到服务端
}
ws.onmessage = function(e){
//当客户端收到服务端发来的消息时,触发onmessage事件,参数e.data包含server传递过来的数据
var data = JSON.parse(e.data)
switch(data['type']){
// 服务端ping客户端
case 'ping':
ws.send('{"type":"pong"}')
console.log("ping: "+e.data)
break
// 登录 更新用户列表
case 'login':
console.log("login: "+e.data)
//{"type":"login","client_id":xxx,"client_name":"xxx","client_list":"[...]","time":"xxx"}
/*say(data['client_id'], data['client_name'], data['client_name']+' 加入了聊天室', data['time'])
if(data['client_list'])
{
client_list = data['client_list']
}
else
{
client_list[data['client_id']] = data['client_name']
}
flush_client_list()
console.log(data['client_name']+"登录成功")*/
break
// 发言
case 'say':
console.log("say: "+e.data)
//{"type":"say","from_client_id":xxx,"to_client_id":"all/client_id","content":"xxx","time":"xxx"}
//say(data['from_client_id'], data['from_client_name'], data['content'], data['time'])
break
// 用户退出 更新用户列表
case 'logout':
console.log("logout: "+e.data)
//{"type":"logout","client_id":xxx,"time":"xxx"}
// say(data['from_client_id'], data['from_client_name'], data['from_client_name']+' 退出了', data['time'])
//delete client_list[data['from_client_id']]
// flush_client_list()
}
}
ws.onclose = function(e){
//当客户端收到服务端发送的关闭连接请求时,触发onclose事件
console.log("close")
}
ws.onerror = function(e){
//如果出现连接、处理、接收、发送数据失败的时候触发onerror事件
console.log(error)
}
function login()
{
console.log("login:111")
var login_data = '{"type":"login","client_name":"zyx","room_id":"1"}'
console.log("websocket握手成功,发送登录数据:"+login_data)
ws.send(login_data)
}
function send()
{
console.log("send:111")
ws.send('{"type":"say","to_client_id":"all","to_client_name":"222","content":"txt"}')
}
function send2()
{
console.log("send:111")
ws.send('{"type":"say","to_client_id":"7f00000108fc00000011","to_client_name":"222","content":"txt"}')
}
</script>
</head>
<body>
<div onclick="login()" style="width:100pxheight:80px">
登录
</div>
<div onclick="send()" style="width:100pxheight:80px">
发送
</div>
<div onclick="send2()" style="width:100pxheight:80px">
发送2
</div>
</body>
</html>
WebSocket协议是基于TCP的一种新的网络协议。 浏览器通信通常是基于HTTP 协议,为什么还需要另一个协议?因为http只能由客户端发起,不能由服务端发起。
而WebSocket 浏览器和服务器只需要完成一次握手,两者之间就直接可以创建持久性的连接,并进行双向数据传输。
WebSocket规范
WebSocket 协议本质上是一个基于 TCP 的协议。为了建立一个 WebSocket 连接,客户端浏览器首先要向服务器发起一个 HTTP 请求,这个请求和通常的 HTTP 请求不同,包含了一些附加头信息,附加信息如图所示
连接过程(以js(客户端)和java(服务器端)为例)
js:ws.send( String msg) ps:入参可以是字符串或者json字符串java:onMessage(String message)message为客户端传来的信息
java:sendUser( String msg) js:ws.onmessage
4.断开连接 onclose ( CloseReason reason)
CloseReason.CloseCode ( WebSocket关闭连接的状态码,类似http的404)
js部分:
java部分(javax实现):
ps: session 用来唯一标识连接对象
使用注解@ServerEndpoint
参考文献
javax websocket:(服务端实现api文档) https://tomcat.apache.org/tomcat-8.0-doc/websocketapi/javax/websocket/package-summary.html
js websocket:(客户端api文档) https://developer.mozilla.org/zh-CN/docs/Web/API/WebSocket
rfc6455 (websocket协议规范): https://datatracker.ietf.org/doc/rfc6455/ ** 产品介绍**
websocket 是一种网络通信协议,一般用来进行实时通信会使用到
websocket 协议和 http 协议类似,http 协议有一个缺陷,只能由客户方端发起请求,服务端根据请求 url 和传过去的参数返回对应结果
websocket 是双向通信的,只要 websocket 连接建立起来,可以由客户端给服务端发送数据,也可以由服务端主动给客户端发送数据
websocket 适用场景:聊天室
websocket 相关简介,可以看 阮老师的文章
nodejs 可以通过 nodejs-websocket 来实现创建一个 websocket 的服务
nodejs-websocket 用法
文档地址: https://www.npmjs.com/package/nodejs-websocket
node 创建的 websocket 服务,主要包含三个概念
可以通过 server.on('event', (res) =>{console.log(res)}) 调用
这次使用 websocket 实现一个基本的聊天室功能,个人感觉还比较简单,只是中间会出现一些由于链接异常断开,导致后端服务抛出异常挂掉的情况
记住前端关闭页面或者刷新页面时,先把连接关掉,每次进入页面时创建连接,然后后端将由于异常关闭导致的出错 try/catch 一下,避免抛出异常,阻塞进程
websocket 对于实现聊天室这样的功能,真的很方便,其实还能扩展到多人合作或者网络游戏等功能