跳到主要内容
极客日志极客日志面向AI+效率的开发者社区
首页博客GitHub 精选镜像工具UI配色美学隐私政策关于联系
搜索内容 / 工具 / 仓库 / 镜像...⌘K搜索
注册
博客列表
JavaAIjava

基于 DashScope Java SDK 实现通义千问多轮对话与流式输出

综述由AI生成如何使用阿里云 DashScope Java SDK 集成通义千问模型。步骤包括注册账号获取 API Key、在 Maven 项目中添加依赖。核心代码展示了如何构建多轮对话的消息列表以保留上下文,并利用流式调用接口实现实时文本输出。最终提供了一个控制台交互 Demo,具备输入用户指令、接收模型流式响应及打印 Token 用量的功能。

路由之心发布于 2026/3/28更新于 2026/5/2830 浏览

背景

在大模型的浪潮中,阿里云推出的通义千问(Qwen)以强大的中文理解能力和开放生态脱颖而出。如果你是一名 Java 开发者,希望快速体验 AI 问答、聊天、知识问答等功能,那么官方提供的 DashScope Java SDK 无疑是最便捷的入口。

本文将带你从零实现一个控制台版 AI 多轮对话 Demo,支持通义千问模型(Qwen)的流式输出,实现类似 ChatGPT 的实时回复体验。

准备工作

1. 注册与获取 API Key

  • 访问阿里云 DashScope 平台。
  • 登录后进入「控制台」 -> 「API Key 管理」,创建并复制你的 API Key。
  • 请妥善保管此 Key,不要上传到公共仓库。

2. 创建 Java 项目并引入依赖

如果你使用 Maven 构建项目,只需在 pom.xml 中添加以下依赖:

<dependency>
    <groupId>com.alibaba</groupId>
    <artifactId>dashscope-sdk-java</artifactId>
    <version>2.21.12</version>
    <!--如果有冲突请排除掉slf4j-simple-->
    <exclusions>
        <exclusion>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-simple</artifactId>
        </exclusion>
    </exclusions>
</dependency>

提示:版本号可到 DashScope SDK 官方仓库查看最新版本。

代码实现

接下来我们实现一个完整的控制台应用:

  • 支持用户多轮输入;
  • 每轮对话都带上下文记忆;
  • 采用通义千问的流式输出模式(边生成边显示)。
核心代码
public class GenerationDemo {
    // API 密钥
    private static final String API_KEY = "替换为你的 API 密钥即可";

    /**
     * 创建 GenerationParam 对象
     * @param messages 对话消息列表
     * @return GenerationParam 对象
     */
    public static GenerationParam createGenerationParam(List<Message> messages) {
        return GenerationParam.builder()
                .apiKey(API_KEY)
                .model("qwen-turbo") // 指定模型名称
                .messages(messages)
                .resultFormat(GenerationParam.ResultFormat.MESSAGE)
                .incrementalOutput(true) // 开启增量输出,流式返回
                .build();
    }

    /**
     * 使用对话消息发起流式生成调用
     * @param param 生成参数
     * @return 流式生成结果
     */
    public static Flowable<GenerationResult> callGenerationWithMessages(GenerationParam param) throws ApiException, NoApiKeyException, InputRequiredException {
        Generation gen = new Generation();
        return gen.streamCall(param); // 通过 streamCall 开启流式调用
    }

    /**
     * 创建消息对象的辅助方法
     * @param role 角色
     * @param content 消息内容
     * @return 消息对象
     */
    private static Message createMessage(Role role, String content) {
        return Message.builder().role(role.getValue()).content(content).build();
    }

    public static void main(String[] args) {
        try {
            List<Message> messages = new ArrayList<>();
            // 添加系统角色消息,设定助手身份
            messages.add(createMessage(Role.SYSTEM, "你是一个非常热心的助手"));

            // 进行 2 轮对话(演示)
            for (int i = 0; i < 2; i++) {
                Scanner scanner = new Scanner(System.in);
                System.out.print("请输入:");
                String userInput = scanner.nextLine();
                if ("exit".equalsIgnoreCase(userInput)) {
                    break;
                }
                // 添加用户消息
                messages.add(createMessage(Role.USER, userInput));

                // 创建生成参数
                GenerationParam param = createGenerationParam(messages);

                // 发起流式调用
                CountDownLatch latch = new CountDownLatch(1); // 用于拼接完整响应内容
                StringBuffer fullContent = new StringBuffer();

                Flowable<GenerationResult> resultFlowable = callGenerationWithMessages(param);
                System.out.print("模型输出:");
                resultFlowable
                        .subscribeOn(Schedulers.io()) // IO 线程执行请求
                        .observeOn(Schedulers.computation()) // 计算线程处理响应
                        .subscribe(result -> {
                            String content = result.getOutput().getChoices().get(0).getMessage().getContent();
                            String finishReason = result.getOutput().getChoices().get(0).getFinishReason();
                            System.out.print(content);
                            fullContent.append(content);

                            // 当 finishReason 不为 null 时,表示是最后一个 chunk,输出用量信息
                            if (finishReason != null && !"null".equals(finishReason)) {
                                System.out.println("\n--- 请求用量 ---");
                                System.out.println("输入 Tokens:" + result.getUsage().getInputTokens());
                                System.out.println("输出 Tokens:" + result.getUsage().getOutputTokens());
                                System.out.print("总 Tokens:" + result.getUsage().getTotalTokens());
                            }
                            System.out.flush(); // 立即刷新输出
                        }, 
                        // onError: 处理错误
                        error -> {
                            System.err.println("\n请求失败:" + error.getMessage());
                            latch.countDown();
                        }, 
                        // onComplete: 完成回调
                        () -> {
                            System.out.println(); // 换行
                            // System.out.println("完整响应:" + fullContent.toString());
                            latch.countDown();
                        });
                latch.await();
                messages.add(createMessage(Role.SYSTEM, fullContent.toString()));
            }
        } catch (ApiException | NoApiKeyException | InputRequiredException e) {
            e.printStackTrace();
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        }
        System.exit(0);
    }
}

