为了账号安全,请及时绑定邮箱和手机立即绑定

使用 Socket.io、Express、React.js 和 Chakra UI(Vite 设置)构建实时聊天应用

在这篇博客中,我们将使用 Socket.io 实现双向通信,使用 Express.js 作为服务器,使用 React.js 作为前端,并使用 Chakra UI 进行样式设计,构建一个 实时聊天应用。我们将使用 Vite 快速搭建项目。

关键特性:

  • 基于用户ID的聊天: 生成一个随机的用户ID并存储在会话存储中。
  • 消息显示: 我们的消息显示在左边,其他人的消息显示在右边,每个消息旁边都有一个图标。

这里是该项目的演示:

Socket demo

聊天演示

服务器 socket 日志

让我们开始吧!

1. 设置项目

创建一个名为 chat-app 的包裹文件夹,我们的前端和后端将位于此文件夹中:

    mkdir chat-app
    cd chat-app

进入全屏模式 退出全屏模式

后端设置: 使用 Express.js 和 Socket.io
首先,为你的后端创建一个文件夹,并使用 npm init -y 初始化它:

    mkdir chat-backend
    cd chat-backend
    npm init -y

进入全屏模式 退出全屏模式

现在安装所需的包:

    npm install express socket.io

进入全屏模式 退出全屏模式

创建以下文件结构用于后端:

    chat-backend/
    │
    ├── server.js
    └── package.json

进入全屏模式 退出全屏模式

server.js - Express和Socket.io
这里是如何使用Socket.io设置Express服务器:

    const express = require('express');
    const http = require('http');
    const { Server } = require('socket.io');

    const app = express();
    const server = http.createServer(app);
    const io = new Server(server, {
      cors: {
        origin: 'http://localhost:5173',
        methods: ['GET', 'POST']
      }
    });

    io.on('connection', (socket) => {
      console.log('用户已连接:', socket.id);

      socket.on('sendMessage', (message) => {
        io.emit('receiveMessage', message);
      });

      socket.on('disconnect', () => {
        console.log('用户已断开连接');
      });
    });

    server.listen(4000, () => {
      console.log('服务器正在监听端口 4000');
    });

进入全屏模式 退出全屏模式

这段代码创建了一个 Express 服务器,监听端口 4000,并设置了 Socket.io 来处理 实时通信。当用户发送消息(sendMessage 事件)时,消息会被广播给所有已连接的客户端。

前端设置:使用 Vite、React 和 Chakra UI

创建一个 Vite React 项目,并参考以下截图(在 chat-app 目录下而不是在 chat-backend 目录下创建项目):

    npm create vite@latest

进入全屏模式 退出全屏模式

创建项目

选择Reactjs

选择Js

进入项目文件夹并安装所需的依赖项:

    cd chat-frontend
    npm install socket.io-client @chakra-ui/react @emotion/react @emotion/styled framer-motion

进入全屏模式 退出全屏模式

现在,让我们为我们的聊天应用程序创建一个基本结构。

2. 实现聊天前端

以下将是前端的结构:

    chat-前端/
    │
    ├── src/
    │   ├── components/
    │   │   └── ChatBox.jsx
    │   ├── App.jsx
    │   └── main.jsx
    ├── index.html
    └── package.json

进入全屏模式 退出全屏模式

App.jsx

App.jsx 中,设置 Chakra UI 并渲染 ChatBox 组件:

    import { ChakraProvider, Box, Heading } from "@chakra-ui/react";
    import ChatBox from "./components/ChatBox";

    function App() {
      return (
        <ChakraProvider>
          <Box p={5}>
            <Heading as="h1" mb={6}>
              实时聊天
            </Heading>
            <ChatBox />
          </Box>
        </ChakraProvider>
      );
    }

    export default App;

进入全屏模式 退出全屏模式

ChatBox.jsx

