大模型多轮对话 流式输出
下面这种EventSource 是一个浏览器 API,它允许你创建一个可以发出事件的对象。new EventSource 构造函数创建了一个新的 EventSource,是传统的SSE实现方法,这种方法默认是get请求,但是我们服务端需要的是POST请求,而且这种方法也不能设置header等参数,那么这种方法就不行啦
<html lang="en">
<head>
<meta charset="UTF-8">
<title>SSE Example</title>
</head>
<body>
<h1>Server-Sent Events Example</h1>
<div id="messages"></div>
<script>
const evtSource = new EventSource('/events');
const messages = document.getElementById('messages');
evtSource.onmessage = function(event) {
const newElement = document.createElement("p");
const eventObject = JSON.parse(event.data);
newElement.textContent = "Message: " + eventObject.message + " at " + eventObject.timestamp;
messages.appendChild(newElement);
};
</script>
</body>
</html>
不过我们可以借助
fetch-event-source这个库就可以像发起fetch请求一样发起服务器单向通信请求。 相对于传统的EventSource API它具有实现POST请求、自定义头部和请求体的灵活性,满足各种复杂需求以及提供onopen、onmessage、onclose和onerror回调,允许精细化管理整个请求生命周期。
安装与使用
npm install @microsoft/fetch-event-source
然后我们可以在自己的工程里面单独封装一个用于流式输出的api文件
import { fetchEventSource } from "@microsoft/fetch-event-source";
// SSE post请求
const controller = new AbortController();
const signal = controller.signal;
/*
* url 接口地址
* params 参数
* sCB 成功回调
* eCB 失败回调
*/
export const sseRequest = (baseUrl: string, obj: any, sCB: Function, eCB: Function) => {
return fetchEventSource(`${baseUrl}/nlpd_servers/streaming_request`, {
method: "POST",
signal: signal,
headers: {
"Content-Type": "application/json",
// Accept: "*/*",
Accept: "text/event-stream",
},
body: JSON.stringify(obj),
onmessage(msg) {
sCB(msg);
},
onerror(err) {
// 必须抛出错误才会停止
eCB(err);
throw err;
},
onclose() {
console.log('关闭连接');
}
});
};
然后我们在可以在多轮对话页面调用api处
const successCallback = async (msg: any) => {
console.log("msg", msg);
};
const errorCallback = (err: any) => {
console.error("发生错误:", err);
};
// 调用 sseRequest 函数
await sseRequest(baseUrl.value, data, successCallback, errorCallback);
***注意 在发送消息时 服务端返回的数据应该符合以下图片中的规则:
同时还需要注意返回信息中的换行和空格符,因为在markdown文本转换的时候可能会因为他俩区分不开,导致意外的换行,所以最好和大模型工程师(Flask,FastAPI)(商量一下在返回数据的时候对空格和换行符转换一下,比如 "\xA"代表空格,"\xA\xB"代表换行