聊天室demo,技术栈:React+Node.js+Express+Socket.io
配置环境
1、首先需要创建一个React项目,略过
2、安装Node.js,略过,使用了基于Node.js的web框架express,安装express
npm install --save express
3、安装Socket.io,Socket.io 由两部分组成:
- 一个服务端用于集成 (或挂载) 到 Node.JS HTTP 服务器: socket.io
- 一个加载到浏览器中的客户端: socket.io-client
//服务端安装
npm install --save socket.io
//客户端安装
npm install --save socket.io-client
//使用标准化JS库,在 index.html用script引入
客户端加载了 socket.io-client,socket.io-client 暴露了一个 io 全局变量,然后连接服务器。
至此,依赖的环境全部安装完了。有兴趣可以试一下下面的demo,欢迎指正。
客户端代码:
//ChatRoom.js
import React, { Component } from 'react';
import io from 'socket.io-client'; //客户端引入socket.io
import './ChatRoom.css';
//连接Node服务,后台服务为http://localhost:8000,生成一个socket对象
const socket = io('http://localhost:8000')
//没有做登录页面,在url中输入的第一个参数作为用户名
const userName = window.location.search.substr(1)
class ChatRoom extends Component {
constructor(props) {
super(props)
}
state = {
count: 0,
message: '',
content: [],
}
componentDidMount() {
const self = this;
socket.on('connect', function() {
//客户端发送进入聊天室
socket.emit('add user', {
userName: userName
})
})
//客户端监听用户加入聊天室
socket.on('user joined', function({userName, count}) {
const content = [...self.state.content, {userName, message: `${userName}加入`, type: 'tip'}]
self.setState({content, count})
})
//客户端监听新消息
socket.on('new message', ({userName, message}) => {
const content = [...self.state.content, {userName, message}]
self.setState({content})
this.chatContent.scrollTop = 400
})
//客户端监听用户离开聊天室
socket.on('user leave', function({userName, count}) {
const content = [...self.state.content, {userName, message: `${userName}离开`, type: 'tip'}]
self.setState({content, count})
})
}
handleChange = event => {
this.setState({message: event.target.value})
}
handleSend = event => {
if (event.key === 'Enter') {
//客户端发送新消息
socket.emit('new message', {
userName: userName,
message: this.state.message
})
this.setState({message: ''})
this.chatContent.scrollTop = 400
}
}
handleQuit = () => {
//断开连接
socket.disconnect();
}
render() {
const {count, content, message} = this.state
const contentNodes = content.map(({userName, message, type}, index) => {
return (
{type === 'tip' ? ({message}) :
(
{userName}
{message}
)}
)
})
return (
Chat Room · {count}人
this.chatContent = ref}>
{contentNodes}
);
}
}
export default ChatRoom;
//ChatRoom.css
.ChatRoom {
width: 500px;
margin: 80px auto 0 auto;
border: 1px solid #eee;
border-radius: 4px;
}
.ChatRoom-header {
padding: 10px;
border-bottom: 1px solid #eee;
}
.ChatRoom-header-quit {
float: right
}
.ChatRoom-content {
height: 400px;
padding: 10px;
overflow: auto;
border-bottom: 1px solid #eee;
}
.ChatRoom-content-item {
padding: 5px 0px;
}
.ChatRoom-content-username {
font-weight: bold
}
.ChatRoom-content-message {
color: #444;
font-size: 13px;
}
.ChatRoom-content-tip {
font-size: 12px;
color: #ddd;
text-align: center;
}
.ChatRoom-message {
padding: 10px;
border: none;
outline: none;
}
接下来是服务端代码:
//server.js
var app = require('express')()
var http = require('http').Server(app)
var io = require('socket.io')(http)
const sessionList = []
io.on('connection', function(socket) {
//服务端监听用户进入聊天室
socket.on('add user', function({userName}) {
socket.userName = userName
if(!sessionList.includes(userName)) {
sessionList.push(userName)
}
//服务端广播用户加入聊天室信息
io.emit('user joined', {
userName,
count: sessionList.length
})
})
//服务端监听客户端发送的新消息
socket.on('new message', function({userName, message}) {
io.emit('new message', {
userName,
message
})
})
socket.on('disconnect', function() {
sessionList.splice(sessionList.indexOf(socket.userName), 1 );
socket.broadcast.emit('user leave', {
userName: socket.userName,
count: sessionList.length
})
})
})
http.listen(8000, function() {
console.log('listening on *:8000')
})
代码写完,执行一下试试:
在命令行切换到server.js文件所在目录,执行node server.js,命令行会打印:
listening on *:8000
至此,node服务已经启动。
然后启动React,会自动打开浏览器,地址默认为http://localhost:3000/,进入聊天室需要加个参数作为用户名,如:http://localhost:3000?asan
这时聊天室有1个人了,如图:
多个人在聊天室,如图: