军标库

This commit is contained in:
2025-09-26 13:46:54 +08:00
parent 26af321271
commit 273fc16f87
24 changed files with 1686 additions and 0 deletions

View File

@ -0,0 +1,395 @@
package com.yj.earth.business.controller;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.lang.UUID;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.yj.earth.annotation.CheckAuth;
import com.yj.earth.business.domain.ModelLibrary;
import com.yj.earth.business.domain.ModelType;
import com.yj.earth.business.service.FileInfoService;
import com.yj.earth.business.service.ModelLibraryService;
import com.yj.earth.common.util.ApiResponse;
import com.yj.earth.common.util.SQLiteUtil;
import com.yj.earth.dto.militaryLibrary.DragMilitaryTypeDto;
import com.yj.earth.dto.modelLibrary.AddModelTypeDto;
import com.yj.earth.dto.modelLibrary.CreateModelLibraryDto;
import com.yj.earth.dto.modelLibrary.DragModelTypeDto;
import com.yj.earth.dto.modelLibrary.UpdateModelTypeNameDto;
import com.yj.earth.vo.ModelTypeVo;
import com.yj.earth.vo.ModelVo;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import javax.annotation.Resource;
import java.io.File;
import java.io.IOException;
import java.sql.SQLException;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;
@Tag(name = "模型库管理")
@CheckAuth
@RestController
@RequestMapping("/modelLibrary")
public class ModelLibraryController {
@Resource
private ModelLibraryService modelLibraryService;
@Resource
private FileInfoService fileInfoService;
@Operation(summary = "创建模型库")
@PostMapping("/createModelLibrary")
public ApiResponse createModelLibrary(@RequestBody CreateModelLibraryDto createModelLibraryDto) {
try {
// 参数校验
String folderPath = createModelLibraryDto.getPath();
String modelName = createModelLibraryDto.getName();
// 处理路径、组合为完整模型库文件路径(.model后缀
File parentDir = new File(folderPath);
File modelFile = new File(parentDir, modelName + ".model");
String modelPath = modelFile.getAbsolutePath().replace("\\", "/");
// 检查父目录是否存在、不存在则创建
if (!parentDir.exists()) {
boolean mkdirsSuccess = parentDir.mkdirs();
if (!mkdirsSuccess) {
return ApiResponse.failure("创建父目录失败:" + folderPath);
}
}
// 检查模型库文件是否已存在
if (modelFile.exists()) {
if (modelFile.isDirectory()) {
return ApiResponse.failure("同名目录已存在、无法创建文件:" + modelPath);
}
return ApiResponse.failure("模型库文件已存在:" + modelPath);
}
// 创建模型库文件(
boolean createSuccess = modelFile.createNewFile();
if (!createSuccess) {
return ApiResponse.failure("创建模型库文件失败:" + modelPath);
}
// 添加模型库信息
addModelLibrary(modelPath);
SQLiteUtil.initializationModel(modelPath);
return ApiResponse.success(null);
} catch (Exception e) {
return ApiResponse.failure("创建模型库失败:" + e.getMessage());
}
}
@Operation(summary = "导入模型库")
@PostMapping("/importModelLibrary")
public ApiResponse importModelLibrary(@RequestParam("modelPath") @Parameter(description = "模型库路径") String modelPath) {
addModelLibrary(modelPath);
return ApiResponse.success(null);
}
@Operation(summary = "添加模型类型")
@PostMapping("/addModelType")
public ApiResponse addModelType(@RequestBody AddModelTypeDto addModelTypeDto) throws SQLException, IllegalAccessException, InstantiationException {
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
// 检查父级是否存在
String parentId = addModelTypeDto.getParentId();
if (parentId != null) {
String sql = "SELECT * FROM model_type WHERE id = ?";
List<Object> params = new ArrayList<>();
params.add(parentId);
ModelType modelType = SQLiteUtil.queryForObject(modelPath, sql, params, ModelType.class);
if (modelType == null) {
return ApiResponse.failure("父级模型类型不存在");
}
}
String sql = "INSERT INTO model_type " +
"(id, name, parent_id, tree_index, created_at) " +
"VALUES (?, ?, ?, ?, ?)";
List<Object> params = new ArrayList<>();
params.add(UUID.fastUUID().toString(true));
params.add(addModelTypeDto.getName());
params.add(addModelTypeDto.getParentId());
params.add(0);
params.add(LocalDateTime.now());
SQLiteUtil.executeUpdate(modelPath, sql, params);
return ApiResponse.success(null);
}
@Operation(summary = "修改模型类型名称")
@PostMapping("/updateModelTypeName")
public ApiResponse updateModelTypeName(@RequestBody UpdateModelTypeNameDto updateModelTypeNameDto) throws SQLException {
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
String sql = "UPDATE model_type SET name = ? WHERE id = ?";
List<Object> params = new ArrayList<>();
params.add(updateModelTypeNameDto.getName());
params.add(updateModelTypeNameDto.getId());
SQLiteUtil.executeUpdate(modelPath, sql, params);
return ApiResponse.success(null);
}
@Operation(summary = "删除模型类型")
@PostMapping("/deleteModelType")
public ApiResponse deleteModelType(@Parameter(description = "模型类型ID") @RequestParam("modelTypeId") String modelTypeId) throws SQLException {
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
String sql = "DELETE FROM model_type WHERE id = ?";
List<Object> params = new ArrayList<>();
params.add(modelTypeId);
SQLiteUtil.executeUpdate(modelPath, sql, params);
return ApiResponse.success(null);
}
@Operation(summary = "模型类型列表")
@GetMapping("/modelTypeList")
public ApiResponse modelTypeTree() throws SQLException, IllegalAccessException, InstantiationException {
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
String sql = """
SELECT id, name, parent_id as parentId,
tree_index as treeIndex, created_at as createdAt,
updated_at as updatedAt FROM model_type ORDER BY tree_index ASC
""";
// 查询所有模型类型
List<ModelType> modelTypes = SQLiteUtil.queryForList(modelPath, sql, null, ModelType.class);
// 转换为树形结构
List<ModelTypeVo> treeList = buildModelTypeTree(modelTypes);
return ApiResponse.success(treeList);
}
@Operation(summary = "拖动模型类型树")
@PostMapping("/dragModelType")
public ApiResponse dragMilitaryType(@RequestBody DragModelTypeDto dragModelTypeDto) throws SQLException {
String militaryPath = getModelLibrary();
if (militaryPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
// 动态构建SQL和参数
List<String> updateFields = new ArrayList<>();
List<Object> params = new ArrayList<>();
// 判断 parentId 是否存在
if (dragModelTypeDto.getParentId() != null) {
updateFields.add("parent_id = ?");
params.add(dragModelTypeDto.getParentId());
}
// 判断 treeIndex 是否存在
if (dragModelTypeDto.getTreeIndex() != null) {
updateFields.add("tree_index = ?");
params.add(dragModelTypeDto.getTreeIndex());
}
// 构建完整 SQL
String sql = "UPDATE model_type SET " + String.join(", ", updateFields) + " WHERE id = ?";
params.add(dragModelTypeDto.getId());
SQLiteUtil.executeUpdate(militaryPath, sql, params);
return ApiResponse.success(null);
}
@Operation(summary = "添加模型文件")
@PostMapping("/addModelFile")
public ApiResponse addModelFile(@RequestParam("files") MultipartFile[] files, @Parameter(description = "模型类型ID") @RequestParam("modelTypeId") String modelTypeId) throws IOException, SQLException {
// 获取最新的模型库路径
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
// 循环处理每个上传的文件
for (MultipartFile file : files) {
// 跳过空文件
if (file.isEmpty()) {
continue;
}
// 获取文件信息
String fileName = file.getOriginalFilename();
if (fileName == null) {
continue;
}
String fileSuffix = FileUtil.extName(fileName);
String fileNameWithoutSuffix = FileUtil.mainName(fileName);
// 构建插入SQL
String sql = "INSERT INTO model " +
"(id, model_type_id, model_name, model_type, data, created_at) " +
"VALUES (?, ?, ?, ?, ?, ?)";
String url = fileInfoService.uploadWithPreview(file);
List<Object> params = new ArrayList<>();
params.add(UUID.fastUUID().toString(true));
params.add(modelTypeId);
params.add(fileNameWithoutSuffix);
params.add(fileSuffix);
params.add(url);
params.add(LocalDateTime.now());
// 执行插入操作
SQLiteUtil.executeUpdate(modelPath, sql, params);
}
return ApiResponse.success(null);
}
@Operation(summary = "根据模型类型查看模型列表")
@PostMapping("/modelList")
public ApiResponse modelList(@Parameter(description = "模型类型ID") @RequestParam("modelTypeId") String modelTypeId) throws SQLException, IllegalAccessException, InstantiationException {
// 获取最新的模型库
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
// 多表联查、查询所有的模型
String sql = """
SELECT
model.id,
model.model_type_id as modelTypeId,
model.model_name as modelName,
model.model_type as modelType,
model.poster_type as posterType,
model.poster,
model.data,
model.view,
model.created_at as createdAt,
model.updated_at as updatedAt,
model_type.name as modelTypeName from
model JOIN model_type ON model.model_type_id = model_type.id
WHERE model.model_type_id = ?
""";
List<Object> params = new ArrayList<>();
params.add(modelTypeId);
List<ModelVo> modelVos = SQLiteUtil.queryForList(modelPath, sql, params, ModelVo.class);
return ApiResponse.success(modelVos);
}
@Operation(summary = "更新模型信息")
@PostMapping("/uploadModelInfo")
public ApiResponse uploadModelInfo(@Parameter(description = "模型封面文件") @RequestParam(value = "file", required = false) MultipartFile file, @Parameter(description = "模型ID") @RequestParam("modelId") String modelId, @Parameter(description = "模型名称") @RequestParam(value = "modelName", required = false) String modelName) throws IOException, SQLException {
// 获取最新的模型库路径
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
// 动态构建SQL更新语句和参数
StringBuilder sql = new StringBuilder("UPDATE model SET updated_at = ? ");
List<Object> params = new ArrayList<>();
// 始终更新时间
params.add(LocalDateTime.now());
// 处理封面文件
if (file != null && !file.isEmpty()) {
String fileSuffix = FileUtil.extName(file.getOriginalFilename());
String url = fileInfoService.uploadWithPreview(file);
sql.append(", poster_type = ?, poster = ? ");
params.add(fileSuffix);
params.add(url);
}
// 处理模型名称
if (StringUtils.hasText(modelName)) {
sql.append(", model_name = ? ");
params.add(modelName);
}
// 拼接WHERE条件
sql.append("WHERE id = ?");
params.add(modelId);
// 执行更新
SQLiteUtil.executeUpdate(modelPath, sql.toString(), params);
return ApiResponse.success(null);
}
@Operation(summary = "删除模型")
@PostMapping("/deleteModel")
public ApiResponse deleteModel(@Parameter(description = "模型ID") @RequestParam("modelId") String modelId) throws SQLException {
String modelPath = getModelLibrary();
if (modelPath == null) {
return ApiResponse.failure("请先创建或导入模型库");
}
String sql = "DELETE FROM model WHERE id = ?";
List<Object> params = new ArrayList<>();
params.add(modelId);
SQLiteUtil.executeUpdate(modelPath, sql, params);
return ApiResponse.success(null);
}
private List<ModelTypeVo> buildModelTypeTree(List<ModelType> modelTypes) {
List<ModelTypeVo> treeNodes = modelTypes.stream()
.map(modelType -> new ModelTypeVo(modelType))
.collect(Collectors.toList());
// 构建节点ID到节点的映射
Map<String, ModelTypeVo> nodeMap = treeNodes.stream()
.collect(Collectors.toMap(ModelTypeVo::getId, node -> node));
// 根节点列表
List<ModelTypeVo> rootNodes = new ArrayList<>();
// 为每个节点添加子节点
for (ModelTypeVo node : treeNodes) {
String parentId = node.getParentId();
if (parentId == null || parentId.isEmpty()) {
// 没有父节点的是根节点
rootNodes.add(node);
} else {
// 找到父节点并添加为子节点
ModelTypeVo parentNode = nodeMap.get(parentId);
if (parentNode != null) {
parentNode.getChildren().add(node);
}
}
}
return rootNodes;
}
private String getModelLibrary() {
// 获取启用的模型库
LambdaQueryWrapper<ModelLibrary> queryWrapper = new LambdaQueryWrapper<>();
queryWrapper.eq(ModelLibrary::getIsEnable, 1);
ModelLibrary modelLibrary = modelLibraryService.getOne(queryWrapper);
if (modelLibrary == null) {
return null;
}
return modelLibrary.getPath();
}
private void addModelLibrary(String modelPath) {
// 查询系统所有的模型库
List<ModelLibrary> modelLibraries = modelLibraryService.list();
// 遍历并更新状态
for (ModelLibrary modelLibrary : modelLibraries) {
// 设置启用状态为0
modelLibrary.setIsEnable(0);
modelLibraryService.updateById(modelLibrary);
}
// 检查相同路径的模型库是否已存在
LambdaQueryWrapper<ModelLibrary> pathWrapper = new LambdaQueryWrapper<>();
pathWrapper.eq(ModelLibrary::getPath, modelPath);
ModelLibrary existingModel = modelLibraryService.getOne(pathWrapper);
// 若存在相同路径的模型库、不做处理、仅仅更新状态为显示
if (existingModel != null) {
existingModel.setIsEnable(1);
modelLibraryService.updateById(existingModel);
return;
} else {
// 新增模型库
ModelLibrary newModel = new ModelLibrary();
File file = FileUtil.file(modelPath);
newModel.setId(UUID.fastUUID().toString(true));
newModel.setPath(modelPath);
newModel.setName(FileUtil.extName(file));
newModel.setIsEnable(1);
modelLibraryService.save(newModel);
}
}
}