当前位置: 首页 > news >正文

使用Java调用OpenAI API并解析响应:详细教程

使用Java调用OpenAI API并解析响应:详细教程

在现代应用程序中,API调用是一个非常常见的任务。本文将通过一个完整的示例,讲解如何使用Java调用OpenAI的ChatGPT API,并通过ObjectMapper处理JSON响应。本文的示例不仅适用于OpenAI的API,也可以扩展到其他API调用中。具体示例中我们会使用HttpURLConnection来发起请求,并使用ObjectMapper进行JSON解析。

项目场景

我们将编写一个方法,通过调用ChatGPT API,模拟发送消息并获取AI的响应。核心步骤包括:

  1. 发起HTTP请求。
  2. 设置请求头和请求体。
  3. 解析服务器返回的JSON响应。

1. URL类

在Java中,URL类用于表示统一资源定位符(即Web地址)。在我们的示例中,URL对象用于指定我们要调用的API的URL地址。

URL url = new URL("https://api.chatanywhere.tech/v1/chat/completions");

这里我们使用了一个中转服务器地址。通常,你会调用OpenAI官方的API地址 https://api.openai.com/v1/chat/completions。但在国内,访问这些外网资源可能受到限制,因此我们可以使用中转服务进行代理访问。

2. HttpURLConnection类

HttpURLConnection类是Java用于发送HTTP请求的核心类。我们通过它来设置请求方法、请求头、请求体,并读取响应。

HttpURLConnection connection = (HttpURLConnection) url.openConnection();
  • 设置请求方法:通过connection.setRequestMethod("GET")"POST"可以指定HTTP请求类型。通常,API请求发送数据使用POST方法。
connection.setRequestMethod("POST");
  • 设置请求头:为了与API服务交互,我们需要设置一些必要的请求头信息,如授权信息和内容类型。
connection.setRequestProperty("Authorization", "Bearer " + apiKey);
connection.setRequestProperty("Content-Type", "application/json");
  • 请求体:在发送POST请求时,需要将请求内容以字节流的形式写入输出流中。这里我们构建了一个JSON格式的请求体,并通过getOutputStream方法发送。
String inputJson = "{\"model\": \"gpt-3.5-turbo\", \"messages\": [{\"role\": \"system\", \"content\": \"你是一个贴心的AI助手,用来解决用户的各种问题,回答用中文!\"}, {\"role\": \"user\", \"content\": \"你是谁,基于什么模型?\"}]}";
try (OutputStream os = connection.getOutputStream()) {byte[] input = inputJson.getBytes(StandardCharsets.UTF_8);os.write(input, 0, input.length);
}

3. 处理响应数据

一旦请求发送后,服务器会返回数据。我们可以通过getInputStream方法获取服务器的响应,使用Scanner类读取并逐行打印响应内容。

//因为InputStream是一种一次性流,它只能读取一次,读完之后就关闭了,不能再读取,所以用Scanner进行读取数据并逐行处理,然后再将其一行行的写入StringBulider中,方便后续操作和使用
try (Scanner scanner = new Scanner(connection.getInputStream(), StandardCharsets.UTF_8)) {StringBuilder response = new StringBuilder();while (scanner.hasNext()) {response.append(scanner.nextLine());}System.out.println("接收到响应为: " + response.toString());
}

4. 使用ObjectMapper解析JSON

在我们的API返回数据中,通常是JSON格式。为了方便解析和操作JSON数据,我们使用Jackson库中的ObjectMapper类。ObjectMapper是Jackson提供的一个核心工具类,可以帮助我们将JSON字符串转换为Java对象,或者将Java对象转换为JSON。

ObjectMapper objectMapper = new ObjectMapper();
JsonNode jsonNode = objectMapper.readTree(response.toString());
JsonNode jsonChoicesNode = jsonNode.get("choices").get(0);
String content = jsonChoicesNode.get("message").get("content").asText();

在上面的代码中,readTree()方法会将JSON字符串转换为JsonNode对象。通过get()方法,我们可以获取JSON中的特定字段,并使用asText()方法将其转换为字符串。

5. 异常处理

在与外部API交互时,可能会遇到各种异常情况,比如连接超时、读写超时或者其他I/O错误。为了确保程序的鲁棒性,我们需要捕获这些异常并进行处理。

catch (IOException e) {throw new RuntimeException(e);
}

完整代码示例

