Merge remote-tracking branch 'origin/master'

# Conflicts:
#	ruoyi-modules/hwmom-qms/src/main/java/org/dromara/qms/service/impl/QcInspectionMainServiceImpl.java
#	ruoyi-modules/hwmom-qms/src/main/java/org/dromara/qms/service/impl/QcUnqualifiedReviewServiceImpl.java
master
wanghao 5 months ago
commit eeebfdae3b

@ -186,7 +186,7 @@
<version>2.2.2</version>
<scope>compile</scope>
<exclusions>
<!-- 排除消息总线依赖DMS模块不需要 -->
<!-- 排除消息总线依赖DMS模块不需要否则会一直引入本地的Kafka -->
<exclusion>
<groupId>org.dromara</groupId>
<artifactId>ruoyi-common-bus</artifactId>

@ -117,6 +117,7 @@
<version>2.2.2</version>
<scope>compile</scope>
</dependency>
<!-- <dependency>-->
<!-- <groupId>com.microsoft.sqlserver</groupId>-->
<!-- <artifactId>mssql-jdbc</artifactId>-->
@ -128,6 +129,29 @@
<!-- </dependency>-->
<dependency>
<groupId>org.dromara</groupId>
<artifactId>hwmom-api-workflow</artifactId>
<version>2.2.2</version>
<scope>compile</scope>
<exclusions>
<!-- 排除消息总线依赖QMS模块不需要,否则会一直引入本地的Kafka -->
<exclusion>
<groupId>org.dromara</groupId>
<artifactId>ruoyi-common-bus</artifactId>
</exclusion>
</exclusions>
</dependency>
<!--通过 Dubbo 远程调用 workflow 服务的 completeTask 方法时。
原因分析:该调用是在一个由 CompletableFuture.runAsync() 创建的异步线程中执行的。在 ruoyi-cloud-plus (以及类似的微服务架构) 中,用户认证信息(如 Sa-Token通常是存储在 ThreadLocal 变量中的,它与当前请求线程绑定。当您创建一个新的子线程时,父线程的 ThreadLocal 变量默认不会传递给子线程。因此在异步线程中Sa-Token 的上下文丢失,导致 StpUtil.getTokenValue() 等方法无法获取到 token当 Dubbo 客户端过滤器尝试将 token 放入 RPC 上下文时失败,或者说,在 workflow 服务端Sa-Token 的服务端过滤器无法从 RPC 上下文中获取到 token最终导致依赖用户身份认证的 FlwTaskServiceImpl.completeTask 方法抛出 "未能读取到有效 token" 的业务异常。
解决方案ruoyi-cloud-plus 框架集成了阿里巴巴的 TransmittableThreadLocal (TTL) 库来解决此问题。TTL可以实现父子线程之间的 ThreadLocal 数据传递。为了让 CompletableFuture 与 TTL 协同工作,需要将提交给它的 Runnable 或 Callable 任务用 TtlRunnable 或 TtlCallable 进行包装。这样在任务执行前TTL 会捕获父线程的上下文(包括 Sa-Token 的信息),并在子线程中恢复它。-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>transmittable-thread-local</artifactId>
<version>2.14.4</version>
</dependency>
</dependencies>
<build>

@ -0,0 +1,117 @@
package org.dromara.qms.controller;
import java.util.List;
import lombok.RequiredArgsConstructor;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.*;
import cn.dev33.satoken.annotation.SaCheckPermission;
import org.springframework.web.bind.annotation.*;
import org.springframework.validation.annotation.Validated;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.web.core.BaseController;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.qms.domain.vo.QcInspectionMainFileRelationVo;
import org.dromara.qms.domain.bo.QcInspectionMainFileRelationBo;
import org.dromara.qms.service.IQcInspectionMainFileRelationService;
import org.dromara.common.mybatis.core.page.TableDataInfo;
/**
*
* 访:/qms/qcInspectionMainFileRelation
*
* @author zch
* @date 2025-07-31
*/
@Validated
@RequiredArgsConstructor
@RestController
@RequestMapping("/qcInspectionMainFileRelation")
public class QcInspectionMainFileRelationController extends BaseController {
private final IQcInspectionMainFileRelationService qcInspectionMainFileRelationService;
/**
*
*/
@SaCheckPermission("qms:qcInspectionMainFileRelation:list")
@GetMapping("/list")
public TableDataInfo<QcInspectionMainFileRelationVo> list(QcInspectionMainFileRelationBo bo, PageQuery pageQuery) {
return qcInspectionMainFileRelationService.queryPageList(bo, pageQuery);
}
/**
*
*/
@SaCheckPermission("qms:qcInspectionMainFileRelation:export")
@Log(title = "质检任务文件关系", businessType = BusinessType.EXPORT)
@PostMapping("/export")
public void export(QcInspectionMainFileRelationBo bo, HttpServletResponse response) {
List<QcInspectionMainFileRelationVo> list = qcInspectionMainFileRelationService.queryList(bo);
ExcelUtil.exportExcel(list, "质检任务文件关系", QcInspectionMainFileRelationVo.class, response);
}
/**
*
*
* @param relationId
*/
@SaCheckPermission("qms:qcInspectionMainFileRelation:query")
@GetMapping("/{relationId}")
public R<QcInspectionMainFileRelationVo> getInfo(@NotNull(message = "主键不能为空")
@PathVariable Long relationId) {
return R.ok(qcInspectionMainFileRelationService.queryById(relationId));
}
/**
*
*/
@SaCheckPermission("qms:qcInspectionMainFileRelation:add")
@Log(title = "质检任务文件关系", businessType = BusinessType.INSERT)
@RepeatSubmit()
@PostMapping()
public R<Void> add(@Validated(AddGroup.class) @RequestBody QcInspectionMainFileRelationBo bo) {
return toAjax(qcInspectionMainFileRelationService.insertByBo(bo));
}
/**
*
*/
@SaCheckPermission("qms:qcInspectionMainFileRelation:edit")
@Log(title = "质检任务文件关系", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping()
public R<Void> edit(@Validated(EditGroup.class) @RequestBody QcInspectionMainFileRelationBo bo) {
return toAjax(qcInspectionMainFileRelationService.updateByBo(bo));
}
/**
*
*
* @param relationIds
*/
@SaCheckPermission("qms:qcInspectionMainFileRelation:remove")
@Log(title = "质检任务文件关系", businessType = BusinessType.DELETE)
@DeleteMapping("/{relationIds}")
public R<Void> remove(@NotEmpty(message = "主键不能为空")
@PathVariable Long[] relationIds) {
return toAjax(qcInspectionMainFileRelationService.deleteWithValidByIds(List.of(relationIds), true));
}
/**
*
*/
@GetMapping("/getQcInspectionMainFileRelationList")
public R<List<QcInspectionMainFileRelationVo>> getQcInspectionMainFileRelationList(QcInspectionMainFileRelationBo bo) {
List<QcInspectionMainFileRelationVo> list = qcInspectionMainFileRelationService.queryList(bo);
return R.ok(list);
}
}

@ -5,7 +5,9 @@ import com.alibaba.fastjson2.JSONObject;
import jakarta.validation.Valid;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.dubbo.config.annotation.DubboReference;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.pda.api.model.bo.GenerateInspectionTaskBo;
@ -18,10 +20,14 @@ import org.dromara.qms.domain.vo.QcInspectionResultVo;
import org.dromara.qms.domain.vo.QcUnqualifiedRecordVo;
import org.dromara.qms.domain.vo.QcUnqualifiedReviewVo;
import org.dromara.qms.service.*;
import org.dromara.resource.api.RemoteFileService;
import org.dromara.resource.api.domain.RemoteFile;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
@ -57,6 +63,66 @@ public class QcPDAController {
//PDA业务Service
private final IQcPDAService qcPDAService;
@DubboReference
private final RemoteFileService remoteFileService;
/**
*
*
* @param files
* @return URL
*/
private List<Long> handleFileUploads(List<MultipartFile> files) {
// 创建一个存储上传文件URL的列表
List<String> fileUrls = new ArrayList<>();
List<Long> ossIds = new ArrayList<>();
// 判断文件列表是否为空
if (files != null) {
// 遍历每个文件
for (MultipartFile file : files) {
// 获取原始文件名
String originalFilename = file.getOriginalFilename();
// 获取文件类型
String contentType = file.getContentType();
byte[] fileBytes;
try {
// 获取文件字节内容
fileBytes = file.getBytes();
} catch (IOException e) {
// 记录错误日志并抛出服务异常
log.error("获取文件字节失败: {}", originalFilename, e);
throw new ServiceException("文件获取失败,请重试。");
}
try {
// 调用远程文件服务的上传方法
RemoteFile sysFile = remoteFileService.upload(originalFilename, originalFilename, contentType, fileBytes);
// 判断上传结果是否成功
if (sysFile != null && sysFile.getUrl() != null) {
// 将文件URL添加到列表中
fileUrls.add(sysFile.getUrl());
ossIds.add(sysFile.getOssId());
} else {
// 记录警告日志
log.warn("文件上传成功但未返回URL或返回数据为空: {}", originalFilename);
}
} catch (ServiceException e) {
// 记录服务异常日志并抛出新的服务异常
log.error("文件上传服务异常: {}", originalFilename, e);
throw new ServiceException("文件上传服务异常:" + e.getMessage());
} catch (Exception e) {
// 记录未知错误日志并抛出新的服务异常
log.error("文件上传过程中发生未知错误: {}", originalFilename, e);
throw new ServiceException("文件上传过程中发生未知错误,请联系管理员。");
}
}
}
// 返回上传文件的URL列表
return ossIds;
}
/**
*
* 退
@ -96,7 +162,10 @@ public class QcPDAController {
@PostMapping("/submitInspection")
public R<Boolean> submitInspection(String json, List<MultipartFile> checkItemFiles) {
// 处理文件上传
List<Long> ossIds = handleFileUploads(checkItemFiles);
QcInspectionMainBo bo= JSONObject.parseObject(json, QcInspectionMainBo.class);
bo.setOssIds(ossIds);
Boolean result = qcPDAService.submitInspection(bo);
if (result != null && result) {
return R.ok(true);

@ -1,26 +1,28 @@
package org.dromara.qms.controller;
import java.util.List;
import java.util.ArrayList;
import lombok.RequiredArgsConstructor;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.*;
import cn.dev33.satoken.annotation.SaCheckPermission;
import org.springframework.web.bind.annotation.*;
import org.springframework.validation.annotation.Validated;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.web.core.BaseController;
import org.dromara.common.mybatis.core.page.PageQuery;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.qms.domain.vo.QcUnqualifiedReviewVo;
import org.dromara.qms.domain.bo.QcUnqualifiedReviewBo;
import org.dromara.qms.service.IQcUnqualifiedReviewService;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController;
import org.dromara.qms.domain.bo.QcUnqualifiedReviewBo;
import org.dromara.qms.domain.vo.QcUnqualifiedReviewVo;
import org.dromara.qms.service.IQcUnqualifiedReviewService;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import java.util.ArrayList;
import java.util.List;
/**
*
@ -126,4 +128,15 @@ public class QcUnqualifiedReviewController extends BaseController {
List<QcUnqualifiedReviewVo> list = qcUnqualifiedReviewService.queryList(bo);
return R.ok(list);
}
/**
*
* @param bo
* @return
*/
@PostMapping("/completeTask")
public R<Boolean> completeTask(@Validated(EditGroup.class) @RequestBody QcUnqualifiedReviewBo bo) {
return R.ok(qcUnqualifiedReviewService.completeTask(bo));
}
}

@ -0,0 +1,47 @@
package org.dromara.qms.domain;
import org.dromara.common.tenant.core.TenantEntity;
import com.baomidou.mybatisplus.annotation.*;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.io.Serial;
/**
* qc_inspection_main_file_relation
*
* @author zch
* @date 2025-07-31
*/
@Data
@EqualsAndHashCode(callSuper = true)
@TableName("qc_inspection_main_file_relation")
public class QcInspectionMainFileRelation extends TenantEntity {
@Serial
private static final long serialVersionUID = 1L;
/**
*
*/
@TableId(value = "relation_id", type = IdType.ASSIGN_ID)
private Long relationId;
/**
*
*/
private Long inspectionId;
/**
*
*/
private Long ossId;
/**
* 02
*/
@TableLogic
private String delFlag;
}

@ -1,14 +1,13 @@
package org.dromara.qms.domain;
import org.dromara.common.tenant.core.TenantEntity;
import com.baomidou.mybatisplus.annotation.*;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.math.BigDecimal;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import org.dromara.common.tenant.core.TenantEntity;
import java.io.Serial;
import java.math.BigDecimal;
import java.util.Date;
/**
* qc_unqualified_review
@ -146,4 +145,20 @@ public class QcUnqualifiedReview extends TenantEntity {
*/
@TableField(exist = false)
private String typeName;
/**
* ID
*/
private Long processInstanceId;
// /**
// * 工作流状态draft草稿、waiting待审核、finish完成、termination终止、back退回、cancel撤销
// */
// private String processStatus;
//
// /**
// * 当前任务ID
// */
// private Long currentTaskId;
}

@ -172,4 +172,9 @@ public class QcInspectionMainBo extends BaseEntity {
*/
private List<QcInspectionResultBo> results;
/**
* ID
*/
List<Long> ossIds;
}

@ -0,0 +1,42 @@
package org.dromara.qms.domain.bo;
import org.dromara.qms.domain.QcInspectionMainFileRelation;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.*;
/**
* qc_inspection_main_file_relation
*
* @author zch
* @date 2025-07-31
*/
@Data
@EqualsAndHashCode(callSuper = true)
@AutoMapper(target = QcInspectionMainFileRelation.class, reverseConvertGenerate = false)
public class QcInspectionMainFileRelationBo extends BaseEntity {
/**
*
*/
@NotNull(message = "质检主键不能为空", groups = { AddGroup.class, EditGroup.class })
private Long relationId;
/**
*
*/
@NotNull(message = "质检主键不能为空", groups = { AddGroup.class, EditGroup.class })
private Long inspectionId;
/**
*
*/
@NotNull(message = "文件主键不能为空", groups = { AddGroup.class, EditGroup.class })
private Long ossId;
}

@ -1,17 +1,13 @@
package org.dromara.qms.domain.bo;
import com.alibaba.excel.annotation.ExcelProperty;
import org.dromara.qms.domain.QcUnqualifiedReview;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.*;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.qms.domain.QcUnqualifiedReview;
import java.math.BigDecimal;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
/**
* qc_unqualified_review
@ -138,4 +134,24 @@ public class QcUnqualifiedReviewBo extends BaseEntity {
*
*/
private String typeName;
/**
* ID
*/
private Long processInstanceId;
// /**
// * 工作流状态draft草稿、waiting待审核、finish完成、termination终止、back退回、cancel撤销
// */
// private String processStatus;
//
//
// /**
// * 当前任务ID
// */
// private Long currentTaskId;
}

