扫码缴费新增参数组id用于记录门诊号

电子健康卡打印日志调整。
微信新增客户端缓存token绕过微信认证,加快页面访问
debug
王绍全 2 months ago
parent c4c24b42c7
commit 1b59077f3e
  1. 2
      src/main/java/com/ynxbd/common/action/InHospAction.java
  2. 1
      src/main/java/com/ynxbd/common/action/PushAction.java
  3. 15
      src/main/java/com/ynxbd/common/action/pay/PEnum.java
  4. 2
      src/main/java/com/ynxbd/common/bean/Patient.java
  5. 56
      src/main/java/com/ynxbd/common/helper/common/DateHelper.java
  6. 27
      src/main/java/com/ynxbd/common/service/HCodeService.java
  7. 2
      src/main/java/com/ynxbd/common/service/RegService.java
  8. 8
      src/main/java/com/ynxbd/common/service/XBDService.java
  9. 9
      src/main/java/com/ynxbd/wx/config/WeChatConfig.java
  10. 14
      src/main/java/com/ynxbd/wx/servlet/QServlet.java
  11. 41
      src/main/java/com/ynxbd/wx/wxfactory/WxAuthHelper.java
  12. 71
      src/main/java/com/ynxbd/wx/wxfactory/bean/auth/AuthData.java