void openAiChatGpt() {String apiKey = "sk-your-api-key";//替换成你自己的API KEY try {URL url = new URL("https://api.chatanywhere.tech/v1/chat/completions");System.out.println("测试连接");HttpURLConnection connection = (HttpURLConnection) url.openConnection();connection.setRequestMethod("GET");connection.setRequestProperty("Authorization", "Bearer " + apiKey);connection.setRequestProperty("Content-Type", "application/json");connection.setDoOutput(true);String inputJson = "{\"model\": \"gpt-3.5-turbo\", \"messages\": [{\"role\": \"system\", \"content\": \"你是一个贴心的AI助手,用来解决用户的各种问题,回答用中文!\"}, {\"role\": \"user\", \"content\": \"你是谁,基于什么模型?\"}]}";try (OutputStream os = connection.getOutputStream()) {byte[] input = inputJson.getBytes(StandardCharsets.UTF_8);os.write(input, 0, input.length);}try (Scanner scanner = new Scanner(connection.getInputStream(), StandardCharsets.UTF_8)) {StringBuilder response = new StringBuilder();while (scanner.hasNext()) {response.append(scanner.nextLine());}System.out.println("接收到响应为: " + response.toString());ObjectMapper objectMapper = new ObjectMapper();JsonNode jsonNode = objectMapper.readTree(response.toString());JsonNode jsonChoicesNode = jsonNode.get("choices").get(0);String content = jsonChoicesNode.get("message").get("content").asText();System.out.println("-----------");System.out.println(content);}} catch (IOException e) {throw new RuntimeException(e);}
}

结果

在这里插入图片描述

总结

通过这篇文章,我们了解了如何使用Java进行HTTP请求,如何设置请求头、发送请求体,如何使用Jackson的ObjectMapper来解析服务器返回的JSON响应。通过这个简单的示例,你可以很容易扩展到其他API调用场景中。如果你需要调用更多复杂的API,比如需要身份验证、文件上传或下载,都可以在此基础上进行扩展。

希望这篇文章对你有所帮助!如果你有任何问题,欢迎留言讨论。

相关文章:

使用Java调用OpenAI API并解析响应:详细教程

使用Java调用OpenAI API并解析响应:详细教程 在现代应用程序中,API调用是一个非常常见的任务。本文将通过一个完整的示例,讲解如何使用Java调用OpenAI的ChatGPT API,并通过ObjectMapper处理JSON响应。本文的示例不仅适用于OpenAI…...

深入学习并发编程中的 synchronized

文章目录 并发编程中的三个问题可见性原子性有序性 了解Java内存模型JMMsynchronized 保证三大特性synchronized 保证原子性synchronized 保证可见性synchronized 保证有序性 synchronized 的特性可重入特性不可中断特性 通过反汇编学习synchronized原理当修饰代码块时当修饰方…...

AMD R9-9950X相比较I9-14900K有哪些提升

AMD R9-9950X相比较I9-14900K有哪些提升?在处理器领域,AMD与英特尔的竞争从未停歇,每一次新品发布都引发业界的高度关注。近日,AMD推出了其新一代桌面级旗舰处理器——Ryzen 9 9950X(简称R9-9950X)&#xf…...

计算机毕业设计 基于Python的个性化旅游线路推荐系统的设计与实现 Python+Django+Vue 前后端分离 附源码 讲解 文档

🍊作者:计算机编程-吉哥 🍊简介:专业从事JavaWeb程序开发,微信小程序开发,定制化项目、 源码、代码讲解、文档撰写、ppt制作。做自己喜欢的事,生活就是快乐的。 🍊心愿:点…...

总结:Flink之DataStream各API介绍

一、介绍 本文主要是详细介绍 DataStream<T> 类中的各个方法,并给出它们的使用场景。 二、基本方法 getId(): 作用:返回转换操作的唯一标识符。场景:当需要调试或日志记录时,有时候需要知道操作的 ID。getParallelism(): 作用:获取流的并行度。场景:在优化作业时…...

设计一个日志管理系统,支持多级别日志记录

设计一个日志管理系统,支持多级别日志记录 作为一名Python程序软件专家,我经常被问到关于日志管理系统的设计和实现。今天,我将分享一篇关于设计一个日志管理系统,支持多级别日志记录的博文,希望能够帮助大家更好地理解和使用Python语言。 日志管理系统的需求 在软件开…...

Javascript动态规划算法

JavaScript中的动态规划&#xff08;Dynamic Programming&#xff0c;简称DP&#xff09;是一种通过把原问题分解为相对简单的子问题的方式来求解复杂问题的方法。它主要致力于将“合适”的问题拆分成更小的子目标&#xff0c;并通过建立状态转移方程、缓存并复用以往结果以及按…...

Java 循环里怎么删除元素才安全

首先 在 Java 中&#xff0c;当你在循环中遍历集合时&#xff0c;直接删除元素可能会引发 ConcurrentModificationException。为了安全地删除元素&#xff0c;推荐使用 Iterator 来进行删除操作。 以下是使用 Iterator 删除元素的常见模式&#xff1a; import java.util.Arr…...