这里将放置主要的聊天逻辑。我们将使用 Socket.io 监听消息并处理实时更新。生成一个随机的 userId 并存储在会话存储中,聊天界面将使用 Chakra UI 构建。

    import React, { useState, useEffect } from "react";
    import { Box, Input, Button, HStack, VStack, Text, Avatar } from "@chakra-ui/react";
    import { io } from "socket.io-client";

    const socket = io("http://localhost:4000");

    const ChatBox = () => {
      const [messages, setMessages] = useState([]);
      const [input, setInput] = useState("");
      const [userId, setUserId] = useState(null);

      useEffect(() => {
        // 从session storage生成或获取userId
        let storedUserId = sessionStorage.getItem("userId");
        if (!storedUserId) {
          storedUserId = Math.random().toString(36).substring(7);
          sessionStorage.setItem("userId", storedUserId);
        }
        setUserId(storedUserId);

        // 监听消息
        socket.on("receiveMessage", (message) => {
          setMessages((prevMessages) => [...prevMessages, message]);
        });

        return () => {
          socket.off("receiveMessage");
        };
      }, []);

      const sendMessage = () => {
        if (input.trim()) {
          const message = {
            userId,
            text: input,
          };
          socket.emit("sendMessage", message);
        //   setMessages((prevMessages) => [...prevMessages, message]);
          setInput("");
        }
      };

      return (
        <VStack spacing={4} align="stretch">
          <Box h="400px" p={4} borderWidth={1} borderRadius="lg" overflowY="auto">
            {messages.map((msg, index) => (
              <HStack key={index} justify={msg.userId === userId ? "flex-start" : "flex-end"}>
                {msg.userId === userId && <Avatar name="Me" />}
                <Box
                  bg={msg.userId === userId ? "blue.100" : "green.100"}
                  p={3}
                  borderRadius="lg"
                  maxW="70%"
                >
                  <Text>{msg.text}</Text>
                </Box>
                {msg.userId !== userId && <Avatar name="Other" />}
              </HStack>
            ))}
          </Box>

          <HStack>
            <Input
              value={input}
              onChange={(e) => setInput(e.target.value)}
              placeholder="输入消息"
            />
            <Button onClick={sendMessage} colorScheme="teal">
              发送
            </Button>
          </HStack>
        </VStack>
      );
    };

    export default ChatBox;

进入全屏模式 退出全屏模式

工作原理:

  • 随机用户ID: 我们生成一个随机字符串作为用户ID,并将其存储在sessionStorage中。这确保即使你刷新页面,当前会话中的用户ID仍然保持不变。

  • Socket.io 消息处理: 应用监听来自服务器的 receiveMessage 事件,并显示收到的消息。当用户发送消息时,消息通过 Socket.io 发出,并且用户界面实时更新。

  • Chakra UI样式: 消息显示在一个框中,我们的消息左对齐(蓝色背景),其他人的消息右对齐(绿色背景)。每条消息还有一个头像,以实现简单个性化的聊天界面。
3. 运行应用程序

启动后端:

    cd chat-backend
    node server.js

进入全屏模式 退出全屏模式

启动前端:

    cd chat-frontend
    npm run dev

进入全屏模式 退出全屏模式

现在,在多个浏览器窗口中打开 http://localhost:5173,以测试实时聊天功能。你会看到每个用户的消息都显示了他们的唯一 userId

你成功地使用 Socket.ioExpressReact.jsChakra UI 构建了一个实时聊天应用!项目通过 Vite 进行了设置! 🎉

这个应用展示了 Socket.io 在实时通信 💬 方面的强大功能以及 Chakra UI 在创建干净、响应式界面 📱 方面的优势。

你可以通过添加如 聊天室 🏠、消息持久化 💾 和 用户认证 🔒 等功能来扩展这个项目。

这就是这篇博客的所有内容了!敬请期待更多更新,继续构建精彩的应用程序吧! 💻✨
编程愉快! 😊

点击查看更多内容
TA 点赞

若觉得本文不错,就分享一下吧!

评论

作者其他优质文章

正在加载中
  • 推荐
  • 评论
  • 收藏
  • 共同学习,写下你的评论
感谢您的支持,我会继续努力的~
扫码打赏,你说多少就多少
赞赏金额会直接到老师账户
支付方式
打开微信扫一扫,即可进行扫码打赏哦
今天注册有机会得

100积分直接送

付费专栏免费学

大额优惠券免费领

立即参与 放弃机会
意见反馈 帮助中心 APP下载
官方微信

举报

0/150
提交
取消