Browse Source

/*光明大模型工程*/

master
htjcAdmin 5 months ago
commit
856dfa6048
49 changed files with 2958 additions and 0 deletions
  1. +33
    -0
      .gitignore
  2. +202
    -0
      pom.xml
  3. +50
    -0
      src/main/java/com/mortal/bigmodelr/BigModelrApplication.java
  4. +29
    -0
      src/main/java/com/mortal/bigmodelr/config/MultimodalWebSocketHandler.java
  5. +30
    -0
      src/main/java/com/mortal/bigmodelr/config/MyWebSocketHandler.java
  6. +20
    -0
      src/main/java/com/mortal/bigmodelr/config/WebSocketConfig.java
  7. +47
    -0
      src/main/java/com/mortal/bigmodelr/controller/AnalysisController.java
  8. +80
    -0
      src/main/java/com/mortal/bigmodelr/controller/ModelController.java
  9. +15
    -0
      src/main/java/com/mortal/bigmodelr/domain/ApiResponse.java
  10. +14
    -0
      src/main/java/com/mortal/bigmodelr/domain/ChatCompletionRequest.java
  11. +33
    -0
      src/main/java/com/mortal/bigmodelr/domain/ChatCompletionResponse.java
  12. +13
    -0
      src/main/java/com/mortal/bigmodelr/domain/Choice.java
  13. +17
    -0
      src/main/java/com/mortal/bigmodelr/domain/Content.java
  14. +15
    -0
      src/main/java/com/mortal/bigmodelr/domain/ContentItem.java
  15. +9
    -0
      src/main/java/com/mortal/bigmodelr/domain/ImageUrl.java
  16. +29
    -0
      src/main/java/com/mortal/bigmodelr/domain/Message.java
  17. +20
    -0
      src/main/java/com/mortal/bigmodelr/domain/Multimodal.java
  18. +10
    -0
      src/main/java/com/mortal/bigmodelr/domain/Usage.java
  19. +26
    -0
      src/main/java/com/mortal/bigmodelr/domain/VisualModel.java
  20. +35
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/in/AnalyseConstants.java
  21. +51
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/in/AnalyseReqItem.java
  22. +50
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/in/AnalyseRequest.java
  23. +43
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/out/AnalyseResItem.java
  24. +127
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/out/AnalyseResPoint.java
  25. +100
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/out/AnalyseResult.java
  26. +12
    -0
      src/main/java/com/mortal/bigmodelr/domain/algorithm/out/Pos.java
  27. +19
    -0
      src/main/java/com/mortal/bigmodelr/domain/analysis/vi/AnalysisObject.java
  28. +20
    -0
      src/main/java/com/mortal/bigmodelr/domain/analysis/vi/AnalysisRequest.java
  29. +23
    -0
      src/main/java/com/mortal/bigmodelr/domain/analysis/vo/AnalysisResult.java
  30. +18
    -0
      src/main/java/com/mortal/bigmodelr/domain/analysis/vo/AnalysisResultEntity.java
  31. +19
    -0
      src/main/java/com/mortal/bigmodelr/domain/analysis/vo/AnalysisResultList.java
  32. +17
    -0
      src/main/java/com/mortal/bigmodelr/mapper/multimodalMapper.java
  33. +16
    -0
      src/main/java/com/mortal/bigmodelr/mapper/visualModelMapper.java
  34. +7
    -0
      src/main/java/com/mortal/bigmodelr/service/AlgorithmService.java
  35. +26
    -0
      src/main/java/com/mortal/bigmodelr/service/ModelService.java
  36. +107
    -0
      src/main/java/com/mortal/bigmodelr/service/impl/AlgorithmServiceImpl.java
  37. +550
    -0
      src/main/java/com/mortal/bigmodelr/service/impl/ModelServiceImpl.java
  38. +17
    -0
      src/main/java/com/mortal/bigmodelr/service/remote/AnalysisRemoteService.java
  39. +42
    -0
      src/main/java/com/mortal/bigmodelr/service/remote/impl/AnalysisRemoteServiceImpl.java
  40. +45
    -0
      src/main/java/com/mortal/bigmodelr/task/ModelTask.java
  41. +146
    -0
      src/main/java/com/mortal/bigmodelr/test/BatchImageDownloader.java
  42. +159
    -0
      src/main/java/com/mortal/bigmodelr/utils/AjaxResult.java
  43. +90
    -0
      src/main/java/com/mortal/bigmodelr/utils/HttpStatus.java
  44. +353
    -0
      src/main/java/com/mortal/bigmodelr/utils/StringUtils.java
  45. +113
    -0
      src/main/resources/application-local.yml
  46. +3
    -0
      src/main/resources/application.yml
  47. +17
    -0
      src/main/resources/mapper/multimodalMapper.xml
  48. +28
    -0
      src/main/resources/mapper/visualModelMapper.xml
  49. +13
    -0
      src/test/java/com/mortal/bigmodelr/BigModelrApplicationTests.java

+ 33
- 0
.gitignore View File

@ -0,0 +1,33 @@
HELP.md
target/
!.mvn/wrapper/maven-wrapper.jar
!**/src/main/**/target/
!**/src/test/**/target/
### STS ###
.apt_generated
.classpath
.factorypath
.project
.settings
.springBeans
.sts4-cache
### IntelliJ IDEA ###
.idea
*.iws
*.iml
*.ipr
### NetBeans ###
/nbproject/private/
/nbbuild/
/dist/
/nbdist/
/.nb-gradle/
build/
!**/src/main/**/build/
!**/src/test/**/build/
### VS Code ###
.vscode/

+ 202
- 0
pom.xml View File

@ -0,0 +1,202 @@
<?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>
<groupId>com.mortal</groupId>
<artifactId>inspect-luminous</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>inspect-luminous</name>
<description>inspect-luminous</description>
<properties>
<java.version>1.8</java.version>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding>
<spring-boot.version>2.6.13</spring-boot.version>
</properties>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-test</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
<version>1.16.18</version>
</dependency>
<dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>5.8.9</version>
</dependency>
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
<version>4.9.3</version>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-websocket</artifactId>
</dependency>
<!-- MySQL 驱动 -->
<dependency>
<groupId>mysql</groupId>
<artifactId>mysql-connector-java</artifactId>
<version>8.0.33</version>
</dependency>
<!-- Druid 数据源 -->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>druid-spring-boot-starter</artifactId>
<version>1.2.20</version>
</dependency>
<!-- Spring JDBC 支持 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency>
<dependency>
<groupId>org.mybatis.spring.boot</groupId>
<artifactId>mybatis-spring-boot-starter</artifactId>
<version>2.2.2</version>
</dependency>
<dependency>
<groupId>org.apache.commons</groupId>
<artifactId>commons-lang3</artifactId>
<version>3.12.0</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.13.0</version>
</dependency>
<dependency>
<groupId>org.projectlombok</groupId>
<artifactId>lombok</artifactId>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.83</version>
</dependency>
<!-- Retrofit Gson 转换器 -->
<dependency>
<groupId>com.squareup.retrofit2</groupId>
<artifactId>converter-gson</artifactId>
<version>2.9.0</version>
</dependency>
<!-- Gson 库 -->
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.9</version>
</dependency>
<!-- 日志拦截器 (可选) -->
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>logging-interceptor</artifactId>
<version>4.9.3</version>
</dependency>
<dependency>
<groupId>com.squareup.retrofit2</groupId>
<artifactId>retrofit</artifactId>
<version>2.9.0</version>
</dependency>
<dependency>
<groupId>com.squareup.retrofit2</groupId>
<artifactId>converter-scalars</artifactId>
<version>2.9.0</version> <!-- 版本应与retrofit核心库一致 -->
</dependency>
<!-- Retrofit Jackson 转换器 -->
<dependency>
<groupId>com.squareup.retrofit2</groupId>
<artifactId>converter-jackson</artifactId>
<version>2.9.0</version> <!-- 版本应与retrofit核心库一致 -->
</dependency>
<!-- Jackson 核心库 -->
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.13.0</version>
</dependency>
</dependencies>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-dependencies</artifactId>
<version>${spring-boot.version}</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.8.1</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
<encoding>UTF-8</encoding>
</configuration>
</plugin>
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>${spring-boot.version}</version>
<configuration>
<mainClass>com.mortal.bigmodelr.BigModelrApplication</mainClass>
</configuration>
<executions>
<execution>
<id>repackage</id>
<goals>
<goal>repackage</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>
</project>

+ 50
- 0
src/main/java/com/mortal/bigmodelr/BigModelrApplication.java View File

@ -0,0 +1,50 @@
package com.mortal.bigmodelr;
import okhttp3.Interceptor;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import org.mybatis.spring.annotation.MapperScan;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.scheduling.annotation.EnableScheduling;
import retrofit2.Retrofit;
import retrofit2.converter.jackson.JacksonConverterFactory;
import retrofit2.converter.scalars.ScalarsConverterFactory;
@SpringBootApplication(exclude = {DataSourceAutoConfiguration.class})
@EnableScheduling
@MapperScan("com.mortal.bigmodelr.mapper")
public class BigModelrApplication {
@Value("${analysis.api.url}")
private String apiUrlOfAnalysis;
@Value("${analysis.api.token}")
private String apiTokenOfAnalysis;
OkHttpClient.Builder clientBuilderOfAnalysis = new OkHttpClient.Builder();
Interceptor interceptorOfAnalysis = chain -> {
Request request = chain.request()
.newBuilder()
.build();
return chain.proceed(request);
};
@Bean(name = "RetrofitOfAnalysis")
public Retrofit retrofitOfAnalysis() {
clientBuilderOfAnalysis.interceptors().add(interceptorOfAnalysis);
return new Retrofit.Builder()
.baseUrl(apiUrlOfAnalysis)
.client(clientBuilderOfAnalysis.build())
.addConverterFactory(ScalarsConverterFactory.create())
.addConverterFactory(JacksonConverterFactory.create())
.build();
}
public static void main(String[] args) {
SpringApplication.run(BigModelrApplication.class, args);
}
}

+ 29
- 0
src/main/java/com/mortal/bigmodelr/config/MultimodalWebSocketHandler.java View File

@ -0,0 +1,29 @@
package com.mortal.bigmodelr.config;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketSession;
import org.springframework.web.socket.handler.TextWebSocketHandler;
import java.io.IOException;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
public class MultimodalWebSocketHandler extends TextWebSocketHandler {
private static final List<WebSocketSession> sessions = new CopyOnWriteArrayList<>();
@Override
public void afterConnectionEstablished(WebSocketSession session) {
sessions.add(session);
}
public static void broadcast(String message) {
for (WebSocketSession session : sessions) {
try {
if (session.isOpen()) {
session.sendMessage(new TextMessage(message));
}
} catch (IOException e) {
e.printStackTrace();
sessions.remove(session);
}
}
}
}

