vue + socket.io实现一个简易聊天室示例代码


Posted in Javascript onMarch 06, 2017

vue + vuex + elementUi + socket.io实现一个简易的在线聊天室,提高自己在对vue系列在项目中应用的深度。因为学会一个库或者框架容易,但要结合项目使用一个库或框架就不是那么容易了。功能虽然不多,但还是有收获。设计和实现思路较为拙劣,恳请各位道友指正。

可以达到的需求

  • 能查看在线用户列表
  • 能发送和接受消息

使用到的框架和库

  • socket.io做为实时通讯基础
  • vuex/vue:客户端Ui层使用
  • Element-ui:客户端Ui组件

类文件关系图

服务端:

vue + socket.io实现一个简易聊天室示例代码

客户端:

vue + socket.io实现一个简易聊天室示例代码

服务端实现

实现聊天服务器的相关功能,包含通讯管道的创建、用户加入、消息的接受与转发等。

一、通讯服务建立

build/server-config.js:聊天服务器的入口

let socketIo = require('socket.io');
let express = require('express'); 
let cxt = require('../src/services-server');

let httpPort = 9001;
let channelId = 1
let app = express();

app.get('/',function(req,res){
  res.send('启动成功:' + httpPort);
});
 
let server = require('http').createServer(app);
let io = socketIo(server);
io.on('connection',function(socket){ 
  console.log('有客户端连接');
  cxt.createChannel(channelId++,socket)
});
server.listen(httpPort); //用server连接
console.log('io listen success !! ' + httpPort);
  • 通过express创建一个server对象,然后利用socketIo创建io对象
  • 然后通过io的on方法监听connection事件
  • 当有客户端连接时,触发connection事件,县立即调用"服务端上下文(后面简称cxt)"的createChannel方法创建一个管道,此时的管道上是没有用户信息的。

二、创建上下文(服务端上下文)

实现一个聊天室上下文,包含:用户、房间、消息、管道等数组,所以代码都在service-server目录中。

  • index.js:聊天室服务端上下文创建入口,创建context,并初始化房间到上下文中。
  • context.js:聊天室服务端上下文类,用户、房间、消息、管道等类在此中做集中管理。
  • room目录:包含房间和房间集合的实现
  • channel:服务端与客户端通讯的管道类

结合"通讯服务建立"中的connectiong事件的触,其后转到cxt.createChannel方法

createChannel (id, socket) {
  let channel = new Channel(id, socket, this)
  channel.init()
  channel.index = this.channels.length
  this.channels.push(channel)
}

此时会创建一个管道实例,然后初始化管道实例,并将管道添加到管道数组中。以下是初始化管道实例的代码:

init () {
  let self = this
  let roomInfo = this.cxt.room.collections[0]
  this.roomInfo = roomInfo
  this.socket.join('roomId' + roomInfo.id)
  this.socket.emit(this.cxt.eventKeys.emit.sendRooms, roomInfo) /* send出去一个默认的房间 */
  this.socket.on(this.cxt.eventKeys.client.registerUser, function (id, name) {
   console.log(id + '-' + name + '--' + self.id)
   self.cxt.createUserById(id, name, self.id)
  }) /** 新用户注册 */
  this.socket.on(this.cxt.eventKeys.client.newMsg, function (msg) { /** 发送消息 */
   self.notifyMsg(msg)
   console.log(msg)
   self.cxt.addMsg(msg)
  })
  this.socket.on(this.cxt.eventKeys.client.closeConn, function () {
   console.log(self.id + '--关闭连接')
   self.cxt.remove(self)
  })
  this.sendUsers()
}

在初始化管道实例时做了如下事件:

  • 将通讯socket添加一个到房间中,方便后期好广播消息
  • 向当前连接上来的socket发送房间信息,设定为第一个房间
  • 监听三个事件:用户注册、新消息、关闭连接。此处都要逻辑处理,可以参考源码。

客户端实现

