work hard work smart

专注于AI+Java后端开发。 不断总结,举一反三。
  博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

Spring AI Alibaba DashScopeChatModel 实战

Posted on 2026-05-30 21:52  work hard work smart  阅读(430)  评论(0)    收藏  举报

摘要:本文详细介绍如何在 Spring Boot 项目中集成 Spring AI 和 Spring AI Alibaba,使用 DashScopeChatModel 调用通义千问等大模型,实现对话和流式输出功能。

一、什么是 DashScope?

DashScope(灵积模型服务)是阿里云推出的大模型服务平台,提供了通义千问(Qwen)、DeepSeek 等多种主流模型的 API 接口。Spring AI Alibaba 是阿里云基于 Spring AI 标准接口开发的阿里云模型实现。

核心优势

  • 模型丰富:支持通义千问、DeepSeek、Llama 等多种模型
  • 开箱即用:通过 Spring AI 标准接口,无需学习新的 API
  • 自动配置:Spring Boot 自动装配,配置简单
  • 流式支持:原生支持 SSE 流式输出

二、环境准备

1. 获取 API Key

  1. 访问 阿里云 DashScope 控制台
  2. 注册/登录账号
  3. 创建 API Key 并复制保存

2. 技术栈版本

组件 版本
Spring Boot 3.5.6
Spring AI 1.1.0
Spring AI Alibaba 1.1.0.0
Java 21+

三、项目集成步骤

步骤 1:添加 Maven 依赖

pom.xml 中添加 Spring AI Alibaba DashScope 依赖:

<properties>
    <spring.ai.alibaba.version>1.1.0.0</spring.ai.alibaba.version>
</properties>

<dependencies>
    <!-- Spring Boot Web -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>

    <!-- Spring AI Alibaba DashScope -->
    <dependency>
        <groupId>com.alibaba.cloud.ai</groupId>
        <artifactId>spring-ai-alibaba-starter-dashscope</artifactId>
        <version>${spring.ai.alibaba.version}</version>
    </dependency>
</dependencies>

依赖说明

  • spring-ai-alibaba-starter-dashscope:包含了 DashScope 的自动配置和客户端实现
  • 会自动引入 Spring AI 核心依赖,无需额外添加

步骤 2:配置 application.yml

application.yml 中配置 DashScope API Key:

spring:
  ai:
    dashscope:
      api-key: sk-your-api-key-here  # 替换为你的 API Key

可选配置

spring:
  ai:
    dashscope:
      api-key: sk-your-api-key-here
      chat:
        options:
          model: qwen-plus  # 默认模型
          temperature: 0.7  # 温度参数
          max-tokens: 2000  # 最大 token 数

步骤 3:注入 DashScopeChatModel

Spring Boot 会自动配置 DashScopeChatModel Bean,直接注入即可使用:

import com.alibaba.cloud.ai.dashscope.chat.DashScopeChatModel;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class ChatController {
    
    @Autowired
    private DashScopeChatModel dashScopeChatModel;
    
    // 使用示例...
}

四、DashScopeChatModel 使用方式

方式 1:简单字符串调用

最简单的调用方式,直接传入用户消息:

@RequestMapping("/call/simple")
public String simpleCall(String message) {
    return dashScopeChatModel.call(message);
}

测试

curl "http://localhost:8000/model/call/simple?message=你好,请介绍一下自己"

方式 2:多消息调用(System + User)

通过 SystemMessage 设置系统提示词,定义 AI 角色和行为:

@RequestMapping("/call/translator")
public String translateMessage(String message) {
    // 系统提示词:定义 AI 的角色
    SystemMessage systemMessage = new SystemMessage(
        "你是一个专业的翻译助手,请把用户的消息翻译成英文"
    );
    
    // 用户消息
    Message userMsg = new UserMessage(message);
    
    // 调用模型
    return dashScopeChatModel.call(systemMessage, userMsg);
}

测试

curl "http://localhost:8000/model/call/translator?message=今天天气真好"
# 输出:The weather is really nice today

方式 3:Prompt 高级调用

使用 Prompt.Builder 构建完整的对话请求,支持自定义模型参数:

@RequestMapping("/call/advanced")
public String advancedCall(String message) {
    // 1. 系统消息
    SystemMessage systemMessage = new SystemMessage("请如实回答我的问题,回答要简洁明了");
    
    // 2. 用户消息
    Message userMsg = new UserMessage(message);
    
    // 3. 自定义模型参数
    ChatOptions chatOptions = ChatOptions.builder()
        .model("deepseek-v3")  // 指定模型
        .temperature(0.8)       // 创造性参数
        .maxTokens(1000)        // 最大输出长度
        .build();
    
    // 4. 构建 Prompt
    Prompt prompt = new Prompt.Builder()
        .messages(systemMessage, userMsg)
        .chatOptions(chatOptions)
        .build();
    
    // 5. 调用并提取结果
    ChatResponse response = dashScopeChatModel.call(prompt);
    return response.getResult().getOutput().getText();
}

支持的模型列表

  • qwen-turbo:快速响应,适合简单对话
  • qwen-plus:均衡性能和成本
  • qwen-max:最强性能,适合复杂任务
  • deepseek-v3:DeepSeek 模型
  • deepseek-r1:DeepSeek 推理模型

方式 4:流式输出(Flux)

实时返回结果,适合长文本生成场景:

@RequestMapping("/stream/chat")
public Flux<String> streamChat(String message, HttpServletResponse response) {
    // 设置字符编码,防止中文乱码
    response.setCharacterEncoding("UTF-8");
    
    // 返回 Flux 流式数据
    return dashScopeChatModel.stream(message);
}