+ 30
- 0
src/main/java/com/mortal/bigmodelr/config/MyWebSocketHandler.java View File

@ -0,0 +1,30 @@
package com.mortal.bigmodelr.config;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketSession;
import org.springframework.web.socket.handler.TextWebSocketHandler;
import java.io.IOException;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
public class MyWebSocketHandler extends TextWebSocketHandler {
private static final List<WebSocketSession> sessions = new CopyOnWriteArrayList<>();
@Override
public void afterConnectionEstablished(WebSocketSession session) {
sessions.add(session);
}
// 向所有客户端推送数据
public static void broadcast(String message) {
for (WebSocketSession session : sessions) {
try {
if (session.isOpen()) {
session.sendMessage(new TextMessage(message));
}
} catch (IOException e) {
e.printStackTrace();
}
}
}
}

+ 20
- 0
src/main/java/com/mortal/bigmodelr/config/WebSocketConfig.java View File

@ -0,0 +1,20 @@
package com.mortal.bigmodelr.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.socket.config.annotation.EnableWebSocket;
import org.springframework.web.socket.config.annotation.WebSocketConfigurer;
import org.springframework.web.socket.config.annotation.WebSocketHandlerRegistry;
@Configuration
@EnableWebSocket
public class WebSocketConfig implements WebSocketConfigurer {
@Override
public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) {
registry.addHandler(new MyWebSocketHandler(), "/visualModel/ws/data")
.setAllowedOrigins("*"); // 允许跨域
registry.addHandler(new MultimodalWebSocketHandler(), "/multimodal/ws/data")
.setAllowedOrigins("*");
}
}

+ 47
- 0
src/main/java/com/mortal/bigmodelr/controller/AnalysisController.java View File

@ -0,0 +1,47 @@
package com.mortal.bigmodelr.controller;
import com.mortal.bigmodelr.service.AlgorithmService;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
@RestController
@CrossOrigin
public class AnalysisController {
@Resource
private AlgorithmService algorithmService;
// {
// "requestId": "72ae37f4b229445fb44701f724efaf55",
// "resultList": [
// {
// "algFactory": "yd",
// "results": [
// {
// "code": "2000",
// "pos": "[]",
// "resImageUrl": "1/2024/05/28/1216/CCD/1216_20240528100000_2024193_02160558340721910121.jpg",
// "conf": 0.99,
// "type": "",
// "value": "0",
// "desc": ""
// }
// ],
// "objectId": "2024193"
// }
// ]
// }
@PostMapping("/picAnalyse")
public ResponseEntity<String> bigModelPicAnalyse(@RequestBody final String analyseRequestStr) {
return ResponseEntity.ok().body(algorithmService.bigModelPicAnalyse(analyseRequestStr));
}
@PostMapping("/picAnalyseRetNotify")
public ResponseEntity<String> bigModelPicAnalyseRetNotify(@RequestBody String picAnalyseResult) {
return ResponseEntity
.ok()
.body(algorithmService.bigModelPicAnalyseRetNotify(picAnalyseResult));
}
}

+ 80
- 0
src/main/java/com/mortal/bigmodelr/controller/ModelController.java View File

@ -0,0 +1,80 @@
package com.mortal.bigmodelr.controller;
import com.mortal.bigmodelr.domain.Multimodal;
import com.mortal.bigmodelr.domain.VisualModel;
import com.mortal.bigmodelr.service.ModelService;
import com.mortal.bigmodelr.utils.AjaxResult;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import java.util.List;
@RestController
@CrossOrigin
public class ModelController {
@Resource
private ModelService modelService;
@PostMapping("/model/analysis")
@ResponseBody
public String Visualization(@RequestBody VisualModel visualModel)
{
return modelService.Visualization(visualModel);
}
@PostMapping("/model/multimodal")
@ResponseBody
public String Multimodal(@RequestBody Multimodal multimodal)
{
return modelService.Multimodal(multimodal);
}
@PostMapping("/model/xunWen")
@ResponseBody
public void runJob() {
// {
// "role": "user",
// "imageType": "image_url",
// "imageData": "/home/atia/bigModel/124.jpg",
// "model": "rsv-0zygizvz",
// "text": "这张图片存在什么问题缺陷吗?",
// "imageName": "121.jpg",
// "maxTokens": 300
// }
//获取基本目录下当前日期的所有图片
List<String> enquire = modelService.enquire();
for (int i = 0; i < enquire.size(); i++) {
Multimodal multimodal=new Multimodal();
multimodal.setRole("user");
multimodal.setImageType("image_url");
multimodal.setText("这张图片存在什么问题缺陷吗");
multimodal.setImageData(enquire.get(i));
//询问多模态大模型
modelService.Multimodal(multimodal);
}
}
//数据库照片下载
@PostMapping("/model/downImg")
public void runJob2() {
modelService.downImg();
}
//测试可正常
@PostMapping("/model/semanticsModel")
@ResponseBody
public AjaxResult semanticsModel(@RequestBody Multimodal multimodal)
{
String string = modelService.semanticsModel(multimodal);
return AjaxResult.success().put("data", string);
}
}

+ 15
- 0
src/main/java/com/mortal/bigmodelr/domain/ApiResponse.java View File

@ -0,0 +1,15 @@
package com.mortal.bigmodelr.domain;
import lombok.Data;
@Data
public class ApiResponse {
private String code;
private String message;
private Object data;
public ApiResponse(String code, String message) {
this.code = code;
this.message = message;
}
}

+ 14
- 0
src/main/java/com/mortal/bigmodelr/domain/ChatCompletionRequest.java View File

@ -0,0 +1,14 @@
package com.mortal.bigmodelr.domain;
import com.fasterxml.jackson.annotation.JsonInclude;
import lombok.Data;
import java.util.List;
@Data
@JsonInclude(JsonInclude.Include.NON_NULL)
public class ChatCompletionRequest {
private String model;
private List<Message> messages;
private int maxTokens;
}

+ 33
- 0
src/main/java/com/mortal/bigmodelr/domain/ChatCompletionResponse.java View File

@ -0,0 +1,33 @@
package com.mortal.bigmodelr.domain;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.util.List;
@Data
@AllArgsConstructor
@NoArgsConstructor
@JsonIgnoreProperties(ignoreUnknown = true)
public class ChatCompletionResponse {
private String id;
private String object;
private long created;
private List<Choice> choices;
private String info;
private Usage usage;
@JsonProperty("model")
private String model;
//存数据库
private String content;
private String picPath;
}

+ 13
- 0
src/main/java/com/mortal/bigmodelr/domain/Choice.java View File

@ -0,0 +1,13 @@
package com.mortal.bigmodelr.domain;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
import lombok.Data;
@Data
@JsonIgnoreProperties(ignoreUnknown = true) // 忽略所有未定义的字段
public class Choice {
private int index;
private Message message;
private String finish_reason;
}

+ 17
- 0
src/main/java/com/mortal/bigmodelr/domain/Content.java View File

@ -0,0 +1,17 @@
package com.mortal.bigmodelr.domain;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;
@Data
public class Content {
private String type; // text/image_url
@JsonInclude(JsonInclude.Include.NON_NULL)
private String text; // type=text时使用
@JsonInclude(JsonInclude.Include.NON_NULL)
@JsonProperty("image_url")
private ImageUrl imageUrl; // type=image_url时使用
}

+ 15
- 0
src/main/java/com/mortal/bigmodelr/domain/ContentItem.java View File

@ -0,0 +1,15 @@
package com.mortal.bigmodelr.domain;
import com.fasterxml.jackson.annotation.JsonProperty;
import lombok.Data;
@Data
public class ContentItem {
private String type; // text/image_url/image_base64
private String text; // type=text时使用
@JsonProperty("image_url")
private ImageUrl imageUrl; // type=image_url时使用
private String image; // type=image_base64时使用
}

+ 9
- 0
src/main/java/com/mortal/bigmodelr/domain/ImageUrl.java View File

@ -0,0 +1,9 @@
package com.mortal.bigmodelr.domain;
import lombok.Data;
@Data
public class ImageUrl {
private String url;
}

+ 29
- 0
src/main/java/com/mortal/bigmodelr/domain/Message.java View File

@ -0,0 +1,29 @@
package com.mortal.bigmodelr.domain;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.fasterxml.jackson.annotation.JsonSetter;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import lombok.Data;
import java.util.Collections;
import java.util.List;
@Data
public class Message {
private String role;
// private List<Content> content;
private Object content; // 可以是 String List<Content>
@JsonSetter("content")
public void setContent(Object content) {
if (content instanceof String) {
this.content = (String) content;
} else if (content instanceof List) {
this.content = (List<ContentItem>) content;
}
}
}

+ 20
- 0
src/main/java/com/mortal/bigmodelr/domain/Multimodal.java View File

@ -0,0 +1,20 @@
package com.mortal.bigmodelr.domain;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
@AllArgsConstructor
public class Multimodal {
private String role;
private String imageType;
private String imageData;
private String model;
private String text;
private String imageName;
private int maxTokens;
}

+ 10
- 0
src/main/java/com/mortal/bigmodelr/domain/Usage.java View File

@ -0,0 +1,10 @@
package com.mortal.bigmodelr.domain;
import lombok.Data;
@Data
public class Usage {
private int prompt_tokens;
private int completion_tokens;
private int total_tokens;
}

+ 26
- 0
src/main/java/com/mortal/bigmodelr/domain/VisualModel.java View File

@ -0,0 +1,26 @@
package com.mortal.bigmodelr.domain;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@NoArgsConstructor
@AllArgsConstructor
public class VisualModel {
//照片类型url ,base64
private String image_type;
//照片名称
private String image_name;
//照片地址(http,https无鉴权)
private String image_url;
//照片base64
private String image_base64;
private String stringData;
}

+ 35
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/in/AnalyseConstants.java View File

