好厉害🙇‍♂️怎么现在ai一个字一个字蹦出来,好像人打字喔

开头

兄弟们,今天给大家整点干货!用 Node.js 调 ChatGPT API 搞个流式聊天效果,就跟官方那个一样一个字一个字往外蹦,贼拉简单!

这里用sse。(chatgpt设置stream为true即可。)

讲一下这里为啥用sse:

第1,简单 :只要http响应头 和 前端用EventSourceapi就可以。相对比websocket,还要心跳机制和一些连接管理那些。

第2,不要浪费:前端不需要频繁向后端发请求,sse单向的就够用了。

准备

安装 Node.js(版本16以上就行)

开个chatgpt号,开通api调用权限。

代码

  1. 前端代码(index.html)
html 复制代码
<html>
<body>
  <!-- 聊天界面 -->
  <div id="answer"></div>
  <input id="input" placeholder="输入问题">
  <button onclick="send()">发送</button>

  <script>
    const inputElem = document.getElementById('input');
    const answerElem = document.getElementById('answer');

    // 发送问题到后端
    function send() {
      const prompt = inputElem.value.trim();
      if (!prompt) return;
      
      answerElem.textContent = ''; // 清空回答区域
      exec(prompt); // 执行请求
      inputElem.value = ''; // 清空输入框
    }

    // 使用EventSource建立流式连接
    function exec(prompt) {
      const url = new URL('/chat', location.href);
      url.searchParams.set('prompt', prompt); // 设置问题参数

      const es = new EventSource(url); // 创建SSE连接
      
      es.onmessage = (event) => {
        const data = event.data;
        if (data === '[DONE]') {  // 流结束标记
          es.close();
          return;
        }

        const chunk = JSON.parse(data);
        const content = chunk.choices[0].delta.content;
        
        if (content) {
          answerElem.textContent += content; // 追加内容到回答区域
        }
      };
    }
  </script>
</body>
</html>
  1. 后端代码(server.js)
js 复制代码
import { createServer } from 'http'
import OpenAI from 'openai'
import { createReadStream } from 'fs'

// 初始化 OpenAI 客户端
const openai = new OpenAI({
  apiKey: process.env.OPENAI_API_KEY,
})

const port = 3001
createServer(async (req, res) => {
  const url = new URL(req.url!, 'file:///')
  const query = Object.fromEntries(url.searchParams.entries())

  // 根路径,返回 index.html
  if (url.pathname === '/') {
    createReadStream('./index.html').pipe(res)
    return
  }

  // /chat 路径,处理聊天请求
  if (url.pathname === '/chat') {
    const prompt = query.prompt || ''
    if (prompt.trim() === '') {
      res.end('query prompt is required')
      return
    }

    // 调用 OpenAI API 获取流式聊天数据
    const gptStream = await openai.chat.completions.create({
      model: 'gpt-3.5-turbo',
      messages: [{ role: 'user', content: prompt }],
      max_tokens: 100,
      stream: true,
    })

    // 设置响应头为 SSE 格式
    res.writeHead(200, { 'Content-Type': 'text/event-stream' })
    for await (const chunk of gptStream) {
      res.write(`data: ${JSON.stringify(chunk)}\n\n`) // 实时推送数据
    }

    req.on('close', () => {
      console.log('req close...')
    })
    return
  }

  // 其他路径返回默认信息
  res.end('other route')
}).listen(port)

console.log(`Server running at http://localhost:${port}/`)

跑起来

环境

  • Node.js
  • npm 或 yarn
  • OpenAI API 密钥

目录结构

lua 复制代码
/my-project
  |-- server.js
  |-- index.html
  |-- .env
  |-- node_modules/
  |-- package.json
  |-- package-lock.json

env文件

后台给的,去复制写上去就好了。

js 复制代码
OPENAI_API_KEY=你的OpenAI API

装依赖:

js 复制代码
npm i openai

跑起来

js 复制代码
node server.js

服务器启动后,我们可以访问 http://localhost:3001/ 来查看聊天效果。在浏览器输入问题,点击发送,等待一会儿,你会看到实时返回的答案。答案会一块一块地显示出来,模拟了 ChatGPT 自己的流式效果。

放到服务器上

买服务器,国内受限,买个外国的服务器,按量付费,自己玩玩,配置低也没关系。把代码部署上去,我一般是在服务器上装宝塔跑。

开端口:

最后主要要开通一下端口3001。

服务器安全组里一般就是,开放3001端口。

完结

sse是啥,sse是server-sent event,叫它实时推送吧。openai的chatgpt本身就有这个一个个字蹦出来的效果,只要加个stream: true这样子在它给出的api里面去配置一下就好了。

前端就用onmessage去收,然后拼接。前后端打个配合。

就这么简单!1分钟就能搞个自己的AI聊天窗口,自己去做套壳ChatGPT。

相关推荐
好运的阿财1 小时前
OpenClaw工具拆解之canvas+message
人工智能·python·ai编程·openclaw·openclaw工具
孟健1 小时前
DeepSeek-V4-Pro 写代码到底行不行?我拿 GLM-5.1 跟它硬碰硬比了一轮
ai编程
|晴 天|1 小时前
Vue 3 + TypeScript + Element Plus 博客系统开发总结与思考
前端·vue.js·typescript
猫3282 小时前
v-cloak
前端·javascript·vue.js
旷世奇才李先生2 小时前
Vue 3\+Vite\+Pinia实战:企业级前端项目架构设计
前端·javascript·vue.js
SoaringHeart4 小时前
Flutter进阶:用OverlayEntry 实现所有弹窗效果
前端·flutter
狼爷4 小时前
AI时代,程序员不被淘汰的核心学习路径
openai·ai编程
子昕4 小时前
DeepSeek V4 终于发了:用国产芯片训出世界级大模型
ai编程
IT_陈寒5 小时前
Vite静态资源加载把我坑惨了
前端·人工智能·后端
herinspace5 小时前
管家婆实用贴-如何分离和附加数据库
开发语言·前端·javascript·数据库·语音识别