chatgpt-java

Project Url: Grt1228/chatgpt-java
Introduction: ChatGPT Java SDK 支持流式输出、Gpt 插件、联网。支持 OpenAI 官方所有接口。ChatGPT 的 Java 客户端。OpenAI GPT-3.5-Turb GPT-4 Api Client for Java
More: Author   ReportBugs   OfficialWebsite   
Tags:

it’s an “unofficial" or "community-maintained” library. 这是一个非官方的社区维护的库。有 bug 欢迎朋友们指出,互相学习。

原创发布转载注明出处!

文档地址:https://chatgpt-java.unfbx.com/

星火大模型 Java SDK: https://github.com/Grt1228/SparkDesk-Java

To English Doc -> English Doc

💬 联系我,ChatGPT 相关学习交流咨询全部免费。

一起探讨 chatgpt-java,SDK 问题咨询
项目产品开发交流
群失效关注公众号恢复:chatgpt-java
二维码 二维码

📖 项目简介

ChatGPT 的 Java 客户端 OpenAI 官方 Api 的 Java SDK,可以快速接入项目使用。支持 OpenAI 官方全部接口,同时支持 Tokens 计算。参考文档:Tokens_README.md

Assistant Dall-e-3 FineTuneJob TTS ChatCompletionWithPicture
自定义知识库、AI 助理 AI 生成图片 微调 job 文本转语音 附加图片的 ChatCompletion
TikToken Chat Completions Images Speech To Text 余额查询
Token 计算 GPT-3.5、4.0 对话模型 GPT-3.0 对话 图片模型 语音转文字,语音翻译 余额查询
Embeddings Files Moderations Fine-tune Models
嵌入 自定义训练模型 文本审核,敏感词鉴别 微调 模型检索相关

支持流式输出: 流式输出实现方式 | 小程序 | 安卓 | ios | H5 ---|---|---|---|--- SSE 参考:OpenAISSEEventSourceListener | 不支持| 支持| 支持 | 支持 WebSocket 参考:OpenAIWebSocketEventSourceListener | 支持| 支持| 支持| 支持

基于本 SDK 开发的 Demo 项目,整合 Spring Boot 实现 CahtGPT 对话模式,思路可以参考: https://github.com/Grt1228/chatgpt-steam-output

🚩 特性

  • 支持附加图片的 ChatCompletion、指定返回数据格式、Tool Call、Dall-e-3 生成图片、FineTuneJob、文本转语音 TTS。
  • 支持 GPT 插件模式 参考实现PluginTest
  • 支持当 key 异常(失效、过期、封禁)时,自定义动态处理 key 参考实现DynamicKeyOpenAiAuthInterceptor
  • 支持当 key 异常时的告警处理(钉钉、飞书、email、企业微信等等需要自定义开发)参考实现DynamicKeyOpenAiAuthInterceptor
  • 支持多种 Tokens 计算方式
  • 支持自定义 OkhttpClient
  • 支持自定义多 Apikey
  • 支持自定义 ApiKey 的获取策略
  • 支持余额查询
  • 支持个人账户信息查询
  • 支持 GPT3、GPT3.5、GPT4.0、GPT3.5—0614、GPT4.0—0614...
  • 支持全部 OpenAI 的 Api