LabVIEW晶体振荡器自动化测试系统

基于LabVIEW平台的晶体振荡器自动化测试系统解决了传统手工测试晶体振荡器繁琐且易出错的问题。该系统通过高度自动化的测试流程&#xff0c;提高了测试效率和精度&#xff0c;实现了数据的自动采集与处理&#xff0c;适用于电子、通信等领域的晶振测试需求。 项目背景与意义 …...

3.6.xx版本SpringBoot创建基于Swagger接口文档

介绍 基于Swagger构建的JavaAPI文档工具&#xff0c;实现后端功能的测试&#xff0c;并撰写API接口文档。 方法 pom.xml中引入依赖,要注意的是&#xff0c;本依赖使用的SpringBoot版本为3.6.xx <!--Knife4j--><dependency><groupId>com.github.xiaoymin<…...

Oracle 12201非PDBS模式单机部署(静默安装)

一、创建Oracle数据库的用户 groupadd oinstall groupadd dba groupadd asmadmin groupadd asmdba useradd -g oinstall -G dba,asmdba oracle -d /home/oracle passwd oracle二、配置Linux 服务器参数 cat /home/oracle/.bash_profile export ORACLE_HOSTNAMEH_orcle01 expo…...

Python 源码编译安装详解:跨平台指南及完整步骤解析

Python 源码编译安装详解&#xff1a;跨平台指南及完整步骤解析 文章目录 Python 源码编译安装详解&#xff1a;跨平台指南及完整步骤解析一 准备工作1&#xff09;Ubuntu/Debian2&#xff09;CentOS/RHEL3&#xff09;macOS 二 下载 Python 源码三 编译与安装1&#xff09;解压…...

MQTT vs HTTP:谁更适合物联网?

前言 随着物联网&#xff08;IoT&#xff09;技术的飞速发展中&#xff0c;其应用规模和使用场景正在持续扩大&#xff0c;但它关键的流程仍然是围绕数据传输来进行的&#xff0c;因此设备通信协议选择至关重要。 作为两种主要的通信协议&#xff0c;MQTT 协议和 HTTP 协议各…...

小北的技术博客:探索华为昇腾CANN训练营与AI技术创新——Ascend C算子开发能力认证考试(初级)

前言 哈喽哈喽友友们,这里是zyll~(小北)智慧龙阁的创始人及核心技术开发者。在技术的广阔天地里,我专注于大数据与全栈开发,并致力于成为这一领域的新锐力量。通过智慧龙阁这个平台,我期望能与大家分享我的技术心得,共同探索技术的无限可能。 Ascend C编程:小北的技术…...

鸿蒙next开发者第一课02.DevEcoStudio的使用-习题

【习题】DevEco Studio的使用 通过/及格分80/ 满分100 判断题 1. 如果代码中涉及到一些网络、数据库、传感器等功能的开发&#xff0c;均可使用预览器进行预览。F 正确(True)错误(False) 预览器不能进行传感器等特殊功能的开发,需要使用真机开发 2. module.json5文件中的…...

【vue】监听table水平滚动条切换tab后还原位置

有个需求就是切换tab后&#xff0c;原先的table水平滚动条要还原位置&#xff08;如下图&#xff09;&#xff0c;先说下思路&#xff0c;大致就是 切出页面时 把滚动距离保存到Storage 中&#xff0c;切回来时在恢复 直接上代码 首先table ref指定一下ref"jtable" …...

C#使用PdfSharp生成PDF文件实例详解

许多项目开发中需要生成PDF, 常规办法使用官方提供的Microsoft.Office.Interop.Worddll插件,但是这种方法需要完全安装OFFICE,另外版本不一致还会出现很多错误。一般不推荐使用。 下面介绍几种巧妙的用法,定能事半功倍。 本文使用PDFsharp完成功能。 PDFsharp一款开源的…...

【软件系统架构设计师-案例-1】架构风格

1. 请用200字以内说明系统可靠性的定义及包含的4个子特性&#xff0c;并简要指出提高系统可靠性一般采用哪些技术&#xff1f; &#xff08;1&#xff09;可靠性定义&#xff1a;系统在规定的时间或环境条件下&#xff0c;完成规定功能的能力&#xff0c;就是系统无故障运行的…...

神经网络整体架构

文章目录 1.输入层Input2.卷积层Conv3.激活函数层(一)Sigmoid 函数(二)Tanh 函数(三)修正线性单元ReLU(四)Leaky ReLU函数(带泄露的Relu)(五)参数化ReLU 4.池化层POOL5.全连接层FC6.输出层Output 用全连接神经网络处理大尺寸图像具有三个明显的缺点&#xff1a; ①将图像展开为…...