@ -0,0 +1,50 @@
package org.dromara.qms.domain.vo;
import org.dromara.qms.domain.QcInspectionMainFileRelation;
import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
import com.alibaba.excel.annotation.ExcelProperty;
import org.dromara.common.excel.annotation.ExcelDictFormat;
import org.dromara.common.excel.convert.ExcelDictConvert;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.util.Date;
/**
* qc_inspection_main_file_relation
*
* @author zch
* @date 2025-07-31
*/
@Data
@ExcelIgnoreUnannotated
@AutoMapper(target = QcInspectionMainFileRelation.class)
public class QcInspectionMainFileRelationVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/**
*
*/
@ExcelProperty(value = "质检主键")
private Long relationId;
/**
*
*/
@ExcelProperty(value = "质检主键")
private Long inspectionId;
/**
*
*/
@ExcelProperty(value = "文件主键")
private Long ossId;
}

@ -1,18 +1,16 @@
package org.dromara.qms.domain.vo;
import java.math.BigDecimal;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import org.dromara.qms.domain.QcUnqualifiedReview;
import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
import com.alibaba.excel.annotation.ExcelProperty;
import org.dromara.common.excel.annotation.ExcelDictFormat;
import org.dromara.common.excel.convert.ExcelDictConvert;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
import org.dromara.common.excel.annotation.ExcelDictFormat;
import org.dromara.common.excel.convert.ExcelDictConvert;
import org.dromara.qms.domain.QcUnqualifiedReview;
import java.io.Serial;
import java.io.Serializable;
import java.math.BigDecimal;
import java.util.Date;
@ -169,4 +167,22 @@ public class QcUnqualifiedReviewVo implements Serializable {
*
*/
private String typeName;
/**
* ID
*/
private Long processInstanceId;
// /**
// * 工作流状态draft草稿、waiting待审核、finish完成、termination终止、back退回、cancel撤销
// */
// private String processStatus;
//
// /**
// * 当前任务ID
// */
// private Long currentTaskId;
}