@ -0,0 +1,35 @@
package com.inspect.simulator.domain.algorithm.in;
public class AnalyseConstants {
public static final String ANALYSE_FILTER_REQUEST = "ANALYSE_FILTER_REQUEST:";
public static final String ANALYSE_REQUEST_ALG = "ANALYSE_REQUEST_ALG:";
public static final String ANALYSE_TASK_REQUEST = "ANALYSE_TASK_REQUEST:";
public static final String ANALYSE_REQUEST_ID = "ANALYSE_REQUEST_ID:";
public static final String ANALYSE_OK = "2000";
public static final String ANALYSE_FAIL_NO_FILE = "2001";
public static final String ANALYSE_FAIL_ALG_EXCEPT = "2002";
public static final String ANALYSE_FAIL_FILE_EXCEPT = "2003";
public static final String ANALYSE_FAIL_FILE_INCOMPATIBLE = "2004";
public static final String ANALYSE_CODE = "code";
public static final String ANALYSE_UPPER_VALUE = "upperValue";
public static final String ANALYSE_LOWER_VALUE = "lowerValue";
public static final String ANALYSE_ALARM_THRESHOLD = "alarm_threshold";
public static final String ANALYSE_VALUE_ERROR = "1";
public static final String ANALYSE_SPLIT = "$analyse$";
public static final String POINT_STATUS_FAIL = "0";
public static final String POINT_STATUS_OK = "1";
public static final String POINT_STATUS_PERSON = "2";
public static final String RES_STATUS_UN = "0";
public static final String RES_STATUS_ED = "1";
public static final String RES_STATUS_NO = "2";
public static final String RESULT_TYPE_ALARM = "0";
public static final String RESULT_TYPE_RESULT = "1";
public static final String RESULT_TYPE_ERROR = "2";
public static final String TASK_PROGRESS_WAITING = "99.99";
public static final String TASK_PROGRESS_OK = "100";
public static final String ANALYSE_IS_FILTER = "ANALYSE_IS_FILTER";
public static final String ANALYSE_IS_METER_FILTER = "ANALYSE_IS_METER_FILTER";
public static final String ANALYSE_FILTER_URL = "ANALYSE_FILTER_URL";
public static final String ANALYSIS_BIG_URL = "ANALYSIS_BIG_URL";
public static final String MAX_NUM = "MAX_NUM";
}

+ 51
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/in/AnalyseReqItem.java View File

@ -0,0 +1,51 @@
package com.mortal.bigmodelr.domain.algorithm.in;
import com.alibaba.fastjson.JSONObject;
import lombok.*;
import java.io.Serializable;
import java.util.Arrays;
import java.util.Objects;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class AnalyseReqItem implements Serializable {
private String objectId;
private String imageNormalUrlPath;
private String[] typeList;
private String[] imageUrlList;
public AnalyseReqItem clone() {
return JSONObject.parseObject(JSONObject.toJSONString(this), AnalyseReqItem.class);
}
public String toResultValue(String type) {
return this.objectId + com.inspect.simulator.domain.algorithm.in.AnalyseConstants.ANALYSE_SPLIT + type;
}
@Override
public boolean equals(Object object) {
if (this == object) return true;
if (object == null || getClass() != object.getClass()) return false;
AnalyseReqItem that = (AnalyseReqItem) object;
return Objects.equals(objectId, that.objectId) && Objects.equals(imageNormalUrlPath, that.imageNormalUrlPath) && Objects.deepEquals(typeList, that.typeList) && Objects.deepEquals(imageUrlList, that.imageUrlList);
}
@Override
public int hashCode() {
return Objects.hash(objectId, imageNormalUrlPath, Arrays.hashCode(typeList), Arrays.hashCode(imageUrlList));
}
@Override
public String toString() {
return "AnalyseReqItem{" +
"objectId='" + objectId + '\'' +
", imageNormalUrlPath='" + imageNormalUrlPath + '\'' +
", typeList=" + Arrays.toString(typeList) +
", imageUrlList=" + Arrays.toString(imageUrlList) +
'}';
}
}

+ 50
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/in/AnalyseRequest.java View File

@ -0,0 +1,50 @@
package com.mortal.bigmodelr.domain.algorithm.in;
import com.alibaba.fastjson.JSONObject;
import lombok.Getter;
import lombok.Setter;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
@Setter
@Getter
public class AnalyseRequest implements Serializable {
private List<AnalyseReqItem> objectList;
private String requestHostIp;
private String requestHostPort;
private String requestId;
private String algorithmPath;
private String taskPatrolId;
private String sftpHostIp;
private String sftpHostPort;
private String sftpUsername;
private String sftpPassword;
public AnalyseRequest clone() {
return JSONObject.parseObject(JSONObject.toJSONString(this), AnalyseRequest.class);
}
public String toString() {
return JSONObject.toJSONString(this);
}
@Override
public boolean equals(Object object) {
if (this == object) return true;
if (object == null || getClass() != object.getClass()) return false;
AnalyseRequest that = (AnalyseRequest) object;
return Objects.equals(objectList, that.objectList) && Objects.equals(requestHostIp, that.requestHostIp) && Objects.equals(requestHostPort, that.requestHostPort) && Objects.equals(requestId, that.requestId) && Objects.equals(algorithmPath, that.algorithmPath) && Objects.equals(taskPatrolId, that.taskPatrolId);
}
@Override
public int hashCode() {
return Objects.hash(objectList, requestHostIp, requestHostPort, requestId, algorithmPath, taskPatrolId);
}
}

+ 43
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/out/AnalyseResItem.java View File

@ -0,0 +1,43 @@
package com.mortal.bigmodelr.domain.algorithm.out;
import com.alibaba.fastjson.JSONObject;
import lombok.*;
import java.io.Serializable;
import java.util.List;
import java.util.Objects;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class AnalyseResItem implements Serializable {
private String objectId;
private String algFactory;
private List<AnalyseResPoint> results;
// public AnalyseResItem clone() {
// return JSONObject.parseObject(JSONObject.toJSONString(this), AnalyseResItem.class);
// }
//
// @Override
// public boolean equals(Object object) {
// if (this == object) return true;
// if (object == null || getClass() != object.getClass()) return false;
// AnalyseResItem that = (AnalyseResItem) object;
// return Objects.equals(objectId, that.objectId) && Objects.equals(results, that.results);
// }
//
// @Override
// public int hashCode() {
// return Objects.hash(objectId, results);
// }
//
// @Override
// public String toString() {
// return "AnalyseResItem{" +
// "objectId='" + objectId + '\'' +
// ", results=" + results +
// '}';
// }
}

+ 127
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/out/AnalyseResPoint.java View File

@ -0,0 +1,127 @@
package com.mortal.bigmodelr.domain.algorithm.out;
import com.alibaba.fastjson.JSONObject;
import com.inspect.simulator.domain.algorithm.in.AnalyseConstants;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.apache.commons.lang3.StringUtils;
import java.io.Serializable;
import java.util.List;
import java.util.Objects;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class AnalyseResPoint implements Serializable {
private String type;
// private String Value;
private String value;
private String code;
// private String resImageUrl;
private String resImagePath;
private String imageNormalUrlPath;
private String conf;
private String desc;
private List<Pos> pos;
// public boolean checkSuccess() {
// return "2000".equals(this.code) && "1".equals(this.value);
// }
//
// public String toString() {
// return JSONObject.toJSONString(this);
// }
//
// public void setValue(String value) {
// this.value = value;
// if (!StringUtils.isEmpty(value)) {
// this.Value = value;
// }
//
// }
//
// public String toResultValue(String objectId) {
// return objectId + AnalyseConstants.ANALYSE_SPLIT + this.type;
// }
//
// public AnalyseResPoint clone() {
// return JSONObject.parseObject(JSONObject.toJSONString(this), AnalyseResPoint.class);
// }
//
// public String getType() {
// return this.type;
// }
//
// public String getValue() {
// return this.Value;
// }
//
// public String getCode() {
// return this.code;
// }
//
// public String getResImageUrl() {
// return this.resImageUrl;
// }
//
// public String getImageNormalUrlPath() {
// return this.imageNormalUrlPath;
// }
//
// public String getConf() {
// return this.conf;
// }
//
// public String getDesc() {
// return this.desc;
// }
//
// public List<Pos> getPos() {
// return this.pos;
// }
//
// public void setType(String type) {
// this.type = type;
// }
//
// public void setCode(String code) {
// this.code = code;
// }
//
// public void setResImageUrl(String resImageUrl) {
// this.resImageUrl = resImageUrl;
// }
//
// public void setImageNormalUrlPath(String imageNormalUrlPath) {
// this.imageNormalUrlPath = imageNormalUrlPath;
// }
//
// public void setConf(String conf) {
// this.conf = conf;
// }
//
// public void setDesc(String desc) {
// this.desc = desc;
// }
//
// public void setPos(List<Pos> pos) {
// this.pos = pos;
// }
//
// @Override
// public boolean equals(Object object) {
// if (this == object) return true;
// if (object == null || getClass() != object.getClass()) return false;
// AnalyseResPoint that = (AnalyseResPoint) object;
// return Objects.equals(type, that.type) && Objects.equals(Value, that.Value) && Objects.equals(value, that.value) && Objects.equals(code, that.code) && Objects.equals(resImageUrl, that.resImageUrl) && Objects.equals(imageNormalUrlPath, that.imageNormalUrlPath) && Objects.equals(conf, that.conf) && Objects.equals(desc, that.desc) && Objects.equals(pos, that.pos);
// }
//
// @Override
// public int hashCode() {
// return Objects.hash(type, Value, value, code, resImageUrl, imageNormalUrlPath, conf, desc, pos);
// }
}

+ 100
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/out/AnalyseResult.java View File

