vue.js+websocket+mongodb实现纯粹的聊天室项目
vue.js+websocket+mongodb实现纯粹的聊天室项目!下面的项目的构建过程和代码展示。
1:项目的整体结构图
chatroom/
│
├── backend/ # 后端服务目录
│ ├── config/ # 配置文件
│ │ └── db.js # 数据库连接配置
│ ├── controllers/ # 控制器目录
│ │ └── messageController.js # 处理消息的控制器
│ ├── models/ # 数据模型
│ │ └── message.js # 聊天消息模型
│ ├── routes/ # 路由配置
│ │ └── messageRoutes.js # 聊天消息相关路由
│ ├── server.js # 主服务器文件(入口)
│ ├── package.json # Node.js 项目配置文件
│ ├── .env # 环境变量配置文件
│
├── frontend/ # 前端服务目录
│ ├── public/ # 公共文件(如HTML模板)
│ │ ├── index.html # 入口HTML文件
│ │ └── favicon.ico # 网站图标
│ ├── src/ # 源代码
│ │ ├── assets/ # 静态资源(图片、音频等)
│ │ └── ...
│ │ ├── components/ # Vue 组件
│ │ │ ├── ChatRoom.vue # 聊天页面组件
│ │ │ ├── MessageList.vue # 消息列表组件
│ │ │ ├── MessageInput.vue # 消息输入框组件
│ │ ├── store/ # Vuex 状态管理
│ │ │ └── chatStore.js # 聊天状态管理
│ │ ├── App.vue # 根组件
│ │ ├── main.js # 项目入口文件(配置路由、全局样式等)
│ │ └── socket.js # WebSocket 客户端配置
│ ├── package.json # Vue 项目配置文件
│ └── vue.config.js # Vue 项目配置文件
│
├── .gitignore # Git 忽略文件
└── README.md # 项目说明文件
2:先看后端服务的内容说明书:
后端服务(backend/)
config/db.js
配置 MongoDB 数据库连接,使用 Mongoose。
const mongoose = require('mongoose');
const mongoURI = process.env.MONGO_URI || 'mongodb://localhost:27017/chatroom';
mongoose.connect(mongoURI, { useNewUrlParser: true, useUnifiedTopology: true })
.then(() => console.log('MongoDB connected'))
.catch((err) => console.log('MongoDB connection error:', err));
module.exports = mongoose;
controllers/messageController.js
处理聊天消息的存储和获取。
const Message = require('../models/message');
// 存储新消息
const saveMessage = (messageData) => {
const newMessage = new Message(messageData);
return newMessage.save();
};
// 获取所有消息
const getMessages = async () => {
return await Message.find().sort({ timestamp: 1 }).limit(100);
};
module.exports = { saveMessage, getMessages };
models/message.js
定义消息数据模型。
const mongoose = require('mongoose');
const messageSchema = new mongoose.Schema({
nickname: { type: String, required: true },
text: { type: String, required: true },
timestamp: { type: Date, default: Date.now },
});
module.exports = mongoose.model('Message', messageSchema);
routes/messageRoutes.js
配置 API 路由,包括消息获取和存储。
const express = require('express');
const router = express.Router();
const { saveMessage, getMessages } = require('../controllers/messageController');
// 获取历史聊天记录
router.get('/messages', async (req, res) => {
try {
const messages = await getMessages();
res.json(messages);
} catch (err) {
res.status(500).send('Error retrieving messages');
}
});
module.exports = router;
server.js
配置 WebSocket 服务和 HTTP API 服务。
const express = require('express');
const http = require('http');
const socketIo = require('socket.io');
const mongoose = require('mongoose');
const cors = require('cors');
const messageRoutes = require('./routes/messageRoutes');
const { saveMessage } = require('./controllers/messageController');
const app = express();
const server = http.createServer(app);
const io = socketIo(server);
// 配置 MongoDB
mongoose.connect('mongodb://localhost:27017/chatroom', { useNewUrlParser: true, useUnifiedTopology: true });
// 配置中间件
app.use(cors());
app.use(express.json());
app.use('/api', messageRoutes);
// WebSocket 连接
io.on('connection', (socket) => {
console.log('User connected:', socket.id);
// 监听客户端消息
socket.on('send-message', (messageData) => {
// 保存消息到数据库
saveMessage(messageData).then(() => {
io.emit('new-message', messageData); // 广播新消息
});
});
socket.on('disconnect', () => {
console.log('User disconnected:', socket.id);
});
});
// 启动服务器
server.listen(3000, () => {
console.log('Server is running on http://localhost:3000');
});
3:下面看看前端的业务说明书:
前端服务(frontend/)
这样,你就有了一个独立、干净的聊天室项目,支持多人互动,能够容纳同时在线1000人,实时广播聊天消息,并且将所有聊天消息存储到 MongoDB 数据库中。
-
src/components/ChatRoom.vue
聊天室界面,包含消息列表和输入框 -
<template> <div class="chatroom"> <!-- 消息列表 --> <MessageList :messages="messages" /> <!-- 输入框 --> <MessageInput @sendMessage="sendMessage" /> </div> </template> <script> import { io } from 'socket.io-client'; import MessageList from './MessageList.vue'; import MessageInput from './MessageInput.vue'; export default { components: { MessageList, MessageInput }, data() { return { socket: null, messages: [], nickname: 'User' // 默认昵称,用户可以修改 }; }, mounted() { this.socket = io('http://localhost:3000'); // 监听服务器发送的新消息 this.socket.on('new-message', (message) => { this.messages.push(message); }); // 获取历史消息 this.socket.emit('get-messages'); }, methods: { sendMessage(text) { const message = { nickname: this.nickname, text }; this.socket.emit('send-message', message); this.messages.push(message); // 本地显示发送的消息 } } }; </script>
-
src/components/MessageList.vue
显示消息列表组件。 -
<template> <div class="message-list"> <div v-for="(msg, index) in messages" :key="index" class="message"> <strong>{{ msg.nickname }}:</strong> {{ msg.text }} </div> </div> </template> <script> export default { props: ['messages'] }; </script>
-
src/components/MessageInput.vue
提供消息输入框并发送消息。 -
<template> <div class="message-input"> <input v-model="text" @keyup.enter="sendMessage" placeholder="输入消息..." /> <button @click="sendMessage">发送</button> </div> </template> <script> export default { data() { return { text: '' }; }, methods: { sendMessage() { if (this.text.trim()) { this.$emit('sendMessage', this.text); this.text = ''; // 清空输入框 } } } }; </script>
src/socket.js
WebSocket 客户端配置。 -
import { io } from 'socket.io-client'; export const socket = io('http://localhost:3000');
运行和部署
- 后端
- 安装依赖:
npm install
- 启动服务器:
node server.js
- 安装依赖:
- 前端
- 安装依赖:
npm install
- 启动开发服务器:
npm run serve
- 安装依赖: