Commit 1feff2b12b4f3c7b5711ce980ae94492bbad44c2
1 parent
e0f08a0f
【代码优化】AI:完善 OpenAIChatModelTests、OpenAiImageModelTests 单测,方便大家快速体验
Showing
6 changed files
with
108 additions
and
73 deletions
yudao-module-ai/yudao-module-ai-biz/src/main/java/cn/iocoder/yudao/module/ai/service/model/AiApiKeyServiceImpl.java
| @@ -101,7 +101,7 @@ public class AiApiKeyServiceImpl implements AiApiKeyService { | @@ -101,7 +101,7 @@ public class AiApiKeyServiceImpl implements AiApiKeyService { | ||
| 101 | public ChatModel getChatModel(Long id) { | 101 | public ChatModel getChatModel(Long id) { |
| 102 | AiApiKeyDO apiKey = validateApiKey(id); | 102 | AiApiKeyDO apiKey = validateApiKey(id); |
| 103 | AiPlatformEnum platform = AiPlatformEnum.validatePlatform(apiKey.getPlatform()); | 103 | AiPlatformEnum platform = AiPlatformEnum.validatePlatform(apiKey.getPlatform()); |
| 104 | - return modelFactory.getOrCreateChatClient(platform, apiKey.getApiKey(), apiKey.getUrl()); | 104 | + return modelFactory.getOrCreateChatModel(platform, apiKey.getApiKey(), apiKey.getUrl()); |
| 105 | } | 105 | } |
| 106 | 106 | ||
| 107 | @Override | 107 | @Override |
yudao-module-ai/yudao-spring-boot-starter-ai/src/main/java/cn/iocoder/yudao/framework/ai/core/factory/AiModelFactory.java
| @@ -23,7 +23,7 @@ public interface AiModelFactory { | @@ -23,7 +23,7 @@ public interface AiModelFactory { | ||
| 23 | * @param url API URL | 23 | * @param url API URL |
| 24 | * @return ChatModel 对象 | 24 | * @return ChatModel 对象 |
| 25 | */ | 25 | */ |
| 26 | - ChatModel getOrCreateChatClient(AiPlatformEnum platform, String apiKey, String url); | 26 | + ChatModel getOrCreateChatModel(AiPlatformEnum platform, String apiKey, String url); |
| 27 | 27 | ||
| 28 | /** | 28 | /** |
| 29 | * 基于默认配置,获得 ChatModel 对象 | 29 | * 基于默认配置,获得 ChatModel 对象 |
yudao-module-ai/yudao-spring-boot-starter-ai/src/main/java/cn/iocoder/yudao/framework/ai/core/factory/AiModelFactoryImpl.java
| @@ -50,7 +50,7 @@ import java.util.List; | @@ -50,7 +50,7 @@ import java.util.List; | ||
| 50 | public class AiModelFactoryImpl implements AiModelFactory { | 50 | public class AiModelFactoryImpl implements AiModelFactory { |
| 51 | 51 | ||
| 52 | @Override | 52 | @Override |
| 53 | - public ChatModel getOrCreateChatClient(AiPlatformEnum platform, String apiKey, String url) { | 53 | + public ChatModel getOrCreateChatModel(AiPlatformEnum platform, String apiKey, String url) { |
| 54 | String cacheKey = buildClientCacheKey(ChatModel.class, platform, apiKey, url); | 54 | String cacheKey = buildClientCacheKey(ChatModel.class, platform, apiKey, url); |
| 55 | return Singleton.get(cacheKey, (Func0<ChatModel>) () -> { | 55 | return Singleton.get(cacheKey, (Func0<ChatModel>) () -> { |
| 56 | //noinspection EnhancedSwitchMigration | 56 | //noinspection EnhancedSwitchMigration |
yudao-module-ai/yudao-spring-boot-starter-ai/src/test/java/cn/iocoder/yudao/framework/ai/chat/OpenAIChatModelTests.java
0 → 100644
| 1 | +package cn.iocoder.yudao.framework.ai.chat; | ||
| 2 | + | ||
| 3 | +import cn.iocoder.yudao.framework.ai.core.model.xinghuo.XingHuoChatClient; | ||
| 4 | +import org.junit.jupiter.api.Disabled; | ||
| 5 | +import org.junit.jupiter.api.Test; | ||
| 6 | +import org.springframework.ai.chat.messages.Message; | ||
| 7 | +import org.springframework.ai.chat.messages.SystemMessage; | ||
| 8 | +import org.springframework.ai.chat.messages.UserMessage; | ||
| 9 | +import org.springframework.ai.chat.model.ChatResponse; | ||
| 10 | +import org.springframework.ai.chat.prompt.Prompt; | ||
| 11 | +import org.springframework.ai.openai.OpenAiChatModel; | ||
| 12 | +import org.springframework.ai.openai.OpenAiChatOptions; | ||
| 13 | +import org.springframework.ai.openai.api.OpenAiApi; | ||
| 14 | +import reactor.core.publisher.Flux; | ||
| 15 | + | ||
| 16 | +import java.util.ArrayList; | ||
| 17 | +import java.util.List; | ||
| 18 | + | ||
| 19 | +/** | ||
| 20 | + * {@link XingHuoChatClient} 集成测试 | ||
| 21 | + * | ||
| 22 | + * @author 芋道源码 | ||
| 23 | + */ | ||
| 24 | +public class OpenAIChatModelTests { | ||
| 25 | + | ||
| 26 | + private final OpenAiApi openAiApi = new OpenAiApi( | ||
| 27 | + "https://api.holdai.top", | ||
| 28 | + "sk-dZEPiVaNcT3FHhef51996bAa0bC74806BeAb620dA5Da10Bf"); | ||
| 29 | + private final OpenAiChatModel chatModel = new OpenAiChatModel(openAiApi, | ||
| 30 | + OpenAiChatOptions.builder().withModel(OpenAiApi.ChatModel.GPT_4_O).build()); | ||
| 31 | + | ||
| 32 | + @Test | ||
| 33 | + @Disabled | ||
| 34 | + public void testCall() { | ||
| 35 | + // 准备参数 | ||
| 36 | + List<Message> messages = new ArrayList<>(); | ||
| 37 | + messages.add(new SystemMessage("你是一个优质的文言文作者,用文言文描述着各城市的人文风景。")); | ||
| 38 | + messages.add(new UserMessage("1 + 1 = ?")); | ||
| 39 | + | ||
| 40 | + // 调用 | ||
| 41 | + ChatResponse response = chatModel.call(new Prompt(messages)); | ||
| 42 | + // 打印结果 | ||
| 43 | + System.out.println(response); | ||
| 44 | + System.out.println(response.getResult().getOutput()); | ||
| 45 | + } | ||
| 46 | + | ||
| 47 | + @Test | ||
| 48 | + @Disabled | ||
| 49 | + public void testStream() { | ||
| 50 | + // 准备参数 | ||
| 51 | + List<Message> messages = new ArrayList<>(); | ||
| 52 | + messages.add(new SystemMessage("你是一个优质的文言文作者,用文言文描述着各城市的人文风景。")); | ||
| 53 | + messages.add(new UserMessage("1 + 1 = ?")); | ||
| 54 | + | ||
| 55 | + // 调用 | ||
| 56 | + Flux<ChatResponse> flux = chatModel.stream(new Prompt(messages)); | ||
| 57 | + // 打印结果 | ||
| 58 | + flux.doOnNext(response -> { | ||
| 59 | +// System.out.println(response); | ||
| 60 | + System.out.println(response.getResult().getOutput()); | ||
| 61 | + }).then().block(); | ||
| 62 | + } | ||
| 63 | + | ||
| 64 | +} |
yudao-module-ai/yudao-spring-boot-starter-ai/src/test/java/cn/iocoder/yudao/framework/ai/image/OpenAiImageClientTests.java deleted
| 1 | -package cn.iocoder.yudao.framework.ai.image; | ||
| 2 | - | ||
| 3 | -import org.junit.jupiter.api.BeforeEach; | ||
| 4 | -import org.junit.jupiter.api.Test; | ||
| 5 | -import org.springframework.ai.image.ImagePrompt; | ||
| 6 | -import org.springframework.ai.image.ImageResponse; | ||
| 7 | -import org.springframework.ai.openai.OpenAiImageModel; | ||
| 8 | -import org.springframework.ai.openai.api.OpenAiImageApi; | ||
| 9 | - | ||
| 10 | -import javax.imageio.ImageIO; | ||
| 11 | -import javax.swing.*; | ||
| 12 | -import java.awt.image.BufferedImage; | ||
| 13 | -import java.io.ByteArrayInputStream; | ||
| 14 | -import java.io.IOException; | ||
| 15 | -import java.util.Base64; | ||
| 16 | -import java.util.Scanner; | ||
| 17 | - | ||
| 18 | -// TODO 芋艿:整理单测 | ||
| 19 | -/** | ||
| 20 | - * author: fansili | ||
| 21 | - * time: 2024/3/17 10:40 | ||
| 22 | - */ | ||
| 23 | -public class OpenAiImageClientTests { | ||
| 24 | - | ||
| 25 | - | ||
| 26 | - private OpenAiImageModel openAiImageClient; | ||
| 27 | - | ||
| 28 | - @BeforeEach | ||
| 29 | - public void setup() { | ||
| 30 | - // 初始化 openAiImageClient | ||
| 31 | - this.openAiImageClient = new OpenAiImageModel( | ||
| 32 | - new OpenAiImageApi("") | ||
| 33 | -// new OpenAiImageOptions().setResponseFormat(OpenAiImageOptions.ResponseFormatEnum.URL.getValue()) TODO 芋艿:临时处理 | ||
| 34 | - ); | ||
| 35 | - } | ||
| 36 | - | ||
| 37 | - @Test | ||
| 38 | - public void callTest() { | ||
| 39 | - ImageResponse call = openAiImageClient.call(new ImagePrompt("中国长城!")); | ||
| 40 | - System.err.println("url: " + call.getResult().getOutput().getUrl()); | ||
| 41 | - System.err.println("base64: " + call.getResult().getOutput().getB64Json()); | ||
| 42 | - | ||
| 43 | - String base64String = call.getResult().getOutput().getB64Json(); | ||
| 44 | - ImageIcon imageIcon = new ImageIcon(decodeBase64ToImage(base64String)); | ||
| 45 | - JLabel label = new JLabel(imageIcon); | ||
| 46 | - | ||
| 47 | - JFrame frame = new JFrame("Base64 Image Display"); | ||
| 48 | - frame.getContentPane().add(label); | ||
| 49 | - frame.pack(); | ||
| 50 | - frame.setVisible(true); | ||
| 51 | - | ||
| 52 | - // 阻止退出 | ||
| 53 | - Scanner scanner = new Scanner(System.in); | ||
| 54 | - scanner.nextLine(); | ||
| 55 | - } | ||
| 56 | - | ||
| 57 | - | ||
| 58 | - // 将Base64解码为BufferedImage | ||
| 59 | - private static BufferedImage decodeBase64ToImage(String base64String) { | ||
| 60 | - try { | ||
| 61 | - byte[] decodedBytes = Base64.getDecoder().decode(base64String); | ||
| 62 | - ByteArrayInputStream bis = new ByteArrayInputStream(decodedBytes); | ||
| 63 | - return ImageIO.read(bis); | ||
| 64 | - } catch (IOException e) { | ||
| 65 | - System.out.println("Error decoding the base64 image: " + e.getMessage()); | ||
| 66 | - return null; | ||
| 67 | - } | ||
| 68 | - } | ||
| 69 | - | ||
| 70 | -} |
yudao-module-ai/yudao-spring-boot-starter-ai/src/test/java/cn/iocoder/yudao/framework/ai/image/OpenAiImageModelTests.java
0 → 100644
| 1 | +package cn.iocoder.yudao.framework.ai.image; | ||
| 2 | + | ||
| 3 | +import org.junit.jupiter.api.Disabled; | ||
| 4 | +import org.junit.jupiter.api.Test; | ||
| 5 | +import org.springframework.ai.image.ImageOptions; | ||
| 6 | +import org.springframework.ai.image.ImagePrompt; | ||
| 7 | +import org.springframework.ai.image.ImageResponse; | ||
| 8 | +import org.springframework.ai.openai.OpenAiImageModel; | ||
| 9 | +import org.springframework.ai.openai.OpenAiImageOptions; | ||
| 10 | +import org.springframework.ai.openai.api.OpenAiImageApi; | ||
| 11 | +import org.springframework.web.client.RestClient; | ||
| 12 | + | ||
| 13 | +/** | ||
| 14 | + * {@link OpenAiImageModel} 集成测试类 | ||
| 15 | + * | ||
| 16 | + * @author fansili | ||
| 17 | + */ | ||
| 18 | +public class OpenAiImageModelTests { | ||
| 19 | + | ||
| 20 | + private final OpenAiImageApi imageApi = new OpenAiImageApi( | ||
| 21 | + "https://api.holdai.top", | ||
| 22 | + "sk-dZEPiVaNcT3FHhef51996bAa0bC74806BeAb620dA5Da10Bf", | ||
| 23 | + RestClient.builder()); | ||
| 24 | + private final OpenAiImageModel imageClient = new OpenAiImageModel(imageApi); | ||
| 25 | + | ||
| 26 | + @Test | ||
| 27 | + @Disabled | ||
| 28 | + public void testCall() { | ||
| 29 | + // 准备参数 | ||
| 30 | + ImageOptions options = OpenAiImageOptions.builder() | ||
| 31 | + .withModel(OpenAiImageApi.ImageModel.DALL_E_2.getValue()) // 这个模型比较便宜 | ||
| 32 | + .withHeight(256).withWidth(256) | ||
| 33 | + .build(); | ||
| 34 | + ImagePrompt prompt = new ImagePrompt("中国长城!", options); | ||
| 35 | + | ||
| 36 | + // 方法调用 | ||
| 37 | + ImageResponse response = imageClient.call(prompt); | ||
| 38 | + System.out.println(response); | ||
| 39 | + } | ||
| 40 | + | ||
| 41 | +} |