@ -0,0 +1,15 @@
package org.dromara.qms.mapper;
import org.dromara.qms.domain.QcInspectionMainFileRelation;
import org.dromara.qms.domain.vo.QcInspectionMainFileRelationVo;
import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
/**
* Mapper
*
* @author zch
* @date 2025-07-31
*/
public interface QcInspectionMainFileRelationMapper extends BaseMapperPlus<QcInspectionMainFileRelation, QcInspectionMainFileRelationVo> {
}

@ -0,0 +1,69 @@
package org.dromara.qms.service;
import org.dromara.qms.domain.QcInspectionMainFileRelation;
import org.dromara.qms.domain.vo.QcInspectionMainFileRelationVo;
import org.dromara.qms.domain.bo.QcInspectionMainFileRelationBo;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
import java.util.Collection;
import java.util.List;
/**
* Service
*
* @author zch
* @date 2025-07-31
*/
public interface IQcInspectionMainFileRelationService {
/**
*
*
* @param relationId
* @return
*/
QcInspectionMainFileRelationVo queryById(Long relationId);
/**
*
*
* @param bo
* @param pageQuery
* @return
*/
TableDataInfo<QcInspectionMainFileRelationVo> queryPageList(QcInspectionMainFileRelationBo bo, PageQuery pageQuery);
/**
*
*
* @param bo
* @return
*/
List<QcInspectionMainFileRelationVo> queryList(QcInspectionMainFileRelationBo bo);
/**
*
*
* @param bo
* @return
*/
Boolean insertByBo(QcInspectionMainFileRelationBo bo);
/**
*
*
* @param bo
* @return
*/
Boolean updateByBo(QcInspectionMainFileRelationBo bo);
/**
*
*
* @param ids
* @param isValid
* @return
*/
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
}