原理说明

多轮对话的关键在于上下文记忆。每轮对话时,我们将之前的所有问答拼接为 prompt,再一起传给模型。

比如第 2 轮对话时:

用户:你好

模型:你好呀!很高兴见到你!😊 今天过得怎么样呀?有什么我可以帮你的吗?

用户:我之前问的啥

这样模型就能'记住'对话语境,实现自然的连续问答。

总结

通过本文,我们实现了一个基于 DashScope Java SDK 的通义千问流式问答 Demo,具有以下特性:

  • 支持多轮对话(上下文记忆)
  • 实时流式输出体验
  • 控制台简单交互

目录

  1. 背景
  2. 准备工作
  3. 1. 注册与获取 API Key
  4. 2. 创建 Java 项目并引入依赖
  5. 代码实现
  6. 核心代码
  7. 原理说明
  8. 总结
  • 💰 8折买阿里云服务器限时8折了解详情
  • Magick API 一键接入全球大模型注册送1000万token查看
  • 🤖 一键搭建Deepseek满血版了解详情
  • 一键打造专属AI 智能体了解详情
极客日志微信公众号二维码

微信扫一扫,关注极客日志

微信公众号「极客日志V2」,在微信中扫描左侧二维码关注。展示文案:极客日志V2 zeeklog

更多推荐文章

查看全部
  • 6 款网络安全模拟与可视化工具网站推荐
  • RMBG-2.0 接入 Stable Diffusion 工作流实现图像生成与抠图合成
  • 后端开发入门:HTML 基础与实战
  • GPU 云计算平台资源选型与大模型应用实践
  • Llama-3.2V-11B-cot 模型在 X 光片异常识别与医学诊断中的推理应用
  • 基于 Spring Boot 的在线拍卖系统设计与实现
  • C++/Qt 智能指针核心分类、原理与实战避坑
  • 国内升级 GitHub Copilot 专业版支付方案
  • Linux 匿名管道:从 pipe 调用到通信测试及原理剖析
  • Microi 吾码:开源低代码平台架构与实战指南
  • Spring Web 模块核心架构与 RESTful API 实战
  • C++ 智能指针详解:内存管理的自动化实践
  • MusicFreeDesktop 开源音乐播放器跨平台与插件架构解析
  • AI 原生重构低代码开发:从工具到智能体的范式变革
  • MIT 室内场景识别数据集详解及 YOLOv8 训练指南
  • HTTP 应用层协议详解:从请求响应到实战编程
  • 大语言模型核心概念:预训练、微调与上下文学习
  • 大模型智能体(Agent)架构与核心原理
  • 企业为何强调建立标准操作流程 SOP
  • 如何降低豆包生成论文的 AIGC 检测率?工具实测对比

相关免费在线工具

  • Keycode 信息

    查找任何按下的键的javascript键代码、代码、位置和修饰符。 在线工具,Keycode 信息在线工具,online

  • Escape 与 Native 编解码

    JavaScript 字符串转义/反转义;Java 风格 \uXXXX(Native2Ascii)编码与解码。 在线工具,Escape 与 Native 编解码在线工具,online

  • JavaScript / HTML 格式化

    使用 Prettier 在浏览器内格式化 JavaScript 或 HTML 片段。 在线工具,JavaScript / HTML 格式化在线工具,online

  • JavaScript 压缩与混淆

    Terser 压缩、变量名混淆,或 javascript-obfuscator 高强度混淆(体积会增大)。 在线工具,JavaScript 压缩与混淆在线工具,online

  • RSA密钥对生成器

    生成新的随机RSA私钥和公钥pem证书。 在线工具,RSA密钥对生成器在线工具,online

  • Mermaid 预览与可视化编辑

    基于 Mermaid.js 实时预览流程图、时序图等图表,支持源码编辑与即时渲染。 在线工具,Mermaid 预览与可视化编辑在线工具,online