vue+koa2高颜值实时聊天简易版QQ

4,116 阅读3分钟

技术栈

vue+vuex+vue-router+better-scroll+socket.io+koa2+mongodb+pm2自动化部署+图灵机器人+nginx+linux部署

功能清单

1、注册登录选择头像功能(canvas压缩大图片);

2、即时查看在线离线人员;

3、对聊、下拉加载更多信息、发送表情、发送文字、文字上浮、长按撤回消息、点击文字语音播报、点击图片查看高清大图可左右滑动

、图片放大缩小移动位置 4、群聊、下拉加载更多信息、发送表情、发送文字、文字上浮、长按撤回消息、点击文字语音播报、点击图片查看高清大图可左右滑动

、图片放大缩小移动位置 5、智能机器人对聊、下拉加载更多信息、发送表情、发送文字、文字上浮、点击文字语音播报、点击图片查看高清大图可左右滑动

、图片放大缩小移动位置 6、点击头像查看用户信息、可看关注、聊天、自己发布的文章、查看高清大图,图片放大缩小 7、查看文章,支持上拉加载下拉刷新、评论个数、收藏、关注个数;

8、进入文章可以评论、回复、收藏、喜欢、点赞;

9、搜索、搜索用户姓名和文章、热门搜索、历史搜索;

10、进入个人中心、查看我的发布、收藏、喜欢的文章、关注、粉丝、评论、回复 私聊

重点难点

1、scoket.io的断开重连

2、实时更新在线离线状态

3、消息的及时推送

4、多人聊天怎么解决数据乱窜

5、已读未读最新消息的及时推送

6、下拉刷新上拉加载怎么实现

7、一级评论二级评论评论回复数据库是怎么设计的

项目目录

E:.
│   .babelrc
│   .editorconfig
│   .gitignore
│   .postcssrc.js
│   index.html
│   package-lock.json
│   package.json
│   README.md
│       
├───build
│       
├───config      
│                      
│           
├───src
│   │   App.vue
│   │   main.js
│   │   
│   ├───assets
│   │   ├───css
│   │   │       base.less
│   │   │       icon.less
│   │   │       index.less
│   │   │       mixin.less
│   │   │       reset.less
│   │   │       variable.less
│   │   │       
│   │   ├───fonts
│   │   │       icomoon.eot
│   │   │       icomoon.svg
│   │   │       icomoon.ttf
│   │   │       icomoon.woff
│   │   │       
│   │   ├───image
│   │   │       logo.png
│   │   │       
│   │   └───js
│   │           appback.js
│   │           history.js
│   │           mixin.js
│   │           util.js
│   │           
│   ├───base
│   │       bubble.vue
│   │       comment.vue
│   │       err.vue
│   │       evaluate.vue
│   │       fileup.vue
│   │       follow.vue
│   │       historyItem.vue
│   │       loading.vue
│   │       message.vue
│   │       nocomment.vue
│   │       nolist.vue
│   │       picture.vue
│   │       return.vue
│   │       scroll.vue
│   │       send.vue
│   │       slider.vue
│   │       toast.vue
│   │       updown.vue
│   │       upload.vue
│   │       vialogList.vue
│   │       
│   ├───components
│   │   │   bgImg.vue
│   │   │   groupItem.vue
│   │   │   listItem.vue
│   │   │   personItem.vue
│   │   │   personlist.vue
│   │   │   search.vue
│   │   │   tab.vue
│   │   │   tbsm.vue
│   │   │   vInput.vue
│   │   │   
│   │   └───messageBox
│   │       │   index.js
│   │       │   message.vue
│   │       │   
│   │       └───assets
│   │               error.svg
│   │               info.svg
│   │               success.svg
│   │               warning.svg
│   │               
│   ├───pages
│   │       article.vue
│   │       common.vue
│   │       dynamic.vue
│   │       fans.vue
│   │       follow.vue
│   │       group.vue
│   │       groupRoom.vue
│   │       login.vue
│   │       me.vue
│   │       message.vue
│   │       myperson.vue
│   │       news.vue
│   │       person.vue
│   │       personal.vue
│   │       photo.vue
│   │       pllist.vue
│   │       replay.vue
│   │       resign.vue
│   │       robot.vue
│   │       room.vue
│   │       searchList.vue
│   │       upUser.vue
│   │       val.vue
│   │       
│   ├───router
│   │       index.js
│   │       
│   └───store
│           actions.js
│           getters.js
│           index.js
│           mutations.js
│           state.js
│           
├───static
│   │   .gitkeep
│   │   
│   └───image
│           006.jpg
│           err.png
│           group.jpg
│           loading.gif
│           loginbg.jpg
│           loginbg1.jpg
│           me.png
│           news.png
│           nocomment.png
│           noList.png
│           preloading.jpg
│           robot.jpg
│           
└───uu
        

