From 6874438af3f780b260bd73658a8cb539435cd828 Mon Sep 17 00:00:00 2001 From: zhanglei Date: Mon, 27 Jul 2026 16:09:20 +0800 Subject: [PATCH] =?UTF-8?q?feat:=20bug=E4=BF=AE=E5=A4=8D?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../config/XssFilterOverrideConfig.java | 75 ++++++++----------- .../app/OrgPersonnelController.java | 34 +++++++++ .../institution/EvalRiskAnalysisExecutor.java | 5 +- .../institution/EvalSurveyAttachExecutor.java | 8 ++ 4 files changed, 78 insertions(+), 44 deletions(-) create mode 100644 safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/web/institution/app/OrgPersonnelController.java diff --git a/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/config/XssFilterOverrideConfig.java b/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/config/XssFilterOverrideConfig.java index 7dfcf22..fec7f88 100644 --- a/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/config/XssFilterOverrideConfig.java +++ b/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/config/XssFilterOverrideConfig.java @@ -2,14 +2,12 @@ package org.qinan.safetyeval.adapter.config; import cn.hutool.core.io.IoUtil; import com.jjb.saas.framework.core.filter.XssFilter; -import com.jjb.saas.framework.core.filter.XssHttpRequestWrapper; import lombok.extern.slf4j.Slf4j; import org.springframework.beans.BeansException; import org.springframework.beans.factory.config.BeanPostProcessor; import org.springframework.boot.web.servlet.FilterRegistrationBean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; -import org.springframework.core.Ordered; import org.springframework.web.filter.OncePerRequestFilter; import javax.servlet.Filter; @@ -30,8 +28,8 @@ import java.nio.charset.StandardCharsets; /** * 框架 XssFilter / LoggingBodyFilter 会按文本处理 body,破坏 WPS 二进制上传。 *

- * /safetyEval-h5/**:用可重复读的 byte[] 包装请求(不改 Interceptor 类型,避免启动失败); - * 其它接口仍走原 XSS / LoggingBodyFilter。 + * 仅对 /safetyEval-h5/** 做特殊处理:XSS 透传、Logging 用可重复读 byte[] 包装; + * 其它接口一律委托原 jar Filter,不改注册与顺序。 */ @Slf4j @Configuration @@ -44,19 +42,20 @@ public class XssFilterOverrideConfig { "org.minbox.framework.logging.client.filter.LoggingBodyFilter"; @Bean - public static BeanPostProcessor disableBinaryCorruptingFilters() { + public static BeanPostProcessor h5OnlyBinarySafeFilters() { return new BeanPostProcessor() { @Override public Object postProcessAfterInitialization(Object bean, String beanName) throws BeansException { if (bean instanceof FilterRegistrationBean) { - return processFilterRegistration((FilterRegistrationBean) bean, beanName); + return wrapFrameworkXssRegistration((FilterRegistrationBean) bean, beanName); } if (bean instanceof Filter && (LOGGING_BODY_FILTER_BEAN_NAME.equals(beanName) || LOGGING_BODY_FILTER_CLASS.equals(bean.getClass().getName()))) { Filter original = (Filter) bean; - log.info("wrap LoggingBodyFilter beanName={}, class={}", beanName, bean.getClass().getName()); + log.info("wrap LoggingBodyFilter for h5 only, beanName={}, class={}", + beanName, bean.getClass().getName()); return new OncePerRequestFilter() { @Override protected void doFilterInternal(HttpServletRequest request, @@ -77,50 +76,40 @@ public class XssFilterOverrideConfig { return bean; } - private Object processFilterRegistration(FilterRegistrationBean registration, String beanName) { - if (beanName.startsWith("safety") - || "safetyXssFilterRegistration".equals(beanName)) { + private Object wrapFrameworkXssRegistration(FilterRegistrationBean registration, String beanName) { + Filter original; + try { + original = registration.getFilter(); + } catch (Exception e) { return registration; } - Filter filter = null; - try { - filter = registration.getFilter(); - } catch (Exception ignored) { - // ignore uninitialized registration - } - boolean match = FRAMEWORK_XSS_BEAN_NAME.equals(beanName) || filter instanceof XssFilter; - if (match) { - registration.setEnabled(false); - log.info("disabled framework XSS filter registration: beanName={}", beanName); + boolean match = FRAMEWORK_XSS_BEAN_NAME.equals(beanName) || original instanceof XssFilter; + if (!match || original == null) { + return registration; } + + @SuppressWarnings("unchecked") + FilterRegistrationBean typed = (FilterRegistrationBean) registration; + typed.setFilter(new OncePerRequestFilter() { + @Override + protected void doFilterInternal(HttpServletRequest request, + HttpServletResponse response, + FilterChain chain) throws ServletException, IOException { + String uri = request.getRequestURI(); + if (isH5Uri(uri)) { + log.info("xss bypass for h5 uri={}", uri); + chain.doFilter(request, response); + return; + } + original.doFilter(request, response, chain); + } + }); + log.info("wrapped framework XSS filter for h5 bypass, beanName={}", beanName); return registration; } }; } - @Bean - public FilterRegistrationBean safetyXssFilterRegistration() { - FilterRegistrationBean bean = new FilterRegistrationBean<>(); - bean.setFilter(new OncePerRequestFilter() { - @Override - protected void doFilterInternal(HttpServletRequest request, - HttpServletResponse response, - FilterChain chain) throws ServletException, IOException { - String uri = request.getRequestURI(); - if (isH5Uri(uri)) { - log.info("xss bypass for h5 uri={}", uri); - chain.doFilter(request, response); - return; - } - chain.doFilter(new XssHttpRequestWrapper(request), response); - } - }); - bean.setName("safetyXssFilter"); - bean.addUrlPatterns("/*"); - bean.setOrder(Ordered.HIGHEST_PRECEDENCE + 20); - return bean; - } - private static boolean isH5Uri(String uri) { return uri != null && uri.contains(H5_URI_MARKER); } diff --git a/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/web/institution/app/OrgPersonnelController.java b/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/web/institution/app/OrgPersonnelController.java new file mode 100644 index 0000000..822cb99 --- /dev/null +++ b/safety-eval-adapter/src/main/java/org/qinan/safetyeval/adapter/web/institution/app/OrgPersonnelController.java @@ -0,0 +1,34 @@ +package org.qinan.safetyeval.adapter.web.institution.app; + +import io.swagger.annotations.Api; +import io.swagger.annotations.ApiOperation; +import org.qinan.safetyeval.client.api.OrgPersonnelApi; +import org.qinan.safetyeval.client.co.OrgPersonnelCO; +import org.qinan.safetyeval.client.dto.SingleResponse; +import org.qinan.safetyeval.infrastructure.adapter.auth.AuthUserContextAdapter; +import org.springframework.web.bind.annotation.GetMapping; +import org.springframework.web.bind.annotation.RequestMapping; +import org.springframework.web.bind.annotation.RestController; + +import javax.annotation.Resource; + +/** + * 人员信息适配层(Controller) + * + * @author safety-eval + */ +@Api(tags = "移动端人员信息管理") +@RestController +@RequestMapping("/safetyEval/org-personnel") +public class OrgPersonnelController { + + @Resource + private OrgPersonnelApi orgPersonnelApi; + + @ApiOperation("获取人员信息详情") + @GetMapping("/getCurrent") + public SingleResponse getCurrent() { + return orgPersonnelApi.get(AuthUserContextAdapter.getCurrentUserId()); + } + +} diff --git a/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalRiskAnalysisExecutor.java b/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalRiskAnalysisExecutor.java index f013611..c5c09a3 100644 --- a/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalRiskAnalysisExecutor.java +++ b/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalRiskAnalysisExecutor.java @@ -24,6 +24,7 @@ import org.qinan.safetyeval.infrastructure.mapper.EvalRiskParticipantMapper; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.transaction.annotation.Transactional; +import org.springframework.util.CollectionUtils; import org.springframework.util.StringUtils; import javax.annotation.Resource; @@ -105,7 +106,9 @@ public class EvalRiskAnalysisExecutor implements EvalRiskAnalysisApi { delIds.add(id); } } - evalRiskParticipantMapper.deleteBatchIds(delIds); + if (!CollectionUtils.isEmpty(delIds)) { + evalRiskParticipantMapper.deleteBatchIds(delIds); + } for (EvalRiskParticipantSaveCmd cmd : cmdList) { EvalRiskAnalysisEntity risk = requireRisk(cmd.getRiskId()); EvalRiskParticipantEntity entity = evalRiskAnalysisCmdConvertor.convertParticipantCmdToE(cmd); diff --git a/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalSurveyAttachExecutor.java b/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalSurveyAttachExecutor.java index 4a34855..ccf3f11 100644 --- a/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalSurveyAttachExecutor.java +++ b/safety-eval-app/src/main/java/org/qinan/safetyeval/app/executor/institution/EvalSurveyAttachExecutor.java @@ -1,5 +1,6 @@ package org.qinan.safetyeval.app.executor.institution; +import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import org.qinan.safetyeval.app.convertor.EvalSurveyCmdConvertor; import org.qinan.safetyeval.client.api.institution.EvalSurveyAttachApi; import org.qinan.safetyeval.client.co.institution.EvalSurveyAttachCO; @@ -9,6 +10,8 @@ import org.qinan.safetyeval.domain.constant.ProjectStageEnum; import org.qinan.safetyeval.domain.entity.EvalSurveyAttachEntity; import org.qinan.safetyeval.domain.service.EvalSurveyDomainService; import org.qinan.safetyeval.domain.service.ProjectStageSyncService; +import org.qinan.safetyeval.infrastructure.dataobject.EvalSurveyAttachDO; +import org.qinan.safetyeval.infrastructure.mapper.EvalSurveyAttachMapper; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.context.annotation.Lazy; import org.springframework.stereotype.Service; @@ -28,11 +31,16 @@ public class EvalSurveyAttachExecutor implements EvalSurveyAttachApi { private EvalSurveyCmdConvertor evalSurveyCmdConvertor; @Autowired private ProjectStageSyncService projectStageSyncService; + @Autowired + private EvalSurveyAttachMapper evalSurveyAttachMapper; @Override @Transactional(rollbackFor = Exception.class) public SingleResponse save(List cmdList) { + evalSurveyAttachMapper.delete(new LambdaQueryWrapper() + .eq(EvalSurveyAttachDO::getProjectId, cmdList.get(0).getProjectId())); for (EvalSurveyAttachSaveCmd cmd : cmdList) { + cmd.setId(null); EvalSurveyAttachEntity entity = evalSurveyCmdConvertor.convertAttachSaveCmdToE(cmd); evalSurveyDomainService.saveOrUpdateAttach(entity); }