Browse Source

Merge remote-tracking branch 'origin/master' into prod_test

lrj 3 weeks ago
parent
commit
7e0ee9eadd

+ 18 - 0
src/main/java/cn/cslg/pas/common/model/dify/OAParamDTO.java

@@ -16,4 +16,22 @@ public class OAParamDTO {
     private String claim;
     private String mainClaimReason;
     private Integer nearIndex;
+    /**
+     * 权要修改意见
+     */
+    private String claimChangeSuggestion;
+    /**
+     * 操作
+     */
+    private String operation;
+    /**
+     * 当前信息的id
+     */
+    private Integer messageId;
+    /**
+     * 调用dify接口是传入的query
+     */
+    private String query;
+
+
 }

+ 1 - 0
src/main/java/cn/cslg/pas/common/model/dify/confessionSession/UpdateConfessionSessionDTO.java

@@ -9,4 +9,5 @@ public class UpdateConfessionSessionDTO {
     private String conversationName;
     private String conversationId;
     private String content;
+    private String guid;
 }

+ 17 - 0
src/main/java/cn/cslg/pas/common/model/dify/oa/OaChatRecordAddDTO.java

@@ -0,0 +1,17 @@
+package cn.cslg.pas.common.model.dify.oa;
+
+import lombok.Data;
+
+@Data
+public class OaChatRecordAddDTO {
+    private Integer id;
+    private Integer confessionSessionId;
+
+    private String question;
+
+    private String operation;
+
+    private String answer;
+
+
+}

+ 12 - 0
src/main/java/cn/cslg/pas/common/model/dify/oa/OaChatRecordQueryDTO.java

@@ -0,0 +1,12 @@
+package cn.cslg.pas.common.model.dify.oa;
+
+import lombok.Data;
+
+@Data
+public class OaChatRecordQueryDTO {
+    private Integer id;
+    private Integer confessionSessionId;
+    private Long current;
+    private Long size;
+
+}

+ 8 - 0
src/main/java/cn/cslg/pas/common/model/dify/oa/OaGenerateResultDTO.java

@@ -0,0 +1,8 @@
+package cn.cslg.pas.common.model.dify.oa;
+
+import lombok.Data;
+
+@Data
+public class OaGenerateResultDTO {
+    private Integer confessionSessionId;
+}

+ 26 - 1
src/main/java/cn/cslg/pas/controller/outApi/DifyController.java

@@ -8,6 +8,9 @@ import cn.cslg.pas.common.model.dify.confessionSession.ConfessionSessionDetailVO
 import cn.cslg.pas.common.model.dify.generateDiscoveryResult.QueryDiscoveryPictureDTO;
 import cn.cslg.pas.common.model.dify.generateDiscoveryResult.UpdateDiscoveryPictureDTO;
 import cn.cslg.pas.common.model.dify.generatePatentResult.GeneratePatentResultDTO;
+import cn.cslg.pas.common.model.dify.oa.OaChatRecordAddDTO;
+import cn.cslg.pas.common.model.dify.oa.OaChatRecordQueryDTO;
+import cn.cslg.pas.common.model.dify.oa.OaGenerateResultDTO;
 import cn.cslg.pas.common.utils.CacheUtils;
 import cn.cslg.pas.common.utils.LoginUtils;
 import cn.cslg.pas.common.utils.Response;