该项目基础组件20个公共组件10个页面组件23个基础组件总共43个组件;

图灵机器人接入

在线离线发送消息使用socket.io实时推送给所有客户端

前端上传图片同步到七牛cdn并上传到服务器的实现

server端前后端分离,已部署到服务器上,通过接口的方式给前端访问

后端的代码暂时不开放出来,因为涉及到很多个人的配置数据,由于该即时通讯隐蔽性比较好,注册功能不开放注册,如需体验可以加我qq我给你测试账号才能进入体验,如果实在需要可以加我qq 384434682

部分代码

客户端 main.js

// The Vue build version to load with the `import` command
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
import Vue from 'vue'
import App from './App'
import router from './router'
import axios from 'axios'
import 'babel-polyfill'
import store from './store'
import VMessage from './components/messageBox'
import './assets/css/index.less'
import FastClick from 'fastclick'
FastClick.attach(document.body)
import VueLoay from 'vue-lazyload';
import Mui from 'vue-awesome-mui'
Vue.use(VueLoay, {
  loading: "/static/image/preloading.jpg",
  error:"/static/image/preloading.jpg",
  try: 3 // default 1
})

Vue.use(VMessage)
Vue.use(Mui)
axios.defaults.baseURL = '/xxxxx';
axios.interceptors.request.use(
  config => {
    const token = localStorage.getItem("token");
    if (token) {
      // Bearer是JWT的认证头部信息
    }
    return config;
  },
  err => {
    return Promise.reject(err);
  });

// http response 拦截器
axios.interceptors.response.use(
  response => {
    return response;
  },
  error => {
    if (error.response) {
      switch (error.response.status) {
        case 404:
          store.commit('set_isToken',true)
          break;
        case 401:
          store.commit('set_isToken', true)
          break;
      }
    }
    return Promise.reject(error.response)
  });
  // import Vconsole from 'vconsole';
  // let vConsole=new Vconsole();
  // export default vConsole
Vue.prototype.$http = axios;
Vue.config.productionTip = false

/* eslint-disable no-new */
new Vue({
  el: '#app',
  router,
  store,
  components: {
    App
  },
  template: '<App/>'
})

server端 app.js

const Koa = require('koa')
const app = new Koa()
const views = require('koa-views')
const json = require('koa-json')
const onerror = require('koa-onerror')
const bodyparser = require('koa-bodyparser')
const logger = require('koa-logger')
const jwt=require("koa-jwt");
const tokenError = require('./public/js/tokenErr');
const index = require('./routes/index')
const config=require("./public/js/config")
const path=require("path")

// error handler
onerror(app)

// middlewares
app.use(bodyparser({
  enableTypes:['json', 'form', 'text']
}))

app.use(json())
app.use(logger())

app.use(require('koa-static')(__dirname + '/public'))

app.use(views(__dirname + '/views', {
  extension: 'pug'
}))
app.use(tokenError());
// logger
app.use(async (ctx, next) => {
  const start = new Date()
  await next()
  const ms = new Date() - start
  console.log(`${ctx.method} ${ctx.url} - ${ms}ms`)
})

app.use(jwt({
    secret: config.fixedVal
}).unless({
    path: [/^\/api\/login/,/^\/api\/userPwd/,/^\/api\/uploadImg/]
}));

// routes
app.use(index.routes(), index.allowedMethods())
// error-handling
app.on('error', (err, ctx) => {
  console.error('server error', err, ctx)
});

module.exports = app

项目概况

注册 登录 页面 发送消息 聊天群 朋友圈 创建群 解散群

搜索 我的 返回

github地址欢迎给个star