@ -66,4 +66,14 @@ public interface IQcUnqualifiedReviewService {
* @return
*/
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
/**
*
*
* @param request
* @return
*/
Boolean completeTask(QcUnqualifiedReviewBo bo);
}

@ -0,0 +1,134 @@
package org.dromara.qms.service.impl;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.github.yulichang.toolkit.JoinWrappers;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;
import org.dromara.qms.domain.bo.QcInspectionMainFileRelationBo;
import org.dromara.qms.domain.vo.QcInspectionMainFileRelationVo;
import org.dromara.qms.domain.QcInspectionMainFileRelation;
import org.dromara.qms.mapper.QcInspectionMainFileRelationMapper;
import org.dromara.qms.service.IQcInspectionMainFileRelationService;
import java.util.List;
import java.util.Map;
import java.util.Collection;
/**
* Service
*
* @author zch
* @date 2025-07-31
*/
@RequiredArgsConstructor
@Service
public class QcInspectionMainFileRelationServiceImpl implements IQcInspectionMainFileRelationService {
private final QcInspectionMainFileRelationMapper baseMapper;
/**
*
*
* @param relationId
* @return
*/
@Override
public QcInspectionMainFileRelationVo queryById(Long relationId){
return baseMapper.selectVoById(relationId);
}
/**
*
*
* @param bo
* @param pageQuery
* @return
*/
@Override
public TableDataInfo<QcInspectionMainFileRelationVo> queryPageList(QcInspectionMainFileRelationBo bo, PageQuery pageQuery) {
MPJLambdaWrapper<QcInspectionMainFileRelation> lqw = buildQueryWrapper(bo);
Page<QcInspectionMainFileRelationVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
return TableDataInfo.build(result);
}
/**
*
*
* @param bo
* @return
*/
@Override
public List<QcInspectionMainFileRelationVo> queryList(QcInspectionMainFileRelationBo bo) {
MPJLambdaWrapper<QcInspectionMainFileRelation> lqw = buildQueryWrapper(bo);
return baseMapper.selectVoList(lqw);
}
private MPJLambdaWrapper<QcInspectionMainFileRelation> buildQueryWrapper(QcInspectionMainFileRelationBo bo) {
Map<String, Object> params = bo.getParams();
MPJLambdaWrapper<QcInspectionMainFileRelation> lqw = JoinWrappers.lambda(QcInspectionMainFileRelation.class)
.selectAll(QcInspectionMainFileRelation.class)
.eq(bo.getRelationId() != null, QcInspectionMainFileRelation::getRelationId, bo.getRelationId())
.eq(bo.getInspectionId() != null, QcInspectionMainFileRelation::getInspectionId, bo.getInspectionId())
.eq(bo.getOssId() != null, QcInspectionMainFileRelation::getOssId, bo.getOssId())
.orderByDesc(QcInspectionMainFileRelation::getCreateTime);
return lqw;
}
/**
*
*
* @param bo
* @return
*/
@Override
public Boolean insertByBo(QcInspectionMainFileRelationBo bo) {
QcInspectionMainFileRelation add = MapstructUtils.convert(bo, QcInspectionMainFileRelation.class);
validEntityBeforeSave(add);
boolean flag = baseMapper.insert(add) > 0;
if (flag) {
bo.setRelationId(add.getRelationId());
}
return flag;
}
/**
*
*
* @param bo
* @return
*/
@Override
public Boolean updateByBo(QcInspectionMainFileRelationBo bo) {
QcInspectionMainFileRelation update = MapstructUtils.convert(bo, QcInspectionMainFileRelation.class);
validEntityBeforeSave(update);
return baseMapper.updateById(update) > 0;
}
/**
*
*/
private void validEntityBeforeSave(QcInspectionMainFileRelation entity){
//TODO 做一些数据校验,如唯一约束
}
/**
*
*
* @param ids
* @param isValid
* @return
*/
@Override
public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
if(isValid){
//TODO 做一些业务上的校验,判断是否需要校验
}
return baseMapper.deleteByIds(ids) > 0;
}
}