📑 更新日志

  • [x] 1.1.5 Bug Fix
  • [x] 1.1.3 支持 Assistant、Run、Thread、Message Api。测试案例OpenAiClientTest
  • [x] 1.1.2-beta0 支持附加图片的 ChatCompletion、指定返回数据格式、Tool Call、Dall-e-3 生成图片、FineTuneJob、文本转语音 TTS。官方文档示例:chatgpt-java.unfbx.com 。测试案例OpenAiClientTest
  • [x] 1.1.1-beta0 function call 改成 GPT 插件模式调用更加简单的调用方式.参考实现PluginTest
  • [x] 1.0.15 moderations 接口更新,代码优化,序列化修复。
  • [x] 1.0.14 升级支持最新版 Gpt-3.5—0614、Gpt-4.0—0614 等模型, 支持 function-calling 完整使用案例参考:OpenAiClientFunctionTest
  • [x] 1.0.13 支持当 key 异常(失效、过期、封禁)时,自定义动态处理 key,参考实现DynamicKeyOpenAiAuthInterceptor ,支持 key 异常时的告警处理(钉钉、飞书、email、企业微信等等需要自定义开发)
  • [x] 1.0.12 tokens 计算优化、删除模型接口修改、语音接口更新支持官方最新参数
  • [x] 1.0.11 增加新的余额查询接口参考:OpenAiClientTestOpenAiStreamClientTest ,修复 tokens 计算慢的问题,
  • [x] 1.0.10 支持 tokens 计算:TikTokensTest ,更多详细的资料参考文档:Tokens_README.md
  • [x] 1.0.9 支持自定义 key 使用策略参考:OpenAiClientTestOpenAiStreamClientTest ,弃用 ChatGPTClient,优化 Moderation 接口
  • [x] 1.0.8 修改 OpenAiClient 和 OpenAiStreamClient 的自定义相关实现,超时设置,代理设置,自定义拦截器设置改为通过自定义 OkHttpClient 实现,将 OkHttpClient 交由用户自定义控制更加合理,可以实现更多的参数自定义。支持多 Api Keys 配置。
  • [x] 1.0.7 修复反序列化报错 Bug:https://github.com/Grt1228/chatgpt-java/issues/79 ,Image SDK 枚举值 bug:https://github.com/Grt1228/chatgpt-java/issues/76 ,感谢两位朋友指出:@CCc3120@seven-cm
  • [x] 1.0.6 支持余额查询参考:OpenAiClientTestOpenAiStreamClientTest creditGrants 方法,支持最新 GPT-4 模型,参考:ChatCompletion.Model构建消息体传入模型即可。感谢群友提供的余额接口地址以及@PlexPt 提供的模型参数
  • [x] 1.0.5 支持自定义 Api Host,使用 Builder 构建。参考下面的快速开始部分代码。
  • [x] 1.0.4 官方最新的 ChatGPT Stream 模式下的 Api 返回值改动。
  • [x] 1.0.3 支持最新的 GPT-3.5-Turbo 模型和 Whisper-1 模型,支持语音功能转文字,语音翻译。OpenAiClient 和 OpenAiStreamClient 支持 Builder 构造,支持代理。
  • [x] 1.0.2 支持 Stream 流式输出,参考:OpenAiStreamClient
  • [x] 1.0.1 支持自定义超时时间,自定义 OkHttpClient 拦截器,参考:OpenAiClient 构造函数
  • [x] 1.0.0 支持所有的 OpenAI 官方接口

🚀 快速开始

本项目支持默认输出流式输出。完整 SDK 测试案例参考:

SDK 测试案例 Tokens 计算测试案例 完整 Function-Call 调用案例
OpenAiClientTestOpenAiStreamClientTest Tokens 计算参考:TikTokensTest OpenAiClientFunctionTest

方式一

1、导入 pom 依赖

<dependency>
    <groupId>com.unfbx</groupId>
    <artifactId>chatgpt-java</artifactId>
    <version>1.0.14-beta1</version>
</dependency>

2、流式客户端使用示例:

更多 SDK 示例参考:OpenAiStreamClientTest

默认 OkHttpClient