@ -0,0 +1,100 @@
package com.mortal.bigmodelr.domain.algorithm.out;
import com.mortal.bigmodelr.domain.algorithm.in.AnalyseReqItem;
import com.mortal.bigmodelr.domain.algorithm.in.AnalyseRequest;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.Getter;
import lombok.NoArgsConstructor;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class AnalyseResult implements Serializable {
private String requestId;
private List<AnalyseResItem> resultList;
private List<AnalyseResItem> resultsList;
private String taskPatrolId;
private String filter = "0";
private String result = "1";
// public void setResultsList(List<AnalyseResItem> resultsList) {
// this.resultsList = resultsList;
// if (resultsList != null) {
// this.resultList = resultsList;
// }
//
// }
//
// public void reloadReq(AnalyseRequest analyseRequest) {
// AnalyseResItem analyseResItem = this.resultList.get(0);
// List<AnalyseResItem> resultList = new ArrayList<>();
// this.setResultsList(resultList);
//
// for (int i = 0; i < analyseRequest.getObjectList().size(); ++i) {
// AnalyseResItem resItem = analyseResItem.clone();
// resultList.add(resItem);
// AnalyseReqItem analyseReqItem = analyseRequest.getObjectList().get(i);
// AnalyseResPoint resPoint = analyseResItem.getResults().get(0);
// List<AnalyseResPoint> results = new ArrayList<>();
// resItem.setResults(results);
// for (String type : analyseReqItem.getTypeList()) {
// AnalyseResPoint clone = resPoint.clone();
// clone.setType(type);
// results.add(clone);
// }
// }
//
// }
//
// public void setRequestId(String requestId) {
// this.requestId = requestId;
// }
//
// public void setResultList(List<AnalyseResItem> resultList) {
// this.resultList = resultList;
// }
//
// public void setTaskPatrolId(String taskPatrolId) {
// this.taskPatrolId = taskPatrolId;
// }
//
// public void setFilter(String filter) {
// this.filter = filter;
// }
//
// public void setResult(String result) {
// this.result = result;
// }
//
// @Override
// public boolean equals(Object object) {
// if (this == object) return true;
// if (object == null || getClass() != object.getClass()) return false;
// AnalyseResult that = (AnalyseResult) object;
// return Objects.equals(requestId, that.requestId) && Objects.equals(resultList, that.resultList) && Objects.equals(resultsList, that.resultsList) && Objects.equals(taskPatrolId, that.taskPatrolId) && Objects.equals(filter, that.filter) && Objects.equals(result, that.result);
// }
//
// @Override
// public int hashCode() {
// return Objects.hash(requestId, resultList, resultsList, taskPatrolId, filter, result);
// }
//
// @Override
// public String toString() {
// return "AnalyseResult{" +
// "requestId='" + requestId + '\'' +
// ", resultList=" + resultList +
// ", resultsList=" + resultsList +
// ", taskPatrolId='" + taskPatrolId + '\'' +
// ", filter='" + filter + '\'' +
// ", result='" + result + '\'' +
// '}';
// }
}

+ 12
- 0
src/main/java/com/mortal/bigmodelr/domain/algorithm/out/Pos.java View File

@ -0,0 +1,12 @@
package com.mortal.bigmodelr.domain.algorithm.out;
import lombok.*;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class Pos {
private String[] areas;
}

+ 19
- 0
src/main/java/com/mortal/bigmodelr/domain/analysis/vi/AnalysisObject.java View File

@ -0,0 +1,19 @@
package com.mortal.bigmodelr.domain.analysis.vi;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
import java.util.List;
@Data
@SuperBuilder
@NoArgsConstructor
@AllArgsConstructor
public class AnalysisObject {
private String objectId;
private String imageNormalUrlPath;
private List<String> typeList;
private List<String> imageUrlList;
}

+ 20
- 0
src/main/java/com/mortal/bigmodelr/domain/analysis/vi/AnalysisRequest.java View File

@ -0,0 +1,20 @@
package com.mortal.bigmodelr.domain.analysis.vi;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
import java.util.List;
@Data
@SuperBuilder
@NoArgsConstructor
@AllArgsConstructor
public class AnalysisRequest {
private String requestId;
private String taskPatrolId;
private String requestHostIp;
private String requestHostPort;
private List<AnalysisObject> objectList;
}

+ 23
- 0
src/main/java/com/mortal/bigmodelr/domain/analysis/vo/AnalysisResult.java View File

@ -0,0 +1,23 @@
package com.mortal.bigmodelr.domain.analysis.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
import java.io.Serializable;
import java.util.List;
@Data
@SuperBuilder
@NoArgsConstructor
@AllArgsConstructor
public class AnalysisResult implements Serializable {
private String code;
private List<String> pos;
private String resImageUrl;
private Double conf;
private String type;
private String value;
private String desc;
}

+ 18
- 0
src/main/java/com/mortal/bigmodelr/domain/analysis/vo/AnalysisResultEntity.java View File

@ -0,0 +1,18 @@
package com.mortal.bigmodelr.domain.analysis.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
import java.io.Serializable;
import java.util.List;
@Data
@SuperBuilder
@NoArgsConstructor
@AllArgsConstructor
public class AnalysisResultEntity implements Serializable {
private String requestId;
private List<AnalysisResultList> resultList;
}

+ 19
- 0
src/main/java/com/mortal/bigmodelr/domain/analysis/vo/AnalysisResultList.java View File

@ -0,0 +1,19 @@
package com.mortal.bigmodelr.domain.analysis.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.experimental.SuperBuilder;
import java.io.Serializable;
import java.util.List;
@Data
@SuperBuilder
@NoArgsConstructor
@AllArgsConstructor
public class AnalysisResultList implements Serializable {
private String algFactory;
private String objectId;
private List<AnalysisResult> results;
}

+ 17
- 0
src/main/java/com/mortal/bigmodelr/mapper/multimodalMapper.java View File

@ -0,0 +1,17 @@
package com.mortal.bigmodelr.mapper;
import com.mortal.bigmodelr.domain.ChatCompletionResponse;
import com.mortal.bigmodelr.domain.VisualModel;
import org.apache.ibatis.annotations.Mapper;
import java.util.List;
@Mapper
public interface multimodalMapper {
int addMultimodalModelInfo(ChatCompletionResponse completionResponse);
}

+ 16
- 0
src/main/java/com/mortal/bigmodelr/mapper/visualModelMapper.java View File

@ -0,0 +1,16 @@
package com.mortal.bigmodelr.mapper;
import com.mortal.bigmodelr.domain.VisualModel;
import org.apache.ibatis.annotations.Mapper;
import java.util.List;
@Mapper
public interface visualModelMapper {
int addVisualModelInfo(List<VisualModel> visualModels);
List<String> selectImgUrl();
}

+ 7
- 0
src/main/java/com/mortal/bigmodelr/service/AlgorithmService.java View File

@ -0,0 +1,7 @@
package com.mortal.bigmodelr.service;
public interface AlgorithmService {
String bigModelPicAnalyse(final String analyseRequestStr);
String bigModelPicAnalyseRetNotify(final String picAnalyseResult);
}

+ 26
- 0
src/main/java/com/mortal/bigmodelr/service/ModelService.java View File

@ -0,0 +1,26 @@
package com.mortal.bigmodelr.service;
import com.mortal.bigmodelr.domain.Multimodal;
import com.mortal.bigmodelr.domain.VisualModel;
import org.springframework.http.ResponseEntity;
import java.util.List;
public interface ModelService {
//视觉大模型服务接口
String Visualization(VisualModel visualModel);
//多模态大模型
public String Multimodal(Multimodal multimodal);
//语义大模型
public String semanticsModel(Multimodal multimodal);
//所有缺陷图片路径
public List<String> enquire();
//图片下载到本地
public void downImg();
}

+ 107
- 0
src/main/java/com/mortal/bigmodelr/service/impl/AlgorithmServiceImpl.java View File

@ -0,0 +1,107 @@
package com.mortal.bigmodelr.service.impl;
import com.google.gson.Gson;
import com.mortal.bigmodelr.domain.Multimodal;
import com.mortal.bigmodelr.domain.algorithm.in.AnalyseRequest;
import com.mortal.bigmodelr.domain.algorithm.out.AnalyseResItem;
import com.mortal.bigmodelr.domain.algorithm.out.AnalyseResPoint;
import com.mortal.bigmodelr.domain.algorithm.out.AnalyseResult;
import com.mortal.bigmodelr.service.AlgorithmService;
import com.mortal.bigmodelr.service.ModelService;
import com.mortal.bigmodelr.service.remote.AnalysisRemoteService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import retrofit2.Call;
import retrofit2.Response;
import javax.annotation.Resource;
import java.awt.*;
import java.util.ArrayList;
import java.util.List;
@Service
public class AlgorithmServiceImpl implements AlgorithmService {
private final Logger log = LoggerFactory.getLogger(this.getClass());
@Value("${file.infraredPath:null}")
private String infraredPath;
@Resource
private AnalysisRemoteService analysisRemoteService;
@Resource
private ModelService modelService;
@Override
public String bigModelPicAnalyse(String analyseRequestStr) {
log.info(Color.MAGENTA + "[BIG MODEL] bigModelPicAnalyse: analyseRequestStr={}", analyseRequestStr);
AnalyseRequest analyseRequest = new Gson().fromJson(analyseRequestStr, AnalyseRequest.class);
Multimodal multimodal=new Multimodal();
multimodal.setModel("rsv-0zygizvz");
multimodal.setText("详细描述一下这张图片中的内容");
multimodal.setImageType("image_url");
multimodal.setImageData(analyseRequest.getObjectList().get(0).getImageUrlList()[0]);
//调用多模态大模型,语义大模型
String multimodalResult = modelService.Multimodal(multimodal);
//返回结构体
String[] typeList = analyseRequest.getObjectList().get(0).getTypeList();
String typeListStr = String.join(",", typeList);
AnalyseResult analyseResult = new AnalyseResult();
analyseResult.setRequestId(analyseRequest.getRequestId());
AnalyseResPoint analyseResPoint = new AnalyseResPoint();
analyseResPoint.setValue("1");
analyseResPoint.setConf("0.95");
analyseResPoint.setCode("2000");
analyseResPoint.setType(typeListStr);
analyseResPoint.setResImagePath(analyseRequest.getObjectList().get(0).getImageUrlList()[0]);
List<AnalyseResPoint> analyseResPoints = new ArrayList<>();
analyseResPoints.add(analyseResPoint);
AnalyseResItem analyseResItem = new AnalyseResItem();
analyseResItem.setObjectId(analyseRequest.getObjectList().get(0).getObjectId());
// analyseResItem.setAlgFactory("yd");
analyseResItem.setResults(analyseResPoints);
List<AnalyseResItem> analyseResItems = new ArrayList<>();
analyseResItems.add(analyseResItem);
analyseResult.setResultList(analyseResItems);
if (infraredPath.equals("null")) {
// 如果nacos中没有配置红外路径则将结果返回调用方
try {
// Call<Object> call = analysisRemoteService.picAnalyseRetNotify(analyseResult);
// Response<Object> response = call.execute();
// System.out.println("result: " + result);
System.out.println(new Gson().toJson(analyseResult));
} catch (Exception e) {
e.printStackTrace();
}
}
return "{\"code\":\"200\"}";
}
@Override
public String bigModelPicAnalyseRetNotify(final String picAnalyseResult) {
AnalyseResult analyseResult = new Gson().fromJson(picAnalyseResult, AnalyseResult.class);
log.info(Color.MAGENTA + "[BIG MODEL] bigModelPicAnalyseRetNotify: picAnalyseResultStr={}, picAnalyseResult: {}", picAnalyseResult, analyseResult);
try {
Call<Object> call = analysisRemoteService.picAnalyseRetNotify(analyseResult);
Response<Object> response = call.execute();
Object result = response.body();
System.out.println("result: " + result);
} catch (Exception e) {
e.printStackTrace();
}
return "";
}
}