@ -114,14 +114,12 @@ public class InHospAction extends BaseAction {
}
JsonResult resp = new HisInHospDao().getInHospFee(patientId, date);
log.error("[getInHospFee] resp={}", JsonHelper.toJsonString(resp));
if (!resp.success()) {
return Result.error(resp.getMessage());
}
InHospFee inHospFee = new InHospFee();
List<InHospFeeItem> items = resp.getDataMapList(InHospFeeItem.class, "Item");
log.error("[getInHospFee] items={}", JsonHelper.toJsonString(items));
items.forEach(item -> {
BigDecimal price = item.getPrice();
Integer count = item.getCount();

@ -4,7 +4,6 @@ import com.ynxbd.common.action.base.BaseAction;
import com.ynxbd.common.helper.common.JsonHelper;
import com.ynxbd.common.helper.http.OkHttpHelper;
import com.ynxbd.common.result.Result;
import com.ynxbd.wx.config.MessagePushConfig;
import lombok.extern.slf4j.Slf4j;
import okhttp3.FormBody;
import okhttp3.RequestBody;

@ -2,7 +2,6 @@ package com.ynxbd.common.action.pay;
import com.ynxbd.common.result.ResultEnum;
import com.ynxbd.common.result.ServiceException;
import com.ynxbd.common.service.PayService;
import lombok.ToString;
import org.apache.commons.lang3.ObjectUtils;
@ -13,22 +12,22 @@ public enum PEnum {
// ------------------------------------
REG("挂号", "register", "G"),
RECIPE("处方", "recipe", "C"),
IN_HOSP("住院预交金", "in_hosp", "Z"),
PEIS_RESERVE("体检预约", "PEIS_reserve", "P"),
IN_HOSP("住院", "in_hosp", "Z"),
OL_REG("问诊挂号", "ol_register", "OG"),
CASEBOOK("病历", "casebook", "BA"),
CASEBOOK("病历复印", "casebook", "BL"),
OUT_COLLECT("外采", "out_collect", "OC"),
OL_REG("问诊挂号", "ol_register", "OG"),
TPP_QR_REG("第三方-扫码挂号", "tpp_qr_reg", "G"),
PEIS_RESERVE("体检预约", "peis_reserve", "P"),
;
public final String NAME;
public final String CODE;
public final String CODE; // Code必须唯一
public final String ORDER_CODE; // 和订单号有关,至多两位
PEnum(String NAME, String CODE, String ORDER_CODE) {

@ -68,4 +68,6 @@ public class Patient implements Serializable {
private String showCardNo;
// 显示的电话号码
private String showTel;
// 地区编码
private String areaCode;
}

@ -461,6 +461,62 @@ public class DateHelper {
return false;
}
/**
* 判断对照时间是否在[day]天内
*
* @param day 几天内[+-]
* @param compareTime 对照时间
* @return boolean
*/
public static Boolean inDateRangeByDay(int day, String compareTime) {
if (ObjectUtils.isEmpty(compareTime) || day == 0) {
return null;
}
if (day < 0) {
String begDateTime = getMoveDateTime(new Date(), day);
return inDateRange(begDateTime, DateHelper.getCurDateTime(), compareTime, DateEnum.yyyy_MM_dd_HH_mm_ss);
} else {
String endDateTime = getMoveDateTime(new Date(), day);
return inDateRange(DateHelper.getCurDateTime(), endDateTime, compareTime, DateEnum.yyyy_MM_dd_HH_mm_ss);
}
}
/**
* 得到一个时间延后或前移几天的时间
*
* @param dateTime 日期和时间
* @param moveDays 移动天数
* @return String 日期和时间
*/
public static String getMoveDateTime(Date dateTime, int moveDays) {
return getMoveDateTime(new SimpleDateFormat(DateEnum.yyyy_MM_dd_HH_mm_ss.TYPE).format(dateTime), moveDays);
}
/**
* 得到一个时间延后或前移几天的时间
*
* @param dateTime 日期和时间
* @param moveDays 移动天数
* @return String 日期和时间
*/
public static String getMoveDateTime(String dateTime, int moveDays) {
try {
if (dateTime == null) {
return null;
}
SimpleDateFormat format = new SimpleDateFormat(DateEnum.yyyy_MM_dd_HH_mm_ss.TYPE);
ParsePosition pos = new ParsePosition(0);
Date day = format.parse(dateTime, pos);
long time = (day.getTime() / 1000) + ((long) moveDays * 24 * 60 * 60);
day.setTime(time * 1000);
return format.format(day);
} catch (Exception e) {
return null;
}
}
/**
* 得到一个时间延后或前移几天的时间

@ -11,6 +11,7 @@ import com.ynxbd.common.bean.enums.HealthCardEnum;
import com.ynxbd.common.bean.Patient;
import com.ynxbd.common.bean.enums.HealthCardRespCodeEnum;
import com.ynxbd.common.helper.ProperHelper;
import com.ynxbd.common.helper.common.JsonHelper;
import com.ynxbd.wx.config.WeChatConfig;
import com.ynxbd.common.dao.PatientDao;
import com.ynxbd.common.config.EhCacheConfig;
@ -117,7 +118,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.getAppToken(commonIn, H_APP_ID);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]获取appToken失败-" + resultObj);
log.info("[电子健康卡]获取appToken失败: {}", resultObj);
return null;
}
@ -213,7 +214,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.registerHealthCard(commonIn, healthCardInfoReq);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]注册失败-" + resultObj);
log.info("[电子健康卡]注册失败: {}", resultObj);
return commonOut;
}
return resultObj.getJSONObject("rsp");
@ -243,7 +244,7 @@ public class HCodeService {
JSONObject commonOut = resultObj.getJSONObject("commonOut");
JSONObject rspObj = resultObj.getJSONObject("rsp");
if (!"0".equals(commonOut.getString("resultCode")) || rspObj == null) {
log.info("[电子健康卡]授权码获取健康卡失败:" + resultObj);
log.info("[电子健康卡]授权码获取健康卡失败: {}", resultObj);
return null;
}
JSONObject card = rspObj.getJSONObject("card");
@ -254,7 +255,7 @@ public class HCodeService {
Patient patient = new Patient();
String phone1 = card.getString("phone1");
if (phone1 == null || "".equals(phone1)) {
if (ObjectUtils.isEmpty(phone1)) {
patient.setTel(card.getString("phone2"));
} else {
patient.setTel(phone1);
@ -268,7 +269,7 @@ public class HCodeService {
patient.setBirthday(card.getString("birthday"));
patient.setHealthCardId(card.getString("healthCardId"));
patient.setCardType(card.getString("idType"));
log.info("[一键绑定]获取用户信息 patient={}", patient);
log.info("[一键绑定]获取用户信息 {}", JsonHelper.toJsonString(patient));
return patient;
} catch (Exception e) {
ErrorHelper.println(e);
@ -299,7 +300,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.getHealthCardByQRCode(commonIn, qrCode);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]二维码获取健康卡失败:" + resultObj);
log.info("[电子健康卡]二维码获取健康卡失败: {}", resultObj);
return null;
}
JSONObject respJson = resultObj.getJSONObject("rsp");
@ -349,7 +350,7 @@ public class HCodeService {
JSONObject resultJson = healthCard.registerUniformVerifyOrder(commonIn, idCardNo, "01", name, wechatCode);
JSONObject commonOut = resultJson.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]实人认证生成orderId接口失败:" + resultJson);
log.info("[电子健康卡]实人认证生成orderId接口失败: {}", resultJson);
return null;
}
JSONObject respJson = resultJson.getJSONObject("rsp");
@ -384,7 +385,7 @@ public class HCodeService {
JSONObject resultJson = healthCard.checkUniformVerifyResult(commonIn, verifyOrderId, registerOrderId);
JSONObject commonOut = resultJson.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]实人认证结果查询失败:" + resultJson);
log.info("[电子健康卡]实人认证结果查询失败: {}", resultJson);
return false;
}
JSONObject respJson = resultJson.getJSONObject("rsp");
@ -419,7 +420,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.getOrderIdByOutAppId(commonIn, WeChatConfig.APP_ID, qrCodeText);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]获取卡包订单ID 失败:" + resultObj);
log.info("[电子健康卡]获取卡包订单ID 失败: {}", resultObj);
return null;
}
return resultObj.getJSONObject("rsp");
@ -512,7 +513,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.getDynamicQRCode(commonIn, healthCardId, "01", idCardNo, codeType);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("获取健康卡二维码失败, resp-{}", resultObj);
log.info("获取健康卡二维码失败: {}", resultObj);
return null;
}
return resultObj.getJSONObject("rsp");
@ -548,7 +549,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.bindCardRelation(commonIn, patientId, qrCodeText);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]绑定健康卡和医院关系-" + resultObj);
log.info("[电子健康卡]绑定健康卡和医院关系失败: {}", resultObj);
return null;
}
return resultObj.getJSONObject("rsp");
@ -670,7 +671,7 @@ public class HCodeService {
JSONObject resultObj = healthCard.ocrInfo(commonIn, imageContent);
JSONObject commonOut = resultObj.getJSONObject("commonOut");
if (!"0".equals(commonOut.getString("resultCode"))) {
log.info("[电子健康卡]身份证识别失败-" + resultObj);
log.info("[电子健康卡]身份证识别失败: {}", resultObj);
return null;
}
JSONObject rsp = resultObj.getJSONObject("rsp");
@ -781,7 +782,7 @@ public class HCodeService {
JSONObject commonOut = healthCardInfosRsp.getJSONObject("commonOut");
JSONObject rspObj = healthCardInfosRsp.getJSONObject("rsp");
if (!"0".equals(commonOut.getString("resultCode")) || rspObj == null) {
log.info("批量领取健康卡-" + healthCardInfosRsp);
log.info("批量领取健康卡失败: {}", healthCardInfosRsp);
return null;
}
JSONArray rspItems = rspObj.getJSONArray("rspItems");

@ -77,7 +77,7 @@ public class RegService {
reg.setHisStatus(-1);
reg.setPayStatus(-1);
boolean isResult = new RegisterDao().insert(reg);
log.info("[挂号预存信息{}", (isResult ? "成功" : "失败"));
log.info("[挂号]预存信息{}", (isResult ? "成功" : "失败"));
return isResult;
}

@ -41,7 +41,7 @@ public class XBDService {
}
/**
* 获取云胶片的授权地址[版本2]
* 获取云胶片的授权地址[版本2](smsPacs是静态资源所在的文件夹nginx中配置需带结尾"/" = /smsPacs/)
*
* @param treatNum 门诊号|住院号
* @param treatType 类型[1:门诊2:住院]
@ -61,13 +61,13 @@ public class XBDService {
}
token = token.substring(3, 12).toUpperCase();
String url = "/smsPacs?token=" + token + ("1".equals(treatType) ? "&opsNum=" : "&inHosNum=") + treatNum;
String url = "/smsPacs/?token=" + token + ("1".equals(treatType) ? "&opsNum=" : "&inHosNum=") + treatNum;
log.info("[云胶片]授权 url={}", url);
return url;
}
/**
* 获取云胶片的授权地址[版本1]
* 获取云胶片的授权地址[版本1](smsPacs是静态资源所在的文件夹nginx中配置需带结尾"/" = /smsPacs/)
*
* @param patientId 患者id
*/
@ -80,7 +80,7 @@ public class XBDService {
if (ObjectUtils.isEmpty(token)) {
throw new ServiceException("token转化失败");
}
String url = "/smsPacs?token=" + token.toUpperCase() + "&patID=" + patientId;
String url = "/smsPacs/?token=" + token.toUpperCase() + "&patID=" + patientId;
log.info("[云胶片]授权 url={}", url);
return url;
}

@ -174,6 +174,15 @@ public class WeChatConfig {
}
public static String getAesKey() {
return ("xbd" + WeChatConfig.APP_ID).substring(0, 16);
}
public static String getAesIV() {
return ("xbd" + WeChatConfig.APP_SECRET).substring(0, 16);
}
// public static String getAccessToken() {
// String accessToken = ACCESS_TOKEN_CACHE.get(ACCESS_TOKEN_KEY);
// if (ObjectUtils.isEmpty(accessToken)) {

@ -54,14 +54,18 @@ public class QServlet extends HttpServlet {
String patientId = request.getParameter("p");
String cardNo = request.getParameter("t");
log.info("{} [patientId={}]多张处方扫码请求,开始解析...", merchantEnum.NAME, patientId);
if (StringUtils.isEmpty(patientId) && StringUtils.isEmpty(cardNo)) {
String groupTreatNum = request.getParameter("g");
boolean hasTreatNum = !ObjectUtils.isEmpty(groupTreatNum);
log.info("{} [patientId={} {}]多张处方扫码请求,开始解析...", merchantEnum.NAME, patientId, hasTreatNum ? (", treatNum=" + groupTreatNum) : "");
if (ObjectUtils.isEmpty(patientId) && ObjectUtils.isEmpty(cardNo)) {
log.info("[支付] 多张扫码请求 patientId is null and idCardNo is null");
return;
}
// 新版体检缴费,patientId赋值为0
if (!StringUtils.isEmpty(cardNo) && StringUtils.isEmpty(patientId)) {
if (!ObjectUtils.isEmpty(cardNo) && ObjectUtils.isEmpty(patientId)) {
patientId = "0"; //patientId 赋值0
}
@ -74,8 +78,10 @@ public class QServlet extends HttpServlet {
cardNo = "&ent=" + AesWxHelper.encode(cardNo);
}
groupTreatNum = hasTreatNum ? ("&treatNum=" + groupTreatNum) : "";
if (MerchantEnum.WX.equals(merchantEnum)) {
response.sendRedirect(WeChatConfig.getWebUrl() + "pay-qr-recipe.html?p=" + patientId + "&enp=" + AesWxHelper.encode(patientId) + cardNo);
response.sendRedirect(WeChatConfig.getWebUrl() + "pay-qr-recipe.html?p=" + patientId + "&enp=" + AesWxHelper.encode(patientId) + cardNo + groupTreatNum);
}
}

@ -1,5 +1,6 @@
package com.ynxbd.wx.wxfactory;
import com.ynxbd.common.bean.Patient;
import com.ynxbd.common.bean.User;
import com.ynxbd.common.helper.common.AesMicroHelper;
import com.ynxbd.common.helper.common.Base64Helper;
@ -10,6 +11,7 @@ import com.ynxbd.common.service.PatientService;
import com.ynxbd.wx.config.WeChatConfig;
import com.ynxbd.wx.wxfactory.bean.SnsOath2AccessToken;
import com.ynxbd.wx.wxfactory.bean.SnsUserInfo;
import com.ynxbd.wx.wxfactory.bean.auth.AuthData;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.ObjectUtils;
import org.ehcache.Cache;
@ -21,6 +23,7 @@ import java.net.URLDecoder;
import java.net.URLEncoder;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
@Slf4j
@ -123,10 +126,44 @@ public class WxAuthHelper {
public static Result isAuth(HttpServletRequest request) throws Exception {
HttpSession session = request.getSession();
Object openid = session.getAttribute("openid");
String token = request.getParameter("token"); // 前端缓存
AuthData authData = new AuthData();
String cacheOpenid = authData.decodeToken(token);
if (cacheOpenid != null) {
log.info("[微信token认证] token={}, openid={}", token, cacheOpenid);
User user = WxCacheHelper.getCacheUser(cacheOpenid);
List<Patient> patients;
if (user == null) {
patients = new PatientService().queryPatientList(cacheOpenid, null, true);
Cache<String, User> cache = WxCacheHelper.getUserCache();
User addCache = new User();
addCache.setUnionId("");
addCache.setOpenid(cacheOpenid);
addCache.setAvatar(authData.getAvatar());
addCache.setNickName(authData.getNickName());
addCache.setPatientList(patients);
cache.put(cacheOpenid, addCache);
} else {
patients = user.getPatientList();
}
Map<String, Object> map = new HashMap<>();
map.put("openid", cacheOpenid);
map.put("token", token);
map.put("unionId", "");
map.put("date", new Date());
map.put("avatar", authData.getAvatar());
map.put("nickName", authData.getNickName());
map.put("patients", CodeHelper.get28UUID() + Base64Helper.encode(URLEncoder.encode(JsonHelper.toJsonString(patients), "UTF-8")));
map.put("hash", request.getParameter("hash"));
map.put("enParams", AesMicroHelper.encode(cacheOpenid));
return Result.success(map);
}
Object openid = session.getAttribute("openid");
if (openid != null) {
log.info("[微信认证]openid={}", openid);
User user = WxCacheHelper.getCacheUser((String) openid);
if (user == null) {
return Result.success(getAuthUrl(request));
@ -141,6 +178,7 @@ public class WxAuthHelper {
Map<String, Object> map = new HashMap<>();
map.put("openid", openid);
map.put("token", new AuthData().createToken(openid.toString(), user.getAvatar(), user.getNickName()));
map.put("unionId", user.getUnionId());
map.put("date", new Date());
map.put("avatar", user.getAvatar());
@ -148,7 +186,6 @@ public class WxAuthHelper {
map.put("patients", CodeHelper.get28UUID() + Base64Helper.encode(URLEncoder.encode(JsonHelper.toJsonString(user.getPatientList()), "UTF-8")));
map.put("hash", request.getParameter("hash"));
map.put("enParams", AesMicroHelper.encode(openid.toString()));
return Result.success(map);
}

@ -0,0 +1,71 @@
package com.ynxbd.wx.wxfactory.bean.auth;
import com.ynxbd.common.helper.common.DateHelper;
import com.ynxbd.common.helper.common.JsonHelper;
import com.ynxbd.wx.config.WeChatConfig;
import com.ynxbd.wx.wxfactory.AesWxHelper;
import lombok.Getter;
import lombok.NoArgsConstructor;
import lombok.Setter;
import lombok.ToString;
import org.apache.commons.lang3.ObjectUtils;
import java.io.Serializable;
@Getter
@Setter
@ToString
@NoArgsConstructor
public class AuthData implements Serializable {
private static final long serialVersionUID = 202511101525001L;
private String openid;
private String createTime;
private String avatar;
private String nickName;
public String createToken(String userOpenid, String avatar, String nickName) {
if (userOpenid == null) {
return null;
}
this.openid = userOpenid;
this.avatar = avatar;
this.nickName = nickName;
this.createTime = DateHelper.getCurDateTime();
String dataJson = JsonHelper.toJsonString(this);
if (ObjectUtils.isEmpty(dataJson)) {
return null;
}
return AesWxHelper.encryptHex(dataJson, WeChatConfig.getAesKey(), WeChatConfig.getAesIV());
}
public String decodeToken(String token) {
if (ObjectUtils.isEmpty(token)) {
return null;
}
String dataJson = AesWxHelper.decryptHex(token, WeChatConfig.getAesKey(), WeChatConfig.getAesIV());
if (ObjectUtils.isEmpty(dataJson)) {
return null;
}
AuthData authData = JsonHelper.parseObject(dataJson, AuthData.class);
if (authData == null) {
return null;
}
String cacheOpenid = authData.getOpenid();
if (ObjectUtils.isEmpty(cacheOpenid)) {
return null;
}
String cacheTime = authData.getCreateTime();
Boolean hasValidity = DateHelper.inDateRangeByDay(-3, cacheTime);
if (hasValidity != null && hasValidity) { // 在有效期内
this.openid = cacheOpenid;
this.avatar = authData.getAvatar();
this.nickName = authData.getNickName();
this.createTime = cacheTime;
return cacheOpenid;
}
return null;
}
}
Loading…
Cancel
Save