AI聊天方案:vue+nodeJs+SSE

sse和websocket有点类似,相比于传统的HTTP协议,他们的通信成本更低,可以建立长连接,实时性高,不必每次收发消息都要进行繁琐的握手挥手。而sse和websocket的区别在于,sse是单向的,只能服务器向客户端发送消息,而websocket是双向的。如果只是单纯实现一个消息推送,而不考虑什么已读未读之类的客户端返回数据,用SSE可能更好一些。

sse本身还是基于HTTP协议的,但是会在请求头中进行特殊的设置,告诉客户端接收的是SSE数据。

今天使用node.js的express框架搭一个后端服务器,客户端用vue搭一个。简单实现一下功能。

一、服务器

用的express框架,做的比较简单,创建一个server.js的文件即可

SSE和普通的HTTP协议的区别就在于响应头

因为前后的分离端口不同,所以最后一行要配置一下跨域

复制代码
const express = require("express"); 
const app = express(); 
app.get("/sse", (req, res) => { 
  // 设置 SSE 相关的响应头 
  res.setHeader("Content-Type", "text/event-stream;charset=utf-8"); 
  res.setHeader("Cache-Control", "no-cache"); 
  res.setHeader("Connection", "keep-alive"); 
  res.setHeader("Access-Control-Allow-Origin", "*"); // 允许跨域 
  let index = 0; 
  const timer = setInterval(() => { 
    res.write(`event:sseEvent\n`); 
    res.write(`id:${index}\n`); 
    res.write(`retry: 30000\n`); 
    res.write("data: " + JSON.stringify({ content: new Date() }) + "\n\n"); 
    index++; 
  }, 2000); 
  // 当客户端点击关闭时 
  req.on("close", () => { 
    clearInterval(timer); 
    res.end(); 
  }); 
}); 
app.listen(3000, () => { 
  console.log("服务开启成功"); 
});

这里的res.write(event:sseEvent\n)不是随便写的,客户端的要和这里匹配。 打开控制台,输入node server,开启服务。

二、客户端

下面是MDN上关于SSE的文档:文档1 文档2

因为公司的node版本都比较老,所以简单创建了一个vue2项目。 url用你本地的地址,端口后端设的3000这里写3000就可以了。 addEventListener中监听的名字要和后端设置的相同。 按钮startConn事件记得检测之前是否有创立过连接,不然会创建很多个。

复制代码
复制代码
<template> 
  <div id="app">
    <button @click="startConn">建立连接</button>
    <button @click="endConn">关闭连接</button> 
    <div> {{ stateData }} </div>
    <div> 
      <div v-for="(item, index) in list" :key="index"> {{ item }} </div>
    </div> 
  </div> 
</template> 

<script> 
export default { 
  name: "App", 
  components: { 
    // HelloWorld 
  }, 
  data() { 
    return { 
      sse: null, 
      stateData: null, 
      list: [], 
    }; 
  }, 
  created() {}, 
  methods: { 
    startConn() { 
      let url = "http://192.168.1.111:3000/sse"; 
      const sse = new EventSource(url); 
      console.log(this.sse,'this.sse') 
      if(this.sse?.readyState==1){ 
        console.log('已建立连接') 
        return 
      } 
      this.sse = sse; 
      sse.onopen = (e) => { 
        let data = `SSE 连接成功,状态${sse.readyState}`; 
        this.stateData = data; 
        console.log("open", e); 
        console.log(data, sse); 
      }; 
      sse.addEventListener("sseEvent", (event) => { 
        const data = JSON.parse(event.data); 
        console.log(data, "data111111"); 
        this.list.push(data.content); 
        console.log(event, "event"); 
      }); 
      sse.onerror = (e) => { 
        console.log("error", e); 
      }; 
    }, 
    endConn() { 
      this.sse.close(); 
      console.log("end"); 
    }, 
  }, 
};
</script>

效果如下

相关推荐
xiaoqi92227 分钟前
React Native鸿蒙跨平台如何实现分类页面组件通过searchQuery状态变量管理搜索输入,实现了分类的实时过滤功能
javascript·react native·react.js·ecmascript·harmonyos
打小就很皮...40 分钟前
Tesseract.js OCR 中文识别
前端·react.js·ocr
qq_177767371 小时前
React Native鸿蒙跨平台实现应用介绍页,实现了应用信息卡片展示、特色功能网格布局、权限/联系信息陈列、评分展示、模态框详情交互等通用场景
javascript·react native·react.js·ecmascript·交互·harmonyos
2603_949462101 小时前
Flutter for OpenHarmony社团管理App实战:预算管理实现
android·javascript·flutter
wuhen_n1 小时前
JavaScript内存管理与执行上下文
前端·javascript
Hi_kenyon1 小时前
理解vue中的ref
前端·javascript·vue.js
jin1233222 小时前
基于React Native鸿蒙跨平台地址管理是许多电商、外卖、物流等应用的重要功能模块,实现了地址的添加、编辑、删除和设置默认等功能
javascript·react native·react.js·ecmascript·harmonyos
2501_920931703 小时前
React Native鸿蒙跨平台医疗健康类的血压记录,包括收缩压、舒张压、心率、日期、时间、备注和状态
javascript·react native·react.js·ecmascript·harmonyos
落霞的思绪3 小时前
配置React和React-dom为CDN引入
前端·react.js·前端框架
Hacker_Z&Q3 小时前
CSS 笔记2 (属性)
前端·css·笔记