主要实现连接服务、注册用户、发送和接受消息的功能。首先以main.js为入口,且需要先装配好vue相关配件,如vuex、ElemUi、客户端通讯管道等,然后创建vue实例和连接消息服务器,代码如下:

import '../node_modules/bootstrap/dist/css/bootstrap.css'
import Vue from 'vue'
import ElemUi from 'element-ui'
import 'element-ui/lib/theme-default/index.css'
import App from './App'
import * as stores from './store'
import { Keys } from './uitls'
import { getCxt } from './services-client'

let initRoomInfo = Keys.SETROOMINFO
Vue.use(ElemUi)
/* eslint-disable no-new */
new Vue({
 store: stores.default,
 el: '#app',
 template: '<App/>',
 components: { App },
 created: function () {
  let self = this
  getCxt().createIo(this, function (roomInfo) {
   stores.busCxt.init() /** 初始化view与service层的交互层(业务层) */
   self.$store.dispatch(initRoomInfo, roomInfo)
   getCxt().refUsers(function (users) {
    stores.busCxt.userCxt.refUsers(users)
   })
  })
 }
})

一、与服务端的通讯

service-client目录中实例的与消息服务器通讯,其中包含创建用户、接受和发送消息等。一个客户端只能拥有一个消息管道,以下代码是消息管理的创建:

import * as io from 'socket.io-client'
import Context from './context'

let eventKeys = require('../services-uitls/event.keys')
let url = 'http://localhost:9001/'
let cxt = null

export function getCxt () {
 if (cxt == null) {
  cxt = new Context(url, eventKeys, io)
 }
 return cxt
}

在main.js中的vue实例的created勾子中调用了Context的createIo实例方法,用于创建一个与消息服务器的连接,并接受其中房间发送回来的房间信息。然后就初始化业务层。

二、vuex的结合

在store目录中实现,包含了vuex类相关的实现,还有业务层的实现。其中业务层会引用"客户端通讯管道",而vuex实现类有可能会引用业务层相关实现类,以此实现ui到"消息服务器"的通讯。 store/index.js代码如下:

import Vuex from 'vuex'
import Vue from 'vue'

import RoomViewCxt from './room/roomViewCxt'
import UserViexCxt from './userViewCxt'
import MsgViewCxt from './msg/msgViewCxt'
import BusCxt from './indexForBus'

let _busCxt = new BusCxt()

let _rvCxt = new RoomViewCxt()
let _uvCxt = new UserViexCxt(_busCxt.userCxt)
let _mvCxt = new MsgViewCxt()

let opt = {
 state: null,
 getters: null,
 mutations: null,
 actions: null
}
_rvCxt.use(opt)
_uvCxt.use(opt)
_mvCxt.use(opt)

Vue.use(Vuex)

let store = new Vuex.Store(opt)
export default store
export const busCxt = _busCxt /** 业务处理上下文 */
export function getBusCxt () {
 return _busCxt
}

三、组件

组件只实现了 用户注册、主界面容器、消息发送和消息接受等。组件只会引用store目录中相关类,不会直接引用管道类。

  • Login.vue:用户注册组件
  • HChat.vue:主界面容器组件
  • Message/MsgWriter.vue:发送消息组件
  • Message/MsgList.vue:接受和显示消息列表组件

如何运行实例

  • cnpm run install 安装所有的依赖
  • npm run sokcetIo 启动消息服务器
  • npm run dev 启动客户端

示例截图

vue + socket.io实现一个简易聊天室示例代码