前端调用示例

// 使用 fetch 接收流式数据
const response = await fetch('/model/stream/chat?message=写一首关于春天的诗');
const reader = response.body.getReader();

while (true) {
    const { done, value } = await reader.read();
    if (done) break;
    const text = new TextDecoder().decode(value);
    console.log(text); // 逐字输出
}

五、完整 Controller 示例

package cn.hollis.llm.llmentor.controller;

import com.alibaba.cloud.ai.dashscope.chat.DashScopeChatModel;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.ai.chat.messages.Message;
import org.springframework.ai.chat.messages.SystemMessage;
import org.springframework.ai.chat.messages.UserMessage;
import org.springframework.ai.chat.prompt.ChatOptions;
import org.springframework.ai.chat.prompt.Prompt;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import reactor.core.publisher.Flux;

@RestController
@RequestMapping("/model")
public class DashScopeChatController {

    @Autowired
    private DashScopeChatModel dashScopeChatModel;

    /**
     * 简单字符串调用
     */
    @RequestMapping("/call/simple")
    public String simpleCall(String message) {
        return dashScopeChatModel.call(message);
    }

    /**
     * 带系统提示词的调用
     */
    @RequestMapping("/call/translator")
    public String translateCall(String message) {
        SystemMessage systemMessage = new SystemMessage(
            "你是一个专业的翻译助手,请把用户的消息翻译成英文"
        );
        Message userMsg = new UserMessage(message);
        return dashScopeChatModel.call(systemMessage, userMsg);
    }

    /**
     * 使用 Prompt 高级调用
     */
    @RequestMapping("/call/advanced")
    public String advancedCall(String message) {
        SystemMessage systemMessage = new SystemMessage("请如实回答我的问题");
        Message userMsg = new UserMessage(message);

        ChatOptions chatOptions = ChatOptions.builder()
            .model("qwen-plus")
            .temperature(0.7)
            .build();
            
        Prompt prompt = new Prompt.Builder()
            .messages(systemMessage, userMsg)
            .chatOptions(chatOptions)
            .build();
            
        return dashScopeChatModel.call(prompt).getResult().getOutput().getText();
    }

    /**
     * 流式输出
     */
    @RequestMapping("/stream/chat")
    public Flux<String> streamChat(String message, HttpServletResponse response) {
        response.setCharacterEncoding("UTF-8");
        return dashScopeChatModel.stream(message);
    }
}

六、常见问题

Q1:如何切换不同模型?

在调用时动态指定模型:

ChatOptions options = ChatOptions.builder()
    .model("qwen-max")  // 切换为 qwen-max
    .build();
    
Prompt prompt = new Prompt.Builder()
    .messages(new UserMessage("你好"))
    .chatOptions(options)
    .build();

或在配置文件中设置默认模型:

spring:
  ai:
    dashscope:
      chat:
        options:
          model: qwen-plus  # 默认模型

Q2:API Key 如何安全管理?

不要硬编码在代码中! 推荐使用以下方式:

  1. 环境变量
spring:
  ai:
    dashscope:
      api-key: ${DASHSCOPE_API_KEY}
  1. Maven 变量(推荐):
<properties>
    <dashscope.api.key>sk-your-key</dashscope.api.key>
</properties>
spring:
  ai:
    dashscope:
      api-key: @dashscope.api.key@

Q3:流式输出中文乱码怎么办?

在 Controller 中设置响应编码:

@RequestMapping("/stream/chat")
public Flux<String> streamChat(String message, HttpServletResponse response) {
    response.setCharacterEncoding("UTF-8");  // 关键!
    return dashScopeChatModel.stream(message);
}

Q4:如何获取更详细的响应信息?

ChatResponse response = dashScopeChatModel.call(prompt);

// 获取完整响应对象
AssistantMessage assistantMsg = response.getResult().getOutput();
String content = assistantMsg.getText();  // 文本内容
Map<String, Object> metadata = assistantMsg.getMetadata();  // 元数据

七、最佳实践

1. 合理设置温度参数

ChatOptions options = ChatOptions.builder()
    .temperature(0.3)  // 低温度:适合代码生成、数据分析
    // .temperature(0.7)  // 中温度:适合日常对话
    // .temperature(0.9)  // 高温度:适合创意写作
    .build();

2. 控制输出长度

ChatOptions options = ChatOptions.builder()
    .maxTokens(500)  // 限制最大输出长度,节省成本
    .build();

3. 使用 SystemMessage 定义角色

SystemMessage system = new SystemMessage(
    """
    你是一个专业的 Java 开发工程师,擅长 Spring Boot 和微服务架构。
    请用简洁的代码示例回答问题,并添加详细注释。
    """
);

4. 错误处理

try {
    String result = dashScopeChatModel.call(message);
    return result;
} catch (Exception e) {
    log.error("调用 DashScope 失败", e);
    return "抱歉,服务暂时不可用,请稍后重试";
}

八、总结

通过 Spring AI Alibaba 集成 DashScope,我们可以:

  1. 快速集成:只需添加依赖和配置 API Key
  2. 标准接口:使用 Spring AI 统一的 ChatModel 接口
  3. 灵活调用:支持简单调用、Prompt 调用、流式输出
  4. 多模型支持:轻松切换通义千问、DeepSeek 等模型

这种方式既保持了 Spring AI 的标准性,又享受了阿里云模型的强大能力,是企业级 AI 应用开发的理想选择。


参考资源