@ -106,6 +106,7 @@ public class QcInspectionMainServiceImpl implements IQcInspectionMainService {
.eq(StringUtils.isNotBlank(bo.getWorkshop()), QcInspectionMain::getWorkshop, bo.getWorkshop())
.eq(bo.getInspectionType() != null, QcInspectionMain::getInspectionType, bo.getInspectionType())
// .eq(bo.getStatus() != null, QcInspectionMain::getStatus, bo.getStatus())
.eq(StringUtils.isNotBlank(bo.getQcInspectionType()), QcInspectionType::getQcInspectionType, bo.getQcInspectionType())
.eq(StringUtils.isNotBlank(bo.getStatus()), QcInspectionMain::getStatus, bo.getStatus())
.eq(StringUtils.isNotBlank(bo.getInspector()), QcInspectionMain::getInspector, bo.getInspector())

@ -1,38 +1,33 @@
package org.dromara.qms.service.impl;
import com.alibaba.ttl.TtlRunnable;
import io.seata.spring.annotation.GlobalTransactional;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.dubbo.config.annotation.DubboService;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.DateUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.core.utils.uuid.IdUtils;
import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.pda.api.RemotePdaMesApiService;
import org.dromara.pda.api.model.ProdQmsPlanDetail;
import org.dromara.pda.api.model.bo.GenerateInspectionTaskBo;
import org.dromara.qms.domain.bo.QcInspectionResultBo;
import org.dromara.qms.domain.bo.QcInspectionTemplateBo;
import org.dromara.qms.domain.bo.QcTemplateItemBo;
import org.dromara.qms.domain.bo.*;
import org.dromara.qms.domain.vo.*;
import org.dromara.qms.service.*;
import org.dromara.system.api.RemoteCodeRuleService;
import org.dromara.workflow.api.RemoteWorkflowService;
import org.dromara.workflow.api.domain.RemoteCompleteTask;
import org.dromara.workflow.api.domain.RemoteStartProcess;
import org.dromara.workflow.api.domain.RemoteStartProcessReturn;
import org.springframework.beans.BeanUtils;
import org.springframework.stereotype.Service;
import org.dromara.qms.domain.bo.QcInspectionMainBo;
import org.dromara.common.core.domain.R;
import org.springframework.transaction.annotation.Transactional;
import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.qms.domain.bo.QcUnqualifiedReviewBo;
import org.dromara.qms.domain.bo.QcUnqualifiedRecordBo;
import org.dromara.common.core.utils.MapstructUtils;
import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.UUID;
import java.util.*;
import java.util.concurrent.CompletableFuture;
/**
* PDAService
@ -40,11 +35,13 @@ import java.util.UUID;
* @author YinQ
* @date 2025-07-24
*/
@Slf4j
@RequiredArgsConstructor
@Service
@DubboService
public class QcPDAServiceImpl implements IQcPDAService {
private final IQcInspectionMainService qcInspectionMainService;
//质检结果子表
@ -59,12 +56,19 @@ public class QcPDAServiceImpl implements IQcPDAService {
//不合格记录子表
private final IQcUnqualifiedRecordService qcUnqualifiedRecordService;
private final IQcInspectionMainFileRelationService qcInspectionMainFileRelationService;
@DubboReference
private final RemotePdaMesApiService remotePdaMesApiService;
@DubboReference
private final RemoteCodeRuleService remoteCodeRuleService;
//WARM-FLOW工作流
@DubboReference(timeout = 30000)
private final RemoteWorkflowService remoteWorkflowService;
private static final String UNQUALIFIED_REVIEW_FLOW_CODE = "unqualified_review";
/**
* planDetailIdprocessId
@ -145,6 +149,17 @@ public class QcPDAServiceImpl implements IQcPDAService {
@Override
@Transactional(rollbackFor = Exception.class)
public Boolean submitInspection(QcInspectionMainBo bo) {
// 保存文件
List<Long> ossIds = bo.getOssIds();
for (Long ossId : ossIds){
QcInspectionMainFileRelationBo relation = new QcInspectionMainFileRelationBo();
relation.setInspectionId(bo.getInspectionId());
relation.setOssId(ossId);
qcInspectionMainFileRelationService.insertByBo(relation);
}
// 根据传入的检验ID查询主记录信息
Long inspectionId = bo.getInspectionId();
Date nowDate = DateUtils.getNowDate();
@ -303,6 +318,7 @@ public class QcPDAServiceImpl implements IQcPDAService {
* @return
*/
@Override
@GlobalTransactional(rollbackFor = Exception.class)
public Boolean handleUnqualified(String dispositionType, Long[] reviewIds) {
for (Long reviewId : reviewIds) {
QcUnqualifiedReviewVo reviewVo = qcUnqualifiedReviewService.queryById(reviewId);
@ -312,13 +328,58 @@ public class QcPDAServiceImpl implements IQcPDAService {
if (StringUtils.isNotEmpty(reviewVo.getReviewResult()) ) {
throw new ServiceException("此不合格评审单已评审");
}
//集成工作流
RemoteStartProcess startProcess = new RemoteStartProcess();
startProcess.setBusinessId(String.valueOf(reviewId));
startProcess.setFlowCode(UNQUALIFIED_REVIEW_FLOW_CODE);
RemoteStartProcessReturn remoteStartProcessReturn = remoteWorkflowService.startWorkFlow(startProcess);
Long processInstanceId = remoteStartProcessReturn.getProcessInstanceId();
Long taskId = remoteStartProcessReturn.getTaskId();
// 更新数据
QcUnqualifiedReviewBo reviewBo = new QcUnqualifiedReviewBo();
reviewBo.setReviewId(reviewId);
reviewBo.setReviewResult(dispositionType);
reviewBo.setReviewer(LoginHelper.getUsername());
reviewBo.setReviewStartTime(new Date());
reviewBo.setProcessInstanceId(processInstanceId);// 流程实例ID
qcUnqualifiedReviewService.updateByBo(reviewBo);
//集成工作流
//异步推动流程
final Long finalTaskId = taskId;
CompletableFuture.runAsync(TtlRunnable.get(() -> {
RemoteCompleteTask completeTask = new RemoteCompleteTask();
completeTask.setTaskId(finalTaskId);
completeTask.setMessage("启动不合格评审,处置类型: " + dispositionType);
// 设置消息类型
List<String> messageTypes = new ArrayList<>();
messageTypes.add("1"); // 站内信
completeTask.setMessageType(messageTypes);
// 设置流程变量
Map<String, Object> variables = new HashMap<>();
variables.put("reviewResult", dispositionType);
completeTask.setVariables(variables);
remoteWorkflowService.completeTask(completeTask);
}));
// RemoteCompleteTask completeTask = new RemoteCompleteTask();
// completeTask.setTaskId(finalTaskId);
// completeTask.setMessage("启动不合格评审,处置类型: " + dispositionType);
//
// // 设置消息类型
// List<String> messageTypes = new ArrayList<>();
// messageTypes.add("1"); // 站内信
// completeTask.setMessageType(messageTypes);
//
// // 设置流程变量
// Map<String, Object> variables = new HashMap<>();
// variables.put("reviewResult", dispositionType);
// completeTask.setVariables(variables);
//
// remoteWorkflowService.completeTask(completeTask);
}
return true;
}

@ -3,23 +3,29 @@ package org.dromara.qms.service.impl;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.github.yulichang.toolkit.JoinWrappers;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import io.seata.spring.annotation.GlobalTransactional;
import lombok.RequiredArgsConstructor;
import org.apache.dubbo.config.annotation.DubboReference;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.ObjectUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.qms.domain.QcInspectionMain;
import org.dromara.qms.domain.QcInspectionType;
import org.dromara.qms.domain.QcUnqualifiedReview;
import org.dromara.qms.domain.bo.QcUnqualifiedReviewBo;
import org.dromara.qms.domain.vo.QcUnqualifiedReviewVo;
import org.dromara.qms.mapper.QcUnqualifiedReviewMapper;
import org.dromara.qms.service.IQcInspectionTypeService;
import org.dromara.qms.service.IQcUnqualifiedReviewService;
import org.dromara.workflow.api.RemoteWorkflowService;
import org.dromara.workflow.api.domain.RemoteCompleteTask;
import org.springframework.stereotype.Service;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.*;
/**
* Service
@ -33,6 +39,12 @@ public class QcUnqualifiedReviewServiceImpl implements IQcUnqualifiedReviewServi
private final QcUnqualifiedReviewMapper baseMapper;
private final IQcInspectionTypeService inspectionTypeService;
//WARM-FLOW工作流
@DubboReference(timeout = 30000)
private final RemoteWorkflowService remoteWorkflowService;
/**
*
*
@ -41,7 +53,11 @@ public class QcUnqualifiedReviewServiceImpl implements IQcUnqualifiedReviewServi
*/
@Override
public QcUnqualifiedReviewVo queryById(Long reviewId) {
return baseMapper.selectVoById(reviewId);
QcUnqualifiedReviewVo qcUnqualifiedReviewVo = baseMapper.selectVoById(reviewId);
//获取检测类型
String typeName = inspectionTypeService.queryById(qcUnqualifiedReviewVo.getInspectionType()).getTypeName();
qcUnqualifiedReviewVo.setTypeName(typeName);
return qcUnqualifiedReviewVo;
}
/**
@ -81,7 +97,7 @@ public class QcUnqualifiedReviewServiceImpl implements IQcUnqualifiedReviewServi
// .eq(bo.getReviewResult() != null, QcUnqualifiedReview::getReviewResult, bo.getReviewResult())
.eq(StringUtils.isNotBlank(bo.getReviewResult()), QcUnqualifiedReview::getReviewResult, bo.getReviewResult())
.eq(StringUtils.isNotBlank(bo.getInspectionNo()), QcUnqualifiedReview::getInspectionNo, bo.getInspectionNo())
.eq(bo.getInspectionType() != null, QcUnqualifiedReview::getInspectionType, bo.getInspectionType())
// .eq(bo.getInspectionType() != null, QcUnqualifiedReview::getInspectionType, bo.getInspectionType())
// .eq(StringUtils.isNotBlank(bo.getInspectionType()), QcUnqualifiedReview::getInspectionType, bo.getInspectionType())
.eq(bo.getProductionDate() != null, QcUnqualifiedReview::getProductionDate, bo.getProductionDate())
.eq(StringUtils.isNotBlank(bo.getWorkOrderNo()), QcUnqualifiedReview::getWorkOrderNo, bo.getWorkOrderNo())
@ -165,4 +181,36 @@ public class QcUnqualifiedReviewServiceImpl implements IQcUnqualifiedReviewServi
}
return baseMapper.deleteByIds(ids) > 0;
}
@Override
@GlobalTransactional(rollbackFor = Exception.class)
public Boolean completeTask(QcUnqualifiedReviewBo bo) {
QcUnqualifiedReview review = baseMapper.selectById(bo.getReviewId());
if (review == null) {
throw new ServiceException("不合格品待评审不存在");
}
if (ObjectUtils.isNotEmpty(review.getReviewEndTime())){
throw new ServiceException("该任务已处理完成");
}
Long currentTaskIdByInstanceId = remoteWorkflowService.getCurrentTaskIdByInstanceId(review.getProcessInstanceId());
if (currentTaskIdByInstanceId == null) {
throw new ServiceException("任务不存在");
}
review.setReviewer(LoginHelper.getUsername());
review.setReviewerId(LoginHelper.getUserId());
review.setReviewEndTime(new Date());
/* 工作流 */
RemoteCompleteTask completeTask = new RemoteCompleteTask();
completeTask.setTaskId(currentTaskIdByInstanceId);
// 设置消息类型
List<String> messageTypes = new ArrayList<>();
messageTypes.add("1"); // 站内信
completeTask.setMessageType(messageTypes);
completeTask.setMessage("审批通过 " );
remoteWorkflowService.completeTask(completeTask);
return baseMapper.updateById(review) > 0;
}
}

@ -0,0 +1,7 @@
<?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="org.dromara.qms.mapper.QcInspectionMainFileRelationMapper">
</mapper>

@ -30,7 +30,7 @@ public class SysPrintTemplateInfo extends TenantEntity {
/**
* ID
*/
private String templateListId;
private Long templateListId;
/**
*

@ -25,7 +25,7 @@ public class SysPrintTemplateInfoBo extends BaseEntity {
/**
* ID
*/
private String templateListId;
private Long templateListId;
/**
*

@ -38,7 +38,7 @@ public class SysPrintTemplateInfoVo implements Serializable {
* ID
*/
@ExcelProperty(value = "模板列表ID")
private String templateListId;
private Long templateListId;
/**
*

@ -9,6 +9,7 @@ import com.github.yulichang.toolkit.JoinWrappers;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import org.dromara.system.domain.SysPrintTemplateList;
import org.springframework.stereotype.Service;
import org.dromara.system.domain.bo.SysPrintTemplateInfoBo;
import org.dromara.system.domain.vo.SysPrintTemplateInfoVo;
@ -73,8 +74,10 @@ public class SysPrintTemplateInfoServiceImpl implements ISysPrintTemplateInfoSer
Map<String, Object> params = bo.getParams();
MPJLambdaWrapper<SysPrintTemplateInfo> lqw = JoinWrappers.lambda(SysPrintTemplateInfo.class)
.selectAll(SysPrintTemplateInfo.class)
.select(SysPrintTemplateList::getTemplateName)
.leftJoin(SysPrintTemplateList.class, SysPrintTemplateList::getTemplateListId, SysPrintTemplateInfo::getTemplateListId)
.eq(bo.getTemplateInfoId() != null, SysPrintTemplateInfo::getTemplateInfoId, bo.getTemplateInfoId())
.eq(StringUtils.isNotBlank(bo.getTemplateListId()), SysPrintTemplateInfo::getTemplateListId, bo.getTemplateListId())
.eq(StringUtils.isNotNull(bo.getTemplateListId()), SysPrintTemplateInfo::getTemplateListId, bo.getTemplateListId())
.eq(StringUtils.isNotBlank(bo.getPaperType()), SysPrintTemplateInfo::getPaperType, bo.getPaperType())
.eq(StringUtils.isNotBlank(bo.getWidth()), SysPrintTemplateInfo::getWidth, bo.getWidth())
.eq(StringUtils.isNotBlank(bo.getHeight()), SysPrintTemplateInfo::getHeight, bo.getHeight())

@ -10,6 +10,8 @@ import com.github.yulichang.toolkit.JoinWrappers;
import com.github.yulichang.wrapper.MPJLambdaWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import org.dromara.system.domain.SysPrintTemplateInfo;
import org.dromara.system.domain.SysPrintTemplateList;
import org.springframework.stereotype.Service;
import org.dromara.system.domain.bo.SysPrintTemplateNodeBo;
import org.dromara.system.domain.vo.SysPrintTemplateNodeVo;
@ -75,6 +77,9 @@ public class SysPrintTemplateNodeServiceImpl implements ISysPrintTemplateNodeSer
Map<String, Object> params = bo.getParams();
MPJLambdaWrapper<SysPrintTemplateNode> lqw = JoinWrappers.lambda(SysPrintTemplateNode.class)
.selectAll(SysPrintTemplateNode.class)
.select(SysPrintTemplateList::getTemplateName)
.leftJoin(SysPrintTemplateInfo.class, SysPrintTemplateInfo::getTemplateInfoId, SysPrintTemplateNode::getTemplateInfoId)
.leftJoin(SysPrintTemplateList.class, SysPrintTemplateList::getTemplateListId, SysPrintTemplateInfo::getTemplateListId)
.eq(bo.getTemplateNodeId() != null, SysPrintTemplateNode::getTemplateNodeId, bo.getTemplateNodeId())
.eq(StringUtils.isNotBlank(bo.getTemplateInfoId()), SysPrintTemplateNode::getTemplateInfoId, bo.getTemplateInfoId())
.like(StringUtils.isNotBlank(bo.getName()), SysPrintTemplateNode::getName, bo.getName())

Loading…
Cancel
Save