DeepSeek 对接springboot 和 vue,聊天界面

操作步骤:

1.安装部署ollama

2.安装deepseek

3.vue代码

4.springboot Java代码,sse接口流式传输

成果展示:

DeepSeek 对接springboot 和 vue,聊天界面_第1张图片

1.java代码:

package com.qeoten.sms.voluntarilyReport.controller;

import com.google.gson.JsonArray;
import com.google.gson.JsonObject;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import okhttp3.RequestBody;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.*;


import com.alibaba.fastjson.JSONObject;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import okhttp3.*;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpEntity;
import org.springframework.http.HttpHeaders;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.client.RestTemplate;
import org.springframework.web.servlet.mvc.method.annotation.SseEmitter;

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import javax.servlet.http.HttpServletResponse;

@RestController
@RequestMapping("/deepseek")
@Slf4j
@RequiredArgsConstructor
@CrossOrigin(origins = "*")
public class TestController {


    private final String API_URL = "http://127.0.0.1:11434/api/chat";

    @GetMapping(value = "/sseChat", produces = "text/event-stream;charset=UTF-8")
    public SseEmitter chat(@RequestParam String message, HttpServletResponse response) {
        SseEmitter emitter = new SseEmitter(60_000L);
        response.setHeader("Cache-Control", "no-cache");
        response.setHeader("Connection", "keep-alive");
        response.setContentType("text/event-stream;charset=UTF-8");

        Executors.newSingleThreadExecutor().submit(() -> {
            try (CloseableHttpClient client = HttpClients.createDefault()) {
                HttpPost post = new HttpPost(API_URL);
                post.setHeader("Content-Type", "application/json");
                post.setHeader("Accept", "text/event-stream");
                String jsonBody = String.format(
                        "{\"messages\":[{\"role\":\"user\",\"content\":\"%s\"}]" +
                                ",\"model\":\"deepseek-r1:1.5b\"" +
                                ",\"stream\":true}",
                        message
                );
                post.setEntity(new StringEntity(jsonBody));

                try (CloseableHttpResponse apiResponse = client.execute(post);
                     BufferedReader reader = new BufferedReader(
                             new InputStreamReader(apiResponse.getEntity().getContent()))) {
                    String line;
                    while ((line = reader.readLine()) != null) {
                        // 按SSE格式包装数据:{content}\n\n
                        System.out.println("line: " + line);
                        String sseFormatted = "" + line + "\n\n";
                        emitter.send(SseEmitter.event().data(sseFormatted,
                                MediaType.parseMediaType("text/plain;charset=UTF-8"))); // 指定媒体类型和编码
//                        emitter.send(SseEmitter.event().data(sseFormatted, MediaType.TEXT_PLAIN));
                    }
                    emitter.complete();
                }
            } catch (Exception e) {
                emitter.completeWithError(e);
            }
        });
        return emitter;
    }


}

2.vue代码: 






 3.本地部署ollama

   解压ollama压缩包至某个目录

    sudo tar -xzf ollama-linux-arm64.tgz -C /home/ollama

4.将ollama作为service(.service文件)

   指定ollama /bin目录

[Unit]
Description=Ollama Service
After=network-online.target
 
[Service]
ExecStart=/home/ollama/bin/ollama serve
User=root
Group=root
Restart=always
RestartSec=3
Environment="OLLAMA_HOST=0.0.0.0"
Environment="OLLAMA_ORIGINS=*"
 
[Install]
WantedBy=default.target

     将ollama设定为service服务,开机自启动,重启ollama

 4.安装deepseek

  sudo systemctl daemon-reload
  sudo systemctl enable ollama
  sudo systemctl start ollama

  查看状态就是  status  停服务就是 stop

结束!!

你可能感兴趣的:(spring,boot,vue.js,后端,AI编程)