Spring AI 第二讲 之 Chat Model API 第十节MiniMax Chat

Spring AI 支持 MiniMax 的各种人工智能语言模型。您可以与 MiniMax 语言模型互动,并基于 MiniMax 模型创建多语言对话助手。

前提条件

要访问 MiniMax 语言模型,您需要创建一个 MiniMax API。

MiniMax 注册页面创建账户,并在 API Keys 页面生成令牌。Spring AI 项目定义了一个名为 spring.ai.minimax.api-key 的配置属性,您应将其设置为从 API Keys 页面获取的 API Key 的值。导出环境变量是设置该配置属性的一种方法:

export SPRING_AI_MINIMAX_API_KEY=<INSERT KEY HERE>

添加资源库和 BOM

Spring AI 工件发布在 Spring Milestone 和 Snapshot 资源库中。请参阅 "资源库 "部分,将这些资源库添加到您的构建系统中。

为了帮助进行依赖性管理,Spring AI 提供了一个 BOM(物料清单),以确保在整个项目中使用一致的 Spring AI 版本。请参阅 "依赖关系管理 "部分,将 Spring AI BOM 添加到构建系统中。

自动配置

Spring AI 为 MiniMax 聊天客户端提供 Spring Boot 自动配置功能。要启用它,请在项目的 Maven pom.xml 文件中添加以下依赖项:

<dependency>
    <groupId>org.springframework.ai</groupId>
    <artifactId>spring-ai-minimax-spring-boot-starter</artifactId>
</dependency>

或 Gradle build.gradle 构建文件。

dependencies {
    implementation 'org.springframework.ai:spring-ai-minimax-spring-boot-starter'
}

请参阅 "依赖关系管理 "部分,将 Spring AI BOM 添加到构建文件中。

聊天属性 

重试属性

spring.ai.retry 前缀是用于配置 MiniMax 聊天模型重试机制的属性前缀。

PropertyDescriptionDefault

spring.ai.retry.max-attempts

重试的最大次数。

10

spring.ai.retry.backoff.initial-interval

指数后退策略的初始睡眠时间。

2 sec.

spring.ai.retry.backoff.multiplier

回退间隔倍增器。

5

spring.ai.retry.backoff.max-interval

最大回退持续时间。

3 min.

spring.ai.retry.on-client-errors

如果为假,则抛出 NonTransientAiException 异常,并且不尝试重试 4xx 客户端错误代码

false

spring.ai.retry.exclude-on-http-codes

不应触发重试(例如抛出 NonTransientAiException)的 HTTP 状态代码列表。

empty

spring.ai.retry.on-http-codes

应触发重试(例如抛出 TransientAiException)的 HTTP 状态代码列表。

empty

 连接属性

spring.ai.minimax 前缀是用于连接 MiniMax 的属性前缀。

PropertyDescriptionDefault

spring.ai.minimax.base-url

要连接的 URL

api.minimax.chat

spring.ai.minimax.api-key

API Key

-

配置属性

spring.ai.minimax.chat 前缀是属性前缀,用于配置 MiniMax 的聊天模型实现。

PropertyDescriptionDefault

spring.ai.minimax.chat.enabled

启用 MiniMax 聊天模式。

true

spring.ai.minimax.chat.base-url

可选择覆盖 spring.ai.minimax.base-url 以提供特定的聊天 URL

api.minimax.chat

spring.ai.minimax.chat.api-key

可选重载 spring.ai.minimax.api-key,以提供特定于聊天的 api-key。

-

spring.ai.minimax.chat.options.model

这就是要使用的 MiniMax 聊天模式

abab5.5-chat (the abab5.5s-chatabab5.5-chat, and abab6-chat point to the latest model versions)

spring.ai.minimax.chat.options.maxTokens

聊天完成时要生成的最大标记数。输入词组和生成词组的总长度受模型上下文长度的限制。

-

spring.ai.minimax.chat.options.temperature

采样温度,用于控制生成的补间明显的创造性。取值越高,输出结果越随机,取值越低,结果越集中和确定。不建议针对同一个补全请求修改温度和 top_p,因为这两个设置之间的相互作用很难预测。

0.7

spring.ai.minimax.chat.options.topP

温度采样的另一种方法是核采样,即模型考虑概率质量为 top_p 的标记的结果。因此,0.1 意味着只考虑概率质量最高的 10%的标记。一般情况下,我们建议改变这一点或温度,但不能同时改变。

1.0

spring.ai.minimax.chat.options.n

为每条输入信息生成多少个聊天完成选项。请注意,您将根据所有选择生成的代币数量收费。默认值为 1,不能大于 5。具体来说,当温度非常小且接近 0 时,我们只能返回 1 个结果。如果此时 n 已设置且大于 1,服务将返回非法输入参数(invalid_request_error)。

