langchain4j搭建失物招领系统(一)---初始化项目

一、项目初始化

首先,先搭建一个简单的springboot 项目,我们通过spring Initializr 初始化一个springboot 项目,jdk版本设置17,springboot 版本3.4.4,引入依赖如下:

xml 复制代码
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency>
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
  <groupId>org.springframework.boot</groupId>
  <artifactId>spring-boot-starter-webflux</artifactId>
</dependency>

<dependency>
  <groupId>com.h2database</groupId>
  <artifactId>h2</artifactId>
  <scope>runtime</scope>
</dependency>
<dependency>
  <groupId>org.projectlombok</groupId>
  <artifactId>lombok</artifactId>
  <optional>true</optional>
</dependency>

定义一个AiController,

java 复制代码
@RestController
@RequestMapping("/ai")
public class AiController {

    @GetMapping("/chat")
    public String chat() {
        return "Hello World";
    }

}

启动,访问http://127.0.0.1:8080/ai/chat

页面输出:

项目初始化结束。

二、引入langchain4j依赖

因为使用的是阿里的百炼平台,这边直接引入百炼的依赖,其他大模型类似。

xml 复制代码
<dependency>
    <groupId>dev.langchain4j</groupId>
    <artifactId>langchain4j-community-dashscope-spring-boot-starter</artifactId>
    <version>1.0.0-beta2</version>
</dependency>

三、langchain4j基本测试

1、文本输出

直接开始测试调用,选择deepseek-r1模型

java 复制代码
@Test
void test_deepseek_chat() {
    QwenChatModel chatModel = QwenChatModel.builder()
            .apiKey(System.getenv("ALI_AI_KEY"))
            .modelName("deepseek-r1")
            .build();

    System.out.println(chatModel.chat("你是谁?"));
}

返回

2、文本流式输出

java 复制代码
@Test
void test_deepseek_stream_chat() throws InterruptedException {
    QwenStreamingChatModel chatModel = QwenStreamingChatModel.builder()
            .apiKey(System.getenv("ALI_AI_KEY"))
            .modelName("deepseek-r1")
            .build();
    CountDownLatch countDownLatch = new CountDownLatch(1);
    chatModel.chat("你是谁?", new StreamingChatResponseHandler() {
        @Override
        public void onPartialResponse(String s) {
            System.out.println(s);
        }

        @Override
        public void onCompleteResponse(ChatResponse chatResponse) {
            System.out.println("完成。。。");
            countDownLatch.countDown();
        }

        @Override
        public void onError(Throwable throwable) {
            System.out.println("出错了。。。");
        }
    });
    countDownLatch.await();
}

返回

可以看到数据是流式输出的。

3、图片生成

使用万相大模型

java 复制代码
@Test
void test_image_generate(){
    WanxImageModel imageModel = WanxImageModel.builder()
            .apiKey(System.getenv("ALI_AI_KEY"))
            .modelName("wanx2.1-t2i-turbo")
            .build();
    Response<Image> generate = imageModel.generate("给我生成一张猫的图片");
    System.out.println(generate.content().url());
}

输出如下:

生成的图片

还不错。。。

4、图片理解

java 复制代码
@Test
void test_image_recognize(){
    QwenChatModel chatModel = QwenChatModel.builder()
            .apiKey(System.getenv("ALI_AI_KEY"))
            .modelName("qwen2.5-vl-32b-instruct")
            .build();
    UserMessage userMessage = UserMessage.from(
            TextContent.from("这个照片上面描述了什么?"),
            ImageContent.from("https://dashscope-result-wlcb-acdr-1.oss-cn-wulanchabu-acdr-1.aliyuncs.com/1d/76/20250325/b0fe3396/c09ada40-37f1-4748-9d32-82a373c79534151007983.png?Expires=1742978890&OSSAccessKeyId=LTAI5tKPD3TMqf2Lna1fASuh&Signature=gOV4MUh2glEKgk2PNXJZBOEENDI%3D")
    );
    ChatResponse chatResponse = chatModel.chat(userMessage);
    System.out.println(chatResponse.aiMessage().toString());
}

输出如下:

5、AI Services

langchain4j还有很多其他的组件,比如对话流记忆,RAG,function call(Tools)等等(这些我就不单独测试了),这些都能自由使用和组合,但在业务中使用,就会写很多类似的模板方法,langchain4j提供了更高层级的封装,就是AI Services。

需要先引入langchain4j的依赖

xml 复制代码
<dependency>
    <groupId>dev.langchain4j</groupId>
    <artifactId>langchain4j-spring-boot-starter</artifactId>
    <version>${langchain4j.version}</version>
</dependency>

使用如下:

定义一个AI Services接口

java 复制代码
interface Assistant {

    String chat(String userMessage);

}

定义Tools

java 复制代码
static class Tools {

    @Tool("获取用户所在的班级")
    public String getUserClass(
            @P("用户姓名") String userName) {
        System.out.println("用户姓名是:"+userName);
        return "三班";
    }

}

组合AI Services