下载地址:vue-Socket_3water.rar

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
js实现简单模态窗口,背景灰显
Nov 14 Javascript
jquery1.5.1中根据元素ID获取元素对象的代码
Apr 02 Javascript
JavaScript按位运算符的应用简析
Feb 04 Javascript
jquery+css3实现网页背景花瓣随机飘落特效
Aug 17 Javascript
JS组件Bootstrap Table表格多行拖拽效果实现代码
Dec 08 Javascript
jquery模拟多级复选框效果的简单实例
Jun 08 Javascript
axios向后台传递数组作为参数的方法
Aug 11 Javascript
解决vue+element 键盘回车事件导致页面刷新的问题
Aug 25 Javascript
值得收藏的八个常用的js正则表达式
Oct 19 Javascript
2019 年编写现代 JavaScript 代码的5个小技巧(小结)
Jan 15 Javascript
react使用antd表单赋值,用于修改弹框的操作
Oct 29 Javascript
vue 通过 Prop 向子组件传递数据的实现方法
Oct 30 Javascript
EasyUI为Numberbox添加blur事件的方法
Mar 05 #Javascript
Web开发中客户端的跳转与服务器端的跳转的区别
Mar 05 #Javascript
js获取元素下的第一级子元素的方法(推荐)
Mar 05 #Javascript
Bootstrap模态框案例解析
Mar 05 #Javascript
video.js使用改变ui过程
Mar 05 #Javascript
Angular开发者指南之入门介绍
Mar 05 #Javascript
JavaScript自定义文本框光标
Mar 05 #Javascript
You might like
一个连接两个不同MYSQL数据库的PHP程序
2006/10/09 PHP
php封装的数据库函数与用法示例【参考thinkPHP】
2016/11/08 PHP
基于Laravel 5.2 regex验证的正确写法
2019/09/29 PHP
PHP设计模式(一)工厂模式Factory实例详解【创建型】
2020/05/02 PHP
Jquery 高亮显示文本中重要的关键字
2009/12/24 Javascript
潜说js对象和数组
2011/05/25 Javascript
使用iframe window的scroll方法控制iframe页面滚动
2014/03/05 Javascript
JavaScript实现更改网页背景与字体颜色的方法
2015/02/02 Javascript
JS实现常见的TAB、弹出层效果(TAB标签,斑马线,遮罩层等)
2015/10/08 Javascript
基于JavaScript如何制作遮罩层对话框
2016/01/26 Javascript
零基础轻松学JavaScript闭包
2016/12/30 Javascript
Vue生命周期示例详解
2017/04/12 Javascript
详解基于webpack2.x的vue2.x的多页面站点
2017/08/21 Javascript
解决iview打包时UglifyJs报错的问题
2018/03/07 Javascript
vue-video-player 通过自定义按钮组件实现全屏切换效果【推荐】
2018/08/29 Javascript
vuex 多模块时 模块内部的mutation和action的调用方式
2020/07/24 Javascript
python使用arcpy.mapping模块批量出图
2017/03/06 Python
numpy找出array中的最大值,最小值实例
2018/04/03 Python
python得到电脑的开机时间方法
2018/10/15 Python
关于python之字典的嵌套,递归调用方法
2019/01/21 Python
将tensorflow.Variable中的某些元素取出组成一个新的矩阵示例
2020/01/04 Python
Python列表list操作相关知识小结
2020/01/29 Python
python下载卫星云图合成gif的方法示例
2020/02/18 Python
pytorch学习教程之自定义数据集
2020/11/10 Python
HTML5移动端开发遇见的东西
2019/10/11 HTML / CSS
全球工业:Global Industrial
2020/02/01 全球购物
硕士研究生自我鉴定
2013/11/08 职场文书
在校学生职业规划范文
2014/01/08 职场文书
教师评语大全
2014/04/28 职场文书
小学师德标兵先进事迹材料
2014/05/25 职场文书
某某同志考察材料
2014/05/28 职场文书
党员学习中共十八大报告思想汇报
2014/09/15 职场文书
县级领导干部开展党的群众路线教育实践活动工作汇报
2014/10/25 职场文书
《火烧云》教学反思
2016/02/23 职场文书
蓝天保卫战收官在即 :15行业将开展环保分级评价
2019/07/19 职场文书
python 单机五子棋对战游戏
2022/04/28 Python