1

spring.ai.minimax.chat.options.presencePenalty

介于 -2.0 和 2.0 之间的数值。正值会根据新标记是否出现在文本中对其进行惩罚,从而增加模型谈论新话题的可能性。

0.0f

spring.ai.minimax.chat.options.frequencyPenalty

介于 -2.0 和 2.0 之间的数值。正值会根据新标记在文本中的现有频率对其进行惩罚,从而降低模型逐字重复同一行的可能性。

0.0f

spring.ai.minimax.chat.options.stop

该模型将停止生成 stop 指定的字符,目前只支持格式为 ["stop_word1"] 的单个停止词。

-

 您可以为 ChatModel 实现覆盖常用的 spring.ai.minimax.base-url 和 spring.ai.minimax.api-key 属性。如果设置了 spring.ai.minimax.chat.base-url 和 spring.ai.minimax.chat.api-key 属性,它们将优先于通用属性。如果您想为不同的模型和不同的模型端点使用不同的 MiniMax 账户,这将非常有用。

所有以 spring.ai.minimax.chat.options 为前缀的属性都可以通过在提示调用中添加特定于请求的运行时选项在运行时重写。 

运行时选项

MiniMaxChatOptions.java 提供了模型配置,如使用的模型、温度、频率惩罚等。

启动时,可使用 MiniMaxChatModel(api, options) 构造函数或 spring.ai.minimax.chat.options.* 属性配置默认选项。

在运行时,您可以通过在提示调用中添加新的、针对特定请求的选项来覆盖默认选项。例如,覆盖特定请求的默认模型和温度:

ChatResponse response = chatModel.call(
    new Prompt(
        "Generate the names of 5 famous pirates.",
        MiniMaxChatOptions.builder()
            .withModel(MiniMaxApi.ChatModel.GLM_3_Turbo.getValue())
            .withTemperature(0.5f)
        .build()
    ));

除了特定于模型的 MiniMaxChatOptions外,您还可以使用通过 ChatOptionsBuilder#builder()创建的便携式 ChatOptions实例。

示例Controller

创建一个新的 Spring Boot 项目,并将 spring-ai-minimax-spring-boot-starter 添加到 pom(或 gradle)依赖项中。

在 src/main/resources 目录下添加 application.properties 文件,以启用和配置 MiniMax 聊天模型:

spring.ai.minimax.api-key=YOUR_API_KEY
spring.ai.minimax.chat.options.model=glm-3-turbo
spring.ai.minimax.chat.options.temperature=0.7

将 api-key 替换为您的 MiniMax 凭据。

这将创建一个 MiniMaxChatModel 实现,您可以将其注入到您的类中。下面是一个使用聊天模型生成文本的简单 @Controller 类的示例。

@RestController
public class ChatController {

    private final MiniMaxChatModel chatModel;

    @Autowired
    public ChatController(MiniMaxChatModel chatModel) {
        this.chatModel = chatModel;
    }