java 复制代码
@Test
void test_ai_service(){
    ChatLanguageModel model = QwenChatModel.builder()
            .apiKey(System.getenv("ALI_AI_KEY"))
            .modelName("qwen2.5-7b-instruct-1m")
            .build();
    Assistant assistant = AiServices.builder(Assistant.class)
            .chatLanguageModel(model)
            // 对话记忆
            .chatMemory(new MessageWindowChatMemory.Builder()
                    .id("test")
                    .maxMessages(10)
                    .chatMemoryStore(new InMemoryChatMemoryStore())
                    .build())
            // function call
            .tools(new Tools())
            .build();
    String message = assistant.chat("你好,我叫张三,今年20岁。");
    System.out.println(message);
    message = assistant.chat("我是谁,我是几班的?");
    System.out.println(message);
}

返回如下:

基本测试使用就这些,后面就直接配合springboot 使用。

四、springboot中使用

定义一个配置类,配置对话流历史的存储方式

java 复制代码
@Configuration
public class AssistantConfig {

    @Bean
    public ChatMemoryProvider chatMemoryProvider(ChatMemoryStore chatMemoryStore){
        return id -> new MessageWindowChatMemory.Builder()
                .id(id)
                .chatMemoryStore(chatMemoryStore)
                .maxMessages(10)
                .build();
    }

    @Bean
    public ChatMemoryStore chatMemoryStore(){
        return new InMemoryChatMemoryStore();
    }

}

定义Tools,使用@Component依赖注入到spring容器中

java 复制代码
@Component
public class TestTools {

    @Tool("获取用户所在的班级")
    public String getUserClass(
            @P("用户姓名") String userName) {
        System.out.println("用户姓名是:"+userName);
        return "三班";
    }

    @Tool("获取今天的天气")
    public String getWeather(
            @P("地址") String address) {
        System.out.println("当前地址是:"+address);
        return "天气晴朗!";
    }

}

定义ai services,配置相应的使用参数

java 复制代码
@AiService(wiringMode = AiServiceWiringMode.EXPLICIT, chatModel = "qwenChatModel",
        streamingChatModel = "qwenStreamingChatModel", chatMemoryProvider = "chatMemoryProvider",
        tools = "testTools")
public interface AiAssistant {

    String chat(@MemoryId String id, @UserMessage String message);

    Flux<String> chatStream(@MemoryId String id, @UserMessage String message);

}

配置属性中配置qwen的配置

properties 复制代码
langchain4j.community.dashscope.chat-model.api-key=${ALI_AI_KEY}
langchain4j.community.dashscope.chat-model.model-name=qwen2.5-7b-instruct-1m
langchain4j.community.dashscope.streaming-chat-model.api-key=${ALI_AI_KEY}
langchain4j.community.dashscope.streaming-chat-model.model-name=qwen2.5-7b-instruct-1m

Flux输出还需要引入langchain4j依赖

xml 复制代码
<dependency>
    <groupId>dev.langchain4j</groupId>
    <artifactId>langchain4j-reactor</artifactId>
    <version>${langchain4j.version}</version>
</dependency>

定义web接口

java 复制代码
@RestController
@RequestMapping("/ai")
@RequiredArgsConstructor
public class AiController {

    private final AiAssistant aiAssistant;

    @GetMapping("/chat")
    public String chat(@RequestParam(value = "message", defaultValue = "Hello") String message,
                       @RequestParam(value = "userId", defaultValue = "111") String userId) {
        return aiAssistant.chat(userId,message);
    }

    @GetMapping(value = "/chat-stream",produces = MediaType.TEXT_PLAIN_VALUE+";charset=utf-8")
    public Flux<String> chatStream(@RequestParam(value = "message", defaultValue = "Hello") String message,
                             @RequestParam(value = "userId", defaultValue = "111") String userId) {
        return aiAssistant.chatStream(userId,message);
    }

}

页面上直接调用

历史对话&tools使用

换另一个用户,发现对话流式是新的

流式输出

over。。。

相关推荐
uhakadotcom5 分钟前
Meta Horizon OS 开发工具:打造更好的 MR/VR 体验
javascript·后端·面试
TianFuRuanJian13 分钟前
天洑参展2025全球产业科技创新与投资促进大会
人工智能·工业软件
程序员小刚18 分钟前
基于SpringBoot + Vue 的考勤管理系统
vue.js·spring boot·后端
你觉得20518 分钟前
山东大学:《DeepSeek应用与部署》|附PPT下载方法
大数据·人工智能·python·机器学习·ai·aigc·内容运营
一尘之中19 分钟前
不落因果与不昧因果
人工智能
本本的小橙子28 分钟前
第38周:文献阅读
人工智能·深度学习·tensorflow
Wnq1007233 分钟前
智慧城市智慧调度系统的架构与关键技术研究
人工智能·架构·智慧城市·big data
星辰大海的精灵34 分钟前
SpringAI轻松构建MCP Client-Server架构
人工智能·后端·架构
果冻人工智能35 分钟前
判断 Python 代码是不是 AI 写的几个简单方法
人工智能
qianmoq38 分钟前
轻松掌握Java多线程 - 第一章:多线程入门
java