前端处理流式数据(SSE服务)

前言

将数据用流的方式返回给客户端,这种技术需求在传统的管理项目中不多见,但是在媒体或者有实时消息等功能上就会用到,这个知识点对于前端还是很重要的。

即时你不写服务端,但是服务端如果给你这样的接口,你也得知道怎么去使用联调。

nodejs实现简单的SSE服务

SSE服务(Server-Sent Events),是一种服务器向客户端推送实时更新的机制模式。

const express = require('express');  
const app = express();  
const port = 8002;  


let strArr = [
    '所有人,都得死!',
    '犯我德邦者,虽远必诛!',
    '吾所成之事,不可逆也!',
    '一点寒芒先到,随后枪出如龙!',
    '我的剑就是你的剑!',
    '刀下生,刀下死!'
]
let setTask = null
  
app.get('/events', (req, res) => {  
  res.setHeader('Content-Type', 'text/event-stream;charset=utf-8');  
  res.setHeader('Cache-Control', 'no-cache');  
  res.setHeader('Connection', 'keep-alive');  
  let num = 0
  setTask =  setInterval(()=>{
    res.write(`data:${strArr[num]}\n\n`)
    num++
    if(num > 5){
        res.write(`data:end\n\n`)
        res.end()
        // res.closed()
        clearInterval(setTask)
        setTask = null
    }
  },1000)
});  
  
app.listen(port, () => {  
  console.log(`${port}端口已启动`);  
});

效果如下

 前端实现接收数据流:

这里使用一个叫做EventSource的api去实现流式接口的调用和数据获取

配置代理(重要)

如果我们用vue,react等等框架开发时,需要在代理处做一些配置,确保数据会以流式的返回。如果不做这层代理的配置,那么你获取的数据就会是执行完所有的res.write,一次性的全部返回给前端,就不是我们想要的效果。

效果如下,在配置代理中将compress设置为false

    devServer:{
      client:{
        overlay:false
      },
      port:8080,
      open:true,
      compress:false,  //流式数据返回的关键配置
      proxy:{
        '/server1':{
          target:'http://localhost:3001',
          ws:false,
          changeOrigin:true,
          pathRewrite:{
            '^/server1':''
          }
        },
        '/server2':{
          target:'http://localhost:3002',
          ws:false,
          changeOrigin:true,
          pathRewrite:{
            '^/server2':''
          }
        },
        '/sse':{
          target:'http://localhost:8002',
          ws:false,
          changeOrigin:true,
          pathRewrite:{
            '^/sse':''
          }
        }
      }
    }

之前没有配置这里,导致数据一直是一次性返回的,困了我一会,后来查找原因,借鉴的这篇文章

fetchEventSource请求,数据没有流式输出_vue2 eventsource为什么没有流式输出-CSDN博客

前端实现接口调用
<template>
    <div>
        <el-button @click="sendMsg">发送消息</el-button>
        <p v-for="(item,index) in msgList" :key="index">{{ item }}</p>
    </div>
   
  </template>
  <script>
   export default{
      name:'admin',
      data(){
        return{
            msgList:[]
        }
      },
      methods:{
    sendMsg(){
        let vm = this

    //方案1:EventSource
      const eventSource = new EventSource('/sse/events');  
  //消息监听
  eventSource.onmessage = function(event) {  
    console.log(eventSource,vm,'状态')
    console.log(event.data); // 输出SSE发送的数据  
    if(event.data === 'end'){
      eventSource.close()
    }else{
      vm.msgList.push(event.data)
    }
 
  };  
  //连接成功
  eventSource.onopen = function(event){

  }
  //连接出错
  eventSource.onerror = function(error) {  
    if (eventSource.readyState === EventSource.CLOSED) {  
      // 连接已关闭,可能需要重新连接  
      console.error('SSE连接已关闭:', error);  
    }  
  }

  //方案2:xhr(不推荐)
  // const xhr = new XMLHttpRequest(); 
  // const url = '/sse/events'; 
  // xhr.open('GET', url,true); 
  // xhr.setRequestHeader('Accept', 'text/event-stream');

  // xhr.onload = (event)=>{
  //   if(xhr.status === 200){
  //     console.log(xhr.responseText,'onload',event)
  //   }
  // }

  // xhr.onreadystatechange = (event)=>{
  //   // if(xhr.status === 200){
  //   //   console.log(xhr.responseText,'onreadystatechange',event)
  //   // }
    
  // }
  // xhr.onprogress = (event)=>{
  //   if(xhr.status === 200){
  //     console.log(xhr.responseText,'onreadystatechange',event)
     
  //   }
  // }
  // xhr.send()
    }
      }
   }
  </script>
  <style lang="less">
  </style>

 这样就大功告成了,如果以后要是做类似于chatgpt这种效果,就可以用到的。

感觉有用的给个三连吧!

相关推荐

最近更新

  1. TCP协议是安全的吗?

    2024-06-06 18:12:05       18 阅读
  2. 阿里云服务器执行yum,一直下载docker-ce-stable失败

    2024-06-06 18:12:05       19 阅读
  3. 【Python教程】压缩PDF文件大小

    2024-06-06 18:12:05       19 阅读
  4. 通过文章id递归查询所有评论(xml)

    2024-06-06 18:12:05       20 阅读

热门阅读

  1. Hive on Spark、Spark on Hive的异同

    2024-06-06 18:12:05       7 阅读
  2. pyqt5 tableView实现excel拖曳填充

    2024-06-06 18:12:05       9 阅读
  3. GPT-4o版本间的对比分析和使用心得

    2024-06-06 18:12:05       9 阅读
  4. php设计模式之策略模式详解

    2024-06-06 18:12:05       12 阅读
  5. XML语法规则介绍及总结

    2024-06-06 18:12:05       9 阅读
  6. EasyExcel之动态表头导出不生效

    2024-06-06 18:12:05       8 阅读
  7. 什么叫防御式编程

    2024-06-06 18:12:05       10 阅读
  8. C++:day2

    C++:day2

    2024-06-06 18:12:05      8 阅读
  9. 糖尿病相关的数据集

    2024-06-06 18:12:05       11 阅读