public class Test {
    public static void main(String[] args) {
        OpenAiStreamClient client = OpenAiStreamClient.builder()
                .apiKey(Arrays.asList("sk-********","sk-********"))
                //自定义 key 的获取策略:默认 KeyRandomStrategy
                //.keyStrategy(new KeyRandomStrategy())
                .keyStrategy(new FirstKeyStrategy())
                //自己做了代理就传代理地址,没有可不不传
//                .apiHost("https://自己代理的服务器地址/")
                .build();
        //聊天模型:gpt-3.5
        ConsoleEventSourceListener eventSourceListener = new ConsoleEventSourceListener();
        Message message = Message.builder().role(Message.Role.USER).content("你好啊我的伙伴!").build();
        ChatCompletion chatCompletion = ChatCompletion.builder().messages(Arrays.asList(message)).build();
        client.streamChatCompletion(chatCompletion, eventSourceListener);
        CountDownLatch countDownLatch = new CountDownLatch(1);
        try {
            countDownLatch.await();
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

自定义 OkHttpClient 客户端使用示例:

public class Test {
    public static void main(String[] args) {
        //国内访问需要做代理,国外服务器不需要
        Proxy proxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress("127.0.0.1", 7890));
        HttpLoggingInterceptor httpLoggingInterceptor = new HttpLoggingInterceptor(new OpenAILogger());
        //!!!!千万别再生产或者测试环境打开 BODY 级别日志!!!!
        //!!!生产或者测试环境建议设置为这三种级别:NONE,BASIC,HEADERS,!!!
        httpLoggingInterceptor.setLevel(HttpLoggingInterceptor.Level.HEADERS);
        OkHttpClient okHttpClient = new OkHttpClient
                .Builder()
                .proxy(proxy)//自定义代理
                .addInterceptor(httpLoggingInterceptor)//自定义日志
                .connectTimeout(30, TimeUnit.SECONDS)//自定义超时时间
                .writeTimeout(30, TimeUnit.SECONDS)//自定义超时时间
                .readTimeout(30, TimeUnit.SECONDS)//自定义超时时间
                .build();
        OpenAiStreamClient client = OpenAiStreamClient.builder()
                .apiKey(Arrays.asList("sk-********","sk-********"))
                //自定义 key 的获取策略:默认 KeyRandomStrategy
                //.keyStrategy(new KeyRandomStrategy())
                .keyStrategy(new FirstKeyStrategy())
                .okHttpClient(okHttpClient)
                //自己做了代理就传代理地址,没有可不不传
//                .apiHost("https://自己代理的服务器地址/")
                .build();
    }
}

输出日志(text 是持续输出的):

23:03:59.158 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 建立 sse 连接...
23:03:59.160 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\n", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.172 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\n", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.251 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u5fc3", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.313 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u60c5", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.380 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u8212", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.439 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u7545", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.532 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\uff0c", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.579 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u5fc3", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.641 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u65f7", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.673 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u795e", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.751 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u6021", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.782 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:{"id": "cmpl-6pIHnOOJiiUEVMesXwxzzcSQFoZHj", "object": "text_completion", "created": 1677683039, "choices": [{"text": "\u3002", "index": 0, "logprobs": null, "finish_reason": null}], "model": "text-davinci-003"}
23:03:59.815 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据:[DONE]
23:03:59.815 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 返回数据结束了
23:03:59.815 [省略无效信息] INFO com.unfbx.chatgpt.sse.ConsoleEventSourceListener - OpenAI 关闭 sse 连接...

3、默认客户端使用示例(支持全部 API):

更多 SDK 示例参考:OpenAiClientTest

默认 OkHttpClient

public class Test {
    public static void main(String[] args) {
        OpenAiClient openAiClient = OpenAiClient.builder()
                .apiKey(Arrays.asList("sk-********","sk-********"))
                //自定义 key 的获取策略:默认 KeyRandomStrategy
                //.keyStrategy(new KeyRandomStrategy())
                .keyStrategy(new FirstKeyStrategy())
                //自己做了代理就传代理地址,没有可不不传
//                .apiHost("https://自己代理的服务器地址/")
                .build();
                //聊天模型:gpt-3.5
        Message message = Message.builder().role(Message.Role.USER).content("你好啊我的伙伴!").build();
        ChatCompletion chatCompletion = ChatCompletion.builder().messages(Arrays.asList(message)).build();
        ChatCompletionResponse chatCompletionResponse = openAiClient.chatCompletion(chatCompletion);
        chatCompletionResponse.getChoices().forEach(e -> {
            System.out.println(e.getMessage());
        });
    }
}

自定义 OkHttpClient 客户端使用示例:

public class Test {
    public static void main(String[] args) {
        //国内访问需要做代理,国外服务器不需要
        Proxy proxy = new Proxy(Proxy.Type.HTTP, new InetSocketAddress("127.0.0.1", 7890));
        HttpLoggingInterceptor httpLoggingInterceptor = new HttpLoggingInterceptor(new OpenAILogger());
        //!!!!千万别再生产或者测试环境打开 BODY 级别日志!!!!
        //!!!生产或者测试环境建议设置为这三种级别:NONE,BASIC,HEADERS,!!!
        httpLoggingInterceptor.setLevel(HttpLoggingInterceptor.Level.HEADERS);
        OkHttpClient okHttpClient = new OkHttpClient
                .Builder()
                .proxy(proxy)//自定义代理
                .addInterceptor(httpLoggingInterceptor)//自定义日志输出
                .addInterceptor(new OpenAiResponseInterceptor())//自定义返回值拦截
                .connectTimeout(10, TimeUnit.SECONDS)//自定义超时时间
                .writeTimeout(30, TimeUnit.SECONDS)//自定义超时时间
                .readTimeout(30, TimeUnit.SECONDS)//自定义超时时间
                .build();
        //构建客户端
        OpenAiClient openAiClient = OpenAiClient.builder()
                .apiKey(Arrays.asList("sk-********","sk-********"))
                //自定义 key 的获取策略:默认 KeyRandomStrategy
                //.keyStrategy(new KeyRandomStrategy())
                .keyStrategy(new FirstKeyStrategy())
                .okHttpClient(okHttpClient)
                //自己做了代理就传代理地址,没有可不不传
//                .apiHost("https://自己代理的服务器地址/")
                .build();
                //聊天模型:gpt-3.5
        Message message = Message.builder().role(Message.Role.USER).content("你好啊我的伙伴!").build();
        ChatCompletion chatCompletion = ChatCompletion.builder().messages(Arrays.asList(message)).build();
        ChatCompletionResponse chatCompletionResponse = openAiClient.chatCompletion(chatCompletion);
        chatCompletionResponse.getChoices().forEach(e -> {
            System.out.println(e.getMessage());
        });
    }
}

方式二(下载源码直接运行)

下载源码打包

❔ QA

Q A
如何实现连续对话? issues:https://github.com/Grt1228/chatgpt-java/issues/8
如何实现流式输出? 升级 1.0.2 版本,参考源码:OpenAiStreamClientTest
如何整合 SpringBoot 实现流式输出的 Api 接口? 参考另外一个项目:chatgpt-steam-output
最新版 GPT-3.5-TURBO 是否支持? 升级 1.0.3 已经支持 ChatCompletion, 参考测试案例:OpenAiStreamClientTestOpenAiStreamClientTest
最新版语言转文字和语言翻译是否支持? 升级 1.0.3 已经支持 whisper 参考测试案例:OpenAiStreamClientTestOpenAiStreamClientTest

📌 国内访问解决方案

国内访问可以看下这个解决方案:https://github.com/noobnooc/noobnooc/discussions/9

📋 开发案例收集

基于本 SDK 开发案例收集chatgpt-java SDK 案例征集

🌟 Star History

Star History Chart

🙏 鸣谢

站在巨人的肩膀:

☕ 打赏

如果项目对你有帮助,可以选择请我喝杯奶茶

微信截图 _20230405222411 微信截图 _20230405222357

开源协议:LICENSE

Apps
About Me
GitHub: Trinea
Facebook: Dev Tools