@@ -48,7 +51,8 @@ public class DifyController {
     @Autowired
     private LoginUtils loginUtils;
     private final PatentResultService patentResultService;
-
+    private final OADifyService oaDifyService;
+    private final OaChatRecordService oaChatRecordService;
     @RequestMapping(value = "/chatMessage", method = RequestMethod.POST, produces = MediaType.TEXT_EVENT_STREAM_VALUE)
     @Operation(summary = "发送对话")
     public Flux<String> chatMessage(@RequestBody ChatMessageDTO chatMessageDTO) throws IOException {
@@ -138,5 +142,26 @@ public class DifyController {
  generateDiscoveryResultService.uploadDiscoveryPictures(updateDiscoveryPictureDTO);
         return Response.success("上传成功");
     }
+    @RequestMapping(value = "/sendOADefense2", method = RequestMethod.POST, produces = MediaType.TEXT_EVENT_STREAM_VALUE)
+    @Operation(summary = "OA答辩")
+    public Flux<String> sendOADefense2(@RequestBody OAParamDTO paramDTO) throws IOException {
+        return oaDifyService.successGetOAHttp1(paramDTO);
+    }
+    @RequestMapping(value = "/oaChatRecord/add", method = RequestMethod.POST)
+    @Operation(summary = "添加oa聊天记录")
+    public Response oaChatRecordAdd(@RequestBody OaChatRecordAddDTO oaChatRecordAddDTO) throws IOException {
+        return Response.success(oaChatRecordService.add(oaChatRecordAddDTO));
+    }
+    @RequestMapping(value = "/oaChatRecord/query", method = RequestMethod.POST)
+    @Operation(summary = "查询oa聊天记录")
+    public Response oaChatRecordQuery(@RequestBody OaChatRecordQueryDTO oaChatRecordQueryDTO) throws IOException {
+        return  Response.success(oaChatRecordService.query(oaChatRecordQueryDTO));
+    }
 
+    @RequestMapping(value = "/oa/generateResult", method = RequestMethod.POST)
+    @Operation(summary = "生成结果文档")
+    public Response oaGenerateResult(@RequestBody OaGenerateResultDTO oaGenerateResultDTO) throws IOException {
+         oaDifyService.generateOaResult(oaGenerateResultDTO);
+        return  Response.success("生成成功");
+    }
 }

+ 30 - 0
src/main/java/cn/cslg/pas/domain/dify/OaChatRecord.java

@@ -0,0 +1,30 @@
+package cn.cslg.pas.domain.dify;
+
+import cn.cslg.pas.domain.BaseEntity;
+import com.baomidou.mybatisplus.annotation.TableName;
+import lombok.Data;
+
+import java.io.Serializable;
+import java.util.Date;
+
+/**
+ * @TableName oa_chat_record
+ */
+@TableName(value ="oa_chat_record")
+@Data
+public class OaChatRecord extends BaseEntity<OaChatRecord> {
+    private Integer confessionSessionId;
+
+    private String question;
+
+    private String operation;
+
+    private String answer;
+
+    private String parameters;
+
+    private Date createTime;
+
+    private String createId;
+
+}

+ 18 - 0
src/main/java/cn/cslg/pas/mapper/dify/OaChatRecordMapper.java

@@ -0,0 +1,18 @@
+package cn.cslg.pas.mapper.dify;
+
+import cn.cslg.pas.domain.dify.OaChatRecord;
+import com.baomidou.mybatisplus.core.mapper.BaseMapper;
+
+/**
+* @author admin
+* @description 针对表【oa_chat_record】的数据库操作Mapper
+* @createDate 2025-11-14 10:52:42
+* @Entity cn.cslg.pas.domain.novelty.domain.OaChatRecord
+*/
+public interface OaChatRecordMapper extends BaseMapper<OaChatRecord> {
+
+}
+
+
+
+

+ 10 - 1
src/main/java/cn/cslg/pas/service/dify/AssoConfessionSessionFileService.java

@@ -1,5 +1,6 @@
 package cn.cslg.pas.service.dify;
 
+import cn.cslg.pas.domain.dify.AssoConfessionConversation;
 import cn.cslg.pas.domain.dify.AssoConfessionSessionFile;
 import cn.cslg.pas.mapper.dify.AssoConfessionSessionFileMapper;
 import cn.cslg.pas.service.common.FileManagerService;
@@ -74,7 +75,8 @@ public class AssoConfessionSessionFileService extends ServiceImpl<AssoConfession
         this.saveBatch(assoConfessionSessionFiles);
         return assoConfessionSessionFiles;
     }