    @GetMapping("/ai/generate")
    public Map generate(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {
        return Map.of("generation", chatModel.call(message));
    }

    @GetMapping("/ai/generateStream")
	public Flux<ChatResponse> generateStream(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {
        var prompt = new Prompt(new UserMessage(message));
        return chatModel.stream(prompt);
    }
}

 手动配置

MiniMaxChatModel实现了 ChatModel 和 StreamingChatModel,并使用底层 MiniMaxApi 客户端连接 MiniMax 服务。

在项目的 Maven pom.xml 文件中添加 Spring-ai-minimax 依赖关系:

<dependency>
    <groupId>org.springframework.ai</groupId>
    <artifactId>spring-ai-minimax</artifactId>
</dependency>

或 Gradle build.gradle 构建文件。

dependencies {
    implementation 'org.springframework.ai:spring-ai-minimax'
}

请参阅 "依赖关系管理 "部分,将 Spring AI BOM 添加到构建文件中。

接下来,创建 MiniMaxChatModel 并将其用于文本生成:

 

var miniMaxApi = new MiniMaxApi(System.getenv("MINIMAX_API_KEY"));

var chatModel = new MiniMaxChatModel(miniMaxApi, MiniMaxChatOptions.builder()
                .withModel(MiniMaxApi.ChatModel.GLM_3_Turbo.getValue())
                .withTemperature(0.4f)
                .withMaxTokens(200)
                .build());

ChatResponse response = chatModel.call(
    new Prompt("Generate the names of 5 famous pirates."));

// Or with streaming responses
Flux<ChatResponse> streamResponse = chatModel.stream(
    new Prompt("Generate the names of 5 famous pirates."));

MiniMaxChatOptions 为聊天请求提供配置信息。MiniMaxChatOptions.Builder 是流畅的选项生成器。

底层 MiniMaxApi 客户端


MiniMaxApi 是 MiniMax API 的轻量级 Java 客户端。

以下是如何以编程方式使用该 API 的简单片段:

MiniMaxApi miniMaxApi =
    new MiniMaxApi(System.getenv("MINIMAX_API_KEY"));

ChatCompletionMessage chatCompletionMessage =
    new ChatCompletionMessage("Hello world", Role.USER);

// Sync request
ResponseEntity<ChatCompletion> response = miniMaxApi.chatCompletionEntity(
    new ChatCompletionRequest(List.of(chatCompletionMessage), MiniMaxApi.ChatModel.GLM_3_Turbo.getValue(), 0.7f, false));

// Streaming request
Flux<ChatCompletionChunk> streamResponse = miniMaxApi.chatCompletionStream(
        new ChatCompletionRequest(List.of(chatCompletionMessage), MiniMaxApi.ChatModel.GLM_3_Turbo.getValue(), 0.7f, true));

更多信息请参见 MiniMaxApi.java 的 JavaDoc。

MiniMaxApi 示例


MiniMaxApiIT.java 测试提供了一些如何使用轻量级库的通用示例。

MiniMaxApiToolFunctionCallIT.java 测试展示了如何使用底层 API 调用工具函数。


功能调用

您可以向 MiniMaxChatModel 注册自定义 Java 函数,并让 MiniMax 模型智能地选择输出包含参数的 JSON 对象,以调用一个或多个已注册函数。这样,您就可以将 LLM 功能与外部工具和 API 相连接。MiniMax 模型经过训练,能够检测函数何时应被调用,并使用符合函数签名的 JSON 做出响应。

MiniMax API 不会直接调用函数;相反,模型会生成 JSON,您可以用它在代码中调用函数,并将结果返回给模型以完成对话。

Spring AI 提供了灵活、用户友好的注册和调用自定义函数的方法。一般来说,自定义函数需要提供函数名称、描述和函数调用签名(作为 JSON 模式),以便让模型知道函数期望使用哪些参数。描述有助于模型了解何时调用该函数。

作为开发人员,您需要实现一个函数,接收人工智能模型发送的函数调用参数,并将结果反馈给模型。您的函数可以反过来调用其他第三方服务来提供结果。

Spring AI 可以轻松实现这一点,只需定义一个 @Bean 定义,返回一个 java.util.Function 并在调用 ChatModel 时将 bean 名称作为一个选项即可。

在引擎盖下,Spring 会用适当的适配器代码封装您的 POJO(函数),从而实现与 AI 模型的交互,使您无需编写繁琐的模板代码。底层基础架构的基础是 FunctionCallback.java 接口和配套的 FunctionCallbackWrapper.java 实用程序类,用于简化 Java 回调函数的实现和注册。

工作原理

假设我们想让人工智能模型回应它所不具备的信息,例如某个地点的当前温度。

我们可以向人工智能模型提供有关我们自身功能的元数据,让它在处理您的提示时可以用来检索这些信息。

例如,如果在处理提示时,人工智能模型确定它需要有关给定地点温度的额外信息,它就会启动服务器端生成的请求/响应交互。人工智能模型会调用客户端函数。人工智能模型以 JSON 格式提供方法调用详情,客户端负责执行该函数并返回响应。

模型与客户端的交互如 [spring-ai-function-calling-flow] 图所示。

Spring AI 极大地简化了为支持函数调用而编写的代码。它为你提供了函数调用对话的中介。您只需以 @Bean 的形式提供函数定义,然后在提示选项中提供函数的 Bean 名称即可。您还可以在提示中引用多个函数 Bean 名称。

快速入门

让我们创建一个聊天机器人,通过调用我们自己的函数来回答问题。为了支持聊天机器人的回答,我们将注册自己的函数,该函数接收一个地点并返回该地点的当前天气。

当需要回答诸如 "波士顿的天气如何?"这样的问题时,人工智能模型将调用客户端,提供位置值作为参数传递给函数。这种类似 RPC 的数据以 JSON 格式传递。

我们的函数会调用一些基于 SaaS 的天气服务 API,并将天气响应返回给模型,以完成对话。在本示例中,我们将使用一个名为 MockWeatherService 的简单实现,它对不同地点的温度进行了硬编码。

下面的 MockWeatherService.java 表示天气服务 API:

public class MockWeatherService implements Function<Request, Response> {

	public enum Unit { C, F }
	public record Request(String location, Unit unit) {}
	public record Response(double temp, Unit unit) {}

	public Response apply(Request request) {
		return new Response(30.0, Unit.C);
	}
}

将函数注册为 Bean

有了 MiniMaxChatModel Auto-Configuration,您就有多种方法在 Spring 上下文中将自定义函数注册为 Bean。

我们首先介绍对 POJO 最友好的选项。

普通 Java 函数

在这种方法中,您可以在应用程序上下文中定义 @Beans,就像定义任何其他 Spring 托管对象一样。

在内部,Spring AI ChatModel 将创建一个 FunctionCallbackWrapper 封装器实例,该封装器将添加通过 AI 模型调用该函数的逻辑。@Bean 的名称将作为 ChatOption 传递。

@Configuration
static class Config {

	@Bean
	@Description("Get the weather in location") // function description
	public Function<MockWeatherService.Request, MockWeatherService.Response> weatherFunction1() {
		return new MockWeatherService();
	}
	...
}

@Description 注解是可选的,它提供了一个函数描述 (2),帮助模型理解何时调用函数。这是一个需要设置的重要属性,可帮助人工智能模型确定要调用的客户端函数。

另一种提供函数说明的方法是在 MockWeatherService.Request 上使用 @JacksonDescription 注解来提供函数说明:

@Configuration
static class Config {

	@Bean
	public Function<Request, Response> currentWeather3() { // (1) bean name as function name.
		return new MockWeatherService();
	}
	...
}

@JsonClassDescription("Get the weather in location") // (2) function description
public record Request(String location, Unit unit) {}

最佳做法是在请求对象中注释信息,使该函数的生成 JSON 模式尽可能具有描述性,以帮助人工智能模型选择要调用的正确函数。

FunctionCallbackWithPlainFunctionBeanIT.java 演示了这种方法。

函数回调包装器

另一种注册函数的方法是创建 FunctionCallbackWrapper 封装器,如下所示:

@Configuration
static class Config {

	@Bean
	public FunctionCallback weatherFunctionInfo() {

		return new FunctionCallbackWrapper<>("CurrentWeather", // (1) function name
				"Get the weather in location", // (2) function description
				(response) -> "" + response.temp() + response.unit(), // (3) Response Converter
				new MockWeatherService()); // function code
	}
	...
}

它封装了第三方 MockWeatherService 函数,并将其注册为 MiniMaxChatModel 的 CurrentWeather 函数。它还提供了一个说明 (2) 和一个可选的响应转换器 (3),用于将响应转换为模型所期望的文本。

默认情况下,响应转换器对响应对象进行 JSON 序列化。

FunctionCallbackWrapper 会根据 MockWeatherService.Request 类在内部解析函数调用签名。

在聊天选项中指定函数

要让模型知道并调用您的 CurrentWeather 函数,您需要在提示请求中启用该函数:

MiniMaxChatModel chatModel = ...

UserMessage userMessage = new UserMessage("What's the weather like in San Francisco, Tokyo, and Paris?");

ChatResponse response = chatModel.call(new Prompt(List.of(userMessage),
		MiniMaxChatOptions.builder().withFunction("CurrentWeather").build())); // (1) Enable the function

logger.info("Response: {}", response);

上述用户问题将触发对 CurrentWeather 函数的 3 次调用(每个城市一次),最终响应将类似于下面这样:

以下是所请求城市的当前天气情况:
- 加利福尼亚州旧金山: 30.0°C
- 日本东京: 10.0°C
- 法国巴黎: 15.0°C

FunctionCallbackWrapperIT.java 测试演示了这种方法。

使用 Prompt 选项注册/调用函数

除了自动配置外,您还可以通过 Prompt 请求动态注册回调函数:

 

MiniMaxChatModel chatModel = ...

UserMessage userMessage = new UserMessage("What's the weather like in San Francisco, Tokyo, and Paris?");

var promptOptions = MiniMaxChatOptions.builder()
	.withFunctionCallbacks(List.of(new FunctionCallbackWrapper<>(
		"CurrentWeather", // name
		"Get the weather in location", // function description
		new MockWeatherService()))) // function code
	.build();

ChatResponse response = chatModel.call(new Prompt(List.of(userMessage), promptOptions));

在该请求的持续时间内,提示中注册的功能默认为启用。

这种方法可以根据用户的输入动态地选择要调用的不同函数。

FunctionCallbackInPromptIT.java 集成测试提供了一个完整示例,说明如何在 MiniMaxChatModel 中注册函数并在提示请求中使用该函数。

  • 7
    点赞
  • 26
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值