智谱文档:智谱AI开放平台
注意:springboot版本要在3.0以上,pom.xml要配置下载的源。
pml文件如下
建议使用下科学上网~~~
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 https://maven.apache.org/xsd/maven-4.0.0.xsd"><modelVersion>4.0.0</modelVersion><parent><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-parent</artifactId><version>3.3.4</version><relativePath/> <!-- lookup parent from repository --></parent><groupId>com.example</groupId><artifactId>ai-puzhi</artifactId><version>0.0.1-SNAPSHOT</version><name>ai-puzhi</name><description>ai-puzhi</description><url/><licenses><license/></licenses><developers><developer/></developers><scm><connection/><developerConnection/><tag/><url/></scm><properties><project.build.sourceEncoding>UTF-8</project.build.sourceEncoding><project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding><fastjson2.version>2.0.52</fastjson2.version><java.version>17</java.version><spring-ai.version>1.0.3</spring-ai.version><testcontainers.version>1.20.1</testcontainers.version></properties><dependencyManagement><dependencies><dependency><groupId>org.springframework.ai</groupId><artifactId>spring-ai-bom</artifactId><version>1.0.0-M1</version><type>pom</type><scope>import</scope></dependency></dependencies></dependencyManagement><dependencies><!-- For Lombok --><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId></dependency><!-- For Commons --><dependency><groupId>org.apache.commons</groupId><artifactId>commons-lang3</artifactId></dependency><!-- For Caffeine --><dependency><groupId>com.github.ben-manes.caffeine</groupId><artifactId>caffeine</artifactId></dependency><!-- For FastJson2 --><dependency><groupId>com.alibaba.fastjson2</groupId><artifactId>fastjson2</artifactId><version>${fastjson2.version}</version></dependency><dependency><groupId>io.springboot.ai</groupId><artifactId>spring-ai-zhipu-ai-spring-boot-starter</artifactId><version>${spring-ai.version}</version></dependency><dependency><groupId>cn.bigmodel.openapi</groupId><artifactId>oapi-java-sdk</artifactId><version>release-V4-2.0.2</version><scope>test</scope></dependency><!-- For Web Server --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId><exclusions><exclusion><artifactId>spring-boot-starter-tomcat</artifactId><groupId>org.springframework.boot</groupId></exclusion></exclusions></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-undertow</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId><scope>test</scope></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-devtools</artifactId><scope>test</scope></dependency></dependencies><!-- 配置下载地址--><!-- 设定远程主仓库,按设定顺序进行查找。 --><repositories><repository><id>spring-milestones</id><name>Spring Milestones</name><url>https://repo.spring.io/milestone</url><snapshots><enabled>false</enabled></snapshots></repository><repository><id>spring-snapshots</id><name>Spring Snapshots</name><url>https://repo.spring.io/snapshot</url><releases><enabled>false</enabled></releases></repository><repository><id>central</id><name>Maven Central</name><url>https://repo.maven.apache.org/maven2</url></repository></repositories><build><plugins><plugin><groupId>org.springframework.boot</groupId><artifactId>spring-boot-maven-plugin</artifactId><configuration><excludes><exclude><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId></exclude></excludes></configuration></plugin></plugins></build></project>
yml配置文件
spring:application:name: ai-puzhiai:zhipuai:api-key: 82770a63b944ae2789b679332cf32
# model: glm-4-plusmodel: codegeex-4retry:backoff:max-interval: 3000multiplier: 2initial-interval: 2000
server:port: 9090
获取key地址:智谱AI开放平台
主要代码
@RestController
@CrossOrigin
public class ChatController {private final ZhipuAiChatClient chatClient;@Autowiredpublic ChatController(ZhipuAiChatClient chatClient) {this.chatClient = chatClient;}@GetMapping(value = "/v1/generate", produces = "application/json")public Map generate(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {String call = chatClient.call(message);System.out.println(call);return Map.of("generation", call);}@GetMapping("/v1/prompt")public List<Generation> prompt(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {PromptTemplate promptTemplate = new PromptTemplate("Tell me a {adjective} joke about {topic}");Prompt prompt = promptTemplate.create(Map.of("adjective", "funny", "topic", "cats"));return chatClient.call(prompt).getResults();}@GetMapping("/v1/chat/completions")public Flux<ChatResponse> chatCompletions(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {Prompt prompt = new Prompt(new UserMessage(message));return chatClient.stream(prompt);}@GetMapping("/v1/chat/completionsTow")public SseEmitter chatCompletionsTow(@RequestParam(value = "message", defaultValue = "Tell me a joke") String message) {SseEmitter emitter = new SseEmitter();Prompt prompt = new Prompt(new UserMessage(message));// 订阅Flux并处理数据chatClient.stream(prompt).subscribe(data -> {try {emitter.send(data);} catch (IOException e) {emitter.completeWithError(e);}},emitter::completeWithError,emitter::complete);return emitter;}@PostMapping("/v1/chat/completionsPost")public Flux<ChatResponse> completionsPost(@RequestBody Message msg) {Prompt prompt = new Prompt(new UserMessage(msg.getMsg()));return chatClient.stream(prompt);}@PostMapping(value = "/completionsPost", produces = MediaType.TEXT_EVENT_STREAM_VALUE)public void completionsPost(@RequestBody Message msg, HttpServletResponse response) throws IOException {Prompt prompt = new Prompt(new UserMessage(msg.getMsg()));// 获取 SSE 的 flux 流Flux<ChatResponse> flux = chatClient.stream(prompt);// 设置必要的 SSE 头部response.setHeader("Cache-Control", "no-cache");response.setHeader("Connection", "keep-alive");response.setHeader("Content-Type", "text/event-stream");// 获取响应输出流PrintWriter writer = response.getWriter();flux.doOnNext(chatResponse -> {try {// 将 ChatResponse 转换为 SSE 格式并写入响应流Generation result = chatResponse.getResult();AssistantMessage output = result.getOutput();String content = output.getContent();System.out.println("content: " + content);writer.write("data: " + content + "\n\n");writer.flush();} catch (Exception e) {// 处理异常e.printStackTrace();}}).doOnError(throwable -> {try {// 在出现错误时关闭响应流writer.write("event: error\ndata: " + throwable.getMessage() + "\n\n");writer.flush();writer.close();} catch (Exception e) {// 处理异常e.printStackTrace();}}).doOnComplete(() -> {try {// 在流完成时关闭响应流writer.write("event: complete\ndata: Stream completed\n\n");writer.flush();writer.close();} catch (Exception e) {// 处理异常e.printStackTrace();}}).subscribe(); // 订阅以启动流}@PostMapping(value = "/completionsPostNew", produces = MediaType.TEXT_EVENT_STREAM_VALUE)public SseEmitter completionsPostNew(@RequestBody Message msg, HttpServletResponse response) {SseEmitter emitter = new SseEmitter();UserMessage userMessage = new UserMessage(msg.getMsg());SystemMessage systemMessage = new SystemMessage("你是一位智能编程助手,你叫CSBlogAi。你会为用户回答关于编程、代码、计算机方面的任何问题," +"并提供格式规范、可以执行、准确安全的代码,并在必要时提供详细的解释。" +"任务:请为输入代码提供格式规范的注释,包含多行注释和单行注释," +"请注意不要改动原始代码,只需要添加注释。 请用中文回答。");List<org.springframework.ai.chat.messages.Message> messages = List.of(userMessage, systemMessage);Prompt prompt = new Prompt(messages);// 设置响应头response.setContentType(MediaType.TEXT_EVENT_STREAM_VALUE);// 订阅Flux并处理数据chatClient.stream(prompt).subscribe(data -> {try {// 发送 JSON 格式的 SSE 事件emitter.send(data);} catch (IOException e) {emitter.completeWithError(e);}},emitter::completeWithError,emitter::complete);return emitter;}}
前端主要代码
javascript">//get使用
getChatCompletions() {// 关闭之前的SSE连接(如果存在)if (this.eventSource) {this.eventSource.close();}let msg = this.userInput.replace(/\s+/g, '')let url = `http://localhost:9090/v1/chat/completionsTow?message=${msg}`// // 创建一个新的EventSource连接this.eventSource = new EventSource(url);let user = this.$store.state.UserInfolet userObj = {user: {userName: user.nickname,avatar: user.avatar,content: this.userInput},chat: {avatar: "https://blog-chen.oss-cn-shanghai.aliyuncs.com/favicon.ico",aiName: "CsBlog-Ai",content: []}}this.chatResponses.push(userObj)this.userInput = ''; // 清空输入框// 监听消息事件this.eventSource.onmessage = event => {const chatResponse = JSON.parse(event.data);if (chatResponse.result.output.content.trim() != '') {// 获取最后有的数组let length = this.chatResponses.lengththis.chatResponses[length - 1].chat.content.push(chatResponse.result.output.content)// this.chatResponses.push(chatResponse.result.output.content);this.$nextTick(() => {prism.highlightAll();// 全局代码高亮// 滚动到底部this.observeContentChanges()});}};// 监听错误事件this.eventSource.onerror = error => {// 将chatResponses添加到localStorage中console.log("关闭eventSource");if (this.chatResponses.length != 0) {localStorage.setItem(user.id, JSON.stringify(this.chatResponses))}this.eventSource.close();};},
//post使用SendAi() {this.abortController = new AbortController();const signal = this.abortController.signal;console.log(signal);// 添加到数组中let user = this.$store.state.UserInfolet userObj = {user: {userName: user.nickname,avatar: user.avatar,content: this.userInput},chat: {avatar: "https://blog-c",aiName: "CsBlog-Ai",content: []}}this.chatResponses.push(userObj)let sendMsg = this.userInput.replace(/\s+/g, '')this.userInput = ''; // 清空输入框fetchEventSource('http://localhost:9090/completionsPostNew', {method: 'POST',headers: {'Content-Type': 'application/json','Cache-Control': 'no-cache','Connection': 'keep-alive'},body: JSON.stringify({ msg: sendMsg }),onmessage: (event) => {const chatResponse = JSON.parse(event.data);if (chatResponse.result.output.content.trim() != '') {// 获取最后有的数组let length = this.chatResponses.lengththis.chatResponses[length - 1].chat.content.push(chatResponse.result.output.content)this.$nextTick(() => {prism.highlightAll();// 全局代码高亮// 滚动到底部this.observeContentChanges()});}},onopen: async (response) => {if (response.ok && response.headers.get('content-type') === 'text/event-stream') {return; // 连接成功} else if (response.status >= 400 && response.status < 500 && response.status === 429) {this.abortController.abort();throw new Error('Client-side error');} else {this.abortController.abort();throw new Error('Retriable error');}},onerror: (event) => {if (event.target.readyState === EventSource.CLOSED) {console.error('Connection was closed by the server.');} else {console.error('Error occurred:', event);}},onclose: () => {if (this.chatResponses.length != 0) {localStorage.setItem(user.id, JSON.stringify(this.chatResponses))}console.log('Connection closed.');},signal: signal});}},beforeDestroy() {this.abortController.abort();},
需要源码的私信~~~