-    public List<AssoConfessionSessionFile> addDiscoveryPicturesByGuid(List<String> guids , Integer confessionSessionId) {
+
+    public List<AssoConfessionSessionFile> addDiscoveryPicturesByGuid(List<String> guids, Integer confessionSessionId) {
         Integer type = 2;
         List<AssoConfessionSessionFile> assoConfessionSessionFiles = new ArrayList<>();
         if (guids == null || guids.size() == 0) {
@@ -90,4 +92,11 @@ public class AssoConfessionSessionFileService extends ServiceImpl<AssoConfession
         this.saveBatch(assoConfessionSessionFiles);
         return assoConfessionSessionFiles;
     }
+
+    public void removeByConversionSessionId(Integer conversionSessionId) {
+        LambdaQueryWrapper<AssoConfessionSessionFile> queryWrapper = new LambdaQueryWrapper<>();
+        queryWrapper.eq(AssoConfessionSessionFile::getConfessionSessionId, conversionSessionId);
+        queryWrapper.eq(AssoConfessionSessionFile::getType,1);
+        this.remove(queryWrapper);
+    }
 }

+ 28 - 1
src/main/java/cn/cslg/pas/service/dify/GenerateInstructionService.java

@@ -31,13 +31,16 @@ import okhttp3.RequestBody;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.beans.factory.annotation.Value;
 import org.springframework.stereotype.Service;
+import org.springframework.web.servlet.mvc.method.annotation.SseEmitter;
 import reactor.core.publisher.Flux;
 import reactor.core.publisher.FluxSink;
 
 import java.io.File;
 import java.io.IOException;
+import java.time.Duration;
 import java.util.*;
 import java.util.concurrent.TimeUnit;
+import java.util.concurrent.atomic.AtomicBoolean;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 import java.util.stream.Collectors;
@@ -163,7 +166,23 @@ public class GenerateInstructionService {
         }
         String mainClaim = mainClaimStr;
         String claimStrs = StringUtils.join(reMainPatentClaims, "\n");
-        return Flux.create(emitter -> {
+
+        AtomicBoolean businessCompleted = new AtomicBoolean(false);
+        Flux<String> heartbeatFlux = Flux.interval(Duration.ofSeconds(5))
+                .map(tick -> {
+                    // 每次发送心跳前检查业务状态
+                    if (businessCompleted.get()) {
+                        // 如果业务已完成,此消息理论上不会发出,因为流会被终止
+                        return ":heartbeat-final\n\n";
+                    }
+                    return "event: ping";
+                })
+                .takeUntil(item -> businessCompleted.get()) // 关键修改:当业务完成时,自动停止心跳流
+                .doFinally(signal -> {
+                    System.out.println("心跳流已停止,原因: " + signal);
+                });
+
+        Flux<String> businessFlux =    Flux.create(emitter -> {
             new Thread(() -> {
                 try {
 
@@ -215,10 +234,13 @@ public class GenerateInstructionService {
                 } catch (Exception e) {
                     e.printStackTrace();
                 } finally {
+                    businessCompleted.set(true);
                     emitter.complete();
                 }
             }).start();
         });
+
+        return Flux.merge(heartbeatFlux, businessFlux);
     }
 
     /**
@@ -287,11 +309,15 @@ public class GenerateInstructionService {
         } else {
             message = getFluxMessage(FIELD_TITLE, MESSAGE, generateTechnicalVO.getTitle());
         }
+        System.out.println("message:"+message);
         fluxSink.next(message);
+        System.out.println("message: 发送成功");
         String endMessage = getFluxMessage(FIELD_TITLE, END, "");
         fluxSink.next(endMessage);
+        System.out.println("message:"+endMessage);
         String startMessage2 = getFluxMessage(FIELD_TECHNICAL, START, "");
         fluxSink.next(startMessage2);
+        System.out.println("message:"+startMessage2);
         String message2 = "";
         if (ifError) {
             message2 = getFluxMessage(FIELD_TECHNICAL, ERROR, "生成技术领域异常");
@@ -299,6 +325,7 @@ public class GenerateInstructionService {
             message2 = getFluxMessage(FIELD_TECHNICAL, MESSAGE, generateTechnicalVO.getTechnical());
         }
         fluxSink.next(message2);
+        System.out.println("message:"+message2);
         String endMessage2 = getFluxMessage(FIELD_TECHNICAL, END, "");
         fluxSink.next(endMessage2);
 

+ 409 - 0
src/main/java/cn/cslg/pas/service/dify/OADifyService.java

@@ -0,0 +1,409 @@
+package cn.cslg.pas.service.dify;
+
+import cn.cslg.pas.common.model.dify.OAMessageDTO;
+import cn.cslg.pas.common.model.dify.OAParamDTO;
+import cn.cslg.pas.common.model.dify.oa.OaGenerateResultDTO;
+import cn.cslg.pas.common.utils.DateUtils;
+import cn.cslg.pas.common.utils.FileUtils;
+import cn.cslg.pas.common.utils.LoginUtils;
+import cn.cslg.pas.domain.business.ReportTemple;
+import cn.cslg.pas.domain.dify.AssoConfessionSessionFile;
+import cn.cslg.pas.domain.dify.ConfessionSession;
+import cn.cslg.pas.exception.ExceptionEnum;
+import cn.cslg.pas.exception.XiaoShiException;
+import cn.cslg.pas.mapper.dify.ConfessionSessionMapper;
+import cn.cslg.pas.service.business.ReportTempleService;
+import cn.cslg.pas.service.common.FileManagerService;
+import com.alibaba.fastjson.JSON;
+import com.alibaba.fastjson.JSONArray;
+import com.alibaba.fastjson.JSONObject;
+import com.deepoove.poi.XWPFTemplate;
+import com.deepoove.poi.config.Configure;
+import com.deepoove.poi.config.ConfigureBuilder;
+import com.google.gson.Gson;
+import com.google.gson.JsonArray;
+import lombok.RequiredArgsConstructor;
+import okhttp3.*;
+import org.apache.commons.lang3.ObjectUtils;
+import org.apache.commons.lang3.StringUtils;
+import org.ddr.poi.html.HtmlRenderPolicy;
+import org.springframework.beans.factory.annotation.Autowired;
+import org.springframework.beans.factory.annotation.Value;
+import org.springframework.http.HttpHeaders;
+import org.springframework.stereotype.Service;
+import org.springframework.transaction.annotation.Transactional;
+import org.springframework.util.CollectionUtils;
+import reactor.core.publisher.Flux;
+
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.IOException;
+import java.io.Reader;
+import java.nio.charset.StandardCharsets;
+import java.util.*;
+import java.util.concurrent.TimeUnit;
+
+@Service
+@RequiredArgsConstructor
+public class OADifyService {
+    @Value("${FileDownloadUrl}")
+    private String fileDownloadUrl;
+
+    private final LoginUtils loginUtils;
+    @Value("${DIFY.OAApiKey2}")
+    private String OAApiKey2;
+    @Value("${DIFY.url}")
+    private String url;
+    private final ConfessionSessionService confessionSessionService;
+    private final FileUtils fileUtils;
+    private final ReportTempleService templeService;
+    private final ConfessionSessionMapper confessionSessionMapper;
+    private final OaChatRecordService oaChatRecordService;
+    private final AssoConfessionSessionFileService assoConfessionSessionFileService;
+    private final FileManagerService fileManagerService;
+
+    public Flux<String> successGetOAHttp1(OAParamDTO vo) {
+        Integer confessionSessionId = vo.getConfessionSessionId();
+        String patentFileUrls = vo.getPatentFileUrls();
+        String appFileGuid = vo.getAppFileGuid();
+        String modifyFileGuid = vo.getModifyFileGuid();
+        String query = vo.getQuery();
+        String operate = vo.getOperation();
+        Integer messageId = vo.getMessageId();
+        ConfessionSession confessionSession = confessionSessionService.getById(confessionSessionId);
+        if (ObjectUtils.isEmpty(confessionSession)) {
+            throw new XiaoShiException(ExceptionEnum.BUSINESS_ERROR, "未查询到OA答辩记录");
+        }
+        String conversationId = confessionSession.getConversationId();
+        String sessionContent = confessionSession.getContent();
+        String conversationName = confessionSession.getConversationName();
+        String fileUrl = fileDownloadUrl + confessionSession.getGuid();
+        String userId = loginUtils.getId().toString();
+
+        OkHttpClient client = new OkHttpClient.Builder()
+                .connectTimeout(600, TimeUnit.SECONDS)
+                .writeTimeout(600, TimeUnit.SECONDS)
+                .readTimeout(600, TimeUnit.SECONDS)
+                .build();
+
+        Map<String, Object> map = new HashMap<>();
+        map.put("fileUrl", fileUrl);
+        map.put("patent_fileUrls", patentFileUrls);
+        map.put("app_file_guid", appFileGuid);
+        map.put("modify_file_guid", modifyFileGuid);
+        map.put("changeClaim", vo.getChangeClaim());
+        map.put("claim", vo.getClaim());
+        map.put("main_claim_reason", vo.getMainClaimReason());
+        map.put("near_index", vo.getNearIndex());
+        map.put("operation", operate);
+        map.put("patent_files", new ArrayList<>());
+        map.put("claimChangeSuggestion", vo.getClaimChangeSuggestion());
+
+        OAMessageDTO oaMessageDTO = new OAMessageDTO();
+        oaMessageDTO.setInputs(map);
+        oaMessageDTO.setResponseMode("streaming");
+        oaMessageDTO.setUser(userId);
+        oaMessageDTO.setQuery(query);
+        oaMessageDTO.setConversationId(conversationId);
+        oaMessageDTO.setFiles(new ArrayList<>());
+
+        String param = new Gson().toJson(oaMessageDTO);
+        RequestBody requestBody = RequestBody.create(MediaType.parse("application/json"), param);
+        Request request = new Request.Builder()
+                .url(url + "chat-messages")
+                .addHeader("Authorization", "Bearer " + OAApiKey2)
+                .addHeader(HttpHeaders.CONTENT_TYPE, "application/json")
+                .post(requestBody)
+                .build();
+
+
+        return Flux.create(emitter -> {
+            client.newCall(request).enqueue(new Callback() {
+
+                @Override
+                public void onFailure(Call call, IOException e) {
+                    emitter.error(e);
+                }
+
+                @Override
+                public void onResponse(Call call, Response response) throws IOException {
+
+                    if (!response.isSuccessful()) {
+                        emitter.error(new IOException("Unexpected code: " + response));
+                        return;
+                    }
+                    String json = "";
+                    try (Reader reader = response.body().charStream()) {
+                        BufferedReader bufferedReader = new BufferedReader(reader);
+                        String line;
+                        String prefixToRemove = "data: ";
+                        String runId = conversationId;
+                        StringBuilder stringBuilder = new StringBuilder("");
+                        while ((line = bufferedReader.readLine()) != null) {
+                            if (line.isEmpty()) {
+                                continue;
+                            }
+                            if (line.startsWith(prefixToRemove)) {
+                                line = line.substring(prefixToRemove.length());
+                            }
+                            try {
+                                JSONObject jsonObject = JSON.parseObject(line);
+                                String sessionConversationId = jsonObject.get("conversation_id").toString();
+                                String event = jsonObject.get("event").toString();
+                                if (StringUtils.isEmpty(runId)) {
+                                    if (StringUtils.isNotEmpty(sessionConversationId)) {
+                                        runId = sessionConversationId;
+                                        confessionSessionMapper.updateSingleField(confessionSessionId, "conversation_id", sessionConversationId);
+                                    }
+                                }
+                                if (event.equals("message")) {
+                                    String data = jsonObject.get("answer").toString();
+                                    if (data != null && operate.equals("6")) {
+                                        String formatData = data.trim();
+                                        if ((formatData.startsWith("{") && formatData.endsWith("}")) || (formatData.startsWith("[") && formatData.endsWith("]"))) {
+                                            json = data;
+                                            data = "";
+                                        }
+                                    }
+                                    stringBuilder.append(data);
+                                }
+                                //保存内容
+
+
+                            } catch (Exception e) {
+                            }
+                            emitter.next(line); // 将每行数据发送到 Flux
+                        }
+                        String reMessage = stringBuilder.toString();
+                        saveMessage(operate, reMessage, sessionContent, confessionSessionId, vo, json);
+                        oaChatRecordService.add(oaMessageDTO, messageId, reMessage);
+                    } catch (IOException e) {
+                        emitter.error(e);
+                    } finally {
+                        emitter.complete();
+                    }
+                }
+            });
+        });
+    }
+
+
+    /**
+     * 生成OA答辩文件
+     *
+     * @param map
+     * @param templateFilePath
+     * @param name
+     * @return
+     * @throws Exception
+     */
+    public String generateOADefenseFile(Map<String, Object> map, String templateFilePath, String name) throws Exception {
+        XWPFTemplate xwpfTemplate = this.getHtmlTemplate(map, templateFilePath);
+        String fileName = name + ".docx";
+        String directoryName = fileUtils.createDirectory();
+        String outPath = fileUtils.getSavePath(directoryName) + fileName;
+        File file = new File(outPath);
+        // 生成word保存在指定目录
+        xwpfTemplate.writeToFile(outPath);
+        xwpfTemplate.close();
+        List<String> ids = fileManagerService.uploadFileGetGuid2(Collections.singletonList(file));
+        if (CollectionUtils.isEmpty(ids)) {
+            throw new XiaoShiException("保存记录失败");
+        }
+        return ids.get(0);
+    }
+
+    private XWPFTemplate getHtmlTemplate(Map<String, Object> map, String filePath) {
+        XWPFTemplate template = null;
+        try {
+            HtmlRenderPolicy htmlRenderPolicy = new HtmlRenderPolicy();
+            ConfigureBuilder configureBuilder = Configure.builder().useSpringEL(false);
+            configureBuilder.bind("#this", htmlRenderPolicy);
+            Configure configure = configureBuilder.build();
+            template = XWPFTemplate.compile(filePath, configure).render(map);
+        } catch (Exception e) {
+            e.printStackTrace();
+            throw new XiaoShiException(ExceptionEnum.BUSINESS_ERROR, "未匹配到模版文件");
+        }
+        return template;
+    }
+
+    /**
+     * 对话完成后保存信息
+     */
+    public void saveMessage(String operateType, String reMessage, String sessionContent, Integer confessionSessionId, OAParamDTO oaParamDTO, String json) {
+        try {
+            JSONObject obj = null;
+            if (sessionContent == null) {
+                obj = new JSONObject();
+            } else {
+                obj = JSON.parseObject(sessionContent);
+            }
+
+            if (operateType.equals("1")) {
+                JSONObject dataObject = JSON.parseObject(reMessage);
+                String code = dataObject.get("code").toString();
+                if (StringUtils.equals(code, "203")) {
+                    Object data = dataObject.get("data");
+                    if (obj.get("query") == null) {
+                        obj.put("query", new JSONObject());
+                    }
+                    JSONObject jsonObject = (JSONObject) obj.get("query");
+                    jsonObject.put("relevant_file", data);
+
+                }
+            } else if (operateType.equals("2")) {
+                if (obj.get("query") == null) {
+                    obj.put("query", new JSONObject());
+                }
+                JSONObject jsonObject = (JSONObject) obj.get("query");
+                if (jsonObject.get("claimChange") == null) {
+                    jsonObject.put("claimChange", new JSONObject());
+                }
+                JSONObject jsonObject1 = (JSONObject) jsonObject.get("claimChange");
+                JSONObject dataObject = JSON.parseObject(reMessage);
+                jsonObject1.put("nearNo", dataObject.get("nearNo"));
+                jsonObject1.put("near_index", dataObject.get("nearIndex"));
+                jsonObject1.put("novelty_innovative", dataObject.get("novelty_innovative"));
+                jsonObject1.put("changeClaim", dataObject.get("claimChange"));
+                jsonObject1.put("claim", oaParamDTO.getClaim());
+                jsonObject1.put("claimChangeSuggestion", oaParamDTO.getClaimChangeSuggestion());
+            } else if (operateType.equals("3")) {
+                if (obj.get("query") == null) {
+                    obj.put("query", new JSONObject());
+                }
+                JSONObject jsonObject = (JSONObject) obj.get("query");
+                if (jsonObject.get("claimChange") == null) {
+                    jsonObject.put("claimChange", new JSONObject());
+                }
+                JSONObject jsonObject1 = (JSONObject) jsonObject.get("claimChange");
+                jsonObject1.put("claimChangeSuggestion", reMessage);
+            } else if (operateType.equals("4")) {
+                if (obj.get("query") == null) {
+                    obj.put("query", new JSONObject());
+                }
+                JSONObject jsonObject = (JSONObject) obj.get("query");
+                if (jsonObject.get("claimChange") == null) {
+                    jsonObject.put("claimChange", new JSONObject());
+                }
+                JSONObject jsonObject1 = (JSONObject) jsonObject.get("claimChange");
+                jsonObject1.put("claimChange", reMessage);
+            } else if (operateType.equals("5")) {
+                if (obj.get("query") == null) {
+                    obj.put("query", new JSONObject());
+                }
+                JSONObject jsonObject = (JSONObject) obj.get("query");
+                List<Object> jsonArray = JSONArray.parseArray(reMessage);
+                jsonObject.put("main_claim_reason", jsonArray);
+            } else if (operateType.equals("6")) {
+                JSONObject dataObject = JSON.parseObject(json);
+                obj.put("data", dataObject);
+            }
+            String reJson = JSONObject.toJSONString(obj);
+            confessionSessionMapper.updateSingleField(confessionSessionId, "content", reJson);
+        } catch (Exception e) {
+            e.printStackTrace();
+        }
+
+
+    }
+
+    @Transactional(rollbackFor = Exception.class)
+    public void generateOaResult(OaGenerateResultDTO oaGenerateResultDTO) {
+        Integer confessionSessionId = oaGenerateResultDTO.getConfessionSessionId();
+        ConfessionSession confessionSession = confessionSessionService.getById(confessionSessionId);
+        assoConfessionSessionFileService.removeByConversionSessionId(confessionSessionId);
+        this.generateDoc(confessionSession);
+        this.generateDoc2(confessionSession);
+
+    }
+
+    public void generateDoc(ConfessionSession confessionSession) {
+        String content = confessionSession.getContent();
+        Integer confessionSessionId = confessionSession.getId();
+        String conversationName = confessionSession.getConversationName();
+        JSONObject orgJsonObject = JSONObject.parseObject(content);
+        JSONObject dataJsonObject = orgJsonObject.getJSONObject("data");
+        JSONObject jsonObject = dataJsonObject.getJSONObject("data");
+        Map<String, Object> map = new HashMap<>();
+        String reason = jsonObject.getString("reason");
+        String num = jsonObject.getString("num");
+        String claimChange = jsonObject.getString("claim_change");
+        List<String> claimList = new ArrayList<>();
+        if (StringUtils.isNotEmpty(claimChange)) {
+            claimList = Arrays.asList(claimChange.split("\r?\n+"));
+        }
+        JSONArray jsonArray = jsonObject.getJSONArray("defense_opinion");
+        // 创建List集合
+        List<String> list = new ArrayList<>();
+        // 遍历JSONArray并添加元素到List
+        if (!CollectionUtils.isEmpty(jsonArray)) {
+            for (Object o : jsonArray) {
+                String str = o.toString();
+                if (StringUtils.isNotEmpty(str)) {
+                    String[] split1 = str.split("\r?\n+");
+                    list.addAll(Arrays.asList(split1));
+                }
+            }
+        }
+        map.put("num", num);
+        map.put("reason", reason);
+        map.put("claim_change", claimList);
+        map.put("defense_opinion", list);
+
+        ReportTemple reportTemplate = templeService.getById(20);
+        String templateFilePath = fileUtils.getPath(reportTemplate.getTemplatePath());
+        //更新会话
+        String name = DateUtils.dateTimeToStr(new Date(), "yyyyMMdd");
+        String finalName = name + "-" + conversationName + "-陈述意见书";
+        //生成文档
+        String fileGuid = null;
+        try {
+            fileGuid = this.generateOADefenseFile(map, templateFilePath, finalName);
+            AssoConfessionSessionFile assoConfessionSessionFile = new AssoConfessionSessionFile();
+            assoConfessionSessionFile.setGuid(fileGuid);
+            assoConfessionSessionFile.setConfessionSessionId(confessionSessionId);
+            assoConfessionSessionFile.setType(1);
+            assoConfessionSessionFile.insert();
+        } catch (Exception e) {
+            throw new XiaoShiException(ExceptionEnum.BUSINESS_ERROR, "加载陈述意见书失败");
+        }
+    }
+
+    public void generateDoc2(ConfessionSession confessionSession) {
+        String content = confessionSession.getContent();
+        Integer confessionSessionId = confessionSession.getId();
+        String conversationName = confessionSession.getConversationName();
+        JSONObject orgJsonObject = JSONObject.parseObject(content);
+        JSONObject jsonObject = orgJsonObject.getJSONObject("data");
+        String modify_claim = "";
+        if (jsonObject.get("data") != null) {
+            JSONObject jsonObject1 = (JSONObject) jsonObject.get("data");
+            modify_claim = jsonObject1.getString("modify_claim");
+        }
+        if (modify_claim == null || modify_claim.trim().equals("")) {
+            return;
+        }
+        List<String> claims = cn.cslg.pas.common.utils.StringUtils.changeStringToString(modify_claim, "\r?\n+|<br>+");
+        Map<String, Object> map = new HashMap<>();
+        map.put("claims", claims);
+
+        ReportTemple reportTemplate = templeService.getById(21);
+        String templateFilePath = fileUtils.getPath(reportTemplate.getTemplatePath());
+        //更新会话
+        String name = DateUtils.dateTimeToStr(new Date(), "yyyyMMdd");
+        String finalName = name + "-" + conversationName + "-修改对照页";
+        //生成文档
+        String fileGuid = null;
+        try {
+            fileGuid = this.generateOADefenseFile(map, templateFilePath, finalName);
+            AssoConfessionSessionFile assoConfessionSessionFile = new AssoConfessionSessionFile();
+            assoConfessionSessionFile.setGuid(fileGuid);
+            assoConfessionSessionFile.setConfessionSessionId(confessionSessionId);
+            assoConfessionSessionFile.setType(1);
+            assoConfessionSessionFile.insert();
+        } catch (Exception e) {
+            throw new XiaoShiException(ExceptionEnum.BUSINESS_ERROR, "加载陈述意见书失败");
+        }
+    }
+}

+ 92 - 0
src/main/java/cn/cslg/pas/service/dify/OaChatRecordService.java

@@ -0,0 +1,92 @@
+package cn.cslg.pas.service.dify;
+
+import cn.cslg.pas.common.model.cronModel.Records;
+import cn.cslg.pas.common.model.dify.OAMessageDTO;
+import cn.cslg.pas.common.model.dify.oa.OaChatRecordAddDTO;
+import cn.cslg.pas.common.model.dify.oa.OaChatRecordQueryDTO;
+import cn.cslg.pas.common.utils.LoginUtils;
+import cn.cslg.pas.domain.dify.OaChatRecord;
+import com.alibaba.fastjson.JSONObject;
+import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.metadata.IPage;
+import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
+import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import cn.cslg.pas.mapper.dify.OaChatRecordMapper;
+import lombok.RequiredArgsConstructor;
+import org.springframework.stereotype.Service;
+
+import java.util.List;
+
+/**
+ * @author admin
+ * @description 针对表【oa_chat_record】的数据库操作Service实现
+ * @createDate 2025-11-14 10:52:42
+ */
+@Service
+@RequiredArgsConstructor
+public class OaChatRecordService extends ServiceImpl<OaChatRecordMapper, OaChatRecord> {
+    private final LoginUtils loginUtils;
+
+    public OaChatRecord add(OAMessageDTO oaMessageDTO, Integer messageId, String reMessage) {
+        OaChatRecord oaChatRecord = this.getById(messageId);
+        String parametersStrs = JSONObject.toJSONString(oaMessageDTO);
+        oaChatRecord.setParameters(parametersStrs);
+        oaChatRecord.setAnswer(reMessage);
+        oaChatRecord.updateById();
+        return oaChatRecord;
+    }
+
+    public OaChatRecord add(OaChatRecordAddDTO oaChatRecordAddDTO) {
+        Integer id = oaChatRecordAddDTO.getId();
+        Integer confessionSessionId = oaChatRecordAddDTO.getConfessionSessionId();
+        String operation = oaChatRecordAddDTO.getOperation();
+        String question = oaChatRecordAddDTO.getQuestion();
+        String answer = oaChatRecordAddDTO.getAnswer();
+
+        OaChatRecord oaChatRecord = new OaChatRecord();
+        if (id != null) {
+            oaChatRecord = this.getById(id);
+        }
+        oaChatRecord.setCreateId(loginUtils.getId().toString());
+        oaChatRecord.setConfessionSessionId(confessionSessionId);
+        oaChatRecord.setOperation(operation);
+        oaChatRecord.setQuestion(question);
+        oaChatRecord.setAnswer(answer);
+        oaChatRecord.insertOrUpdate();
+        return oaChatRecord;
+    }
+
+    public Object query(OaChatRecordQueryDTO oaChatRecordQueryDTO) {
+        Integer id = oaChatRecordQueryDTO.getId();
+        Integer confessionSessionId = oaChatRecordQueryDTO.getConfessionSessionId();
+        Long current = oaChatRecordQueryDTO.getCurrent();
+        Long size = oaChatRecordQueryDTO.getSize();
+        if (id != null) {
+            OaChatRecord oaChatRecord = this.getById(id);
+            return oaChatRecord;
+        } else {
+            Records records = new Records();
+
+            LambdaQueryWrapper<OaChatRecord> queryWrapper = new LambdaQueryWrapper<>();
+            queryWrapper.orderByDesc(OaChatRecord::getCreateTime);
+            if (confessionSessionId != null) {
+                queryWrapper.eq(OaChatRecord::getConfessionSessionId, confessionSessionId);
+            }
+            if (current != null && size != null) {
+                IPage<OaChatRecord> oaChatRecordIPage = this.page(new Page<>(current, size), queryWrapper);
+                records.setSize(size);
+                records.setCurrent(current);
+                records.setTotal(oaChatRecordIPage.getTotal());
+                records.setData(oaChatRecordIPage.getRecords());
+            } else {
+                List<OaChatRecord> oaChatRecordList = this.list(queryWrapper);
+                records.setData(oaChatRecordList);
+            }
+            return records;
+        }
+    }
+}
+
+
+
+

+ 3 - 1
src/main/resources/application-dev.yml

@@ -92,8 +92,10 @@ DIFY:
   OAApiKey: app-NvKwdHvEK2UmJdmjTGDR0xu6
   checkApiKey: aa
   cliamKey: app-jF3akhYKgljPLdpeIpTNbs6f
-#  gInstructionKey: app-7ImBmlr7kvBTSvBj1mTvgKyp
+#  gInstructionKey: app-YfoUDlED4oJNO9hVk6hfdKSw
   gInstructionKey: app-7ImBmlr7kvBTSvBj1mTvgKyp
   discoveryResultKey: app-G5gnZ4s7GlMEIft79fk7hUR7
   aiPatentResultKey: app-KLneZ6O7qXL2DjKm169ltxJI
+  OAApiKey2: app-UTUV4s0TkGMBqHBEF3oqAbVp
+
   url: http://192.168.2.24/v1/

+ 4 - 11
src/test/java/cn/cslg/pas/DifyTest.java

@@ -16,6 +16,7 @@ import cn.cslg.pas.service.dify.GenerateDiscoveryResultService;
 import cn.cslg.pas.service.dify.GenerateInstructionService;
 import com.alibaba.fastjson.JSONObject;
 import com.alibaba.fastjson2.JSON;
+import jakarta.json.Json;
 import org.apache.commons.lang3.StringUtils;
 import org.apache.poi.ss.usermodel.Cell;
 import org.apache.poi.xssf.usermodel.XSSFCell;
@@ -276,17 +277,9 @@ public class DifyTest {
 
     @Test
     public void test3() {
-        String cleanText = "";
-        String a = "1.一种,13开发";
-        String regex = "[\u4e00-\u9fff]+";  // 匹配连续中文字符
-        Pattern pattern = Pattern.compile(regex);
-        Matcher matcher = pattern.matcher(a);
-        while (matcher.find()) {
-            cleanText = matcher.group();
-            break;
-        }
-
-        System.out.println(cleanText);
+        String reMessage="张三{\"aa\":123,\"b\":{}}";
+        String allText = reMessage.replaceAll("\\{[^}]*\\}", "").replaceAll("\\[[^]]*\\]", "");
+System.out.println(allText);
     }
 
 }