代码 使用 Gin 和 OpenAI 实现实时聊天:后端代码与前端集成

2024-11-19 01:23:58 +0800 CST views 1466

使用 Gin 和 OpenAI 实现实时聊天:后端代码与前端集成

在本篇文章中,我们将详细介绍如何使用 Go 语言的 Gin 框架与 OpenAI API 实现一个实时聊天功能。本文涵盖了后端代码的实现、.env 配置文件的设置方法,以及前端如何通过 SSE(Server-Sent Events)与后端交互以实现实时消息的接收。

1. 后端代码简介

首先,让我们来了解一下后端代码的主要逻辑。

该代码通过 Gin 框架创建了一个 API 接口,接收用户的请求内容,并将其转发给 OpenAI 的 GPT-4 模型进行处理。然后,后端会通过 SSE 实时将 OpenAI 的响应推送给前端,实现与用户的实时互动。

主要的步骤包括:

  • 接收并处理用户请求。
  • 加载配置文件 .env
  • 向 OpenAI API 发送请求。
  • 通过 SSE 将 OpenAI 的响应实时推送给前端。

2. .env 配置文件

为了管理 API 密钥和其他配置项,我们使用了 .env 文件。这个文件存储了与 OpenAI API 交互所需的关键配置信息,如 API 密钥、模型类型、最大 Token 数量、温度值等。

以下是一个示例 .env 文件的配置内容:

# OpenAI API Key
OPENAI_API_KEY=your-openai-api-key

# OpenAI API Base URL
OPENAI_URL=https://api.openai.com

# 使用的 GPT 模型(例如:gpt-3.5-turbo)
GPT_MODEL=gpt-4

# 最大Token数
MAX_TOKENS=1000

# 生成文本的温度(控制输出的随机性)
TEMPERATURE=0.7
  • OPENAI_API_KEY: 你的 OpenAI API 密钥,确保其安全性。
  • OPENAI_URL: OpenAI API 的基础 URL,通常为 https://api.openai.com
  • GPT_MODEL: 要使用的 GPT 模型,如 gpt-3.5-turbo
  • MAX_TOKENS: 设置 GPT 模型生成的最大 token 数量,影响输出长度。
  • TEMPERATURE: 控制生成文本的随机性,值越高越随机。

3. 后端代码实现细节

在代码中,我们首先通过 godotenv 包加载 .env 文件中的配置项。然后,创建一个 POST 请求,将用户输入的内容发送给 OpenAI API。

以下是代码片段的主要逻辑:

// 加载 .env 文件中的配置
err := godotenv.Load()
if err != nil {
    c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to load .env file"})
    return
}

apiKey := os.Getenv("OPENAI_API_KEY")
url := os.Getenv("OPENAI_URL")
model := os.Getenv("GPT_MODEL")
maxTokens, _ := strconv.Atoi(os.Getenv("MAX_TOKENS"))
temperature, _ := strconv.ParseFloat(os.Getenv("TEMPERATURE"), 64)

接下来,将用户输入的内容封装到请求体中,并将其发送到 OpenAI API:

requestBody := GPTRequest{
    Model: model,
    Messages: []Message{
        {
            Role:    "system",
            Content: "You are a helpful assistant.",
        },
        {
            Role:    "user",
            Content: content,
        },
    },
    Stream:      true,
    MaxTokens:   maxTokens,
    Temperature: temperature,
}

jsonData, err := json.Marshal(requestBody)
if err != nil {
    c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to marshal request"})
    return
}

req, err := http.NewRequest("POST", url+"/v1/chat/completions", bytes.NewBuffer(jsonData))
if err != nil {
    c.JSON(http.StatusInternalServerError, gin.H{"error": "Failed to create request"})
    return
}

req.Header.Set("Content-Type", "application/json")
req.Header.Set("Authorization", "Bearer "+apiKey)

然后,我们通过 http.Client 发送请求,并处理返回的流式响应。Gin 的 SSE 功能可以帮助我们实时将数据推送到前端:

