微信小程序对接SSE接口记录
微信小程序对接SSE接口记录
- 需求:公司项目对接gpt,gpt产生的结果是分段返回,所以要求在产生结果时,有打字机的效果。原本是由定时器调用,后来优化改为服务端使用SSE接口。
- 小程序使用起来比较方便,但是要求小程序基本库的版本需要在2.20.2以上。文档地址移步这里
- 微信小程序代码
// 基础库为2.33.0const requestTask = wx.request({url: `xxxxxxxx`, // 需要请求的接口地址enableChunked: true // enableChunked必须为true})// 开发工具存在问题,使用真机测试const listener = data => {// data为返回的数据,可以在此对数据进行处理}// 监听服务端返回的数据requestTask.onChunkReceived(listener)// 移除监听 需传入与监听时同一个的函数对象requestTask.offChunkReceived(listener)
注意:
- 接收到的结果数据类型固定为arrayBuffer,需要开发者自己进行转换,可以使用下面方法进行转换。
function arrayBufferToString(arr){if(typeof arr === 'string') { return arr; } var dataview = new DataView(arr);var ints = new Uint8Array(arr.byteLength);for(var i=0;i<ints.length;i++){ints[i]=dataview.getUint8(i);}var str = '', _arr = ints; for(var i = 0; i < _arr.length; i++) {if (_arr[i]) {var one = _arr[i].toString(2), v = one.match(/^1+?(?=0)/); if(v && one.length == 8) {var bytesLength = v[0].length;var store = _arr[i].toString(2).slice(7 - bytesLength); for(var st = 1; st < bytesLength; st++) { if ( _arr[st + i]) {store += _arr[st + i].toString(2).slice(2); }} str += String.fromCharCode(parseInt(store, 2)); i += bytesLength - 1; } else { str += String.fromCharCode(_arr[i]); } }} return str;
}
- 微信开发工具中无法转换数据。可能是由于开发工具问题,在服务端返回的字符串中存在中文时,开发工具是无法正常转换的。但是在真机是正常的。如果需要在开发工具中实现转换,可以与服务端协商将数据进行URL编码返回。
- 服务端一次返回的结果,微信小程序有时会将其截开,并分两次返回。由于截开的位置并不固定,所以可能会存在转换ArrayBuffer时,出现结果异常的问题。使用SSE接口一般有两种需求:一种是将所有的结果累加起来、还有一种就是后面的结果覆盖前面的。在使用第一种时,每次的返回量不会太大,所以应该不会出现微信小程序截开两次返回的情况。但是第二种每次返回的接口都在逐渐增大,可能会出现这种情况,我就是第二种。我是使用下面方法解决
// 我的数据是json字符串,如果出现分开返回,在转json时,会出现报错,所以使用try处理
let timer = null
const listener = data => {try {// 上次结果出现报错 这次正常 清除延时器if (timer) {clearTimeout(timer)timer = null}// 小程序存在数据截开的情况 存五次数据if (arr.length > 4) {arr.shift()}// 这里要存储的是arrayBuffer,不能存储string数据arr.push(data.data)// 数据处理 .......} catch (e) {// 最后一次出现报错 三秒后重组数据timer = setTimeout(() => {const len = arr.lengthlet index = len - 2,data = arr[len - 1],result = nullwhile(index > -1) {// 从后往前 合并data = mergeArrayBuffers(arr[index], data)try{// 数据处理 .......index = -1}catch(e){index -= 1}}}, 3000)}}
// 合并arrayBuffer
function mergeArrayBuffers(buffer1, buffer2) {if (!buffer1) {return buffer2;} else if (!buffer2) {return buffer1;}var tmp = new Uint8Array(buffer1.byteLength + buffer2.byteLength);tmp.set(new Uint8Array(buffer1), 0);tmp.set(new Uint8Array(buffer2), buffer1.byteLength);return tmp.buffer;
}
- 由于是后面的结果覆盖前面的,我只需要处理最后一次结果,如果结果正常则不用处理。不正常再将前面存储的数据一一合并,再做处理。
- 通常一个中文是两个字节,所以可能会出现一个中文恰好被截开的情况,所以需要存储的是原数据
- 由于SSE特性,需要由用户端断开连接,所以在使用完毕时,需要调用
requestTask.abort()断开连接
ps: 此文章做个人平常记录
相关文章:
微信小程序对接SSE接口记录
微信小程序对接SSE接口记录 需求:公司项目对接gpt,gpt产生的结果是分段返回,所以要求在产生结果时,有打字机的效果。原本是由定时器调用,后来优化改为服务端使用SSE接口。小程序使用起来比较方便,但是要求…...
Ngrok 的绝佳替代品,内网穿透神器 Serveo
什么是 Serveo Serveo 是一个免费的内网穿透服务,Serveo 可以将本地计算机暴露在互联网上,官方声称其为 Ngrok 的绝佳替代品。 Serveo 其最大优点是使用现有的 SSH 客户端,无需安装任何客户端软件即可完成端口转发。 Serveo 工作原理很简单…...
网络知识点之-路由
路由(routing)是指分组从源到目的地时,决定端到端路径的网络范围的进程。路由工作在OSI参考模型第三层——网络层的数据包转发设备。路由器通过转发数据包来实现网络互连。虽然路由器可以支持多种协议(如TCP/IP、IPX/SPX、AppleTa…...
input 框如何移动光标,设置光标位置?
获取 input 光标位置 const inputDom document.getElementById("input") const selectionStart inputDom.selectionStart设置 input 光标 inputDom.focus() // focus() 异步,所以加了 setTimeout setTimeout(() > {const nextSelection selection…...
linux内核系统调用学习5:SYSCALL_DEFINE<0-6>
系统调用最大参数是6,由下面这个宏定义,位于文件include\linux\syscalls.h #define SYSCALL_DEFINE_MAXARGS 6 SYSCALL_DEFINE0(fork) fork:系统调用名。 SYSCALL_DEFINE1(set_tid_address, int __user *, tidptr) set_tid_address&#x…...
maven镜像仓库配置(多镜像自动切换)
大家在使用IDEA的时候会遇到这样的一个问题,就是在下载源代码和资源文档的时候,有些镜像仓库里面没有源代码和资源文档,然后会导致下载失败。 这时候就需要多个镜像仓库的地址了。 附上我自己的配置文件: <mirrors><!--…...
ChatGPT在智能监控和安防系统中的应用如何?
ChatGPT在智能监控和安防系统中有着广泛的应用潜力。智能监控和安防系统是利用人工智能和计算机视觉技术来实现对环境的实时监控和安全保障的系统。ChatGPT作为一种通用的预训练语言模型,可以在智能监控和安防系统中发挥以下作用: 1. **智能视频监控**&…...
【Spring Boot Admin】介绍以及使用
介绍 概述 Spring Boot Admin是一个监控工具,旨在以一种漂亮且易于访问的方式可视化Spring Boot Actuators提供的信息。 主要功能点 显示应用程序的监控状态应用程序上下线监控查看 JVM,线程信息可视化的查看日志以及下载日志文件动态切换日志级别Http…...
本地私有仓库部署、docker--harbor私有仓库部署和管理
部署本地私有仓库 拉取镜像 修改daemon.json配置文件 重启docker服务 创建容器 为镜像打标签 上传镜像 查看私有仓库 其他主机拉取私有仓库镜像 Docker--harbor私有仓库 (1)什么是Harbor Harbor 是 VMware 公司开源的企业级 Docker Registry 项目…...
java根据模板导出word
java根据模板导出word 日常开发中,常常会遇到各种各样的表格进行导出,比较好的办法就是提前弄好word模版,再通过遍历的方式进行导出文档 1、制作word模版 模版编写 内容替换 目标下面模版进行多页展示 将word转换成xml 将xml格式化 再将x…...
spring学习笔记十四
注解开发Bean总结 功能 xml配置注解定义Bean bean标签 id属性class属性 Component ControllerServiceRepositorComponentScan 设置依赖注入 setter注入(set方法) 引用类型/简单类型构造器注入 引用类型和简单类型自动装配 Autowired QualifierValue 配置第三方Bean be…...
【springmvc部分功能源码仿写第一步】实现java对目录下所有文件的遍历
废话不多说,直接上源码! public class MiniSpring {public static void main(String[] args) {String path "D:\\ideaProject\\thread";File file new File(path);List<String> list new ArrayList<>();System.out.println(fi…...
SpringBoot中接口幂等性实现方案-自定义注解+Redis+拦截器实现防止订单重复提交
场景 SpringBootRedis自定义注解实现接口防刷(限制不同接口单位时间内最大请求次数): SpringBootRedis自定义注解实现接口防刷(限制不同接口单位时间内最大请求次数)_redis防刷_霸道流氓气质的博客-CSDN博客 以下接口幂等性的实现方式与上面博客类似,…...
论文解读|用于从RGB-D数据进行3D物体检测的Frustum PointNets
原创 | 文 BFT机器人 01 摘要 论文研究了室内和室外场景中基于RGBD数据的3D目标检测。论文的方法不仅仅依赖于3D方案,而是利用成熟的2D对象检测器和先进的3D深度学习进行对象定位,即使是小对象也能实现高效率和高召回。 直接在原始点云中学习࿰…...
3ds Max图文教程: 使用动态工具Mass FX 创建风铃动画
推荐: NSDT场景编辑器助你快速搭建可二次开发的3D应用场景 1. 简单的场景设置 步骤 1 打开 3ds Max。 打开 3ds Max 步骤 2 我将向您展示风铃背后的动态 通过简单的场景设置进行模拟。一旦你有了这个想法,你就可以应用这个 技术到复杂的风铃结构。 基…...
抖音矩阵系统源码开发搭建部署分享
一、 功能开发设计 (1)数据概览:账号,视频top10数据统计 (2)AI视频创意:原创视频批量剪辑,阶乘算法,去重原理 (3)同城拓客:线下门店…...
Grafana图形web监控的安装与配置
目录 一、安装并配置 二、Web访问 三、Grafana启用zabbix插件 四、Grafana添加zabbix数据源 五、创建仪表盘 创建监控项完成保存仪表盘 六、查看创建的仪表盘 七、在现有的dashboard(仪表盘)中添加图形 八、查看最终dashborad(仪表盘&#x…...
【机器学习】了解 AUC - ROC 曲线
一、说明 在机器学习中,性能测量是一项基本任务。因此,当涉及到分类问题时,我们可以依靠AUC - ROC曲线。当我们需要检查或可视化多类分类问题的性能时,我们使用AUC(曲线下面积)ROC(接收器工作特…...
Docker 容器生命周期:创建、启动、暂停与停止----从创建到停止多角度分析
🌷🍁 博主 libin9iOak带您 Go to New World.✨🍁 🦄 个人主页——libin9iOak的博客🎐 🐳 《面试题大全》 文章图文并茂🦕生动形象🦖简单易学!欢迎大家来踩踩~ἳ…...
C++STL库中的vector
文章目录 vector的介绍及使用 vector深度剖析及模拟实现 动态二维数组理解 一、vector的介绍及使用 1.vector的介绍 1. vector是表示可变大小数组的序列容器。 2. 就像数组一样,vector也采用的连续存储空间来存储元素。也就是意味着可以采用下标对vector的元素进…...
Ubuntu系统中Miniconda的安装与配置指南
1. 为什么选择Miniconda? 在开始之前,我们先聊聊为什么要在Ubuntu上安装Miniconda。作为一个长期使用Python进行数据分析和机器学习开发的工程师,我尝试过各种Python环境管理工具,最终发现Miniconda是最适合个人开发者的选择。它比…...
OpenClaw(首选,全能执行) - 支持平台:**WhatsApp、Telegram、微信、企业微信、飞书、Slack、Discord**等15+平台
一、自动处理邮件的AI(过滤、归档、代发、总结) 1. OpenClaw(全能型,本地多平台) 核心能力:垃圾邮件过滤、自动归档、按规则分类、提取待办、代发模板邮件、批量退订、邮件摘要。优势:本地部署、…...
Flutter 鸿蒙(OpenHarmony)化适配实战:从零实现「点击按钮退出应用」插件
一、引言 随着鸿蒙生态的持续发展,Flutter 作为跨平台开发的主流框架,对鸿蒙系统的支持也越来越完善。很多 Flutter 开发者在迁移鸿蒙应用时,都会遇到「应用退出」的基础需求:点击按钮直接关闭应用,回到系统桌面。 本…...
OpenClaw数据清洗:Qwen3-4B-Thinking-2507-GPT-5-Codex-Distill-GGUF处理混乱CSV文件
OpenClaw数据清洗:Qwen3-4B-Thinking-2507-GPT-5-Codex-Distill-GGUF处理混乱CSV文件 1. 为什么需要自动化数据清洗 上周我接手了一个市场调研项目,客户发来的CSV文件打开就让我头皮发麻——编码混乱、字段名全是大写拼音缩写、日期格式五花八门。手动…...
告别传统方法:LogAnomaly如何用NLP技术提升日志异常检测准确率?
告别传统方法:LogAnomaly如何用NLP技术重构日志异常检测范式? 日志数据如同数字世界的神经系统,记录着系统运行的每一次"心跳"与"呼吸"。传统检测方法就像拿着放大镜寻找心电图异常,而LogAnomaly则带来了全新…...
彻底清除TortoiseSVN:从基础卸载到深度清理全指南
1. 为什么TortoiseSVN卸载这么麻烦? 很多朋友第一次卸载TortoiseSVN时都会遇到各种"后遗症"——右键菜单残留、注册表垃圾、文件夹图标异常。这其实和它的工作原理有关。TortoiseSVN作为Windows资源管理器的Shell扩展,会深度集成到系统底层。我…...
Java多线程实战:ReentrantLock与信号量Semaphore的5个高频使用场景解析
Java多线程实战:ReentrantLock与信号量Semaphore的5个高频使用场景解析 在Java并发编程领域,ReentrantLock和Semaphore是两个至关重要的同步工具。它们虽然都属于JUC(java.util.concurrent)包中的并发控制机制,但设计理…...
个人 AI 助理——打造你的第二大脑
个人 AI 助理——打造你的第二大脑摘要:信息过载时代,个人 AI 助理不再是奢侈品,而是必需品。本文教你如何搭建专属 AI 助理,实现信息管理、知识沉淀、决策辅助的智能化,让 AI 成为你的"第二大脑"。一、为什…...
给嵌入式开发者的英飞凌HSM实战指南:从AUTOSAR集成到密钥安全存储
英飞凌HSM深度实战:AUTOSAR集成与密钥管理全解析 在汽车电子领域,安全性能已经从"加分项"变成了"必选项"。想象一下,当一辆智能汽车以120公里时速行驶时,任何微小的安全漏洞都可能导致灾难性后果。这正是英飞…...
告别‘千人千脑’:用DMMR模型搞定EEG情感识别的跨被试难题(附PyTorch代码)
突破脑电情感识别的个体差异壁垒:DMMR模型实战指南与PyTorch实现 当你在实验室里看着屏幕上跳动的脑电波形时,是否曾为不同受试者数据间的巨大差异而头疼?这种被称为"脑电指纹"的个体特异性,一直是情感识别领域最棘手的…...