+ 550
- 0
src/main/java/com/mortal/bigmodelr/service/impl/ModelServiceImpl.java View File

@ -0,0 +1,550 @@
package com.mortal.bigmodelr.service.impl;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.google.gson.*;
import com.mortal.bigmodelr.config.MultimodalWebSocketHandler;
import com.mortal.bigmodelr.config.MyWebSocketHandler;
import com.mortal.bigmodelr.domain.*;
import com.mortal.bigmodelr.mapper.multimodalMapper;
import com.mortal.bigmodelr.mapper.visualModelMapper;
import com.mortal.bigmodelr.service.ModelService;
import okhttp3.*;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import javax.annotation.Resource;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.SocketTimeoutException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.concurrent.TimeUnit;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import static com.mortal.bigmodelr.test.BatchImageDownloader.batchDownloadImages;
@Service
public class ModelServiceImpl implements ModelService {
@Value("${file.baseUrl}")
private String baseUrl;
@Value("${file.apiPath}")
private String apiPath;
@Value("${file.multimodalPath}")
private String multimodalPath;
@Value("${file.semanticsModalPath}")
private String semanticsModalPath;
// @Value("${file.semanticsModalAsk}")
// private String semanticsModalAsk;
@Value("${file.authKey}")
private String authKey;
@Value("${file.model}")
private String model;
@Value("${file.picPath}")
private String picPath;
//智能巡视图片存放的基础目录
@Value("${file.baseDirectory}")
private String baseDirectory;
// private String baseDirectory = "C:\\Users\\王寻\\Desktop\\1111\\1";
// 设置支持的图片文件扩展名
private static final List<String> IMAGE_EXTENSIONS = Arrays.asList(".jpg", ".jpeg", ".png");
private final ObjectMapper objectMapper = new ObjectMapper();
private final OkHttpClient httpClient = new OkHttpClient.Builder()
.connectTimeout(40, TimeUnit.SECONDS) // 连接超时
.readTimeout(60, TimeUnit.SECONDS) // 读取超时
.writeTimeout(30, TimeUnit.SECONDS) // 写入超时
.build();
@Resource
private visualModelMapper visualModelMapper;
@Resource
private multimodalMapper multimodalMapper;
public ModelServiceImpl() {
// 设置JSON序列化时忽略null值
objectMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL);
}
//视觉大模型
@Override
public String Visualization(VisualModel visualModel) {
System.out.println("请求路径:"+baseUrl+apiPath+"使用密钥:"+authKey+"使用模型id"+model);
System.out.println("访问的图片地址"+picPath);
String base64String = convertToBase64(picPath);
List<VisualModel> visualModels=new ArrayList<>();
// 测试连接-------------------
// 1. 创建WebSocket处理器
MyWebSocketHandler webSocketHandler = new MyWebSocketHandler();
// // 2. 生成100条数据并逐条推送
// JsonArray mockDataArray = new JsonArray();
// Random random = new Random();
//
// for (int i = 1; i <= 100; i++) {
// // 生成单条数据
// JsonObject item = new JsonObject();
// item.addProperty("id", i);
// item.addProperty("name", "Item-" + i);
// item.addProperty("value", random.nextInt(1000)); // 随机值0-999
//
// // 将单条数据转为JSON字符串并推送
// String itemJson = item.toString();
// webSocketHandler.broadcast(itemJson); // 推送当前条目
//
// VisualModel visual=new VisualModel();
// visual.setStringData(itemJson);
// visualModels.add(visual);
//
// // 可选添加延迟模拟实时推送效果
// try {
// Thread.sleep(100); // 延迟100毫秒
// } catch (InterruptedException e) {
// e.printStackTrace();
// }
//
// // 如果需要仍可保留添加到数组的逻辑非必须
// mockDataArray.add(item);
// }
// --------------------
OkHttpClient client = new OkHttpClient();
// 使用 Map List 动态构建 JSON 结构
Map<String, Object> requestBody = new HashMap<>();
Map<String, String> imageData = new HashMap<>();
imageData.put("image_name", "111.jpg");
imageData.put("image_type", "base64");
imageData.put("image_data", base64String);
requestBody.put("data", Collections.singletonList(imageData));
requestBody.put("model", model);
Gson gson = new Gson();
String jsonBody = gson.toJson(requestBody);
RequestBody body = RequestBody.create(jsonBody, MediaType.parse("application/json"));
Request request = new Request.Builder()
.url(baseUrl + apiPath)
.post(body)
.addHeader("Content-Type", "application/json")
.addHeader("Authorization", authKey)
.build();
try (Response response = client.newCall(request).execute()) {
System.out.println("打印response"+response);
if (!response.isSuccessful()) {
throw new IOException("请求失败: " + response.code());
}
if (response.body() != null) {
String responseBody = response.body().string();
System.out.println("返回数据String"+responseBody);
// webSocketHandler.broadcast(responseBody); // 推送当前条目
// VisualModel visual=new VisualModel();
// visual.setStringData(responseBody);
// visualModels.add(visual);
// JsonObject jsonResponse = JsonParser.parseString(responseBody).getAsJsonObject();
//// 解析返回数据
// // 提取基础字段
// String traceld = jsonResponse.get("traceld").getAsString();
// boolean success = jsonResponse.get("success").getAsBoolean();
// System.out.println("traceld: " + traceld);
// System.out.println("success: " + success);
//
// // 解析 data 对象
// JsonObject data = jsonResponse.getAsJsonObject("data");
// String imageName = data.get("image_name").getAsString();
// int imageHeight = data.get("image_height").getAsInt();
// int imageWidth = data.get("image_width").getAsInt();
// System.out.println("\n图片信息:");
// System.out.println(" name: " + imageName);
// System.out.println(" height: " + imageHeight);
// System.out.println(" width: " + imageWidth);
//
// // 解析 infer_results 数组
// JsonArray inferResults = data.getAsJsonArray("infer_results");
// System.out.println("\n推理结果:");
// for (JsonElement element : inferResults) {
// JsonObject result = element.getAsJsonObject();
// JsonArray bbox = result.getAsJsonArray("bbox");
// String category = result.get("category").getAsString();
// float score = result.get("score").getAsFloat();
//
// System.out.println(" category: " + category);
// System.out.println(" score: " + score);
// System.out.println(" bbox: [" +
// bbox.get(0).getAsInt() + ", " +
// bbox.get(1).getAsInt() + ", " +
// bbox.get(2).getAsInt() + ", " +
// bbox.get(3).getAsInt() + "]");
// }
}else {
System.out.println("无返回内容!!!");
System.out.println("请求返回数据"+response.body());
}
} catch (IOException e) {
e.printStackTrace();
}
//添加到数据库
if (visualModels.size()>0){
visualModelMapper.addVisualModelInfo(visualModels);
}
return "";
}
//图片路径转base64
public String convertToBase64(String imagePath) {
try {
byte[] imageBytes = Files.readAllBytes(Paths.get(imagePath));
return Base64.getEncoder().encodeToString(imageBytes);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
//多模态大模型
public String Multimodal(Multimodal multimodal) {
System.out.println("请求路径:" + baseUrl + multimodalPath);
MultimodalWebSocketHandler webSocketHandler = new MultimodalWebSocketHandler();
// 重试次数
int maxRetries = 3;
int attempt = 0;
while (attempt < maxRetries) {
try {
attempt++;
ChatCompletionRequest request = buildCorrectRequest(multimodal);
ChatCompletionResponse response = sendRequest(request);
System.out.println("响应ID: " + response.getId());
String content = String.valueOf(response.getChoices().get(0).getMessage().getContent());
// ChatCompletionResponse completionResponse=new ChatCompletionResponse();
// completionResponse.setContent(content);
// completionResponse.setPicPath(multimodal.getImageData());
// completionResponse.setId(response.getId());
// completionResponse.setInfo(response.toString());
// 存入数据库
// if (completionResponse!=null) {
// multimodalMapper.addMultimodalModelInfo(completionResponse);
// }
//调用语义大模型
Multimodal askSemanticsModel =new Multimodal();
askSemanticsModel.setText(content);
this.semanticsModel(askSemanticsModel);
return processResponse(response);
} catch (SocketTimeoutException e) {
if (attempt == maxRetries) {
webSocketHandler.broadcast("请求超时,已达最大重试次数");
return "请求超时,请稍后重试";
}
System.out.println("第" + attempt + "次尝试超时,准备重试...");
try {
Thread.sleep(1000 * attempt); // 指数退避
} catch (InterruptedException ie) {
Thread.currentThread().interrupt();
}
} catch (Exception e) {
e.printStackTrace();
webSocketHandler.broadcast("请求失败: " + e.getMessage());
return "请求处理失败: " + e.getMessage();
}
}
return "请求处理失败";
}
/**
* 构建符合规范的请求体
*/
private ChatCompletionRequest buildCorrectRequest(Multimodal multimodal) {
ChatCompletionRequest request = new ChatCompletionRequest();
// 设置模型名称默认"rsv-0zygizvz"
request.setModel(multimodal.getModel() != null ? multimodal.getModel() : "rsv-0zygizvz");
// 构建消息内容列表
List<Content> contents = new ArrayList<>();
// 添加文本内容
if (StringUtils.isNotBlank(multimodal.getText())) {
Content textContent = new Content();
textContent.setType("text");
textContent.setText(multimodal.getText());
contents.add(textContent);
} else {
// 默认文本
Content textContent = new Content();
textContent.setType("text");
textContent.setText("图片设备是否存在缺陷情况?");
contents.add(textContent);
}
// 添加图片内容
if (StringUtils.isNotBlank(multimodal.getImageData())) {
Content imageContent = new Content();
imageContent.setType("image_url");
ImageUrl imageUrl = new ImageUrl();
// 获取文件扩展名默认为jpg
String fileExtension = "jpg";
if (StringUtils.isNotBlank(multimodal.getImageName())) {
int lastDot = multimodal.getImageName().lastIndexOf('.');
if (lastDot > 0) {
fileExtension = multimodal.getImageName().substring(lastDot + 1).toLowerCase();
}
}
// 转换图片为base64
String base64String = convertToBase64(multimodal.getImageData());
imageUrl.setUrl("data:image/" + fileExtension + ";base64," + base64String);
imageContent.setImageUrl(imageUrl);
contents.add(imageContent);
}
// 构建消息
Message message = new Message();
message.setRole(StringUtils.isNotBlank(multimodal.getRole()) ? multimodal.getRole() : "user");
message.setContent(contents);
// 设置max_tokens默认300
request.setMaxTokens(multimodal.getMaxTokens() > 0 ? multimodal.getMaxTokens() : 300);
request.setMessages(Collections.singletonList(message));
return request;
}
private ChatCompletionResponse sendRequest(ChatCompletionRequest request) throws IOException {
MultimodalWebSocketHandler webSocketHandler = new MultimodalWebSocketHandler();
String requestBody;
try {
requestBody = objectMapper.writeValueAsString(request);
} catch (JsonProcessingException e) {
throw new IOException("请求体序列化失败", e);
}
Request httpRequest = new Request.Builder()
.url(baseUrl + multimodalPath)
.post(RequestBody.create(requestBody, MediaType.parse("application/json")))
.addHeader("Authorization", authKey)
.addHeader("Content-Type", "application/json")
.build();
try (Response response = httpClient.newCall(httpRequest).execute()) {
if (!response.isSuccessful()) {
String errorBody = response.body() != null ? response.body().string() : "无响应体";
throw new IOException(String.format("请求失败,状态码: %d,错误信息: %s", response.code(), errorBody));
}
String responseBody = response.body().string();
System.out.println("多模态API响应内容: " + responseBody);
// 发送WebSocket通知
webSocketHandler.broadcast(responseBody);
return objectMapper.readValue(responseBody, ChatCompletionResponse.class);
} catch (SocketTimeoutException e) {
throw new IOException("请求超时,请检查网络连接或增加超时时间", e);
}
}
private String processResponse(ChatCompletionResponse response) {
if (response == null || response.getChoices() == null || response.getChoices().isEmpty()) {
return "未收到有效响应";
}
return java.lang.String.valueOf(response.getChoices().get(0).getMessage().getContent());
}
//调用语义大模型接口
public String semanticsModel(Multimodal multimodal){
// 重试次数
int maxRetries = 3;
int attempt = 0;
while (attempt < maxRetries) {
try {
// 构建请求JSON
ChatCompletionRequest request = buildRequestBody(multimodal);
System.out.println("创建json" + request.getClass());
// 发送请求并获取响应
ChatCompletionResponse response = semanticsModelResponse(request);
String content = String.valueOf(response.getChoices().get(0).getMessage().getContent());
System.out.println("语义大模型返回结果:"+content);
return content;
} catch (IOException e) {
if (attempt == maxRetries) {
return "请求超时,请稍后重试";
}
System.out.println("第" + attempt + "次尝试超时,准备重试...");
try {
Thread.sleep(1000 * attempt); // 指数退避
} catch (InterruptedException ie) {
Thread.currentThread().interrupt();
}
}
}
return "请求处理失败";
}
private ChatCompletionRequest buildRequestBody(Multimodal multimodal) {
ChatCompletionRequest request = new ChatCompletionRequest();
// 设置模型名称默认"SGGM-VL-74B-V1.2"
request.setModel(multimodal.getModel() != null ? multimodal.getModel() : "SGGM-VL-74B-V1.2");
// 构建消息
Message message = new Message();
message.setRole(StringUtils.isNotBlank(multimodal.getRole()) ? multimodal.getRole() : "user");
message.setContent(multimodal.getText());
request.setMessages(Collections.singletonList(message));
return request;
}
private ChatCompletionResponse semanticsModelResponse(ChatCompletionRequest request) throws IOException {
String requestBody;
try {
requestBody = objectMapper.writeValueAsString(request);
} catch (JsonProcessingException e) {
throw new IOException("请求体序列化失败", e);
}
Request httpRequest = new Request.Builder()
.url(baseUrl + semanticsModalPath)
.post(RequestBody.create(requestBody, MediaType.parse("application/json")))
.addHeader("Authorization", "Bearer "+authKey)
.addHeader("Content-Type", "application/json")
.build();
try (Response response = httpClient.newCall(httpRequest).execute()) {
if (!response.isSuccessful()) {
String errorBody = response.body() != null ? response.body().string() : "无响应体";
throw new IOException(String.format("请求失败,状态码: %d,错误信息: %s", response.code(), errorBody));
}
String responseBody = response.body().string();
System.out.println("语义大模型API响应内容: " + responseBody);
return objectMapper.readValue(responseBody, ChatCompletionResponse.class);
} catch (SocketTimeoutException e) {
throw new IOException("请求超时,请检查网络连接或增加超时时间", e);
}
}
/**
*获取根目录下当前日期的所有图片
*/
public List<String> enquire() {
String currentDatePath = getCurrentDatePath();
// 获取日期目录下所有图片
List<String> allImages = getAllImagesUnderDateDir(baseDirectory, currentDatePath);
return allImages;
}
/**
* 获取当前日期的文件夹路径格式//
* @return 格式化的日期路径字符串
*/
private static String getCurrentDatePath() {
SimpleDateFormat sdf = new SimpleDateFormat("yyyy/MM/dd");
return sdf.format(new Date());
}
/**
* 获取指定日期目录下所有子目录中的图片文件路径
* @param baseDir 基础目录路径
* @param datePath 日期路径格式yyyy/MM/dd
* @return 包含基础目录的完整图片路径列表
*/
public static List<String> getAllImagesUnderDateDir(String baseDir, String datePath) {
List<String> imagePaths = new ArrayList<>();
Path dateDirPath = Paths.get(baseDir, datePath);
// 检查日期目录是否存在
if (!Files.exists(dateDirPath)) {
System.out.println("日期目录不存在: " + dateDirPath);
return imagePaths;
}
try (Stream<Path> walk = Files.walk(dateDirPath)) {
imagePaths = walk
.filter(Files::isRegularFile)
.filter(path -> isImageFile(path.getFileName().toString()))
.map(path -> path.toString().replace("\\", "/"))
.collect(Collectors.toList());
} catch (IOException e) {
System.err.println("遍历目录时出错: " + e.getMessage());
}
return imagePaths;
}
/**
* 检查文件是否是图片文件
* @param fileName 文件名
* @return 是否是图片文件
*/
private static boolean isImageFile(String fileName) {
String lowerFileName = fileName.toLowerCase();
return IMAGE_EXTENSIONS.stream()
.anyMatch(lowerFileName::endsWith);
}
private static final int DEFAULT_THREADS = 5;
private static final int DEFAULT_TIMEOUT = 10000; // 10秒超时
public void downImg() {
List<String> imageUrls = visualModelMapper.selectImgUrl();
batchDownloadImages(imageUrls, "C:\\Users\\王寻\\Desktop\\1111\\大模型\\模型图片集", DEFAULT_THREADS, DEFAULT_TIMEOUT);
}
}

+ 17
- 0
src/main/java/com/mortal/bigmodelr/service/remote/AnalysisRemoteService.java View File

@ -0,0 +1,17 @@
package com.mortal.bigmodelr.service.remote;
import com.mortal.bigmodelr.domain.algorithm.out.AnalyseResult;
import com.mortal.bigmodelr.domain.analysis.vo.AnalysisResultEntity;
import retrofit2.Call;
import retrofit2.http.Body;
import retrofit2.http.POST;
public interface AnalysisRemoteService {
@POST("picAnalyseRetNotify")
Call<Object> analysisResultNotify(@Body AnalysisResultEntity analysisResultEntity);
@POST("picAnalyseRetNotify")
Call<Object> picAnalyseRetNotify(@Body AnalyseResult analyseResult);
}

+ 42
- 0
src/main/java/com/mortal/bigmodelr/service/remote/impl/AnalysisRemoteServiceImpl.java View File

@ -0,0 +1,42 @@
package com.mortal.bigmodelr.service.remote.impl;
import com.mortal.bigmodelr.domain.algorithm.out.AnalyseResult;
import com.mortal.bigmodelr.domain.analysis.vo.AnalysisResultEntity;
import com.mortal.bigmodelr.service.remote.AnalysisRemoteService;
import lombok.EqualsAndHashCode;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.stereotype.Service;
import retrofit2.Call;
import retrofit2.Retrofit;
import javax.annotation.PostConstruct;
@EqualsAndHashCode
@Service
public class AnalysisRemoteServiceImpl implements AnalysisRemoteService {
private final Retrofit retrofit;
private AnalysisRemoteService analysisRemoteService;
public AnalysisRemoteServiceImpl(@Qualifier("RetrofitOfAnalysis") Retrofit retrofit) {
this.retrofit = retrofit;
}
@PostConstruct
public void setup() {
analysisRemoteService = retrofit.create(AnalysisRemoteService.class);
}
@Override
public Call<Object> analysisResultNotify(AnalysisResultEntity analysisResultEntity) {
return analysisRemoteService.analysisResultNotify(analysisResultEntity);
}
@Override
public Call<Object> picAnalyseRetNotify(AnalyseResult analyseResult) {
return analysisRemoteService.picAnalyseRetNotify(analyseResult);
}
}

+ 45
- 0
src/main/java/com/mortal/bigmodelr/task/ModelTask.java View File

@ -0,0 +1,45 @@
package com.mortal.bigmodelr.task;
import com.mortal.bigmodelr.domain.Multimodal;
import com.mortal.bigmodelr.service.ModelService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import javax.annotation.Resource;
import java.util.List;
@Component
public class ModelTask {
@Resource
private ModelService modelService;
//每天18点执行对当天的图片询问多模态大模型
// @Scheduled(cron = "0 0 18 * * ?")
public void runJob() {
// {
// "role": "user",
// "imageType": "image_url",
// "imageData": "/home/atia/bigModel/124.jpg",
// "model": "rsv-0zygizvz",
// "text": "这张图片存在什么问题缺陷吗?",
// "imageName": "121.jpg",
// "maxTokens": 300
// }
//获取基本目录下当前日期的所有图片
List<String> enquire = modelService.enquire();
for (int i = 0; i < enquire.size(); i++) {
Multimodal multimodal=new Multimodal();
multimodal.setRole("user");
multimodal.setImageType("image_url");
multimodal.setText("这张图片存在什么问题缺陷吗");
multimodal.setImageData(enquire.get(i));
//询问多模态大模型
modelService.Multimodal(multimodal);
}
}
}

+ 146
- 0
src/main/java/com/mortal/bigmodelr/test/BatchImageDownloader.java View File

@ -0,0 +1,146 @@
package com.mortal.bigmodelr.test;
import com.mortal.bigmodelr.mapper.visualModelMapper;
import javax.annotation.Resource;
import java.io.*;
import java.net.*;
import java.nio.file.*;
import java.util.*;
import java.util.concurrent.*;
//批量缺陷图片下载
public class BatchImageDownloader {
/**
* 批量下载图片
* @param imageUrls 图片URL列表
* @param saveDir 本地保存目录
* @param threadCount 线程数
* @param timeout 超时时间(毫秒)
*/
public static void batchDownloadImages(List<String> imageUrls, String saveDir,
int threadCount, int timeout) {
// 创建线程池
ExecutorService executor = Executors.newFixedThreadPool(threadCount);
List<Future<DownloadResult>> futures = new ArrayList<>();
try {
// 创建保存目录
Path dirPath = Paths.get(saveDir);
if (!Files.exists(dirPath)) {
Files.createDirectories(dirPath);
}
// 提交下载任务
for (String url : imageUrls) {
Future<DownloadResult> future = executor.submit(() -> {
try {
String fileName = extractFileName(url);
Path savePath = dirPath.resolve(fileName);
return downloadSingleImage(url, savePath.toString(), timeout);
} catch (Exception e) {
return new DownloadResult(url, false, e.getMessage());
}
});
futures.add(future);
}
// 统计结果
int successCount = 0;
for (Future<DownloadResult> future : futures) {
DownloadResult result = future.get();
if (result.success) {
successCount++;
System.out.printf("下载成功: %s -> %s%n", result.url, result.message);
} else {
System.err.printf("下载失败: %s, 原因: %s%n", result.url, result.message);
}
}
System.out.printf("批量下载完成! 成功: %d, 失败: %d%n",
successCount, imageUrls.size() - successCount);
} catch (Exception e) {
System.err.println("批量下载出错: " + e.getMessage());
} finally {
executor.shutdown();
}
}
/**
* 下载单个图片
*/
private static DownloadResult downloadSingleImage(String imageUrl, String savePath, int timeout)
throws IOException {
HttpURLConnection conn = null;
try {
URL url = new URL(imageUrl);
conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
conn.setConnectTimeout(timeout);
conn.setReadTimeout(timeout);
// 检查响应码
int responseCode = conn.getResponseCode();
if (responseCode != HttpURLConnection.HTTP_OK) {
return new DownloadResult(imageUrl, false,
"HTTP错误码: " + responseCode);
}
// 获取文件类型
String contentType = conn.getContentType();
if (!contentType.startsWith("image/")) {
return new DownloadResult(imageUrl, false,
"不是图片类型: " + contentType);
}
// 下载文件
try (InputStream in = conn.getInputStream()) {
Files.copy(in, Paths.get(savePath), StandardCopyOption.REPLACE_EXISTING);
return new DownloadResult(imageUrl, true, savePath);
}
} finally {
if (conn != null) conn.disconnect();
}
}
/**
* 从URL提取文件名
*/
private static String extractFileName(String url) {
String fileName = url.substring(url.lastIndexOf('/') + 1);
if (fileName.isEmpty()) {
fileName = "image_" + System.currentTimeMillis() + ".jpg";
}
// 移除URL参数
if (fileName.contains("?")) {
fileName = fileName.substring(0, fileName.indexOf('?'));
}
return fileName;
}
/**
* 下载结果封装类
*/
private static class DownloadResult {
String url;
boolean success;
String message;
DownloadResult(String url, boolean success, String message) {
this.url = url;
this.success = success;
this.message = message;
}
}
// public static void main(String[] args) {
// List<String> imageUrls = visualModelMapper.selectImgUrl();
//
// batchDownloadImages(imageUrls, "C:\\Users\\王寻\\Desktop\\1111\\大模型\\模型图片集", DEFAULT_THREADS, DEFAULT_TIMEOUT);
// }
}

+ 159
- 0
src/main/java/com/mortal/bigmodelr/utils/AjaxResult.java View File

@ -0,0 +1,159 @@
package com.mortal.bigmodelr.utils;
import java.util.HashMap;
/**
* 操作消息提醒
*/
public class AjaxResult extends HashMap<String, Object>
{
private static final long serialVersionUID = 1L;
/** 状态码 */
public static final String CODE_TAG = "code";
/** 返回内容 */
public static final String MSG_TAG = "msg";
/** 数据对象 */
public static final String DATA_TAG = "data";
/**
* 初始化一个新创建的 AjaxResult 对象使其表示一个空消息
*/
public AjaxResult()
{
}
/**
* 初始化一个新创建的 AjaxResult 对象
*
* @param code 状态码
* @param msg 返回内容
*/
public AjaxResult(int code, String msg)
{
super.put(CODE_TAG, code);
super.put(MSG_TAG, msg);
}
/**
* 初始化一个新创建的 AjaxResult 对象
*
* @param code 状态码
* @param msg 返回内容
* @param data 数据对象
*/
public AjaxResult(int code, String msg, Object data)
{
super.put(CODE_TAG, code);
super.put(MSG_TAG, msg);
if (StringUtils.isNotNull(data))
{
super.put(DATA_TAG, data);
}
}
/**
* 返回成功消息
*
* @return 成功消息
*/
public static AjaxResult success()
{
return AjaxResult.success("操作成功");
}
/**
* 返回成功数据
*
* @return 成功消息
*/
public static AjaxResult success(Object data)
{
return AjaxResult.success("操作成功", data);
}
/**
* 返回成功消息
*
* @param msg 返回内容
* @return 成功消息
*/
public static AjaxResult success(String msg)
{
return AjaxResult.success(msg, null);
}
/**
* 返回成功消息
*
* @param msg 返回内容
* @param data 数据对象
* @return 成功消息
*/
public static AjaxResult success(String msg, Object data)
{
return new AjaxResult(HttpStatus.SUCCESS, msg, data);
}
/**
* 返回错误消息
*
* @return
*/
public static AjaxResult error()
{
return AjaxResult.error("操作失败");
}
/**
* 返回错误消息
*
* @param msg 返回内容
* @return 警告消息
*/
public static AjaxResult error(String msg)
{
return AjaxResult.error(msg, null);
}
/**
* 返回错误消息
*
* @param msg 返回内容
* @param data 数据对象
* @return 警告消息
*/
public static AjaxResult error(String msg, Object data)
{
return new AjaxResult(HttpStatus.ERROR, msg, data);
}
/**
* 返回错误消息
*
* @param code 状态码
* @param msg 返回内容
* @return 警告消息
*/
public static AjaxResult error(int code, String msg)
{
return new AjaxResult(code, msg, null);
}
/**
* 方便链式调用
*
* @param key
* @param value
* @return 数据对象
*/
@Override
public AjaxResult put(String key, Object value)
{
super.put(key, value);
return this;
}
}

+ 90
- 0
src/main/java/com/mortal/bigmodelr/utils/HttpStatus.java View File

@ -0,0 +1,90 @@
package com.mortal.bigmodelr.utils;
/**
* 返回状态码
*
* @author ruoyi
*/
public class HttpStatus
{
/**
* 操作成功
*/
public static final int SUCCESS = 200;
/**
* 对象创建成功
*/
public static final int CREATED = 201;
/**
* 请求已经被接受
*/
public static final int ACCEPTED = 202;
/**
* 操作已经执行成功但是没有返回数据
*/
public static final int NO_CONTENT = 204;
/**
* 资源已被移除
*/
public static final int MOVED_PERM = 301;
/**
* 重定向
*/
public static final int SEE_OTHER = 303;
/**
* 资源没有被修改
*/
public static final int NOT_MODIFIED = 304;
/**
* 参数列表错误缺少格式不匹配
*/
public static final int BAD_REQUEST = 400;
/**
* 未授权
*/
public static final int UNAUTHORIZED = 401;
/**
* 访问受限授权过期
*/
public static final int FORBIDDEN = 403;
/**
* 资源服务未找到
*/
public static final int NOT_FOUND = 404;
/**
* 不允许的http方法
*/
public static final int BAD_METHOD = 405;
/**
* 资源冲突或者资源被锁
*/
public static final int CONFLICT = 409;
/**
* 不支持的数据媒体类型
*/
public static final int UNSUPPORTED_TYPE = 415;
/**
* 系统内部错误
*/
public static final int ERROR = 500;
/**
* 接口未实现
*/
public static final int NOT_IMPLEMENTED = 501;
}

+ 353
- 0
src/main/java/com/mortal/bigmodelr/utils/StringUtils.java View File

@ -0,0 +1,353 @@
package com.mortal.bigmodelr.utils;
import cn.hutool.core.text.StrFormatter;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.text.StrBuilder;
import java.nio.ByteBuffer;
import java.nio.CharBuffer;
import java.nio.charset.Charset;
import java.util.Collection;
import java.util.Map;
/**
* 字符串工具类
*/
public class StringUtils extends org.apache.commons.lang3.StringUtils {
/**
* 空字符串
*/
private static final String NULLSTR = "";
/**
* 下划线
*/
private static final char SEPARATOR = '_';
/**
* 获取参数不为空值
*
* @param value defaultValue 要判断的value
* @return value 返回值
*/
public static <T> T nvl(T value, T defaultValue) {
return value != null ? value : defaultValue;
}
/**
* * 判断一个Collection是否为空 包含ListSetQueue
*
* @param coll 要判断的Collection
* @return true为空 false非空
*/
public static boolean isEmpty(Collection<?> coll) {
return isNull(coll) || coll.isEmpty();
}
/**
* * 判断一个Collection是否非空包含ListSetQueue
*
* @param coll 要判断的Collection
* @return true非空 false
*/
public static boolean isNotEmpty(Collection<?> coll) {
return !isEmpty(coll);
}
/**
* * 判断一个对象数组是否为空
*
* @param objects 要判断的对象数组
* * @return true为空 false非空
*/
public static boolean isEmpty(Object[] objects) {
return isNull(objects) || (objects.length == 0);
}
/**
* * 判断一个对象数组是否非空
*
* @param objects 要判断的对象数组
* @return true非空 false
*/
public static boolean isNotEmpty(Object[] objects) {
return !isEmpty(objects);
}
/**
* * 判断一个Map是否为空
*
* @param map 要判断的Map
* @return true为空 false非空
*/
public static boolean isEmpty(Map<?, ?> map) {
return isNull(map) || map.isEmpty();
}
/**
* * 判断一个Map是否为空
*
* @param map 要判断的Map
* @return true非空 false
*/
public static boolean isNotEmpty(Map<?, ?> map) {
return !isEmpty(map);
}
/**
* * 判断一个字符串是否为空串
*
* @param str String
* @return true为空 false非空
*/
public static boolean isEmpty(String str) {
return isNull(str) || NULLSTR.equals(str.trim());
}
/**
* * 判断一个字符串是否为非空串
*
* @param str String
* @return true非空串 false空串
*/
public static boolean isNotEmpty(String str) {
return !isEmpty(str);
}
/**
* * 判断一个对象是否为空
*
* @param object Object
* @return true为空 false非空
*/
public static boolean isNull(Object object) {
return object == null;
}
/**
* * 判断一个对象是否非空
*
* @param object Object
* @return true非空 false
*/
public static boolean isNotNull(Object object) {
return !isNull(object);
}
/**
* * 判断一个对象是否是数组类型Java基本型别的数组
*
* @param object 对象
* @return true是数组 false不是数组
*/
public static boolean isArray(Object object) {
return isNotNull(object) && object.getClass().isArray();
}
/**
* 去空格
*/
public static String trim(String str) {
return (str == null ? "" : str.trim());
}
/**
* 截取字符串
*
* @param str 字符串
* @param start 开始
* @return 结果
*/
public static String substring(final String str, int start) {
if (str == null) {
return NULLSTR;
}
if (start < 0) {
start = str.length() + start;
}
if (start < 0) {
start = 0;
}
if (start > str.length()) {
return NULLSTR;
}
return str.substring(start);
}
/**
* 截取字符串
*
* @param str 字符串
* @param start 开始
* @param end 结束
* @return 结果
*/
public static String substring(final String str, int start, int end) {
if (str == null) {
return NULLSTR;
}
if (end < 0) {
end = str.length() + end;
}
if (start < 0) {
start = str.length() + start;
}
if (end > str.length()) {
end = str.length();
}
if (start > end) {
return NULLSTR;
}
if (start < 0) {
start = 0;
}
if (end < 0) {
end = 0;
}
return str.substring(start, end);
}
/**
* 格式化文本, {} 表示占位符<br>
* 此方法只是简单将占位符 {} 按照顺序替换为参数<br>
* 如果想输出 {} 使用 \\转义 { 即可如果想输出 {} 之前的 \ 使用双转义符 \\\\ 即可<br>
* <br>
* 通常使用format("this is {} for {}", "a", "b") -> this is a for b<br>
* 转义{} format("this is \\{} for {}", "a", "b") -> this is \{} for a<br>
* 转义\ format("this is \\\\{} for {}", "a", "b") -> this is \a for b<br>
*
* @param template 文本模板被替换的部分用 {} 表示
* @param params 参数值
* @return 格式化后的文本
*/
public static String format(String template, Object... params) {
if (isEmpty(params) || isEmpty(template)) {
return template;
}
return StrFormatter.format(template, params);
}
/**
* 驼峰首字符小写
*/
public static String uncapitalize(String str) {
int strLen;
if (str == null || (strLen = str.length()) == 0) {
return str;
}
return new StrBuilder(strLen).append(Character.toLowerCase(str.charAt(0))).append(str.substring(1)).toString();
}
/**
* 下划线转驼峰命名
*/
public static String toUnderScoreCase(String s) {
if (s == null) {
return null;
}
StringBuilder sb = new StringBuilder();
boolean upperCase = false;
for (int i = 0; i < s.length(); i++) {
char c = s.charAt(i);
boolean nextUpperCase = true;
if (i < (s.length() - 1)) {
nextUpperCase = Character.isUpperCase(s.charAt(i + 1));
}
if ((i > 0) && Character.isUpperCase(c)) {
if (!upperCase || !nextUpperCase) {
sb.append(SEPARATOR);
}
upperCase = true;
} else {
upperCase = false;
}
sb.append(Character.toLowerCase(c));
}
return sb.toString();
}
/**
* 是否包含字符串
*
* @param str 验证字符串
* @param strs 字符串组
* @return 包含返回true
*/
public static boolean inStringIgnoreCase(String str, String... strs) {
if (str != null && strs != null) {
for (String s : strs) {
if (str.equalsIgnoreCase(trim(s))) {
return true;
}
}
}
return false;
}
/**
* 将下划线大写方式命名的字符串转换为驼峰式如果转换前的下划线大写方式命名的字符串为空则返回空字符串 例如HELLO_WORLD->HelloWorld
*
* @param name 转换前的下划线大写方式命名的字符串
* @return 转换后的驼峰式命名的字符串
*/
public static String convertToCamelCase(String name) {
StringBuilder result = new StringBuilder();
// 快速检查
if (name == null || name.isEmpty()) {
// 没必要转换
return "";
} else if (!name.contains("_")) {
// 不含下划线仅将首字母大写
return name.substring(0, 1).toUpperCase() + name.substring(1);
}
// 用下划线将原始字符串分割
String[] camels = name.split("_");
for (String camel : camels) {
// 跳过原始字符串中开头结尾的下换线或双重下划线
if (camel.isEmpty()) {
continue;
}
// 首字母大写
result.append(camel.substring(0, 1).toUpperCase());
result.append(camel.substring(1).toLowerCase());
}
return result.toString();
}
public static String getRandomString(Integer length) {
return RandomStringUtils.randomAlphanumeric(length);
}
/**校验是否存在字符串,不存在返回空字符*/
public static String getString(Object obj){
if(obj == null || obj.equals("null") || obj.equals("")){
return "";
}
return obj.toString();
}
public static String bytetoString(byte[] bs,String charsetName){
//确定编码格式
Charset charset = Charset.forName(charsetName);
ByteBuffer buf = ByteBuffer.wrap(bs);
CharBuffer cBuf = charset.decode(buf);
return cBuf.toString();
}
}

+ 113
- 0
src/main/resources/application-local.yml View File

@ -0,0 +1,113 @@
# 项目相关配置
lightiot:
# 名称
name: lightiots
# 版本
version: 3.0.0
# 版权年份
copyrightYear: 2018
# 文件上传路径
profile: D:/profile/
# 获取ip地址开关
addressEnabled: true
# 开发环境配置
server:
# 服务端口
port: 8080
servlet:
# 项目contextPath
context-path: /
tomcat:
# tomcat的URI编码
uri-encoding: UTF-8
# tomcat最大线程数,默认为200
max-threads: 800
# Tomcat启动初始化的线程数,默认值25
min-spare-threads: 30
# 日志配置
logging:
level:
com.lightiot: debug
org.springframework: WARN
org.spring.springboot.dao: debug
# 用户配置
user:
password:
# 密码错误{maxRetryCount}次锁定10分钟
maxRetryCount: 5
# Spring配置
spring:
resources:
cache:
period: 0
static-locations: classpath:/static/
# 模板引擎
thymeleaf:
mode: HTML
encoding: utf-8
# 禁用缓存
cache: false
prefix: classpath:/templates/
# 资源信息
messages:
# 国际化资源文件路径
basename: i18n/messages
jackson:
time-zone: GMT+8
date-format: yyyy-MM-dd HH:mm:ss
serialization:
WRITE_DATES_AS_TIMESTAMPS: false
FAIL_ON_EMPTY_BEANS: false
# 文件上传
servlet:
multipart:
max-file-size: 30MB
max-request-size: 30MB
# 临时存放上传文件
location: d:/pic
# 服务模块
devtools:
restart:
# 热部署开关
enabled: true
additional-paths: resources/**
datasource:
druid:
driver-class-name: com.mysql.cj.jdbc.Driver
url: jdbc:mysql://192.168.4.129:4406/inspect?useSSL=false&characterEncoding=utf8&serverTimezone=Asia/Shanghai
username: root
password: atia2018
mybatis:
mapper-locations: classpath:mapper/*.xml
type-aliases-package: com.mortal.bigmodelr.domain
analysis:
api:
url: http://199.199.199.104:9901
token: 01234567890
file:
# 接口地址
baseUrl: http://25.80.45.92:18063
#接口路径
apiPath: /lmp-cloud-ias-server/api/lvm/completions/
multimodalPath: /lmp-cloud-ias-server/api/vlm/chat/completions/
semanticsModalPath: /lmp-cloud-ias-server/api/llm/chat/completions/
#密钥
authKey: 54c1ae2c5fd54afe85e74d6fe9161f7f
model: 591304447029141504
picPath: /home/atia/docker-deploy-encrypt/data/vsftpd/ftpuser/1/2025/06/23/1602/CCD/1602_20250623092918940_2080369_02160558348953680142.jpg
#下载缺陷图片到本地的基础路径
baseDirectory: C:/1111/1

+ 3
- 0
src/main/resources/application.yml View File

@ -0,0 +1,3 @@
spring:
profiles:
active: local

+ 17
- 0
src/main/resources/mapper/multimodalMapper.xml View File

@ -0,0 +1,17 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.mortal.bigmodelr.mapper.multimodalMapper">
<resultMap type="com.mortal.bigmodelr.domain.ChatCompletionResponse" id="ChatCompletionResponseResult">
<result property="picPath" column="pic_path"/>
<result property="info" column="info"/>
<result property="content" column="content"/>
<result property="id" column="data_id"/>
</resultMap>
<insert id="addMultimodalModelInfo" parameterType="com.mortal.bigmodelr.domain.ChatCompletionResponse">
insert into multimodal (info,content,pic_path,data_id) values (#{info},#{content},#{picPath},#{id})
</insert>
</mapper>

+ 28
- 0
src/main/resources/mapper/visualModelMapper.xml View File

@ -0,0 +1,28 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.mortal.bigmodelr.mapper.visualModelMapper">
<insert id="addVisualModelInfo">
insert into visual (info)
<foreach collection="list" item="visualModels" separator="),(" open="values (" close=")">
#{visualModels.stringData}
</foreach>
</insert>
<select id="selectImgUrl" resultType="java.lang.String">
SELECT
CONCAT('http://192.168.4.129:18891/lingzhou/videoMonitor/app/htjc6/htjcImage/', res_img_url) AS full_img_url
FROM
`result_analysis`
WHERE
result_type = 1
GROUP BY
res_img_url;
</select>
</mapper>

+ 13
- 0
src/test/java/com/mortal/bigmodelr/BigModelrApplicationTests.java View File

@ -0,0 +1,13 @@
package com.mortal.bigmodelr;
import org.junit.jupiter.api.Test;
import org.springframework.boot.test.context.SpringBootTest;
@SpringBootTest
class BigModelrApplicationTests {
@Test
void contextLoads() {
}
}

Loading…
Cancel
Save