山西农业大学20241010

02-JAVASCRIPT 一.JS基础语法1. 数据类型转换1.1 隐式转换1.2 强制转换 2. 运算符 二.JS语句1. 条件语句2. 循环语句 三.函数(方法)1. 声明函数的第一种方法2. 声明函数的第二种方法3. 声明函数的第三种方法 四.对象1. 对象的创建 -- 字面量2. 访问对象的属性3. 内置构造函数以…...

golang循环变量捕获问题​​

在 Go 语言中&#xff0c;当在循环中启动协程&#xff08;goroutine&#xff09;时&#xff0c;如果在协程闭包中直接引用循环变量&#xff0c;可能会遇到一个常见的陷阱 - ​​循环变量捕获问题​​。让我详细解释一下&#xff1a; 问题背景 看这个代码片段&#xff1a; fo…...

VB.net复制Ntag213卡写入UID

本示例使用的发卡器&#xff1a;https://item.taobao.com/item.htm?ftt&id615391857885 一、读取旧Ntag卡的UID和数据 Private Sub Button15_Click(sender As Object, e As EventArgs) Handles Button15.Click轻松读卡技术支持:网站:Dim i, j As IntegerDim cardidhex, …...

日语学习-日语知识点小记-构建基础-JLPT-N4阶段(33):にする

日语学习-日语知识点小记-构建基础-JLPT-N4阶段(33):にする 1、前言(1)情况说明(2)工程师的信仰2、知识点(1) にする1,接续:名词+にする2,接续:疑问词+にする3,(A)は(B)にする。(2)復習:(1)复习句子(2)ために & ように(3)そう(4)にする3、…...

解锁数据库简洁之道:FastAPI与SQLModel实战指南

在构建现代Web应用程序时&#xff0c;与数据库的交互无疑是核心环节。虽然传统的数据库操作方式&#xff08;如直接编写SQL语句与psycopg2交互&#xff09;赋予了我们精细的控制权&#xff0c;但在面对日益复杂的业务逻辑和快速迭代的需求时&#xff0c;这种方式的开发效率和可…...

今日科技热点速览

&#x1f525; 今日科技热点速览 &#x1f3ae; 任天堂Switch 2 正式发售 任天堂新一代游戏主机 Switch 2 今日正式上线发售&#xff0c;主打更强图形性能与沉浸式体验&#xff0c;支持多模态交互&#xff0c;受到全球玩家热捧 。 &#x1f916; 人工智能持续突破 DeepSeek-R1&…...

大学生职业发展与就业创业指导教学评价

这里是引用 作为软工2203/2204班的学生&#xff0c;我们非常感谢您在《大学生职业发展与就业创业指导》课程中的悉心教导。这门课程对我们即将面临实习和就业的工科学生来说至关重要&#xff0c;而您认真负责的教学态度&#xff0c;让课程的每一部分都充满了实用价值。 尤其让我…...

AGain DB和倍数增益的关系

我在设置一款索尼CMOS芯片时&#xff0c;Again增益0db变化为6DB&#xff0c;画面的变化只有2倍DN的增益&#xff0c;比如10变为20。 这与dB和线性增益的关系以及传感器处理流程有关。以下是具体原因分析&#xff1a; 1. dB与线性增益的换算关系 6dB对应的理论线性增益应为&…...

处理vxe-table 表尾数据是单独一个接口,表格tableData数据更新后,需要点击两下,表尾才是正确的

修改bug思路&#xff1a; 分别把 tabledata 和 表尾相关数据 console.log() 发现 更新数据先后顺序不对 settimeout延迟查询表格接口 ——测试可行 升级↑&#xff1a;async await 等接口返回后再开始下一个接口查询 ________________________________________________________…...

STM32HAL库USART源代码解析及应用

STM32HAL库USART源代码解析 前言STM32CubeIDE配置串口USART和UART的选择使用模式参数设置GPIO配置DMA配置中断配置硬件流控制使能生成代码解析和使用方法串口初始化__UART_HandleTypeDef结构体浅析HAL库代码实际使用方法使用轮询方式发送使用轮询方式接收使用中断方式发送使用中…...

快刀集(1): 一刀斩断视频片头广告

一刀流&#xff1a;用一个简单脚本&#xff0c;秒杀视频片头广告&#xff0c;还你清爽观影体验。 1. 引子 作为一个爱生活、爱学习、爱收藏高清资源的老码农&#xff0c;平时写代码之余看看电影、补补片&#xff0c;是再正常不过的事。 电影嘛&#xff0c;要沉浸&#xff0c;…...