feat: 全面对齐原 hospitalmiddle 出参契约

- Result 对齐旧结构 {"success","msg","data"}(移除 code 体系,异常统一 error(msg))
- nullAsWriteable=true:VO 序列化保留 null 字段(对齐 Jackson 默认)
- getPeStatus/getExamListByDate 强类型化(PeStatusPhyVo/ExamListVo,契约不变)
- getResultByPeId/getResultByIdcardAndYearAll 补报告组装(hospitalId/结论/建议/item子表)
- bsm SQL 换回旧视图(V_PHYEXAM_PE_STATUS/V_PHYEXAM_PE_PERSONAL_ITEM),修复
  PE_TRANSFER_HOSPITAL 列缺失与 peItemList 字段差异
- OkHttp → JDK HttpClient;shade 过滤重叠资源;排除重复 mybatis-plus-core 3.5.5

Co-Authored-By: Claude Code <noreply@anthropic.com>
This commit is contained in:
2026-09-04 18:54:11 +08:00
co-authored by Claude Code
parent 754448e370
commit 51b050bd4c
27 changed files with 791 additions and 1154 deletions
+1 -1
View File
@@ -54,4 +54,4 @@ mvnw.cmd
# JDK
*.jdk
*.jre
*.jredist/
+20 -10
View File
@@ -79,6 +79,14 @@
<dependency>
<groupId>org.noear</groupId>
<artifactId>mybatis-plus-solon-plugin</artifactId>
<!-- 排除插件传递的 core 3.5.5:显式声明的 mybatis-plus 3.5.9 已内含 core 类,
双版本共存既造成 shade 同类冲突(随机取一边混搭),也白白多出 ~4MB 体积 -->
<exclusions>
<exclusion>
<groupId>com.baomidou</groupId>
<artifactId>mybatis-plus-core</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>com.baomidou</groupId>
@@ -111,15 +119,8 @@
- sqlite-jdbc:原为 B 端 Agent 用,Agent 已拆分为独立 Python 项目
- h2:开发 Mock 数据源,需要时本地临时加回
- sa-token-solon-plugin:鉴权已改为 OrderApi 手写 HTTP Basic
- okhttpUptimeKuma 心跳已改用 JDK 内置 java.net.http.HttpClient
-->
<!-- ========== HTTPUptimeKuma 心跳用) ========== -->
<dependency>
<groupId>com.squareup.okhttp3</groupId>
<artifactId>okhttp</artifactId>
</dependency>
<!-- ========== JSON 解析(Solon 生态标准库) ========== -->
<dependency>
<groupId>org.noear</groupId>
<artifactId>snack3</artifactId>
@@ -134,7 +135,7 @@
</dependencies>
<build>
<finalName>hospital-front-${project.version}</finalName>
<finalName>hospital-front</finalName>
<plugins>
<!-- 打 fat jar(包含所有依赖) -->
@@ -163,10 +164,19 @@
<exclude>META-INF/*.SF</exclude>
<exclude>META-INF/*.DSA</exclude>
<exclude>META-INF/*.RSA</exclude>
<!-- 依赖自带的模块描述文件与 fat jar 不兼容,剔除以消除 shade 警告 -->
<exclude>module-info.class</exclude>
<exclude>META-INF/versions/*/module-info.class</exclude>
<!-- 以下重叠资源均为 IDE 提示/native-image 元数据/许可证文本,
运行时不读取,剔除以消除 shade 的 overlapping 警告 -->
<exclude>META-INF/solon/solon-configuration-metadata.json</exclude>
<exclude>META-INF/native-image/**</exclude>
<exclude>META-INF/LICENSE</exclude>
<exclude>META-INF/MANIFEST.MF</exclude>
</excludes>
</filter>
</filters>
<finalName>hospital-front-${project.version}</finalName>
<finalName>hospital-front</finalName>
</configuration>
</execution>
</executions>
@@ -1,5 +1,11 @@
package com.hospital.front.adapter;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import com.hospital.front.dto.ProcResult;
import com.hospital.front.dto.Result;
import com.hospital.front.mapper.bsm.BsmOrderMapper;
@@ -32,7 +38,7 @@ public abstract class BsmAdapterBase implements HospitalAdapter {
try {
return Result.success(mapper.ping() == 1);
} catch (Exception e) {
return Result.error(Result.CODE_DB_UNREACHABLE, "数据库连接失败:" + e.getMessage());
return Result.error("数据库连接失败:" + e.getMessage());
}
}
@@ -87,7 +93,7 @@ public abstract class BsmAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getPhyexamStatus(String peIds) {
public List<PeStatusVo> getPhyexamStatus(String peIds) {
return mapper.getPhyexamStatus(peIds);
}
@@ -122,65 +128,45 @@ public abstract class BsmAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getConclusion(String peId) {
return mapper.getConclusion(peId);
}
@Override
public List<Map<String, Object>> getConclusionAll(String peId) {
public List<ConclusionVo> getConclusionAll(String peId) {
return mapper.getConclusionAll(peId);
}
@Override
public List<Map<String, Object>> getSuggest(String peId) {
return mapper.getSuggest(peId);
}
@Override
public List<Map<String, Object>> getSuggestAll(String peId) {
public List<SuggestVo> getSuggestAll(String peId) {
return mapper.getSuggestAll(peId);
}
@Override
public Map<String, Object> getPeStatusByIdnoAndYear(String idNo, String year) {
public PeStatusVo getPeStatusByIdnoAndYear(String idNo, String year) {
return mapper.getPeStatusByIdnoAndYear(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByIdcardAndYear(String idNo, String year) {
public List<MedicalMiddleResultVo> getResultByIdcardAndYear(String idNo, String year) {
return mapper.getResultByIdcardAndYear(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByIdcardAndYearAll(String idNo, String year) {
public List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(String idNo, String year) {
return mapper.getResultByIdcardAndYearAll(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByPeId(String peId) {
public List<MedicalMiddleResultVo> getResultByPeId(String peId) {
return mapper.getResultByPeId(peId);
}
@Override
public List<Map<String, Object>> getDisResultByAuditDate(String auditDate) {
return mapper.getDisResultByAuditDate(auditDate);
}
@Override
public List<Map<String, Object>> getItemByPeId(String peId) {
public List<MedicalMiddleResultVo> getItemByPeId(String peId) {
return mapper.getItemByPeId(peId);
}
@Override
public List<Map<String, Object>> getItemByPeIdAll(String peId) {
public List<MedicalMiddleResultVo> getItemByPeIdAll(String peId) {
return mapper.getItemByPeIdAll(peId);
}
@Override
public List<Map<String, Object>> getResultByIdNoOrPeId(String idNo, String peId, String auditYear) {
return mapper.getResultByIdNoOrPeId(idNo, peId, auditYear);
}
@Override
public Map<String, Object> getPeIdAndDateByIdcard(String idNo) {
return mapper.getPeIdAndDateByIdcard(idNo);
@@ -192,7 +178,7 @@ public abstract class BsmAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getExamListByDate(String auditDate) {
public List<ExamListVo> getExamListByDate(String auditDate) {
return mapper.getExamListByDate(auditDate);
}
@@ -1,5 +1,11 @@
package com.hospital.front.adapter;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import com.hospital.front.dto.ProcResult;
import com.hospital.front.dto.Result;
import com.hospital.front.vo.UnitVo;
@@ -8,93 +14,76 @@ import java.util.List;
import java.util.Map;
/**
* 医院适配器接口(策略模式)。
* 医院适配器接口(各医院方言实现:bsm/nx/ya)。
*
* 5 家医院各自实现本接口,通过 HospitalRouter 按医院编码路由。
* 所有数据库差异(Oracle/SqlServer 方言、存储过程名)均封装在实现内;
* 存储过程的入参出参契约由医院 HIS 系统约定,不可修改。
*
* 查询类方法统一返回 Map 列表(列名与医院视图/存储过程保持一致)。
* getConclusion/getSuggest 与其 All 版 SQL 完全重复,已合并为 All 版
* (对外接口路径 /getConclusion、/getSuggest 保留,内部走 All 版)。
*/
public interface HospitalAdapter {
/** 医院编码(拼音):xinglongyuan / qingyang / ningxia / yanan / jinghe / dev */
/** 医院编码(唯一,如 jinghe */
String code();
/** 医院中文名(日志与展示用) */
/** 医院显示名 */
String displayName();
/** Mapper 方言类型bsmOracle/ nx / yaSqlServer */
/** 医院方言类型bsm/nx/ya */
String hmType();
/** 轻量健康检查SELECT 1 探测) */
/** 数据库健康检查 */
Result<Boolean> healthCheck();
// ================= 存储过程(写) =================
/** 提交预约(P_ADD_PE_REGIST */
/** 提交预约(存储过程) */
ProcResult saveOrder(String peInfoStr, String peItemStr);
/** 取消预约(P_DEL_PE_REGIST */
/** 取消预约(存储过程 */
ProcResult cancelOrder(String peId, String name, String idcard);
/** 添加/修改单位(P_ADD_UNIT */
/** 添加/修改单位(存储过程,V1/V2 参数不同 */
ProcResult addUnit(UnitVo unit, boolean useV2);
// ================= 查询(视图) =================
/** 体检状态查询(多个 peId 逗号分隔) */
List<PeStatusVo> getPhyexamStatus(String peIds);
/** 体检预约 ID(逗号分隔多个)查询体检状态 */
List<Map<String, Object>> getPhyexamStatus(String peIds);
/** 医院所有体检项目(组合项) */
/** 体检项目查询 */
List<Map<String, Object>> getItemList();
/** 医院所有体检项目及指标项 */
/** 体检指标项及体检组合数据 */
List<Map<String, Object>> getAllItemList();
/** 医院所有体检指标项 */
/** 体检指标项数据 */
List<Map<String, Object>> getPeItemList();
/** 按指标项 CODE 查询所属体检组合 */
/** 按体检指标项查所属组合 */
List<Map<String, Object>> getItemInfo(String peItemCode);
/** 员工体检项目 */
List<Map<String, Object>> getEmpItem(String peId);
/** 员工体检结果 */
/** 按体检编号查体检结果 */
List<Map<String, Object>> getResult(String peId);
/** 体检结论(列表 / 全量 */
List<Map<String, Object>> getConclusion(String peId);
/** 体检结论(列表) */
List<ConclusionVo> getConclusionAll(String peId);
List<Map<String, Object>> getConclusionAll(String peId);
/** 体检建议(列表 / 全量) */
List<Map<String, Object>> getSuggest(String peId);
List<Map<String, Object>> getSuggestAll(String peId);
/** 体检建议(全量,内部组装用) */
List<SuggestVo> getSuggestAll(String peId);
/** 按身份证号 + 年份查询体检状态 */
Map<String, Object> getPeStatusByIdnoAndYear(String idNo, String year);
PeStatusVo getPeStatusByIdnoAndYear(String idNo, String year);
/** 按身份证号 + 年份查询体检结果(默认 / 全量) */
List<Map<String, Object>> getResultByIdcardAndYear(String idNo, String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYear(String idNo, String year);
List<Map<String, Object>> getResultByIdcardAndYearAll(String idNo, String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(String idNo, String year);
/** 按体检编号查询体检结果 */
List<Map<String, Object>> getResultByPeId(String peId);
/** 按审核日期查询体检报告(去重主表) */
List<Map<String, Object>> getDisResultByAuditDate(String auditDate);
List<MedicalMiddleResultVo> getResultByPeId(String peId);
/** 按体检编号查询体检项目子表(默认 / 全量) */
List<Map<String, Object>> getItemByPeId(String peId);
List<MedicalMiddleResultVo> getItemByPeId(String peId);
List<Map<String, Object>> getItemByPeIdAll(String peId);
/** 按身份证号或体检编号 + 审核年份查询体检结果 */
List<Map<String, Object>> getResultByIdNoOrPeId(String idNo, String peId, String auditYear);
List<MedicalMiddleResultVo> getItemByPeIdAll(String peId);
/** 按身份证号查询当年 peId 与预约日期(单条 / 列表) */
Map<String, Object> getPeIdAndDateByIdcard(String idNo);
@@ -102,5 +91,5 @@ public interface HospitalAdapter {
List<Map<String, Object>> getPeIdAndDateByIdcardList(String idNo);
/** 按审核日期查询当天体检人员列表(去重;日期空则当天) */
List<Map<String, Object>> getExamListByDate(String auditDate);
List<ExamListVo> getExamListByDate(String auditDate);
}
@@ -1,5 +1,11 @@
package com.hospital.front.adapter;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import com.hospital.front.dto.ProcResult;
import com.hospital.front.dto.Result;
import com.hospital.front.mapper.nx.NxOrderMapper;
@@ -31,7 +37,7 @@ public abstract class NxAdapterBase implements HospitalAdapter {
try {
return Result.success(mapper.ping() == 1);
} catch (Exception e) {
return Result.error(Result.CODE_DB_UNREACHABLE, "数据库连接失败:" + e.getMessage());
return Result.error("数据库连接失败:" + e.getMessage());
}
}
@@ -83,7 +89,7 @@ public abstract class NxAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getPhyexamStatus(String peIds) {
public List<PeStatusVo> getPhyexamStatus(String peIds) {
return mapper.getPhyexamStatus(peIds);
}
@@ -118,65 +124,45 @@ public abstract class NxAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getConclusion(String peId) {
return mapper.getConclusion(peId);
}
@Override
public List<Map<String, Object>> getConclusionAll(String peId) {
public List<ConclusionVo> getConclusionAll(String peId) {
return mapper.getConclusionAll(peId);
}
@Override
public List<Map<String, Object>> getSuggest(String peId) {
return mapper.getSuggest(peId);
}
@Override
public List<Map<String, Object>> getSuggestAll(String peId) {
public List<SuggestVo> getSuggestAll(String peId) {
return mapper.getSuggestAll(peId);
}
@Override
public Map<String, Object> getPeStatusByIdnoAndYear(String idNo, String year) {
public PeStatusVo getPeStatusByIdnoAndYear(String idNo, String year) {
return mapper.getPeStatusByIdnoAndYear(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByIdcardAndYear(String idNo, String year) {
public List<MedicalMiddleResultVo> getResultByIdcardAndYear(String idNo, String year) {
return mapper.getResultByIdcardAndYear(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByIdcardAndYearAll(String idNo, String year) {
public List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(String idNo, String year) {
return mapper.getResultByIdcardAndYearAll(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByPeId(String peId) {
public List<MedicalMiddleResultVo> getResultByPeId(String peId) {
return mapper.getResultByPeId(peId);
}
@Override
public List<Map<String, Object>> getDisResultByAuditDate(String auditDate) {
return mapper.getDisResultByAuditDate(auditDate);
}
@Override
public List<Map<String, Object>> getItemByPeId(String peId) {
public List<MedicalMiddleResultVo> getItemByPeId(String peId) {
return mapper.getItemByPeId(peId);
}
@Override
public List<Map<String, Object>> getItemByPeIdAll(String peId) {
public List<MedicalMiddleResultVo> getItemByPeIdAll(String peId) {
return mapper.getItemByPeIdAll(peId);
}
@Override
public List<Map<String, Object>> getResultByIdNoOrPeId(String idNo, String peId, String auditYear) {
return mapper.getResultByIdNoOrPeId(idNo, peId, auditYear);
}
@Override
public Map<String, Object> getPeIdAndDateByIdcard(String idNo) {
return mapper.getPeIdAndDateByIdcard(idNo);
@@ -188,7 +174,7 @@ public abstract class NxAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getExamListByDate(String auditDate) {
public List<ExamListVo> getExamListByDate(String auditDate) {
return mapper.getExamListByDate(auditDate);
}
@@ -1,5 +1,11 @@
package com.hospital.front.adapter;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import com.hospital.front.dto.ProcResult;
import com.hospital.front.dto.Result;
import com.hospital.front.mapper.ya.YaOrderMapper;
@@ -31,7 +37,7 @@ public abstract class YaAdapterBase implements HospitalAdapter {
try {
return Result.success(mapper.ping() == 1);
} catch (Exception e) {
return Result.error(Result.CODE_DB_UNREACHABLE, "数据库连接失败:" + e.getMessage());
return Result.error("数据库连接失败:" + e.getMessage());
}
}
@@ -64,6 +70,7 @@ public abstract class YaAdapterBase implements HospitalAdapter {
@Override
public ProcResult addUnit(UnitVo unit, boolean useV2) {
// 延安医院仅有 V1 存储过程(对齐旧项目 YaOrderMapper),useV2 忽略统一走 V1
Map<String, Object> map = new HashMap<>();
map.put("unitCode", unit.getUnitCode());
map.put("unitName", unit.getUnitName());
@@ -73,11 +80,7 @@ public abstract class YaAdapterBase implements HospitalAdapter {
map.put("phone1", unit.getPhone1());
map.put("connecter2", unit.getConnecter2());
map.put("phone2", unit.getPhone2());
if (useV2) {
mapper.addUnitV2(map);
} else {
mapper.addUnit(map);
}
mapper.addUnit(map);
return new ProcResult(
str(map.get("resultCode")),
str(map.get("errorMsg")),
@@ -86,7 +89,7 @@ public abstract class YaAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getPhyexamStatus(String peIds) {
public List<PeStatusVo> getPhyexamStatus(String peIds) {
return mapper.getPhyexamStatus(peIds);
}
@@ -121,65 +124,45 @@ public abstract class YaAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getConclusion(String peId) {
return mapper.getConclusion(peId);
}
@Override
public List<Map<String, Object>> getConclusionAll(String peId) {
public List<ConclusionVo> getConclusionAll(String peId) {
return mapper.getConclusionAll(peId);
}
@Override
public List<Map<String, Object>> getSuggest(String peId) {
return mapper.getSuggest(peId);
}
@Override
public List<Map<String, Object>> getSuggestAll(String peId) {
public List<SuggestVo> getSuggestAll(String peId) {
return mapper.getSuggestAll(peId);
}
@Override
public Map<String, Object> getPeStatusByIdnoAndYear(String idNo, String year) {
public PeStatusVo getPeStatusByIdnoAndYear(String idNo, String year) {
return mapper.getPeStatusByIdnoAndYear(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByIdcardAndYear(String idNo, String year) {
public List<MedicalMiddleResultVo> getResultByIdcardAndYear(String idNo, String year) {
return mapper.getResultByIdcardAndYear(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByIdcardAndYearAll(String idNo, String year) {
public List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(String idNo, String year) {
return mapper.getResultByIdcardAndYearAll(idNo, year);
}
@Override
public List<Map<String, Object>> getResultByPeId(String peId) {
public List<MedicalMiddleResultVo> getResultByPeId(String peId) {
return mapper.getResultByPeId(peId);
}
@Override
public List<Map<String, Object>> getDisResultByAuditDate(String auditDate) {
return mapper.getDisResultByAuditDate(auditDate);
}
@Override
public List<Map<String, Object>> getItemByPeId(String peId) {
public List<MedicalMiddleResultVo> getItemByPeId(String peId) {
return mapper.getItemByPeId(peId);
}
@Override
public List<Map<String, Object>> getItemByPeIdAll(String peId) {
public List<MedicalMiddleResultVo> getItemByPeIdAll(String peId) {
return mapper.getItemByPeIdAll(peId);
}
@Override
public List<Map<String, Object>> getResultByIdNoOrPeId(String idNo, String peId, String auditYear) {
return mapper.getResultByIdNoOrPeId(idNo, peId, auditYear);
}
@Override
public Map<String, Object> getPeIdAndDateByIdcard(String idNo) {
return mapper.getPeIdAndDateByIdcard(idNo);
@@ -191,7 +174,7 @@ public abstract class YaAdapterBase implements HospitalAdapter {
}
@Override
public List<Map<String, Object>> getExamListByDate(String auditDate) {
public List<ExamListVo> getExamListByDate(String auditDate) {
return mapper.getExamListByDate(auditDate);
}
@@ -53,7 +53,7 @@ public class AdminApi {
private void checkToken(Context ctx) {
String expected = Solon.cfg().get("admin.token", "");
if (expected != null && !expected.trim().isEmpty() && !expected.equals(ctx.header("X-Admin-Token"))) {
throw BusinessException.of(Result.CODE_AUTH_FAILED, "管理接口鉴权失败");
throw BusinessException.of("管理接口鉴权失败");
}
}
@@ -66,12 +66,12 @@ public class AdminApi {
Runtime mem = Runtime.getRuntime();
Result<Boolean> db = router.active().healthCheck();
Map<String, Object> out = new LinkedHashMap<>();
out.put("status", db.getCode() == 0 ? "UP" : "DEGRADED");
out.put("status", db.isSuccess() ? "UP" : "DEGRADED");
out.put("hospital", router.activeCode());
out.put("hospitalName", router.active().displayName());
out.put("registeredHospitals", router.registeredCodes());
Map<String, Object> database = new HashMap<>();
database.put("ok", db.getCode() == 0);
database.put("ok", db.isSuccess());
database.put("msg", db.getMsg());
out.put("database", database);
Map<String, Object> jvm = new HashMap<>();
@@ -1,6 +1,7 @@
package com.hospital.front.api.order;
import java.util.ArrayList;
import com.hospital.front.vo.MedicalMiddleResultVo;
import java.util.Base64;
import java.util.List;
import java.util.Map;
@@ -14,13 +15,14 @@ import org.noear.solon.annotation.Path;
import org.noear.solon.core.handle.Context;
import org.noear.solon.core.handle.MethodType;
import org.noear.solon.Solon;
import org.noear.snack.ONode;
import com.hospital.front.dto.Result;
import com.hospital.front.infra.annotation.ApiMeta;
import com.hospital.front.infra.annotation.ApiParam;
import com.hospital.front.infra.exception.BusinessException;
import com.hospital.front.service.OrderService;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.PeStatusPhyVo;
/**
* 体检预约业务接口,路径前缀 /order。
@@ -74,7 +76,7 @@ public class OrderApi {
// 认证失败:401 + 质询头(对齐 Sa-Token SaBasicUtil.check 的响应行为)
ctx.status(401);
ctx.headerSet("WWW-Authenticate", "Basic realm=\"hospital-front\"");
throw BusinessException.of(Result.CODE_AUTH_FAILED, "Basic 认证失败");
throw BusinessException.of("Basic 认证失败");
}
/** 恒定时间字符串比较(防时序攻击) */
@@ -91,12 +93,10 @@ public class OrderApi {
@ApiParam(name = "body", desc = "预约 JSON 体")
})
@Mapping(value = "/saveOrder", method = {MethodType.POST})
public Result<String> saveOrder(Context ctx, @Body String body) {
public Result<String> saveOrder(Context ctx, @Body com.hospital.front.vo.OrderV2Vo body) {
checkBasic(ctx);
// Solon 对 Map 泛型 body 反序列化支持不佳,用 snack3 手动解析
@SuppressWarnings("unchecked")
Map<String, Object> map = (Map<String, Object>) ONode.load(body).toObject(Map.class);
return Result.success(service.saveOrder(map));
// 强类型 DTO 直收(Solon 对 DTO 反序列化无问题),避免 Map 中转
return Result.success(service.saveOrder(body));
}
/** 5. 取消体检预约 */
@@ -123,7 +123,7 @@ public class OrderApi {
@ApiParam(name = "peIds", desc = "体检编号逗号分隔")
})
@Mapping("/getPeStatus/{peIds}")
public Result<List<Map<String, String>>> getPeStatus(Context ctx, @Path("peIds") String peIds) {
public Result<List<PeStatusPhyVo>> getPeStatus(Context ctx, @Path("peIds") String peIds) {
checkBasic(ctx);
return Result.success(service.getPhyexamStatus(peIds));
}
@@ -197,58 +197,14 @@ public class OrderApi {
return Result.success(service.getResult(peId));
}
/** 9. 体检结论(汇总) */
@ApiMeta(desc = "体检结论(汇总)", params = {
@ApiParam(name = "peId", desc = "体检编号")
})
@Mapping("/getTotalConclusion/{peId}")
public Result<Map<String, String>> getTotalConclusion(Context ctx, @Path("peId") String peId) {
checkBasic(ctx);
return Result.success(service.getTotalConclusion(peId));
}
/** 10. 体检建议(汇总) */
@ApiMeta(desc = "体检建议(汇总)", params = {
@ApiParam(name = "peId", desc = "体检编号")
})
@Mapping("/getTotalSuggest/{peId}")
public Result<Map<String, String>> getTotalSuggest(Context ctx, @Path("peId") String peId) {
checkBasic(ctx);
return Result.success(service.getTotalSuggest(peId));
}
/** 11. 体检结论(列表) */
@ApiMeta(desc = "体检结论(列表)", params = {
@ApiParam(name = "peId", desc = "体检编号")
})
@Mapping("/getConclusion/{peId}")
public Result<List<Map<String, Object>>> getConclusion(Context ctx, @Path("peId") String peId) {
checkBasic(ctx);
return Result.success(service.getConclusion(peId));
}
/** 12. 体检建议(列表) */
@ApiMeta(desc = "体检建议(列表)", params = {
@ApiParam(name = "peId", desc = "体检编号")
})
@Mapping("/getSuggest/{peId}")
public Result<List<Map<String, Object>>> getSuggest(Context ctx, @Path("peId") String peId) {
checkBasic(ctx);
return Result.success(service.getSuggest(peId));
}
// 9/10/11/12(体检结论/建议 汇总与列表)不再对外暴露:结论/建议仅作为
// 体检报告的组成部分在应用层组装,相关查询(getConclusionAll/getSuggestAll)为内部使用
// ================= 5. 按身份证 / 日期查询 =================
/** 14. 根据身份证及年份获取体检结果 */
@ApiMeta(desc = "按身份证及年份查体检结果", params = {
@ApiParam(name = "idNo", desc = "身份证号"),
@ApiParam(name = "year", desc = "年份")
})
@Mapping("/getResultByIdcardAndYear/{idNo}/{year}")
public Result<List<Map<String, Object>>> getResultByIdcardAndYear(Context ctx, @Path("idNo") String idNo, @Path("year") String year) {
checkBasic(ctx);
return Result.success(service.getResultByIdcardAndYear(idNo, year));
}
// 14(按身份证及年份查结果)/ 15.3(按审查日期查报告)/ 16(按身份证或编号+年份查报告)
// 不再对外暴露:相关查询为内部使用(如 getPeStatusByIdnoAndYear 的宁夏兜底)
// 14.1 全量版保留对外
/** 14.1 根据身份证号及年份获取体检结果(全量) */
@ApiMeta(desc = "按身份证及年份查全量结果", params = {
@@ -256,7 +212,7 @@ public class OrderApi {
@ApiParam(name = "year", desc = "年份")
})
@Mapping("/getResultByIdcardAndYearAll/{idNo}/{year}")
public Result<List<Map<String, Object>>> getResultByIdcardAndYearAll(Context ctx, @Path("idNo") String idNo, @Path("year") String year) {
public Result<List<MedicalMiddleResultVo>> getResultByIdcardAndYearAll(Context ctx, @Path("idNo") String idNo, @Path("year") String year) {
checkBasic(ctx);
return Result.success(service.getResultByIdcardAndYearAll(idNo, year));
}
@@ -266,7 +222,7 @@ public class OrderApi {
@ApiParam(name = "peId", desc = "体检编号")
})
@Mapping("/getResultByPeId/{peId}")
public Result<List<Map<String, Object>>> getResultByPeId(Context ctx, @Path("peId") String peId) {
public Result<List<MedicalMiddleResultVo>> getResultByPeId(Context ctx, @Path("peId") String peId) {
checkBasic(ctx);
return Result.success(service.getResultByPeId(peId));
}
@@ -276,40 +232,11 @@ public class OrderApi {
@ApiParam(name = "peId", desc = "体检编号")
})
@Mapping("/getResultStatus/{peId}")
public Result<List<Map<String, Object>>> getResultStatus(Context ctx, @Path("peId") String peId) {
public Result<List<MedicalMiddleResultVo>> getResultStatus(Context ctx, @Path("peId") String peId) {
checkBasic(ctx);
return Result.success(service.getResultByPeId(peId));
}
/** 15.3 根据 audit_date 查询当天的体检报告 */
@ApiMeta(desc = "按审查日期查体检报告", params = {
@ApiParam(name = "auditDate", desc = "审查日期 yyyy-MM-dd")
})
@Mapping("/getResultByAuditDate/{auditDate}")
public Result<List<Map<String, Object>>> getResultByAuditDate(Context ctx, @Path("auditDate") String auditDate) {
checkBasic(ctx);
return Result.success(service.getResultByAuditDate(auditDate));
}
/** 16. 根据 id_code 或 pe_id 和审查年份查询体检报告 */
@ApiMeta(desc = "按身份证或体检编号及年份查报告", params = {
@ApiParam(name = "idNo", desc = "身份证号(与 peId 二选一)"),
@ApiParam(name = "peId", desc = "体检编号(与 idNo 二选一)"),
@ApiParam(name = "auditYear", desc = "审查年份")
})
@Mapping(value = "/getResultByIdNoOrPeId", method = {MethodType.POST})
public Result<List<Map<String, Object>>> getResultByIdNoOrPeId(
Context ctx,
@Param(value = "idNo", required = false) String idNo,
@Param(value = "peId", required = false) String peId,
@Param("auditYear") String auditYear) {
checkBasic(ctx);
if (isNullOrBlank(idNo) && isNullOrBlank(peId)) {
throw BusinessException.paramMissing("身份证号或体检编号");
}
return Result.success(service.getResultByIdNoOrPeId(idNo, peId, auditYear));
}
/** 17. 根据身份证号查询当前年的 peId 和预约日期 */
@ApiMeta(desc = "按身份证查当年 peId 和预约日期", params = {
@ApiParam(name = "idNo", desc = "身份证号")
@@ -339,16 +266,8 @@ public class OrderApi {
@Mapping(value = "/addUnit", method = {MethodType.POST})
public Result<?> addUnit(Context ctx, @Body String body) {
checkBasic(ctx);
// Solon 对 List 泛型 body 反序列化支持不佳,此处用 snack3 手动解析
List<Map<String, Object>> units;
if (body == null || body.trim().isEmpty()) {
units = new ArrayList<>();
} else {
@SuppressWarnings("unchecked")
List<Map<String, Object>> parsed = (List<Map<String, Object>>) ONode.load(body).toObject(List.class);
units = parsed;
}
String errors = service.addUnits(units);
// Solon 对 List 泛型 body 支持不佳,用 JsonUtils 统一解析(空串返回空列表)
String errors = service.addUnits(com.hospital.front.infra.util.JsonUtils.parseList(body));
return errors != null ? Result.error(errors) : Result.success();
}
@@ -357,7 +276,7 @@ public class OrderApi {
@ApiParam(name = "auditDate", desc = "审查日期(空则查当天)")
})
@Mapping("/getExamListByDate")
public Result<List<Map<String, Object>>> getExamListByDate(Context ctx, @Param("auditDate") String auditDate) {
public Result<List<ExamListVo>> getExamListByDate(Context ctx, @Param("auditDate") String auditDate) {
checkBasic(ctx);
return Result.success(service.getExamListByDate(auditDate));
}
@@ -1,114 +1,49 @@
package com.hospital.front.dto;
import lombok.Data;
/**
* 统一 API 响应包装。
*
* 业务接口均使用此结构返回,便于前端统一处理。
* 结构与原 hospitalmiddle 的 Result 保持一致(对外 JSON 契约,不可修改):
* {"success": true/false, "msg": "成功", "data": ...}
*
* @param <T> 数据类型
* @author hospital-front重构
*/
@Data
public class Result<T> {
/** 业务码(0=成功 */
private final int code;
/** 是否成功 */
private boolean success = false;
/** 提示信息 */
private final String msg;
private String msg;
/** 业务数据 */
private final T data;
private T data;
/**
* 全参构造器。
*
* @param code 业务码(0=成功)
* @param msg 提示信息
* @param data 业务数据(可为 null
*/
public Result(int code, String msg, T data) {
this.code = code;
this.msg = msg;
this.data = data;
/** 成功响应(无数据),msg 固定"成功"(对齐原项目) */
public static Result success() {
Result result = new Result();
result.setSuccess(true);
result.setMsg("成功");
return result;
}
/**
* 两参构造器(data 默认为 null,与 Kotlin 默认参数语义一致)。
*
* @param code 业务码
* @param msg 提示信息
*/
public Result(int code, String msg) {
this(code, msg, null);
/** 成功响应(带数据) */
public static <T> Result success(T t) {
Result result = new Result();
result.setSuccess(true);
result.setMsg("成功");
result.setData(t);
return result;
}
/** 业务成功码 */
public static final int SUCCESS_CODE = 0;
/** 业务失败默认码 */
public static final int ERROR_CODE = 5001;
/** 参数缺失 */
public static final int CODE_PARAM_MISSING = 1001;
/** 参数格式错误 */
public static final int CODE_PARAM_FORMAT = 1002;
/** 业务校验失败 */
public static final int CODE_BUSINESS = 1003;
/** 存储过程调用失败 */
public static final int CODE_PROC_FAILED = 2001;
/** 数据库连接失败 */
public static final int CODE_DB_UNREACHABLE = 2002;
/** 医院系统返回业务失败 */
public static final int CODE_HOSPITAL_FAILED = 2003;
/** 鉴权失败 */
public static final int CODE_AUTH_FAILED = 3001;
/** Token 过期 */
public static final int CODE_TOKEN_EXPIRED = 3002;
/**
* 成功响应(无数据)。
*/
public static <T> Result<T> success() {
return new Result<>(SUCCESS_CODE, "success", null);
}
/**
* 成功响应。
*/
public static <T> Result<T> success(T data) {
return new Result<>(SUCCESS_CODE, "success", data);
}
/**
* 错误响应(默认错误码)。
*/
public static <T> Result<T> error(String msg) {
return new Result<>(ERROR_CODE, msg, null);
}
/**
* 错误响应(指定错误码)。
*/
public static <T> Result<T> error(int code, String msg) {
return new Result<>(code, msg, null);
}
public int getCode() {
return code;
}
public String getMsg() {
return msg;
}
public T getData() {
return data;
/** 错误响应 */
public static Result error(String msg) {
Result result = new Result();
result.setSuccess(false);
result.setMsg(msg);
return result;
}
}
@@ -58,11 +58,15 @@ public final class ApiScanner {
// 拼接完整路径
String path = prefix + (methodMapping.value() == null ? "" : methodMapping.value());
// HTTP 方法:method() 空数组视为 GET
// HTTP 方法:Solon @Mapping 不显式指定时 method() 返回 ALL(支持所有方法),
// 接口测试场景下默认按 GET 处理(OrderApi 的 GET 接口均未显式指定 method)
String httpMethod = "GET";
MethodType[] mtypes = methodMapping.method();
if (mtypes != null && mtypes.length > 0) {
httpMethod = mtypes[0].name();
String name = mtypes[0].name();
if (!"ALL".equals(name) && !"UNKNOWN".equals(name)) {
httpMethod = name;
}
}
// @ApiMeta.params 转 name→desc 映射,供参数补充描述
@@ -1,11 +1,10 @@
package com.hospital.front.infra.exception;
import com.hospital.front.dto.Result;
/**
* 业务异常。
*
* 用于业务层显式抛出指定错误码的异常,会被 GlobalExceptionHandler 捕获并包装为 Result。
* 对外契约与原 hospitalmiddle 一致:异常统一以 {"success":false,"msg":...} 返回,
* 不携带错误码(code 体系已随 Result 对齐移除,分类信息仅用于日志排查)。
*
* @author hospital-front重构
*/
@@ -13,46 +12,32 @@ public class BusinessException extends RuntimeException {
private static final long serialVersionUID = 1L;
/** 业务错误码(参见 Result 中的常量) */
private final int code;
/**
* 构造业务异常。
*
* @param code 业务错误码
* @param message 错误描述
*/
public BusinessException(int code, String message) {
public BusinessException(String message) {
super(message);
this.code = code;
}
/**
* 静态工厂方法。
*
* @param code 业务错误码
* @param message 错误描述
*/
public static BusinessException of(int code, String message) {
return new BusinessException(code, message);
/** 静态工厂方法 */
public static BusinessException of(String message) {
return new BusinessException(message);
}
/** 参数缺失异常 */
public static BusinessException paramMissing(String field) {
return new BusinessException(Result.CODE_PARAM_MISSING, "参数缺失:" + field);
return new BusinessException("参数缺失:" + field);
}
/** 业务校验失败异常 */
public static BusinessException businessFailed(String msg) {
return new BusinessException(Result.CODE_BUSINESS, msg);
return new BusinessException(msg);
}
/** 存储过程调用失败异常 */
public static BusinessException procFailed(String msg) {
return new BusinessException(Result.CODE_PROC_FAILED, msg);
}
public int getCode() {
return code;
return new BusinessException(msg);
}
}
@@ -25,34 +25,32 @@ public class GlobalExceptionHandler implements Filter {
chain.doFilter(ctx);
} catch (BusinessException e) {
String msg = e.getMessage() != null ? e.getMessage() : "业务异常";
log.warn("业务异常:code={}, msg={}", e.getCode(), e.getMessage());
renderResult(ctx, Result.error(e.getCode(), msg));
log.warn("业务异常:{}", e.getMessage());
renderResult(ctx, Result.error(msg));
} catch (IllegalArgumentException e) {
String msg = e.getMessage() != null ? e.getMessage() : "参数错误";
log.warn("参数异常:{}", e.getMessage());
renderResult(ctx, Result.error(Result.CODE_PARAM_FORMAT, msg));
renderResult(ctx, Result.error(msg));
} catch (Exception e) {
log.error("系统异常", e);
String msg = e.getMessage() != null ? e.getMessage() : e.getClass().getSimpleName();
renderResult(ctx, Result.error(Result.ERROR_CODE, "系统异常:" + msg));
renderResult(ctx, Result.error("系统异常:" + msg));
} catch (Throwable t) {
// 兜底:捕获 Error 及其它 Throwable(如 OOM),保证响应不悬挂
log.error("严重异常(Throwable", t);
renderResult(ctx, Result.error(Result.ERROR_CODE, "严重异常:" + t.getClass().getSimpleName()));
renderResult(ctx, Result.error("严重异常:" + t.getClass().getSimpleName()));
}
}
/**
* 输出 Result JSON 响应。
* 输出 Result JSON 响应(与原 hospitalmiddle 契约一致:{"success":false,"msg":...}
*/
private void renderResult(Context ctx, Result<?> result) {
ctx.status(200);
ctx.contentType("application/json;charset=UTF-8");
// 简易 JSON 序列化(避免引入 fastjson 依赖)
String dataJson = result.getData() != null ? toJsonValue(result.getData()) : "null";
ctx.output("{\"code\":" + result.getCode()
ctx.output("{\"success\":" + result.isSuccess()
+ ",\"msg\":" + toJsonValue(result.getMsg())
+ ",\"data\":" + dataJson + "}");
+ ",\"data\":null}");
}
/**
@@ -0,0 +1,42 @@
package com.hospital.front.infra.util;
import org.noear.snack.ONode;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
/**
* JSON 解析工具(snack3 封装)。
*
* Solon 对 Map/List 泛型 body 反序列化支持不佳(接口层只能拿 String body),
* 此处集中封装手动解析,接口层一行调用;单 DTO 结构应优先用 @Body 强类型直收。
*/
public final class JsonUtils {
private JsonUtils() {
}
/** JSON 对象字符串 → Map(解析失败抛 IllegalArgumentException */
@SuppressWarnings("unchecked")
public static Map<String, Object> parseMap(String json) {
try {
return (Map<String, Object>) ONode.load(json).toObject(Map.class);
} catch (Exception e) {
throw new IllegalArgumentException("JSON 对象格式错误:" + e.getMessage());
}
}
/** JSON 数组字符串 → List&lt;Map&gt;(空串返回空列表) */
@SuppressWarnings("unchecked")
public static List<Map<String, Object>> parseList(String json) {
if (json == null || json.trim().isEmpty()) {
return new ArrayList<>();
}
try {
return (List<Map<String, Object>>) ONode.load(json).toObject(List.class);
} catch (Exception e) {
throw new IllegalArgumentException("JSON 数组格式错误:" + e.getMessage());
}
}
}
@@ -1,5 +1,11 @@
package com.hospital.front.mapper.bsm;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
@@ -33,7 +39,7 @@ public interface BsmOrderMapper {
void addUnitV2(Map<String, Object> map);
/** 按体检预约 ID(逗号分隔)查询体检状态 */
List<Map<String, Object>> getPhyexamStatus(@Param("peIds") String peIds);
List<PeStatusVo> getPhyexamStatus(@Param("peIds") String peIds);
/** 医院所有体检项目(组合项) */
List<Map<String, Object>> getItemList();
@@ -53,45 +59,32 @@ public interface BsmOrderMapper {
/** 员工体检结果 */
List<Map<String, Object>> getResult(@Param("peId") String peId);
/** 体检结论(列表) */
List<Map<String, Object>> getConclusion(@Param("peId") String peId);
/** 体检结论(全量) */
List<Map<String, Object>> getConclusionAll(@Param("peId") String peId);
/** 体检建议(列表) */
List<Map<String, Object>> getSuggest(@Param("peId") String peId);
List<ConclusionVo> getConclusionAll(@Param("peId") String peId);
/** 体检建议(全量) */
List<Map<String, Object>> getSuggestAll(@Param("peId") String peId);
List<SuggestVo> getSuggestAll(@Param("peId") String peId);
/** 按身份证号及年份查询体检状态 */
Map<String, Object> getPeStatusByIdnoAndYear(@Param("idNo") String idNo, @Param("year") String year);
PeStatusVo getPeStatusByIdnoAndYear(@Param("idNo") String idNo, @Param("year") String year);
/** 按身份证号及年份查询体检结果 */
List<Map<String, Object>> getResultByIdcardAndYear(@Param("idNo") String idNo, @Param("year") String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYear(@Param("idNo") String idNo, @Param("year") String year);
/** 按身份证号及年份查询体检结果(全量) */
List<Map<String, Object>> getResultByIdcardAndYearAll(@Param("idNo") String idNo, @Param("year") String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(@Param("idNo") String idNo, @Param("year") String year);
/** 按体检编号查询体检结果 */
List<Map<String, Object>> getResultByPeId(@Param("peId") String peId);
List<MedicalMiddleResultVo> getResultByPeId(@Param("peId") String peId);
/** 按审核日期查询体检报告(去重) */
List<Map<String, Object>> getDisResultByAuditDate(@Param("auditDate") String auditDate);
/** 按体检编号查询体检项目子表 */
List<Map<String, Object>> getItemByPeId(@Param("peId") String peId);
List<MedicalMiddleResultVo> getItemByPeId(@Param("peId") String peId);
/** 按体检编号查询体检项目子表(全量) */
List<Map<String, Object>> getItemByPeIdAll(@Param("peId") String peId);
List<MedicalMiddleResultVo> getItemByPeIdAll(@Param("peId") String peId);
/** 按身份证号或体检编号 + 审核年份查询体检结果 */
List<Map<String, Object>> getResultByIdNoOrPeId(
@Param("idNo") String idNo,
@Param("peId") String peId,
@Param("auditYear") String auditYear
);
/** 按身份证号查询当年 peId 与预约日期 */
Map<String, Object> getPeIdAndDateByIdcard(@Param("idNo") String idNo);
@@ -100,5 +93,5 @@ public interface BsmOrderMapper {
List<Map<String, Object>> getPeIdAndDateByIdcardList(@Param("idNo") String idNo);
/** 按审核日期查询当天体检人员列表(去重) */
List<Map<String, Object>> getExamListByDate(@Param("auditDate") String auditDate);
List<ExamListVo> getExamListByDate(@Param("auditDate") String auditDate);
}
@@ -1,5 +1,11 @@
package com.hospital.front.mapper.nx;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
@@ -7,91 +13,70 @@ import java.util.List;
import java.util.Map;
/**
* BSM 医院 MapperOracle 方言)。
*
* 适用医院:ningxia(宁夏宝石花,SqlServer
* XML 位置:classpath:mapper/nx/OrderMapper.xml
*
* 存储过程参数与医院 HIS 系统约定,不可修改。
* 宁夏医院 MapperSqlServer 方言)。
* getConclusion/getSuggest 与 All 版 SQL 完全重复,已合并为 All 版。
*/
@Mapper
public interface NxOrderMapper {
/** 健康探测SELECT 1 */
/** 健康探测 */
int ping();
/** 预约提交(存储过程 P_ADD_PE_REGIST,出参 resultCode/errorMsg/peId */
/** 提交预约(存储过程) */
void saveOrder(Map<String, Object> map);
/** 取消预约(存储过程 P_DEL_PE_REGIST */
/** 取消预约(存储过程) */
void cancelOrder(Map<String, Object> map);
/** 添加/修改单位 V1(存储过程 P_ADD_UNIT */
void addUnit(Map<String, Object> map);
/** 添加/修改单位 V2(存储过程 P_ADD_UNIT8 入参版) */
/** 添加/修改单位 V2(存储过程) */
void addUnitV2(Map<String, Object> map);
/** 体检预约 ID(逗号分隔)查询体检状态 */
List<Map<String, Object>> getPhyexamStatus(@Param("peIds") String peIds);
/** 体检状态查询(多个 peId 逗号分隔) */
List<PeStatusVo> getPhyexamStatus(@Param("peIds") String peIds);
/** 医院所有体检项目(组合项) */
/** 体检项目查询 */
List<Map<String, Object>> getItemList();
/** 医院所有体检项目及指标项 */
/** 体检指标项及体检组合数据 */
List<Map<String, Object>> getAllItemList();
/** 医院所有体检指标项 */
/** 体检指标项数据 */
List<Map<String, Object>> getPeItemList();
/** 按体检指标项查所属组合 */
List<Map<String, Object>> getItemInfo(@Param("peItemCode") String peItemCode);
/** 员工体检项目 */
List<Map<String, Object>> getEmpItem(@Param("peId") String peId);
/** 按指标项 CODE 查询体检组合 */
List<Map<String, Object>> getItemInfo(@Param("peItemCode") String peItemCode);
/** 员工体检结果 */
/** 按体检编号查体检结果 */
List<Map<String, Object>> getResult(@Param("peId") String peId);
/** 体检结论(列表) */
List<Map<String, Object>> getConclusion(@Param("peId") String peId);
/** 体检结论(全量) */
List<Map<String, Object>> getConclusionAll(@Param("peId") String peId);
/** 体检建议(列表) */
List<Map<String, Object>> getSuggest(@Param("peId") String peId);
List<ConclusionVo> getConclusionAll(@Param("peId") String peId);
/** 体检建议(全量) */
List<Map<String, Object>> getSuggestAll(@Param("peId") String peId);
List<SuggestVo> getSuggestAll(@Param("peId") String peId);
/** 按身份证号及年份查询体检状态 */
Map<String, Object> getPeStatusByIdnoAndYear(@Param("idNo") String idNo, @Param("year") String year);
PeStatusVo getPeStatusByIdnoAndYear(@Param("idNo") String idNo, @Param("year") String year);
/** 按身份证号及年份查询体检结果 */
List<Map<String, Object>> getResultByIdcardAndYear(@Param("idNo") String idNo, @Param("year") String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYear(@Param("idNo") String idNo, @Param("year") String year);
/** 按身份证号及年份查询体检结果(全量) */
List<Map<String, Object>> getResultByIdcardAndYearAll(@Param("idNo") String idNo, @Param("year") String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(@Param("idNo") String idNo, @Param("year") String year);
/** 按体检编号查询体检结果 */
List<Map<String, Object>> getResultByPeId(@Param("peId") String peId);
List<MedicalMiddleResultVo> getResultByPeId(@Param("peId") String peId);
/** 按审核日期查询体检报告(去重) */
List<Map<String, Object>> getDisResultByAuditDate(@Param("auditDate") String auditDate);
/** 按体检编号查询体检项目子表 */
List<Map<String, Object>> getItemByPeId(@Param("peId") String peId);
List<MedicalMiddleResultVo> getItemByPeId(@Param("peId") String peId);
/** 按体检编号查询体检项目子表(全量) */
List<Map<String, Object>> getItemByPeIdAll(@Param("peId") String peId);
List<MedicalMiddleResultVo> getItemByPeIdAll(@Param("peId") String peId);
/** 按身份证号或体检编号 + 审核年份查询体检结果 */
List<Map<String, Object>> getResultByIdNoOrPeId(
@Param("idNo") String idNo,
@Param("peId") String peId,
@Param("auditYear") String auditYear
);
/** 按身份证号查询当年 peId 与预约日期 */
Map<String, Object> getPeIdAndDateByIdcard(@Param("idNo") String idNo);
@@ -100,5 +85,5 @@ public interface NxOrderMapper {
List<Map<String, Object>> getPeIdAndDateByIdcardList(@Param("idNo") String idNo);
/** 按审核日期查询当天体检人员列表(去重) */
List<Map<String, Object>> getExamListByDate(@Param("auditDate") String auditDate);
List<ExamListVo> getExamListByDate(@Param("auditDate") String auditDate);
}
@@ -1,5 +1,11 @@
package com.hospital.front.mapper.ya;
import com.hospital.front.vo.ConclusionVo;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.MedicalMiddleResultVo;
import com.hospital.front.vo.PeStatusVo;
import com.hospital.front.vo.SuggestVo;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
@@ -7,91 +13,70 @@ import java.util.List;
import java.util.Map;
/**
* BSM 医院 MapperOracle 方言)。
*
* 适用医院:yanan(延安,SqlServer
* XML 位置:classpath:mapper/ya/OrderMapper.xml
*
* 存储过程参数与医院 HIS 系统约定,不可修改。
* 延安医院 MapperSqlServer 方言)。
* getConclusion/getSuggest 与 All 版 SQL 完全重复,已合并为 All 版。
*/
@Mapper
public interface YaOrderMapper {
/** 健康探测SELECT 1 */
/** 健康探测 */
int ping();
/** 预约提交(存储过程 P_ADD_PE_REGIST,出参 resultCode/errorMsg/peId */
/** 提交预约(存储过程) */
void saveOrder(Map<String, Object> map);
/** 取消预约(存储过程 P_DEL_PE_REGIST */
/** 取消预约(存储过程) */
void cancelOrder(Map<String, Object> map);
/** 添加/修改单位 V1(存储过程 P_ADD_UNIT */
/** 添加/修改单位(存储过程V1 */
void addUnit(Map<String, Object> map);
/** 添加/修改单位 V2(存储过程 P_ADD_UNIT8 入参版 */
void addUnitV2(Map<String, Object> map);
/** 体检状态查询(多个 peId 逗号分隔 */
List<PeStatusVo> getPhyexamStatus(@Param("peIds") String peIds);
/** 体检预约 ID(逗号分隔)查询体检状态 */
List<Map<String, Object>> getPhyexamStatus(@Param("peIds") String peIds);
/** 医院所有体检项目(组合项) */
/** 体检项目查询 */
List<Map<String, Object>> getItemList();
/** 医院所有体检项目及指标项 */
/** 体检指标项及体检组合数据 */
List<Map<String, Object>> getAllItemList();
/** 医院所有体检指标项 */
/** 体检指标项数据 */
List<Map<String, Object>> getPeItemList();
/** 按体检指标项查所属组合 */
List<Map<String, Object>> getItemInfo(@Param("peItemCode") String peItemCode);
/** 员工体检项目 */
List<Map<String, Object>> getEmpItem(@Param("peId") String peId);
/** 按指标项 CODE 查询体检组合 */
List<Map<String, Object>> getItemInfo(@Param("peItemCode") String peItemCode);
/** 员工体检结果 */
/** 按体检编号查体检结果 */
List<Map<String, Object>> getResult(@Param("peId") String peId);
/** 体检结论(列表) */
List<Map<String, Object>> getConclusion(@Param("peId") String peId);
/** 体检结论(全量) */
List<Map<String, Object>> getConclusionAll(@Param("peId") String peId);
/** 体检建议(列表) */
List<Map<String, Object>> getSuggest(@Param("peId") String peId);
List<ConclusionVo> getConclusionAll(@Param("peId") String peId);
/** 体检建议(全量) */
List<Map<String, Object>> getSuggestAll(@Param("peId") String peId);
List<SuggestVo> getSuggestAll(@Param("peId") String peId);
/** 按身份证号及年份查询体检状态 */
Map<String, Object> getPeStatusByIdnoAndYear(@Param("idNo") String idNo, @Param("year") String year);
PeStatusVo getPeStatusByIdnoAndYear(@Param("idNo") String idNo, @Param("year") String year);
/** 按身份证号及年份查询体检结果 */
List<Map<String, Object>> getResultByIdcardAndYear(@Param("idNo") String idNo, @Param("year") String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYear(@Param("idNo") String idNo, @Param("year") String year);
/** 按身份证号及年份查询体检结果(全量) */
List<Map<String, Object>> getResultByIdcardAndYearAll(@Param("idNo") String idNo, @Param("year") String year);
List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(@Param("idNo") String idNo, @Param("year") String year);
/** 按体检编号查询体检结果 */
List<Map<String, Object>> getResultByPeId(@Param("peId") String peId);
List<MedicalMiddleResultVo> getResultByPeId(@Param("peId") String peId);
/** 按审核日期查询体检报告(去重) */
List<Map<String, Object>> getDisResultByAuditDate(@Param("auditDate") String auditDate);
/** 按体检编号查询体检项目子表 */
List<Map<String, Object>> getItemByPeId(@Param("peId") String peId);
List<MedicalMiddleResultVo> getItemByPeId(@Param("peId") String peId);
/** 按体检编号查询体检项目子表(全量) */
List<Map<String, Object>> getItemByPeIdAll(@Param("peId") String peId);
List<MedicalMiddleResultVo> getItemByPeIdAll(@Param("peId") String peId);
/** 按身份证号或体检编号 + 审核年份查询体检结果 */
List<Map<String, Object>> getResultByIdNoOrPeId(
@Param("idNo") String idNo,
@Param("peId") String peId,
@Param("auditYear") String auditYear
);
/** 按身份证号查询当年 peId 与预约日期 */
Map<String, Object> getPeIdAndDateByIdcard(@Param("idNo") String idNo);
@@ -100,5 +85,5 @@ public interface YaOrderMapper {
List<Map<String, Object>> getPeIdAndDateByIdcardList(@Param("idNo") String idNo);
/** 按审核日期查询当天体检人员列表(去重) */
List<Map<String, Object>> getExamListByDate(@Param("auditDate") String auditDate);
List<ExamListVo> getExamListByDate(@Param("auditDate") String auditDate);
}
@@ -1,5 +1,7 @@
package com.hospital.front.service;
import com.hospital.front.vo.MedicalMiddleResultVo;
import lombok.extern.slf4j.Slf4j;
import java.util.ArrayList;
@@ -17,8 +19,10 @@ import com.hospital.front.adapter.HospitalAdapter;
import com.hospital.front.adapter.HospitalRouter;
import com.hospital.front.infra.exception.BusinessException;
import com.hospital.front.infra.util.DateUtils;
import com.hospital.front.vo.ExamListVo;
import com.hospital.front.vo.OrderItemVo;
import com.hospital.front.vo.OrderV2Vo;
import com.hospital.front.vo.PeStatusPhyVo;
import com.hospital.front.vo.UnitVo;
/**
@@ -79,8 +83,7 @@ public class OrderService {
*
* @return 成功时返回 peId
*/
public String saveOrder(Map<String, Object> body) {
OrderV2Vo vo = convertOrderV2(body);
public String saveOrder(com.hospital.front.vo.OrderV2Vo vo) {
if (isAllsecondFlag()) {
vo = vo.applyAllsecondFlag();
}
@@ -160,33 +163,17 @@ public class OrderService {
return adapter().getResult(peId);
}
public List<Map<String, Object>> getConclusion(String peId) {
return adapter().getConclusion(peId);
}
public List<Map<String, Object>> getSuggest(String peId) {
return adapter().getSuggest(peId);
}
public List<Map<String, Object>> getResultByIdcardAndYear(String idNo, String year) {
/** 按身份证及年份查体检结果(内部使用:宁夏 getPeStatusByIdnoAndYear 兜底) */
public List<MedicalMiddleResultVo> getResultByIdcardAndYear(String idNo, String year) {
return adapter().getResultByIdcardAndYear(idNo, year);
}
public List<Map<String, Object>> getResultByIdcardAndYearAll(String idNo, String year) {
return adapter().getResultByIdcardAndYearAll(idNo, year);
public List<MedicalMiddleResultVo> getResultByIdcardAndYearAll(String idNo, String year) {
return enrichResultAll(adapter().getResultByIdcardAndYearAll(idNo, year));
}
public List<Map<String, Object>> getResultByPeId(String peId) {
return adapter().getResultByPeId(peId);
}
/** 按审核日期查询体检报告(去重主表) */
public List<Map<String, Object>> getResultByAuditDate(String auditDate) {
return adapter().getDisResultByAuditDate(auditDate);
}
public List<Map<String, Object>> getResultByIdNoOrPeId(String idNo, String peId, String auditYear) {
return adapter().getResultByIdNoOrPeId(idNo, peId, auditYear);
public List<MedicalMiddleResultVo> getResultByPeId(String peId) {
return enrichResultAll(adapter().getResultByPeId(peId));
}
public Map<String, Object> getPeIdAndDateByIdcard(String idNo) {
@@ -200,14 +187,13 @@ public class OrderService {
/**
* 体检状态查询:按医院返回的 PE_STATUS 名转字典数字。
*/
public List<Map<String, String>> getPhyexamStatus(String peIds) {
List<Map<String, String>> out = new ArrayList<>();
for (Map<String, Object> row : adapter().getPhyexamStatus(peIds)) {
Map<String, String> item = new HashMap<>();
item.put("peId", row.get("PE_ID") != null ? String.valueOf(row.get("PE_ID")) : "");
String statusName = row.get("PE_STATUS") != null ? String.valueOf(row.get("PE_STATUS")) : "";
item.put("peStatus", PE_STATUS_DICT.getOrDefault(statusName, ""));
out.add(item);
public List<PeStatusPhyVo> getPhyexamStatus(String peIds) {
List<PeStatusPhyVo> out = new ArrayList<>();
for (com.hospital.front.vo.PeStatusVo row : adapter().getPhyexamStatus(peIds)) {
out.add(new PeStatusPhyVo(
row.getPeId() != null ? row.getPeId() : "",
PE_STATUS_DICT.getOrDefault(
row.getPeStatus() != null ? row.getPeStatus() : "", "")));
}
return out;
}
@@ -215,63 +201,39 @@ public class OrderService {
/**
* 按日期查询当天体检人员列表(日期空则当天)。
*/
public List<Map<String, Object>> getExamListByDate(String auditDate) {
public List<ExamListVo> getExamListByDate(String auditDate) {
return adapter().getExamListByDate(auditDate != null ? auditDate : DateUtils.today());
}
/**
* 体检结论(汇总为单字符串)。
*/
public Map<String, String> getTotalConclusion(String peId) {
Map<String, String> map = new HashMap<>();
map.put("totalConclusion", buildSummary(adapter().getConclusion(peId)));
return map;
}
/** 体检结论(汇总,全量来源) */
public Map<String, String> getTotalConclusionAll(String peId) {
Map<String, String> map = new HashMap<>();
map.put("totalConclusion", buildSummary(adapter().getConclusionAll(peId)));
return map;
}
/**
* 体检建议(汇总)。宁夏(nx)仅取首条 GUIDE_CONTENT。
*/
public Map<String, String> getTotalSuggest(String peId) {
Map<String, String> map = new HashMap<>();
map.put("totalSuggest", buildSuggest(adapter().getSuggest(peId), "nx".equals(adapter().hmType())));
return map;
}
/** 体检建议(汇总,全量来源) */
public Map<String, String> getTotalSuggestAll(String peId) {
Map<String, String> map = new HashMap<>();
map.put("totalSuggest", buildSuggest(adapter().getSuggestAll(peId), "nx".equals(adapter().hmType())));
return map;
}
/**
* 按身份证号 + 年份查询体检状态及项目(含宁夏体检报告兜底)。
*/
public Map<String, Object> getPeStatusByIdnoAndYear(String idNo, String year) {
Map<String, Object> map = adapter().getPeStatusByIdnoAndYear(idNo, year);
if (map != null && map.get("PE_ID") != null) {
Map<String, Object> result = new LinkedHashMap<>(map);
result.put("peItemList", adapter().getEmpItem(String.valueOf(map.get("PE_ID"))));
com.hospital.front.vo.PeStatusVo vo = adapter().getPeStatusByIdnoAndYear(idNo, year);
if (vo != null && vo.getPeId() != null) {
Map<String, Object> result = new LinkedHashMap<>();
result.put("PE_ID", vo.getPeId());
result.put("NAME", vo.getName());
result.put("ID_NO", vo.getIdNo());
result.put("UNIT_NAME", vo.getUnitName());
result.put("DEPARTMENT", vo.getDepartment());
result.put("PE_PRE_DATE", vo.getPePreDate());
result.put("PE_QUEUE_DATE", vo.getPeQueueDate());
result.put("PE_STATUS", vo.getPeStatus());
result.put("peItemList", adapter().getEmpItem(vo.getPeId()));
return result;
} else {
// 宁夏:从体检报告继续查
if ("nx".equals(adapter().hmType())) {
List<Map<String, Object>> rows = adapter().getResultByIdcardAndYear(idNo, year);
List<MedicalMiddleResultVo> rows = adapter().getResultByIdcardAndYear(idNo, year);
if (!rows.isEmpty()) {
Map<String, Object> row = rows.get(0);
String auditDate = row.get("AUDIT_DATE") != null ? String.valueOf(row.get("AUDIT_DATE")) : null;
MedicalMiddleResultVo row = rows.get(0);
String auditDate = row.getAuditDate();
Map<String, Object> out = new LinkedHashMap<>();
out.put("PE_ID", row.get("PE_ID"));
out.put("PE_ID", row.getPeId());
out.put("PE_PRE_DATE",
auditDate != null && auditDate.length() >= 10 ? auditDate.substring(0, 10) : auditDate);
out.put("peItemList", adapter().getEmpItem(String.valueOf(row.get("PE_ID"))));
out.put("peItemList", adapter().getEmpItem(row.getPeId()));
return out;
} else {
return null;
@@ -284,107 +246,58 @@ public class OrderService {
// ================= 私有工具 =================
/** 医院侧业务失败:抛出 2003 业务异常 */
/**
* 报告组装(对齐原 hospitalmiddle 的 dealMiddleChildDataAll):
* 为每条结果补 hospitalId、item 子表(全量)、体检结论、体检建议。
*/
private List<MedicalMiddleResultVo> enrichResultAll(List<MedicalMiddleResultVo> rows) {
String hospitalId = Solon.cfg().get("hospital.id", "");
for (MedicalMiddleResultVo row : rows) {
row.setHospitalId(hospitalId);
// item 子表(全量版)
row.setResultVoList(adapter().getItemByPeIdAll(row.getPeId()));
// 体检结论:多条按 "序号.科室:结论文本;<br/>" 拼接
StringBuilder conclusion = new StringBuilder();
int cIndex = 1;
for (com.hospital.front.vo.ConclusionVo c : adapter().getConclusionAll(row.getPeId())) {
String deptName = c.getPeDeptName() != null ? c.getPeDeptName() : "";
String text = c.getConclusionText() != null ? c.getConclusionText() : "";
conclusion.append(cIndex).append(".").append(deptName).append(":").append(text).append(";<br/>");
cIndex++;
}
row.setConclusion(conclusion.toString());
// 体检建议:宁夏取首条 guideContent;其余按 "序号.建议项:建议内容;<br/>" 拼接(跳过建议内容为空的行)
StringBuilder suggest = new StringBuilder();
List<com.hospital.front.vo.SuggestVo> suggestRows = adapter().getSuggestAll(row.getPeId());
if ("nx".equals(adapter().hmType())) {
if (!suggestRows.isEmpty() && suggestRows.get(0).getGuideContent() != null) {
suggest.append(suggestRows.get(0).getGuideContent());
}
} else {
int sIndex = 1;
for (com.hospital.front.vo.SuggestVo s : suggestRows) {
if (s.getGuideContent() != null && !s.getGuideContent().isEmpty()) {
String rec = s.getRecContent() != null ? s.getRecContent() : "";
suggest.append(sIndex).append(".").append(rec).append(":")
.append(s.getGuideContent()).append(";<br/>");
sIndex++;
}
}
}
row.setSuggest(suggest.toString());
}
return rows;
}
/** 医院侧业务失败:抛出业务异常 */
private void throwHospitalFailed(String errorMsg) {
if (errorMsg != null && !errorMsg.isEmpty()) {
throw BusinessException.of(2003, errorMsg);
throw BusinessException.of(errorMsg);
} else {
throw BusinessException.procFailed("医院系统返回业务失败");
}
}
/** 结论汇总:1.科室:结论;<br/> */
private String buildSummary(List<Map<String, Object>> rows) {
StringBuilder sb = new StringBuilder();
for (int i = 0; i < rows.size(); i++) {
Map<String, Object> row = rows.get(i);
String deptName = row.get("PE_DEPT_NAME") != null ? String.valueOf(row.get("PE_DEPT_NAME")) : "";
String dept = !deptName.isEmpty() ? deptName + ":" : "";
Object conclusion = row.get("CONCLUSION_TEXT");
sb.append(i + 1).append(".").append(dept).append(conclusion != null ? conclusion : "").append(";<br/>");
}
return sb.toString();
}
/** 建议汇总:宁夏仅取首条 GUIDE_CONTENT;其余 1.建议项:内容;<br/> */
private String buildSuggest(List<Map<String, Object>> rows, boolean nxStyle) {
if (nxStyle) {
if (rows.isEmpty() || rows.get(0).get("GUIDE_CONTENT") == null) {
return "";
}
return String.valueOf(rows.get(0).get("GUIDE_CONTENT"));
} else {
StringBuilder sb = new StringBuilder();
int i = 1;
for (Map<String, Object> row : rows) {
String guide = row.get("GUIDE_CONTENT") != null ? String.valueOf(row.get("GUIDE_CONTENT")) : "";
if (guide.isEmpty()) {
continue;
}
Object rec = row.get("REC_CONTENT");
sb.append(i).append(".").append(rec != null ? rec : "").append(":").append(guide).append(";<br/>");
i++;
}
return sb.toString();
}
}
/** Map → OrderV2Vo(数值/空值容错) */
private OrderV2Vo convertOrderV2(Map<String, Object> body) {
List<OrderItemVo> itemList = null;
Object rawList = body.get("itemList");
if (rawList instanceof List) {
itemList = new ArrayList<>();
for (Object item : (List<?>) rawList) {
if (item instanceof Map) {
Map<?, ?> m = (Map<?, ?>) item;
itemList.add(new OrderItemVo(
m.get("itemNo") != null ? String.valueOf(m.get("itemNo")) : null,
m.get("itemName") != null ? String.valueOf(m.get("itemName")) : null));
}
}
}
return new OrderV2Vo(
str(body, "orderDate"),
str(body, "secondDepartId"),
str(body, "secondDepartName"),
str(body, "thirdDepartName"),
str(body, "name"),
str(body, "sexName"),
str(body, "birthDay"),
body.get("age") instanceof Number ? ((Number) body.get("age")).intValue() : null,
str(body, "idCard"),
str(body, "marrigeStatusName"),
str(body, "country"),
str(body, "nationName"),
str(body, "birthplace"),
str(body, "position"),
str(body, "profession"),
str(body, "feeType"),
str(body, "liveSpace"),
str(body, "zipCode"),
str(body, "mobile"),
str(body, "email"),
str(body, "empSysno"),
str(body, "medicalType"),
str(body, "medicalClass"),
str(body, "workShape"),
str(body, "workDate"),
str(body, "jobLevel"),
str(body, "workPlace"),
str(body, "baseSite"),
str(body, "workTypeCode"),
str(body, "workTypeOther"),
str(body, "education"),
str(body, "title"),
str(body, "oldDepartName"),
str(body, "harmReasonCode"),
str(body, "harmReasonOther"),
str(body, "harmDate"),
str(body, "defendCancer"),
itemList);
}
/** 取字符串值(null 安全) */
private static String str(Map<String, Object> map, String key) {
Object v = map.get(key);
@@ -2,11 +2,12 @@ package com.hospital.front.task;
import lombok.extern.slf4j.Slf4j;
import java.util.concurrent.TimeUnit;
import java.net.URI;
import java.net.http.HttpClient;
import java.net.http.HttpRequest;
import java.net.http.HttpResponse;
import java.time.Duration;
import okhttp3.OkHttpClient;
import okhttp3.Request;
import okhttp3.Response;
import org.noear.solon.Solon;
import org.noear.solon.annotation.Component;
import org.noear.solon.annotation.Inject;
@@ -33,9 +34,9 @@ public class UptimeKumaTask {
@Inject
private HospitalRouter router;
private final OkHttpClient http = new OkHttpClient.Builder()
.connectTimeout(5, TimeUnit.SECONDS)
.readTimeout(10, TimeUnit.SECONDS)
/** JDK 内置 HttpClient(替代 OkHttp,免额外依赖):连接 5s、读取 10s */
private final HttpClient http = HttpClient.newBuilder()
.connectTimeout(Duration.ofSeconds(5))
.build();
/**
@@ -51,15 +52,19 @@ public class UptimeKumaTask {
}
// 检查数据库连接
com.hospital.front.dto.Result<Boolean> health = router.active().healthCheck();
if (health.getCode() == 0) {
if (health.isSuccess()) {
try {
Response resp = http.newCall(new Request.Builder().url(kumaUrl).get().build()).execute();
if (resp.isSuccessful()) {
HttpResponse<String> resp = http.send(
HttpRequest.newBuilder(URI.create(kumaUrl))
.GET()
.timeout(Duration.ofSeconds(10))
.build(),
HttpResponse.BodyHandlers.ofString());
if (resp.statusCode() >= 200 && resp.statusCode() < 300) {
log.info("[Kuma] 心跳推送成功:{}", kumaUrl);
} else {
log.warn("[Kuma] 心跳推送失败:HTTP {}", resp.code());
log.warn("[Kuma] 心跳推送失败:HTTP {}", resp.statusCode());
}
resp.close();
} catch (Exception e) {
log.warn("[Kuma] 心跳推送异常:{}", e.getMessage());
}
@@ -0,0 +1,22 @@
package com.hospital.front.vo;
import lombok.Data;
/**
* 体检结论明细 VOgetConclusionAll 强类型映射,内部使用)。
*
* 一个 peId 按科室返回多条结论(汇总拼接用),故为列表元素。
*/
@Data
public class ConclusionVo {
/** 体检编号 */
private String peId;
/** 就诊编号 */
private String peVisitId;
/** 科室编码 */
private String peDeptCode;
/** 科室名称 */
private String peDeptName;
/** 结论文本(已去换行) */
private String conclusionText;
}
@@ -0,0 +1,25 @@
package com.hospital.front.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* 当天体检人员列表 VOgetExamListByDate 对外强类型出参)。
*
* 三院 SQL 出参统一(列别名即驼峰字段),日期已在 SQL 层转为字符串。
* 字段名与 snack3 默认序列化输出 key 一致,可直接返回 HTTP 调用方。
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class ExamListVo {
/** 体检编号 */
private String peId;
/** 身份证号 */
private String idNo;
/** 姓名 */
private String name;
/** 审查日期 yyyy-MM-dd */
private String auditDate;
}
@@ -0,0 +1,22 @@
package com.hospital.front.vo;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
/**
* 体检状态简版 VOgetPhyexamStatus 对外强类型出参)。
*
* 字段名与 snack3 默认序列化输出 key 一致(peId / peStatus),
* 可直接返回给 HTTP 调用方,无需手工 Map 包装。
* peStatus 已由 OrderService 加工为字典数字(与原 Map 契约一致)。
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class PeStatusPhyVo {
/** 体检编号(null 时输出空字符串,保持与原 Map 契约一致) */
private String peId;
/** 体检状态字典数字(原始状态名查不到时输出空字符串) */
private String peStatus;
}
@@ -0,0 +1,29 @@
package com.hospital.front.vo;
import lombok.Data;
/**
* 体检状态 VOgetPhyexamStatus / getPeStatusByIdnoAndYear 强类型映射,内部中间态)。
*
* 对外出参由 OrderService 加工(key 小写 peId/peStatus + 状态字典转换),
* 本 VO 仅作 adapter → service 的内部传输,不影响 HTTP 契约。
*/
@Data
public class PeStatusVo {
/** 体检编号 */
private String peId;
/** 姓名 */
private String name;
/** 身份证号 */
private String idNo;
/** 单位名称 */
private String unitName;
/** 部门 */
private String department;
/** 预约日期 */
private String pePreDate;
/** 排队日期 */
private String peQueueDate;
/** 状态名(报到/检中/初审/终审/预约/转向) */
private String peStatus;
}
@@ -0,0 +1,18 @@
package com.hospital.front.vo;
import lombok.Data;
/**
* 体检建议 VOgetSuggestAll 强类型映射,内部使用)。
*
* 按 peId 查询仅一条建议记录,adapter 层取首条返回单对象。
*/
@Data
public class SuggestVo {
/** 体检编号 */
private String peId;
/** 建议项(科室/类别描述) */
private String recContent;
/** 建议内容(已去换行) */
private String guideContent;
}
+4
View File
@@ -11,6 +11,10 @@ solon:
app:
name: "hospital-front"
group: "hospital"
# JSON 序列化对齐原 hospitalmiddleJackson 默认保留 null 字段)
serialization:
json:
nullAsWriteable: true
# 应用配置
# 医院注册清单由代码决定(各 Adapter 的 @Component),此处仅指定激活哪家
@@ -7,102 +7,113 @@
SELECT 1 FROM DUAL
</select>
<!-- ==================== 存储过程:预约/取消/单位 ==================== -->
<parameterMap id="pm" type="java.util.Map">
<parameter property="peInfoStr" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="peItemStr" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="peId" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="peInfoStr" jdbcType="VARCHAR" mode="IN"/>
<parameter property="peItemStr" jdbcType="VARCHAR" mode="IN"/>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"/>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"/>
<parameter property="peId" jdbcType="VARCHAR" mode="OUT"/>
</parameterMap>
<insert id="saveOrder" parameterMap="pm" statementType="CALLABLE">
{call P_ADD_PE_REGIST(
#{peInfoStr,mode=IN,jdbcType=VARCHAR},
#{peItemStr,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR},
#{peId,mode=OUT,jdbcType=VARCHAR}
#{peInfoStr,mode=IN,jdbcType=VARCHAR},
#{peItemStr,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR},
#{peId,mode=OUT,jdbcType=VARCHAR}
)}
</insert>
<parameterMap id="cancenlPm" type="java.util.Map">
<parameter property="peId" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="name" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="idcard" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="peId" jdbcType="VARCHAR" mode="IN"/>
<parameter property="name" jdbcType="VARCHAR" mode="IN"/>
<parameter property="idcard" jdbcType="VARCHAR" mode="IN"/>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"/>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"/>
</parameterMap>
<insert id="cancelOrder" parameterMap="cancenlPm" statementType="CALLABLE">
{call P_DEL_PE_REGIST(
#{peId,mode=IN,jdbcType=VARCHAR},
#{name,mode=IN,jdbcType=VARCHAR},
#{idcard,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR}
#{peId,mode=IN,jdbcType=VARCHAR},
#{name,mode=IN,jdbcType=VARCHAR},
#{idcard,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR}
)}
</insert>
<parameterMap id="unitPm" type="java.util.Map">
<parameter property="unitCode" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="unitName" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="unitCode" jdbcType="VARCHAR" mode="IN"/>
<parameter property="unitName" jdbcType="VARCHAR" mode="IN"/>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"/>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"/>
</parameterMap>
<insert id="addUnit" parameterMap="unitPm" statementType="CALLABLE">
{call P_ADD_UNIT(
#{unitCode,mode=IN,jdbcType=VARCHAR},
#{unitName,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR}
#{unitCode,mode=IN,jdbcType=VARCHAR},
#{unitName,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR}
)}
</insert>
<parameterMap id="unitPmV2" type="java.util.Map">
<parameter property="unitCode" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="unitName" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="parentUnitCode" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="address" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="connecter1" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="phone1" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="connecter2" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="phone2" jdbcType="VARCHAR" mode="IN"></parameter>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"></parameter>
<parameter property="unitCode" jdbcType="VARCHAR" mode="IN"/>
<parameter property="unitName" jdbcType="VARCHAR" mode="IN"/>
<parameter property="parentUnitCode" jdbcType="VARCHAR" mode="IN"/>
<parameter property="address" jdbcType="VARCHAR" mode="IN"/>
<parameter property="connecter1" jdbcType="VARCHAR" mode="IN"/>
<parameter property="phone1" jdbcType="VARCHAR" mode="IN"/>
<parameter property="connecter2" jdbcType="VARCHAR" mode="IN"/>
<parameter property="phone2" jdbcType="VARCHAR" mode="IN"/>
<parameter property="resultCode" jdbcType="VARCHAR" mode="OUT"/>
<parameter property="errorMsg" jdbcType="VARCHAR" mode="OUT"/>
</parameterMap>
<insert id="addUnitV2" parameterMap="unitPmV2" statementType="CALLABLE">
{call P_ADD_UNIT(
#{unitCode,mode=IN,jdbcType=VARCHAR},
#{unitName,mode=IN,jdbcType=VARCHAR},
#{parentUnitCode,mode=IN,jdbcType=VARCHAR},
#{address,mode=IN,jdbcType=VARCHAR},
#{connecter1,mode=IN,jdbcType=VARCHAR},
#{phone1,mode=IN,jdbcType=VARCHAR},
#{connecter2,mode=IN,jdbcType=VARCHAR},
#{phone2,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR}
#{unitCode,mode=IN,jdbcType=VARCHAR},
#{unitName,mode=IN,jdbcType=VARCHAR},
#{parentUnitCode,mode=IN,jdbcType=VARCHAR},
#{address,mode=IN,jdbcType=VARCHAR},
#{connecter1,mode=IN,jdbcType=VARCHAR},
#{phone1,mode=IN,jdbcType=VARCHAR},
#{connecter2,mode=IN,jdbcType=VARCHAR},
#{phone2,mode=IN,jdbcType=VARCHAR},
#{resultCode,mode=OUT,jdbcType=VARCHAR},
#{errorMsg,mode=OUT,jdbcType=VARCHAR}
)}
</insert>
<select id="getPhyexamStatus" resultType="java.util.Map">
<!-- ==================== 体检状态 ==================== -->
<select id="getPhyexamStatus" resultType="com.hospital.front.vo.PeStatusVo">
select PE_ID, NAME, ID_NO, UNIT_NAME, DEPARTMENT, PE_PRE_DATE, PE_QUEUE_DATE, PE_STATUS
from V_PHYEXAM_PE_STATUS
where instr(',' || #{peIds} || ',', ',' || pe_id || ',') > 0
</select>
<select id="getItemList" resultType="java.util.Map">
select distinct item_assem_code, item_assem_name
from V_PHYEXAM_ITEM_ASSEMBLED
<select id="getPeStatusByIdnoAndYear" resultType="com.hospital.front.vo.PeStatusVo">
select * from V_PHYEXAM_PE_STATUS
where ID_NO = #{idNo}
and to_char(PE_PRE_DATE, 'yyyy') = #{year}
</select>
<!-- ==================== 体检项目 ==================== -->
<select id="getItemList" resultType="java.util.Map">
SELECT DISTINCT ITEM_ASSEM_CODE, ITEM_ASSEM_NAME
FROM V_PHYEXAM_ITEM_ASSEMBLED
</select>
<select id="getAllItemList" resultType="java.util.Map">
select ITEM_ASSEM_CODE, ITEM_ASSEM_NAME, PE_ITEM_CODE, PE_ITEM_NAME
from V_PHYEXAM_ITEM_ASSEMBLED
SELECT ITEM_ASSEM_CODE, ITEM_ASSEM_NAME, PE_ITEM_CODE, PE_ITEM_NAME
FROM V_PHYEXAM_ITEM_ASSEMBLED
</select>
<select id="getPeItemList" resultType="java.util.Map">
select *
from V_PHYEXAM_ITEM
SELECT PE_ITEM_CODE, PE_ITEM_NAME
FROM V_PHYEXAM_ITEM
</select>
<select id="getEmpItem" resultType="java.util.Map">
@@ -112,315 +123,232 @@
</select>
<select id="getItemInfo" resultType="java.util.Map">
select ITEM_ASSEM_CODE, ITEM_ASSEM_NAME, PE_ITEM_CODE, PE_ITEM_NAME
from V_PHYEXAM_ITEM_ASSEMBLED
where PE_ITEM_CODE = #{peItemCode}
SELECT ITEM_ASSEM_CODE, ITEM_ASSEM_NAME, PE_ITEM_CODE, PE_ITEM_NAME
FROM V_PHYEXAM_ITEM_ASSEMBLED
WHERE PE_ITEM_CODE = #{peItemCode}
</select>
<!-- ==================== 体检结果 ==================== -->
<select id="getResult" resultType="java.util.Map">
select PE_ID,
PE_VISIT_ID,
ID_NO,
NAME,
UNIT_CODE,
UNIT_NAME,
TO_CHAR(PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss') PE_QUEUE_DATE,
TO_CHAR(AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss') AUDIT_DATE,
PE_DEPT_CODE,
PE_DEPT_NAME,
ITEM_ASSEM_CODE,
ITEM_ASSEM_NAME,
PE_ITEM_CODE,
PE_ITEM_NAME,
PE_RESULT,
UNIT,
PRINT_CONTEXT
from V_PHYEXAM_RESULT
where PE_ID = #{peId}
SELECT PE_ID,
PE_VISIT_ID,
ID_NO,
NAME,
UNIT_CODE,
UNIT_NAME,
TO_CHAR(PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss') PE_QUEUE_DATE,
TO_CHAR(AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss') AUDIT_DATE,
PE_DEPT_CODE,
PE_DEPT_NAME,
ITEM_ASSEM_CODE,
ITEM_ASSEM_NAME,
PE_ITEM_CODE,
PE_ITEM_NAME,
PE_RESULT,
UNIT,
PRINT_CONTEXT
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.name, b.unit_code,
(SELECT t.unit_name FROM pe_unit_dict t WHERE t.unit_code = b.unit_code) unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a, pe_visit b, pe_result_dict c
WHERE a.pe_id = b.pe_id
AND b.pe_id = c.pe_id
AND b.pe_visit_id = c.pe_visit_id
)
WHERE PE_ID = #{peId}
</select>
<select id="getConclusion" resultType="java.util.Map">
select PE_ID,
PE_VISIT_ID,
PE_DEPT_CODE,
PE_DEPT_NAME,
REPLACE(REPLACE(REPLACE(DBMS_LOB.SUBSTR(CONCLUSION_TEXT, 4000, 1), chr(13) || chr(10), ''), chr(13), ''), chr(10), '') CONCLUSION_TEXT
from V_PHYEXAM_DEPT_RESULT
where PE_ID = #{peId}
and CONCLUSION_TEXT is not null
</select>
<select id="getConclusionAll" resultType="java.util.Map">
select PE_ID,
PE_VISIT_ID,
PE_DEPT_CODE,
PE_DEPT_NAME,
REPLACE(REPLACE(REPLACE(DBMS_LOB.SUBSTR(CONCLUSION_TEXT, 4000, 1), chr(13) || chr(10), ''), chr(13), ''), chr(10), '') CONCLUSION_TEXT
from (select a.pe_id,
a.pe_visit_id,
a.pe_dept_code,
a.pe_dept_name,
a.conclusion_text
from pe_dept_result_dict a,pe_visit b
where a.pe_id = b.pe_id
and a.pe_visit_id = b.pe_visit_id) a
where PE_ID = #{peId}
and CONCLUSION_TEXT is not null
</select>
<!-- getTotalConclusion/getTotalSuggest 已删除:原实现依赖 wm_concatOracle 18c 起移除,
且接口未引用);汇总逻辑由 OrderService 基于本文件列表查询在应用层完成 -->
<!-- ==================== 体检结论 / 建议 ==================== -->
<select id="getSuggest" resultType="java.util.Map">
select PE_ID, PE_VISIT_ID, REC_CONTENT, REPLACE(REPLACE(REPLACE(DBMS_LOB.SUBSTR(GUIDE_CONTENT, 4000, 1), chr(13) || chr(10), ''), chr(13), ''), chr(10), '') GUIDE_CONTENT
from V_PHYEXAM_DIAGNOSIS
where PE_ID = #{peId}
and GUIDE_CONTENT is not null
<select id="getConclusionAll" resultType="com.hospital.front.vo.ConclusionVo">
SELECT PE_ID,
PE_VISIT_ID,
PE_DEPT_CODE,
PE_DEPT_NAME,
REPLACE(REPLACE(REPLACE(DBMS_LOB.SUBSTR(CONCLUSION_TEXT, 4000, 1), chr(13) || chr(10), ''), chr(13), ''), chr(10), '') CONCLUSION_TEXT
FROM (
SELECT a.pe_id, a.pe_visit_id, a.pe_dept_code, a.pe_dept_name, a.conclusion_text
FROM pe_dept_result_dict a, pe_visit b
WHERE a.pe_id = b.pe_id
AND a.pe_visit_id = b.pe_visit_id
)
WHERE PE_ID = #{peId}
AND CONCLUSION_TEXT IS NOT NULL
</select>
<select id="getSuggestAll" resultType="java.util.HashMap">
select PE_ID, PE_VISIT_ID, REC_CONTENT, REPLACE(REPLACE(REPLACE(DBMS_LOB.SUBSTR(GUIDE_CONTENT, 4000, 1), chr(13) || chr(10), ''), chr(13), ''), chr(10), '') GUIDE_CONTENT
from (select a.pe_id,
a.pe_visit_id,
a.rec_content,
a.guide_content
from pe_diagnosis_record a,pe_visit b
where a.pe_id = b.pe_id
and a.pe_visit_id = b.pe_visit_id) a
where PE_ID = #{peId}
and GUIDE_CONTENT is not null
</select>
<select id="getPeStatusByIdnoAndYear" resultType="java.util.HashMap">
select *
from V_PHYEXAM_PE_STATUS
where ID_NO = #{idNo}
and PE_PRE_DATE &gt;= TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD')
and PE_PRE_DATE &lt; ADD_MONTHS(TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD'), 12)
<select id="getSuggestAll" resultType="com.hospital.front.vo.SuggestVo">
SELECT PE_ID, PE_VISIT_ID, REC_CONTENT,
REPLACE(REPLACE(REPLACE(DBMS_LOB.SUBSTR(GUIDE_CONTENT, 4000, 1), chr(13) || chr(10), ''), chr(13), ''), chr(10), '') GUIDE_CONTENT
FROM (
SELECT a.pe_id, a.pe_visit_id, a.rec_content, a.guide_content
FROM pe_diagnosis_record a, pe_visit b
WHERE a.pe_id = b.pe_id
AND a.pe_visit_id = b.pe_visit_id
)
WHERE PE_ID = #{peId}
AND GUIDE_CONTENT IS NOT NULL
</select>
<!-- ==================== 按身份证 / 日期 / 编号查询结果 ==================== -->
<select id="getResultByIdcardAndYear" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select DISTINCT
ID_NO,
NAME,
PE_ID,
PE_VISIT_ID,
UNIT_CODE,
UNIT_NAME,
to_char( PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss' ) PE_QUEUE_DATE,
to_char( AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss' ) AUDIT_DATE
from V_PHYEXAM_RESULT
where ID_NO = #{idNo}
and PE_QUEUE_DATE &gt;= TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD')
and PE_QUEUE_DATE &lt; ADD_MONTHS(TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD'), 12)
SELECT DISTINCT
ID_NO, NAME, PE_ID, PE_VISIT_ID, UNIT_CODE, UNIT_NAME,
to_char(PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss') PE_QUEUE_DATE,
to_char(AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss') AUDIT_DATE
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.name, b.unit_code,
(SELECT t.unit_name FROM pe_unit_dict t WHERE t.unit_code = b.unit_code) unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a, pe_visit b, pe_result_dict c
WHERE a.pe_id = b.pe_id
AND b.pe_id = c.pe_id
AND b.pe_visit_id = c.pe_visit_id
)
WHERE ID_NO = #{idNo}
AND PE_QUEUE_DATE &gt;= TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD')
AND PE_QUEUE_DATE &lt; ADD_MONTHS(TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD'), 12)
</select>
<select id="getResultByIdcardAndYearAll" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT DISTINCT
ID_NO,
NAME,
PE_ID,
PE_VISIT_ID,
UNIT_CODE,
UNIT_NAME,
to_char ( PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss' ) PE_QUEUE_DATE,
to_char ( AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss' ) AUDIT_DATE
FROM
(
SELECT
b.pe_id,
b.pe_visit_id,
a.id_no,
a.NAME,
b.unit_code,
t.unit_name,
b.pe_queue_date,
b.audit_date,
c.pe_dept_code,
c.pe_dept_name,
c.item_assem_code,
c.item_assem_name,
c.pe_item_code,
c.pe_item_name,
c.pe_result,
c.unit,
c.print_context
FROM
pe_master_index a
JOIN pe_visit b ON b.pe_id = a.pe_id
JOIN pe_result_dict c ON c.pe_id = b.pe_id AND c.pe_visit_id = b.pe_visit_id
LEFT JOIN pe_unit_dict t ON t.unit_code = b.unit_code
WHERE
b.audit_date &gt;= TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD')
and b.audit_date &lt; ADD_MONTHS(TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD'), 12)
and a.id_no = #{idNo}
) a
</select>
<select id="getResultByAuditDate" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select *
from V_PHYEXAM_RESULT
where to_char(AUDIT_DATE,'yyyy-mm-dd')=#{auditDate}
</select>
<select id="getDisResultByAuditDate" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT DISTINCT
ID_NO,
NAME,
PE_ID,
PE_VISIT_ID,
UNIT_CODE,
UNIT_NAME,
to_char( PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss' ) PE_QUEUE_DATE,
to_char( AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss' ) AUDIT_DATE
FROM
V_PHYEXAM_RESULT
WHERE
AUDIT_DATE &gt;= TO_DATE(#{auditDate}, 'YYYY-MM-DD')
and AUDIT_DATE &lt; TO_DATE(#{auditDate}, 'YYYY-MM-DD') + 1
ID_NO, NAME, PE_ID, PE_VISIT_ID, UNIT_CODE, UNIT_NAME,
to_char(PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss') PE_QUEUE_DATE,
to_char(AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss') AUDIT_DATE
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.NAME, b.unit_code, t.unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a
JOIN pe_visit b ON b.pe_id = a.pe_id
JOIN pe_result_dict c ON c.pe_id = b.pe_id AND c.pe_visit_id = b.pe_visit_id
LEFT JOIN pe_unit_dict t ON t.unit_code = b.unit_code
WHERE b.audit_date &gt;= TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD')
AND b.audit_date &lt; ADD_MONTHS(TO_DATE(#{year} || '-01-01', 'YYYY-MM-DD'), 12)
AND a.id_no = #{idNo}
)
</select>
<select id="getItemByPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT
ITEM_ASSEM_CODE,
ITEM_ASSEM_NAME,
PE_ITEM_CODE,
PE_ITEM_NAME,
PE_RESULT,
UNIT,
PRINT_CONTEXT
FROM
(
SELECT
b.pe_id,
b.pe_visit_id,
a.id_no,
a.NAME,
b.unit_code,
t.unit_name,
b.pe_queue_date,
b.audit_date,
c.pe_dept_code,
c.pe_dept_name,
c.item_assem_code,
c.item_assem_name,
c.pe_item_code,
c.pe_item_name,
c.pe_result,
c.unit,
c.print_context
FROM
pe_master_index a
JOIN pe_visit b ON b.pe_id = a.pe_id
JOIN pe_result_dict c ON c.pe_id = b.pe_id AND c.pe_visit_id = b.pe_visit_id
LEFT JOIN pe_unit_dict t ON t.unit_code = b.unit_code
WHERE
b.pe_id = #{peId}
) a
SELECT ITEM_ASSEM_CODE, ITEM_ASSEM_NAME, PE_ITEM_CODE, PE_ITEM_NAME, PE_RESULT, UNIT, PRINT_CONTEXT
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.NAME, b.unit_code, t.unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a
JOIN pe_visit b ON b.pe_id = a.pe_id
JOIN pe_result_dict c ON c.pe_id = b.pe_id AND c.pe_visit_id = b.pe_visit_id
LEFT JOIN pe_unit_dict t ON t.unit_code = b.unit_code
WHERE b.pe_id = #{peId}
)
</select>
<select id="getItemByPeIdAll" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT
ITEM_ASSEM_CODE,
ITEM_ASSEM_NAME,
PE_ITEM_CODE,
PE_ITEM_NAME,
PE_RESULT,
UNIT,
PRINT_CONTEXT
FROM
(
SELECT
b.pe_id,
b.pe_visit_id,
a.id_no,
a.NAME,
b.unit_code,
t.unit_name,
b.pe_queue_date,
b.audit_date,
c.pe_dept_code,
c.pe_dept_name,
c.item_assem_code,
c.item_assem_name,
c.pe_item_code,
c.pe_item_name,
c.pe_result,
c.unit,
c.print_context
FROM
pe_master_index a
JOIN pe_visit b ON b.pe_id = a.pe_id
JOIN pe_result_dict c ON c.pe_id = b.pe_id AND c.pe_visit_id = b.pe_visit_id
LEFT JOIN pe_unit_dict t ON t.unit_code = b.unit_code
WHERE
b.pe_id = #{peId}
) a
SELECT ITEM_ASSEM_CODE, ITEM_ASSEM_NAME, PE_ITEM_CODE, PE_ITEM_NAME, PE_RESULT, UNIT, PRINT_CONTEXT
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.NAME, b.unit_code, t.unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a
JOIN pe_visit b ON b.pe_id = a.pe_id
JOIN pe_result_dict c ON c.pe_id = b.pe_id AND c.pe_visit_id = b.pe_visit_id
LEFT JOIN pe_unit_dict t ON t.unit_code = b.unit_code
WHERE b.pe_id = #{peId}
)
</select>
<select id="getResultByIdNoOrPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select DISTINCT
ID_NO,
NAME,
PE_ID,
PE_VISIT_ID,
UNIT_CODE,
UNIT_NAME,
to_char( PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss' ) PE_QUEUE_DATE,
to_char( AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss' ) AUDIT_DATE
from V_PHYEXAM_RESULT
<where>
1=1
<if test="idNo != null and idNo != '' ">
and ID_NO = #{idNo}
</if>
<if test="peId != null and peId != '' ">
and PE_ID = #{peId}
</if>
and AUDIT_DATE &gt;= TO_DATE(#{auditYear} || '-01-01', 'YYYY-MM-DD')
and AUDIT_DATE &lt; ADD_MONTHS(TO_DATE(#{auditYear} || '-01-01', 'YYYY-MM-DD'), 12)
</where>
<select id="getResultByPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT DISTINCT
ID_NO, NAME, PE_ID, PE_VISIT_ID, UNIT_CODE, UNIT_NAME,
to_char(PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss') PE_QUEUE_DATE,
to_char(AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss') AUDIT_DATE
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.name, b.unit_code,
(SELECT t.unit_name FROM pe_unit_dict t WHERE t.unit_code = b.unit_code) unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a, pe_visit b, pe_result_dict c
WHERE a.pe_id = b.pe_id
AND b.pe_id = c.pe_id
AND b.pe_visit_id = c.pe_visit_id
)
WHERE PE_ID = #{peId}
</select>
<!-- ==================== 按身份证查 peId/预约日期 / 人员列表 ==================== -->
<select id="getPeIdAndDateByIdcard" resultType="java.util.Map">
select PE_ID,to_char( PE_PRE_DATE, 'yyyy-mm-dd' ) PE_PRE_DATE from V_PHYEXAM_PE_STATUS
SELECT PE_ID, to_char(PE_PRE_DATE, 'yyyy-mm-dd') PE_PRE_DATE
FROM (
SELECT b.pe_id, b.name, b.id_no,
(SELECT unit_name FROM pe_unit_dict t WHERE t.unit_code = a.unit_code) unit_name,
a.department, a.pe_pre_date, a.pe_queue_date,
DECODE(a.queue_flag, '1',
DECODE(result_status, '7', '初审', '9', '终审', '1', '检中', '报到'),
DECODE(pe_transfer_hospital, '', '预约', '转向' || pe_transfer_hospital)) pe_status
FROM pe_visit a, pe_master_index b
WHERE a.pe_id = b.pe_id
)
<where>
<if test="idNo != null and idNo != '' ">
and ID_NO = #{idNo}
<if test="idNo != null and idNo != ''">
AND ID_NO = #{idNo}
</if>
and PE_PRE_DATE &gt;= TRUNC(SYSDATE, 'YYYY')
and PE_PRE_DATE &lt; ADD_MONTHS(TRUNC(SYSDATE, 'YYYY'), 12)
AND PE_PRE_DATE &gt;= TRUNC(SYSDATE, 'YYYY')
AND PE_PRE_DATE &lt; ADD_MONTHS(TRUNC(SYSDATE, 'YYYY'), 12)
</where>
order by PE_PRE_DATE desc
ORDER BY PE_PRE_DATE DESC
</select>
</select>
<select id="getResultByPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select DISTINCT
ID_NO,
NAME,
PE_ID,
PE_VISIT_ID,
UNIT_CODE,
UNIT_NAME,
to_char( PE_QUEUE_DATE, 'yyyy-mm-dd HH24:mi:ss' ) PE_QUEUE_DATE,
to_char( AUDIT_DATE, 'yyyy-mm-dd HH24:mi:ss' ) AUDIT_DATE
from V_PHYEXAM_RESULT
where PE_ID = #{peId}
</select>
<select id="getPeIdAndDateByIdcardList" resultType="java.util.Map">
select PE_ID,to_char( PE_PRE_DATE, 'yyyy-mm-dd' ) PE_PRE_DATE from V_PHYEXAM_PE_STATUS
SELECT PE_ID, to_char(PE_PRE_DATE, 'yyyy-mm-dd') PE_PRE_DATE
FROM (
SELECT b.pe_id, b.name, b.id_no,
(SELECT unit_name FROM pe_unit_dict t WHERE t.unit_code = a.unit_code) unit_name,
a.department, a.pe_pre_date, a.pe_queue_date,
DECODE(a.queue_flag, '1',
DECODE(result_status, '7', '初审', '9', '终审', '1', '检中', '报到'),
DECODE(pe_transfer_hospital, '', '预约', '转向' || pe_transfer_hospital)) pe_status
FROM pe_visit a, pe_master_index b
WHERE a.pe_id = b.pe_id
)
<where>
<if test="idNo != null and idNo != '' ">
and ID_NO = #{idNo}
<if test="idNo != null and idNo != ''">
AND ID_NO = #{idNo}
</if>
and PE_PRE_DATE &gt;= TRUNC(SYSDATE, 'YYYY')
and PE_PRE_DATE &lt; ADD_MONTHS(TRUNC(SYSDATE, 'YYYY'), 12)
AND PE_PRE_DATE &gt;= TRUNC(SYSDATE, 'YYYY')
AND PE_PRE_DATE &lt; ADD_MONTHS(TRUNC(SYSDATE, 'YYYY'), 12)
</where>
order by PE_PRE_DATE desc
ORDER BY PE_PRE_DATE DESC
</select>
<!-- 根据audit_date查询当天体检人员列表(去重) -->
<select id="getExamListByDate" resultType="java.util.Map">
<select id="getExamListByDate" resultType="com.hospital.front.vo.ExamListVo">
SELECT DISTINCT PE_ID AS "peId",
ID_NO AS "idNo",
NAME AS "name",
TO_CHAR(audit_date, 'YYYY-MM-DD') AS "auditDate"
FROM V_PHYEXAM_RESULT
FROM (
SELECT b.pe_id, b.pe_visit_id, a.id_no, a.name, b.unit_code,
(SELECT t.unit_name FROM pe_unit_dict t WHERE t.unit_code = b.unit_code) unit_name,
b.pe_queue_date, b.audit_date,
c.pe_dept_code, c.pe_dept_name, c.item_assem_code, c.item_assem_name,
c.pe_item_code, c.pe_item_name, c.pe_result, c.unit, c.print_context
FROM pe_master_index a, pe_visit b, pe_result_dict c
WHERE a.pe_id = b.pe_id
AND b.pe_id = c.pe_id
AND b.pe_visit_id = c.pe_visit_id
)
<where>
<choose>
<when test="auditDate != null and auditDate != ''">
@@ -434,4 +362,5 @@
</choose>
</where>
</select>
</mapper>
</mapper>
@@ -69,7 +69,7 @@
)}
</insert>
<select id="getPhyexamStatus" resultType="java.util.Map">
<select id="getPhyexamStatus" resultType="com.hospital.front.vo.PeStatusVo">
SELECT
PE_ID,
NAME,
@@ -144,17 +144,7 @@
<select id="getConclusion" resultType="java.util.Map">
select PE_ID,
'' PE_VISIT_ID,
PE_DEPT_CODE,
PE_DEPT_NAME,
REPLACE(REPLACE(REPLACE(REPLACE(CONCLUSION_TEXT,CHAR(10),''), ' ', ''),char(9),''),char(13),'') CONCLUSION_TEXT
from V_PHYEXAM_DEPT_RESULT
where PE_ID = #{peId}
and CONCLUSION_TEXT is not null
</select>
<select id="getConclusionAll" resultType="java.util.Map">
<select id="getConclusionAll" resultType="com.hospital.front.vo.ConclusionVo">
select PE_ID,
'' PE_VISIT_ID,
PE_DEPT_CODE,
@@ -165,7 +155,7 @@
and CONCLUSION_TEXT is not null
</select>
<select id="getSuggest" resultType="java.util.Map">
<select id="getSuggestAll" resultType="com.hospital.front.vo.SuggestVo">
SELECT top 1
PE_ID,
REPLACE(
@@ -183,25 +173,7 @@
where PE_ID = #{peId}
AND REC_CONTENT IS NOT NULL
</select>
<select id="getSuggestAll" resultType="java.util.Map">
SELECT top 1
PE_ID,
REPLACE(
REPLACE(
REPLACE(
REPLACE(
REPLACE(REPLACE(GUIDE_CONTENT, CHAR(10), '&lt;br/&gt;'), ' ', ''),
CHAR(9),''
), CHAR(13), ''
), '&lt;br/&gt;&lt;br/&gt;','&lt;br/&gt;'
), '&lt;br/&gt;-谢谢合作祝您健康!&lt;br/&gt;',''
) GUIDE_CONTENT
FROM
V_PHYEXAM_DIAGNOSIS
where PE_ID = #{peId}
AND REC_CONTENT IS NOT NULL
</select>
<select id="getPeStatusByIdnoAndYear" resultType="java.util.Map">
<select id="getPeStatusByIdnoAndYear" resultType="com.hospital.front.vo.PeStatusVo">
SELECT
PE_ID,
NAME,
@@ -314,23 +286,6 @@
group by id_no,NAME,PE_ID,UNIT_NAME
</select>
<select id="getDisResultByAuditDate" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select
ID_NO,
NAME,
PE_ID,
'' PE_VISIT_ID,
'' UNIT_CODE,
UNIT_NAME,
CONVERT(varchar(100),max(PE_QUEUE_DATE),20) PE_QUEUE_DATE,
CONVERT(varchar(100),max(AUDIT_DATE),20) AUDIT_DATE
from V_PHYEXAM_RESULT
where AUDIT_DATE &gt;= CONVERT(DATETIME, #{auditDate})
AND AUDIT_DATE &lt; DATEADD(DAY, 1, CONVERT(DATETIME, #{auditDate}))
group by id_no,NAME,PE_ID,UNIT_NAME
</select>
<select id="getItemByPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT
ITEM_ASSEM_CODE,
@@ -362,31 +317,6 @@
and PE_RESULT is not null
</select>
<select id="getResultByIdNoOrPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select
ID_NO,
NAME,
PE_ID,
'' PE_VISIT_ID,
'' UNIT_CODE,
UNIT_NAME,
CONVERT(varchar(100),max(PE_QUEUE_DATE),20) PE_QUEUE_DATE,
CONVERT(varchar(100),max(AUDIT_DATE),20) AUDIT_DATE
from V_PHYEXAM_RESULT
<where>
1=1
<if test="idNo != null and idNo != '' ">
and ID_NO = #{idNo}
</if>
<if test="peId != null and peId != '' ">
and PE_ID = #{peId}
</if>
and AUDIT_DATE &gt;= CONVERT(DATETIME, #{auditYear} + '-01-01')
and AUDIT_DATE &lt; DATEADD(YEAR, 1, CONVERT(DATETIME, #{auditYear} + '-01-01'))
</where>
group by id_no,NAME,PE_ID,UNIT_NAME
</select>
<select id="getResultByPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
select
ID_NO,
@@ -403,7 +333,7 @@
group by id_no,NAME,PE_ID,UNIT_NAME
</select>
<!-- 根据audit_date查询当天体检人员列表(去重) -->
<select id="getExamListByDate" resultType="java.util.Map">
<select id="getExamListByDate" resultType="com.hospital.front.vo.ExamListVo">
SELECT DISTINCT PE_ID AS "peId",
ID_NO AS "idNo",
NAME AS "name",
@@ -57,7 +57,7 @@
)}
</insert>
<select id="getPhyexamStatus" resultType="java.util.Map">
<select id="getPhyexamStatus" resultType="com.hospital.front.vo.PeStatusVo">
SELECT
t.tjh PE_ID,
t.xm NAME,
@@ -156,14 +156,7 @@
and TJZBXBM is not null
</select>
<select id="getConclusion" resultType="java.util.Map">
select TJH PE_ID,'' PE_VISIT_ID,
REPLACE(REPLACE(REPLACE(REPLACE(TJJL,CHAR(10),''), ' ', ''),char(9),''),char(13),'') CONCLUSION_TEXT
from V_TJJY
where TJH = #{peId}
and TJJL is not null
</select>
<select id="getConclusionAll" resultType="java.util.Map">
<select id="getConclusionAll" resultType="com.hospital.front.vo.ConclusionVo">
select TJH PE_ID,'' PE_VISIT_ID,
REPLACE(REPLACE(REPLACE(REPLACE(TJJL,CHAR(10),''), ' ', ''),char(9),''),char(13),'') CONCLUSION_TEXT
from V_TJJY
@@ -177,15 +170,7 @@
and CONCLUSION_TEXT is not null
</select>-->
<select id="getSuggest" resultType="java.util.Map">
select TJH PE_ID,'' PE_VISIT_ID,
REPLACE(REPLACE(REPLACE(REPLACE(TJJL,CHAR(10),''), ' ', ''),char(9),''),char(13),'') REC_CONTENT,
REPLACE(REPLACE(REPLACE(REPLACE(TJJY,CHAR(10),''), ' ', ''),char(9),''),char(13),'') GUIDE_CONTENT
from V_TJJY
where TJH = #{peId}
and TJJL is not null
</select>
<select id="getSuggestAll" resultType="java.util.Map">
<select id="getSuggestAll" resultType="com.hospital.front.vo.SuggestVo">
select TJH PE_ID,'' PE_VISIT_ID,
REPLACE(REPLACE(REPLACE(REPLACE(TJJL,CHAR(10),''), ' ', ''),char(9),''),char(13),'') REC_CONTENT,
REPLACE(REPLACE(REPLACE(REPLACE(TJJY,CHAR(10),''), ' ', ''),char(9),''),char(13),'') GUIDE_CONTENT
@@ -199,7 +184,7 @@
where PE_ID = #{peId}
and GUIDE_CONTENT is not null
</select>-->
<select id="getPeStatusByIdnoAndYear" resultType="java.util.Map">
<select id="getPeStatusByIdnoAndYear" resultType="com.hospital.front.vo.PeStatusVo">
SELECT
t.tjh PE_ID,
t.xm NAME,
@@ -262,30 +247,12 @@
group by SFZH,XM,TJH,DWMC
</select>
<!--<select id="getResultByAuditDate" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
<!--<select id="getResultByAuditDate" resultType="java.util.Map">
select *
from V_PHYEXAM_RESULT
where to_char(AUDIT_DATE,'yyyy-mm-dd')=#{auditDate}
</select>-->
<select id="getDisResultByAuditDate" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT
SFZH ID_NO,
XM NAME,
TJH PE_ID,
'' PE_VISIT_ID,
'' UNIT_CODE,
DWMC UNIT_NAME,
CONVERT(varchar(100),max(shsj),20) PE_QUEUE_DATE,
CONVERT(varchar(100),max(shsj),20) AUDIT_DATE
FROM
V_TJBGJG
WHERE
shsj &gt;= CONVERT(DATETIME, #{auditDate})
AND shsj &lt; DATEADD(DAY, 1, CONVERT(DATETIME, #{auditDate}))
GROUP BY SFZH,XM,TJH,DWMC
</select>
<select id="getItemByPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT DISTINCT
TJZHXBM ITEM_ASSEM_CODE,
@@ -317,33 +284,6 @@
and TJZBXBM is not null
</select>
<select id="getResultByIdNoOrPeId" resultType="com.hospital.front.vo.MedicalMiddleResultVo">
SELECT
SFZH ID_NO,
XM NAME,
TJH PE_ID,
'' PE_VISIT_ID,
'' UNIT_CODE,
DWMC UNIT_NAME,
CONVERT(varchar(100),max(shsj),20) PE_QUEUE_DATE,
CONVERT(varchar(100),max(shsj),20) AUDIT_DATE
FROM
V_TJBGJG
<where>
1=1
<if test="idNo != null and idNo != '' ">
and SFZH = #{idNo}
</if>
<if test="peId != null and peId != '' ">
and TJH = #{peId}
</if>
and shsj &gt;= CONVERT(DATETIME, #{auditYear} + '-01-01')
and shsj &lt; DATEADD(YEAR, 1, CONVERT(DATETIME, #{auditYear} + '-01-01'))
</where>
GROUP BY SFZH,XM,TJH,DWMC
</select>
<select id="getPeIdAndDateByIdcard" resultType="java.util.Map">
SELECT
tjh pe_id,
@@ -394,7 +334,7 @@
</select>
<!-- 根据audit_date查询当天体检人员列表(去重) -->
<select id="getExamListByDate" resultType="java.util.Map">
<select id="getExamListByDate" resultType="com.hospital.front.vo.ExamListVo">
SELECT DISTINCT TJH AS "peId",
SFZH AS "idNo",
XM AS "name",