废话不多说进入正题,登陆这块交互,当用户访问服务器并且成功登陆算一个在线登陆人数,每登陆一个用户,服务器都会把用户信息存入一个数组中,保存在服务器,这里要注意一点,服务器会对用户登陆的用户名进行校验,校验结果会返回给客户端,客户端通过校验结果,改变当前页面是否进入聊天页面。
上面的服务器和客户端交互都是通过socket.io来实现通讯的,前端的业务交互我们这里就采用jquery来实现,在public文件夹下新建js文件夹,下载jquery-3.2.1.min.js、新建main.js。然后对chat.html引入需要的sdk:
<script src="js/jquery-3.2.1.min.js"></script> <script src="js/main.js"></script> //socket.io官网要求这么引入 <script src="/socket.io/socket.io.js"></script>
引入完sdk,我们对main的js添加登录功能:
//main.js /** * Created by ddvdd on 2018-02-08. */ $(function(){ const url = 'http://127.0.0.1:3000'; let _username = ''; let _$inputname = $('#name'); let _$loginButton = $('#loginbutton'); let socket = io.connect(url); //设置用户名,当用户登录的时候触发 let setUsername = () => { _username = _$inputname.val().trim(); //得到输入框中用户输入的用户名 //判断用户名是否存在 if(_username) { socket.emit('login',{username: _username}); //如果用户名存在,就代表可以登录了,我们就触发登录事件,就相当于告诉服务器我们要登录了 } else{ alert('请输入用户名!'); } }; /*前端事件*/ _$loginButton.on('click',function (event) { //监听按钮的点击事件,如果点击,就说明用户要登录,就执行setUsername函数 setUsername(); }); /*socket.io部分逻辑*/ socket.on('loginResult',(data)=>{ /** * 如果服务器返回的用户名和刚刚发送的相同的话,就登录 * 否则说明有地方出问题了,拒绝登录 */ if(data.code === 0) { // 登陆成功,切换至聊天室页面 } else if(data.code ===1){ alert('用户已登录!'); } else{ alert('登录失败!'); } }) }); //app.js /** * Created by ddvdd on 2018-02-07. */ const express = require('express'); const app = express(); // 创建express实例,赋值给app。 const server = require('http').Server(app); const io = require('socket.io')(server); //将socket的监听加到app设置的模块里。这两句理解不了的可以去socket.io官网去看 const path = require('path'); // 这是node的路径处理模块,可以格式化路径 const users = []; //用来保存所有的用户信息 let usersNum = 0; //统计在线登录人数 server.listen(3000,()=>{ console.log("server running at 127.0.0.1:3000"); // 代表监听3000端口,然后执行回调函数在控制台输出。 }); /** * app.get(): express中的一个中间件,用于匹配get请求,说的简单点就是node处理请求的路由,对于不同url请求,让对应的不同app.get()去处理 * '/': 它匹配get请求的根路由 '/'也就是 127.0.0.1:3000/就匹配到它了 * req带表浏览器的请求对象,res代表服务器的返回对象 */ app.get('/',(req,res)=>{ res.redirect('/static/chat.html'); // express的重定向函数。如果浏览器请求了根路由'/',浏览器就给他重定向到 '127.0.0.1:3000/chat.html'路由中 }); /** * __dirname表示当前文件所在的绝对路径,所以我们使用path.join将app.js的绝对路径和public加起来就得到了public的绝对路径。 * 用path.join是为了避免出现 ././public 这种奇怪的路径 * express.static就帮我们托管了public文件夹中的静态资源。 * 只要有 127.0.0.1:3000/XXX/AAA 的路径都会去public文件夹下找XXX文件夹下的AAA文件然后发送给浏览器。 */ app.use('/static',express.static(path.join(__dirname,'./public'))); //一句话就搞定。 /*socket*/ io.on('connection',(socket)=>{ //监听客户端的连接事件 socket.on('login',(data)=>{ if(checkUserName(data)){ socket.emit('loginResult',{code:1}); //code=1 用户已登录 } else{ //将该用户的信息存进数组中 users.push({ username: data.username, message: [] }); socket.emit('loginResult',{code:0}); //code=0 用户登录成功 usersNum = users.length; console.log(`用户${data.username}登录成功,进入ddvdd聊天室,当前在线登录人数:${usersNum}`); } }); //断开连接后做的事情 socket.on('disconnect',()=>{ //注意,该事件不需要自定义触发器,系统会自动调用 usersNum = users.length; console.log(`当前在线登录人数:${usersNum}`); }); }); //校验用户是否已经登录 const checkUserName = (data) => { let isExist = false; users.map((user) => { if(user.username === data.username){ isExist = true; } }); return isExist; }
内容版权声明:除非注明,否则皆为本站原创文章。