c.Stream(func(w io.Writer) bool {
    scanner := bufio.NewScanner(resp.Body)
    for scanner.Scan() {
        line := strings.TrimPrefix(scanner.Text(), "data: ")
        if len(line) > 0 {
            var streamResp StreamResponse
            err := json.Unmarshal([]byte(line), &streamResp)
            if err != nil {
                continue
            }

            if len(streamResp.Choices) > 0 {
                content := streamResp.Choices[0].Delta.Content
                c.SSEvent("message", content)
            }
            flusher, ok := w.(http.Flusher)
            if ok {
                flusher.Flush()
            }
        }
    }

    if err := scanner.Err(); err != nil {
        fmt.Fprintf(w, "data: %s\n\n", "Stream ended with an error")
        return false
    }

    return false // End the stream
})

4. 前端使用方法

为了在前端与后端进行实时交互,你可以使用 JavaScript 的 EventSource 对象来接收服务端推送的消息。

以下是前端代码示例:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>GPT-3 Chat</title>
</head>
<body>
    <h1>GPT-3 Chat</h1>
    <div id="chat"></div>
    <input type="text" id="userInput" placeholder="Type a message...">
    <button onclick="sendMessage()">Send</button>

    <script>
        function sendMessage() {
            var userInput = document.getElementById('userInput').value;
            var eventSource = new EventSource(`/openai?action=chat&content=${encodeURIComponent(userInput)}`);
            
            eventSource.onmessage = function(event) {
                var chatDiv = document.getElementById('chat');
                var newMessage = document.createElement('p');
                newMessage.textContent = event.data;
                chatDiv.appendChild(newMessage);
            };

            eventSource.onerror = function() {
                console.error("EventSource failed.");
                eventSource.close();
            };
        }
    </script>
</body>
</html>

步骤解释

  1. 输入框与发送按钮:用户在输入框中输入消息,并通过点击“Send”按钮发送消息。
  2. 创建 EventSource:在用户点击按钮后,创建一个 EventSource 对象,指定后端 API 的路径并带上用户输入的消息作为查询参数。
  3. 处理 onmessage 事件:当后端推送消息时,前端通过 onmessage 事件接收消息并将其显示在页面上。
  4. 处理错误:通过 onerror 事件处理连接错误,并关闭 EventSource 连接。

5. 总结

通过本文,你已经学会了如何使用 Go 和 Gin 实现一个与 OpenAI 的 GPT-3 模型实时交互的后端 API,并且能够通过前端使用 SSE 技术实时接收来自后端的响应。 .env 文件使得 API 配置管理更加简单和安全,前端的 EventSource 允许你轻松实现实时通讯功能。这个方案适用于需要实时反馈的应用场景,如智能客服、实时聊天机器人等。

通过这种方式,你可以将强大的 GPT-4 模型集成到你的应用中,为用户提供智能且即时的交互体验。

推荐文章

Rust async/await 异步运行时
2024-11-18 19:04:17 +0800 CST
liunx宝塔php7.3安装mongodb扩展
2024-11-17 11:56:14 +0800 CST
38个实用的JavaScript技巧
2024-11-19 07:42:44 +0800 CST
使用 Vue3 和 Axios 实现 CRUD 操作
2024-11-19 01:57:50 +0800 CST
Gin 框架的中间件 代码压缩
2024-11-19 08:23:48 +0800 CST
js迭代器
2024-11-19 07:49:47 +0800 CST
四舍五入五成双
2024-11-17 05:01:29 +0800 CST
go发送邮件代码
2024-11-18 18:30:31 +0800 CST
智能视频墙
2025-02-22 11:21:29 +0800 CST
Vue3中的组件通信方式有哪些?
2024-11-17 04:17:57 +0800 CST
黑客帝国代码雨效果
2024-11-19 01:49:31 +0800 CST
介绍 Vue 3 中的新的 `emits` 选项
2024-11-17 04:45:50 +0800 CST
如何在Vue3中处理全局状态管理?
2024-11-18 19:25:59 +0800 CST
Git 常用命令详解
2024-11-18 16:57:24 +0800 CST
Vue 3 路由守卫详解与实战
2024-11-17 04:39:17 +0800 CST
使用 node-ssh 实现自动化部署
2024-11-18 20:06:21 +0800 CST
java MySQL如何获取唯一订单编号?
2024-11-18 18:51:44 +0800 CST
Nginx 反向代理 Redis 服务
2024-11-19 09:41:21 +0800 CST
Go的父子类的简单使用
2024-11-18 14:56:32 +0800 CST
程序员茄子在线接单