新增了同步app视频,

This commit is contained in:
wucongxing8150 2025-07-28 09:13:34 +08:00
parent 7b09f59b51
commit 6372a75c1c
5 changed files with 127 additions and 83 deletions

View File

@ -405,17 +405,16 @@ public class CaseClinicalVideoController {
*/ */
@PostMapping("/app/clinical/video") @PostMapping("/app/clinical/video")
public Response<T> AddClinicalVideoApp( public Response<T> AddClinicalVideoApp(
@Validated() HttpServletRequest request
@RequestBody addClinicalVideoApp request
) { ) {
// try { try {
// boolean res = caseClinicalVideoService.AddClinicalVideoApp(request); boolean res = caseClinicalVideoService.AddClinicalVideoApp(request);
// if (!res){ if (!res){
// return Response.error("操作失败"); return Response.error("操作失败");
// } }
// } catch (BusinessException e) { } catch (BusinessException e) {
// return Response.error(e.getMessage()); return Response.error(e.getMessage());
// } }
return Response.success(); return Response.success();
} }

View File

@ -12,9 +12,12 @@ import org.apache.commons.io.IOUtils;
import javax.crypto.Mac; import javax.crypto.Mac;
import javax.crypto.spec.SecretKeySpec; import javax.crypto.spec.SecretKeySpec;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.nio.charset.StandardCharsets; import java.nio.charset.StandardCharsets;
import java.util.Map; import java.util.Map;
import java.util.*; import java.util.*;
import java.util.stream.Collectors;
@Slf4j @Slf4j
public class Base { public class Base {
@ -125,39 +128,36 @@ public class Base {
} }
/** /**
* 校验签名 * 校验签名使用已反序列化的 dto 对象
* @param request 请求对象 * @param request HttpServletRequest用于获取 appId sign
* @param secretKey 密钥 * @param secretKey 签名用的密钥
* @param mapper ObjectMapper 实例用于 JSON 反序列化 * @param dto 请求对象 addClinicalVideoApp
* @param mapper ObjectMapper 实例用于序列化 dto
*/ */
public static void checkSign(HttpServletRequest request, String secretKey, ObjectMapper mapper) { public void checkSign(HttpServletRequest request, String secretKey, Object dto, ObjectMapper mapper) {
try { try {
String appId = request.getHeader("appId"); String appId = request.getHeader("appId");
String sign = request.getHeader("sign"); String sign = request.getHeader("sign");
if (appId == null || appId.isEmpty()) { if (appId == null || appId.isEmpty()) {
throw new BusinessException("-1", "请求未授权"); throw new BusinessException("-1", "请求未授权(缺少 appId");
} }
if (sign == null || sign.isEmpty()) { if (sign == null || sign.isEmpty()) {
throw new BusinessException("-1", "缺少签名"); throw new BusinessException("-1", "缺少签名");
} }
// 读取请求体 // 转换 dto Map<String, Object> 用于签名生成
String body = IOUtils.toString(request.getInputStream(), StandardCharsets.UTF_8); @SuppressWarnings("unchecked")
if (body == null || body.isEmpty()) { Map<String, Object> params = mapper.convertValue(dto, Map.class);
throw new BusinessException("-1", "请求体为空");
}
// 使用 TypeReference 明确泛型类型避免警告
Map<String, Object> params = mapper.readValue(body, new TypeReference<Map<String, Object>>() {});
// 生成签名 // 生成签名
String serverSign = Base.genSignature(params, secretKey); String serverSign = genSignature(params, secretKey);
System.out.println("客户端签名: " + sign);
System.out.println("服务端签名: " + serverSign);
if (!sign.equals(serverSign)) { if (!sign.equals(serverSign)) {
throw new BusinessException("-1", "签名错误"); throw new BusinessException("-1", "签名错误");
} }
} catch (BusinessException e) { } catch (BusinessException e) {
throw e; throw e;
} catch (Exception e) { } catch (Exception e) {

View File

@ -0,0 +1,19 @@
package com.example.caseData.extend.app.Video;
import com.example.caseData.exception.BusinessException;
import com.example.caseData.extend.app.Base;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.ObjectMapper;
import jakarta.servlet.http.HttpServletRequest;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.io.IOUtils;
import org.springframework.stereotype.Component;
import java.nio.charset.StandardCharsets;
import java.util.Map;
@Slf4j
@Component
public class Video extends Base {
}

View File

@ -1,25 +1,67 @@
package com.example.caseData.request.CaseClinicalVideoRequest; package com.example.caseData.request.CaseClinicalVideoRequest;
import com.example.caseData.request.clinicalRequest.getClinicalArticleSearchPage;
import com.fasterxml.jackson.annotation.JsonProperty; import com.fasterxml.jackson.annotation.JsonProperty;
import jakarta.validation.constraints.NotEmpty; import jakarta.validation.constraints.NotEmpty;
import lombok.Data; import lombok.Data;
import org.springframework.util.StringUtils;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@Data @Data
public class addClinicalVideoApp { public class addClinicalVideoApp {
// 父级 次级评论此字段必须存在 // 动作add:新增 update:修改 delete:删除
@JsonProperty("parent_id") @JsonProperty("action")
private String parentId; private String action;
// 根评论标识 次级评论此字段必须存在 // 视频编号保利
@JsonProperty("root_id") @JsonProperty("videoNo")
private String rootId; private String videoNo;
// 评论内容 // 是否外部链接0: 1:
@JsonProperty("content") @JsonProperty("isLink")
@NotEmpty(message = "请输入评论内容") private String isLink;
private String content;
// 评论图片 // 外部链接地址
@JsonProperty("comment_image") @JsonProperty("isLinkUrl")
private String commentImage; private String isLinkUrl;
// 标题
@JsonProperty("videoTitle")
@NotEmpty(message = "标题不能为空")
private String videoTitle;
// 作者
@JsonProperty("author")
private List<Author> author;
// 标签
@JsonProperty("label")
private List<Label> label;
/**
* 作者
*/
@Data
public static class Author {
@JsonProperty("doctorIden")
private String doctorIden; // 医生app唯一标识
@JsonProperty("hospitalIden")
private String hospitalIden; // 医院app唯一标识
}
/**
* 标签
*/
@Data
public static class Label {
@JsonProperty("appIden")
private String appIden; // app唯一标识
@JsonProperty("labelName")
private String labelName; // 标签名称
}
} }

View File

@ -4,12 +4,19 @@ import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.example.caseData.dao.*; import com.example.caseData.dao.*;
import com.example.caseData.exception.BusinessException; import com.example.caseData.exception.BusinessException;
import com.example.caseData.extend.app.Base; import com.example.caseData.extend.app.Base;
import com.example.caseData.extend.app.UserPoint.UserPoint;
import com.example.caseData.extend.app.Video.Video;
import com.example.caseData.model.*; import com.example.caseData.model.*;
import com.example.caseData.model.UserCollectClinicalVideoModel; import com.example.caseData.model.UserCollectClinicalVideoModel;
import com.example.caseData.request.CaseClinicalVideoRequest.addClinicalVideoApp;
import com.example.caseData.request.CaseClinicalVideoRequest.addClinicalVideoComment; import com.example.caseData.request.CaseClinicalVideoRequest.addClinicalVideoComment;
import com.example.caseData.utils.Replace; import com.example.caseData.utils.Replace;
import com.fasterxml.jackson.databind.ObjectMapper;
import jakarta.annotation.Resource; import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletRequest; import jakarta.servlet.http.HttpServletRequest;
import jakarta.validation.ConstraintViolation;
import jakarta.validation.Validation;
import jakarta.validation.Validator;
import org.apache.commons.io.IOUtils; import org.apache.commons.io.IOUtils;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional; import org.springframework.transaction.annotation.Transactional;
@ -20,6 +27,7 @@ import java.nio.charset.StandardCharsets;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Objects; import java.util.Objects;
import java.util.Set;
//import static com.baomidou.mybatisplus.extension.toolkit.Db.removeById; //import static com.baomidou.mybatisplus.extension.toolkit.Db.removeById;
//import static com.baomidou.mybatisplus.extension.toolkit.Db.save; //import static com.baomidou.mybatisplus.extension.toolkit.Db.save;
@ -56,6 +64,9 @@ public class CaseClinicalVideoService {
@Resource @Resource
private UserCommentClinicalVideoDao userCommentClinicalVideoDao; private UserCommentClinicalVideoDao userCommentClinicalVideoDao;
@Resource
private Video Video;
/** /**
* 新增收藏-临床病例库-视频 * 新增收藏-临床病例库-视频
* @param videoId 视频id * @param videoId 视频id
@ -507,57 +518,30 @@ public class CaseClinicalVideoService {
/** /**
* 临床病例库-视频-同步app视频 * 临床病例库-视频-同步app视频
* @param videoId 视频id
* @param userId 用户id
* @return bool * @return bool
*/ */
@Transactional @Transactional
public boolean AddClinicalVideoApp(String videoId, String userId, addClinicalVideoComment request){ public boolean AddClinicalVideoApp(HttpServletRequest request){
// 获取视频数据 try {
CaseClinicalVideoModel video = caseClinicalVideoDao.selectById(videoId); // 1. 手动读取请求体并转为 addClinicalVideoApp 对象
if (video == null) { ObjectMapper objectMapper = new ObjectMapper();
throw new BusinessException("非法视频"); addClinicalVideoApp dto = objectMapper.readValue(request.getInputStream(), addClinicalVideoApp.class);
}
if (video.getVideoStatus() != 1){ // 2. 自动校验@Validated
throw new BusinessException("非法视频"); Validator validator = Validation.buildDefaultValidatorFactory().getValidator();
} Set<ConstraintViolation<addClinicalVideoApp>> violations = validator.validate(dto);
if (!violations.isEmpty()) {
String errorMessage = violations.iterator().next().getMessage();
throw new BusinessException("-1", errorMessage);
}
// 处理评论内容 // 检测签名
BasicSensitiveWordService.FilterResult result = basicSensitiveWordService.filter(request.getContent()); Video.checkSign(request,"26e8675f44565b1ed4eaaa0fcf3531d7",dto,objectMapper);
if (result.hasSensitive == 1){
throw new BusinessException("存在敏感词,请修改后提交");
}
// 新增评论 // 处理业务逻辑
UserCommentClinicalVideoModel userCommentClinicalVideoData = new UserCommentClinicalVideoModel();
userCommentClinicalVideoData.setUserId(Long.valueOf(userId));
userCommentClinicalVideoData.setVideoId(Long.valueOf(videoId));
userCommentClinicalVideoData.setStatus(1);
userCommentClinicalVideoData.setIsSensitive(0);
userCommentClinicalVideoData.setContent(request.getContent());
userCommentClinicalVideoData.setCommentImage(Replace.removeOssDomain(request.getCommentImage()));
// 评论根id } catch (Exception e) {
if (request.getRootId() != null) { throw new BusinessException("-1", e.getMessage());
userCommentClinicalVideoData.setRootId(Long.valueOf(request.getRootId()));
}
// 评论父级id
if (request.getParentId() != null) {
userCommentClinicalVideoData.setParentId(Long.valueOf(request.getParentId()));
}
int res = userCommentClinicalVideoDao.insert(userCommentClinicalVideoData);
if (res <= 0){
return false;
}
// 新增文章的统计字段
boolean r = IncClinicalVideoStats(videoId,3);
if (!r){
TransactionAspectSupport.currentTransactionStatus().setRollbackOnly();
return false;
} }
return true; return true;