package com.emato.biz.service.impl; import com.alibaba.fastjson.JSON; import com.alibaba.fastjson.JSONObject; import com.emato.biz.util.OmsUtils; import com.emato.biz.domain.OperateLogDTO; import com.emato.biz.domain.OutRequest; import com.emato.biz.domain.mall.*; import com.emato.biz.domain.merchant.MerchantSecret; import com.emato.biz.exception.Assert; import com.emato.biz.mapper.mall.InventoryDataMapper; import com.emato.biz.mapper.mall.MallMngChangeMapper; import com.emato.biz.mapper.mall.SalesDetailMapper; import com.emato.biz.mapper.merchant.MerchantSecretMapper; import com.emato.biz.service.SignService; import com.emato.biz.service.mall.ISalesDetaiServicel; import com.emato.biz.util.DateUtil; import com.emato.biz.util.MatchUtil; import com.emato.common.core.Result; import com.emato.common.exception.ServiceException; import com.emato.common.utils.DateUtils; import com.emato.common.utils.StringUtils; import com.emato.common.utils.oms.response.ResultCodeEnum; import com.emato.common.utils.sign.Md5Utils; import com.emato.system.mapper.SysConfigMapper; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.BeanUtils; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import javax.annotation.Resource; import javax.servlet.http.HttpServletRequest; import java.sql.*; import java.util.ArrayList; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.stream.Collectors; /** * CW推送数据接口 */ @Service public class SalesDetaiServicelImpl implements ISalesDetaiServicel { private final Logger logger = LoggerFactory.getLogger(SalesDetaiServicelImpl.class); @Resource private InventoryDataMapper inventoryDataMapper; @Resource private MallMngChangeMapper mallMngChangeMapper; @Autowired private SysConfigMapper configMapper; @Resource private MerchantSecretMapper merchantSecretMapper; @Autowired private OmsUtils omsUtils; @Resource private SalesDetailMapper salesDetailMapper; @Autowired private SignService signService; /** * 记录请求日志 * * @param reqData * @param merchantSn */ @Override public void insertReqLog(String reqData, String merchantSn) { try { OperateLogDTO operateLogDTO = new OperateLogDTO(); operateLogDTO.setReqData(reqData); operateLogDTO.setMerchSn(merchantSn); salesDetailMapper.insertSalesDataReqLog(operateLogDTO); } catch (Exception e) { logger.error("记录商户请求日志异常", e); throw new ServiceException("系统异常,请稍后再试!"); } } /** * 获取销售数据 * * @param outRequest * @return */ @Override public Result getSalesDetailData(OutRequest outRequest) { try { logger.info("---------- 查询销售数据开始 ----------"); logger.info("========== 电商请求 eccs 报文 =========> {}", outRequest); // 验签 Assert.notTrue(!signService.verifySign(outRequest), ResultCodeEnum.SIGN_ERROR); // 转为请求类 SalesDataReqVO reqVO = JSON.parseObject(outRequest.getData(), SalesDataReqVO.class); logger.debug("========== 解析后的请求数据 ==========> 【{}】", reqVO); // 分页页码 String pageIndexStr = reqVO.getPageIndex(); // 分页大小 String pageSizeStr = reqVO.getPageSize(); // 起始时间戳 String startTimeTimeStamp = reqVO.getStarTime(); // 起始时间戳 String endTimeTimeStamp = reqVO.getEndTime(); // 参数校验 Assert.notNull(pageIndexStr, ResultCodeEnum.PARAM_ERROR_PAGE_INDEX_NOT_NULL); Assert.notNull(pageSizeStr, ResultCodeEnum.PARAM_ERROR_PAGE_SIZE_NOT_NULL); Assert.notTrue(!MatchUtil.isPositiveInteger(pageIndexStr), ResultCodeEnum.PARAM_ERROR_PAGE_INDEX_NOT_POS_INT); Assert.notTrue(!MatchUtil.isPositiveInteger(pageSizeStr), ResultCodeEnum.PARAM_ERROR_PAGE_SIZE_NOT_POS_INT); Assert.notTrue(!MatchUtil.isTimestamp(reqVO.getStarTime()), ResultCodeEnum.PARAM_ERROR_START_TIME_NOT_TIMES_STAMP); Assert.notTrue(!MatchUtil.isTimestamp(reqVO.getEndTime()), ResultCodeEnum.PARAM_ERROR_END_TIME_NOT_TIMES_STAMP); // 计算起始时间和结束时间相差多少小时, long hourBetweenTimesStamp = DateUtil.getHourBetweenTimesStamp(startTimeTimeStamp, endTimeTimeStamp); Assert.notTrue(hourBetweenTimesStamp > 24, ResultCodeEnum.TIME_INTERVAL_TOO_LARGE); // 分页大小 int pageSize = Integer.parseInt(pageSizeStr); // 大于500就取500,否则取 pageSize pageSize = Math.min(pageSize, 500); int pageIndex = Integer.parseInt(pageIndexStr); // 小于1就取1,否则取 pageIndex pageIndex = Math.max(pageIndex, 1); pageIndex = (pageIndex - 1) * pageSize; // 格式化起始时间 String startTime = DateUtil.dateFormat(startTimeTimeStamp, "yyyy-MM-dd HH:mm:ss"); // 格式化结束时间 String endTime = DateUtil.dateFormat(endTimeTimeStamp, "yyyy-MM-dd HH:mm:ss"); // 设置查询条件 reqVO.setOffset(pageIndex); reqVO.setLimit(pageSize); reqVO.setStarTime(startTime); reqVO.setEndTime(endTime); // 查询销售数据 List salesDataList = salesDetailMapper.selectSalesDetailData(reqVO); Assert.notTrue(salesDataList.isEmpty(), ResultCodeEnum.NO_DATA); // 记录查询日志 insertReqLog(JSON.toJSONString(outRequest), outRequest.getMerchId()); // 将数据库数据转换为接口输出的数据格式 List salesDataVOList = salesDataList.stream().map(salesData -> { SalesDataResVO resVO = new SalesDataResVO(); BeanUtils.copyProperties(salesData, resVO); return resVO; }).collect(Collectors.toList()); // 查询总记录数 int total = salesDetailMapper.selectSalesDetailDataTotal(reqVO); // 组装返回数据 Map resultMap = new HashMap<>(); resultMap.put("rows", salesDataVOList); resultMap.put("total", total); logger.info("---------- 查询销售数据结束 ----------"); return Result.success(resultMap); } catch (ServiceException se) { throw se; } catch (Exception e) { logger.error("外部商户获取销售数据异常 => ", e); throw new ServiceException("获取销售数据异常,请稍后再试!"); } } /** * kmall向eccs系统推送数据 * @param newSystemFormatEntiy * @return */ @Override public int pushSalesDetaiServicel(NewSystemFormatEntiy newSystemFormatEntiy) { logger.debug("---------- Eccs 接收 Kmall 销售数据开始 ----------"); int rows = 0; try { // 查询订单查看是否存在 SalesDataReqVO reqVO = new SalesDataReqVO(); reqVO.setOrderNo(newSystemFormatEntiy.getReceiptNo()); reqVO.setEmatouCode(newSystemFormatEntiy.getEmatouCode()); List salesDataList = salesDetailMapper.selectSalesDetailData(reqVO); if (salesDataList.isEmpty()) { // 如果不存在, 新增 // 设置创建人和创建时间 newSystemFormatEntiy.setCreateSn("admin"); newSystemFormatEntiy.setCreateTime(new Date()); rows = salesDetailMapper.insertSalesDetaiDate(newSystemFormatEntiy); }else { // 如果存在则修改 // 设置修改人和修改时间 newSystemFormatEntiy.setModerSn("admin"); newSystemFormatEntiy.setModTime(new Date()); rows = salesDetailMapper.updateSalesDetailData(newSystemFormatEntiy); } } catch (Exception e) { logger.error("Eccs 接收 Kmall 销售数据异常 => ", e); throw new ServiceException("Eccs 接收 Kmall 销售数据异常!"); } logger.debug("---------- Eccs 接收 Kmall 销售数据结束 ----------"); return rows; } /** * 外部商户系统查询订单销售数据 * @param msg * @return */ @Override public Result getSalesDetaiData(JSONObject msg, HttpServletRequest httpServletRequest) { try { logger.debug("---------- 处理商户获取销售明细::开始 ----------"); //校验签名 Map weChatMapSalesMsg = JSONObject.toJavaObject(msg, Map.class); //签名验证 String strSign = weChatMapSalesMsg.get("sign").toString().trim(); String merchId = weChatMapSalesMsg.get("merchId").toString().trim()==null?"":weChatMapSalesMsg.get("merchId").toString().trim(); String timestamp = weChatMapSalesMsg.get("timestamp").toString().trim()==null?"":weChatMapSalesMsg.get("timestamp").toString().trim(); // String str = configMapper.getConfigValue("salesdetai").trim(); if(StringUtils.isEmpty(merchId)){ return Result.error("900051","merchId为空"); } // 改为使用密钥配置 MerchantSecret merchantSecret = new MerchantSecret(); merchantSecret.setMerchSn(merchId); List merchantSecrets = merchantSecretMapper.selectMerchantSecretList(merchantSecret); if (null == merchantSecrets || merchantSecrets.isEmpty()) { return Result.error("900051","merchId参数错误"); } MerchantSecret MerchantSecret_2 = merchantSecrets.get(0); String str = MerchantSecret_2.getMd5Salt(); if(StringUtils.isEmpty(timestamp)){ return Result.error("900051","timestamp为空"); } String md5CheckCode = checkType(weChatMapSalesMsg.get("data").toString(), timestamp, str); logger.debug("--- getSalesDetaiData md5CheckCode:", md5CheckCode); if (!strSign.trim().equals(md5CheckCode)) { return Result.error("900052", "签名错误"); } Map weSalesMsg = JSONObject.toJavaObject(JSON.parseObject(weChatMapSalesMsg.get("data").toString()), Map.class); String starTime = (String) weSalesMsg.get("starTime"); String endTime = (String) weSalesMsg.get("endTime"); Integer pageIndex = Integer.parseInt(weSalesMsg.get("pageIndex")+""); pageIndex = pageIndex <= 1 ? 1 : pageIndex; Integer pageSize = Integer.parseInt(weSalesMsg.get("pageSize")+""); pageSize = pageSize <= 0 ? 1 : pageSize; pageSize = pageSize >= 500 ? 500 : pageSize; weSalesMsg.put("starTime", DateUtils.getStrDate((String) weSalesMsg.get("starTime"))); weSalesMsg.put("endTime",DateUtils.getStrDate((String)weSalesMsg.get("endTime"))); if(pageIndex>500){ return Result.error("900053","请求总数或时间区间过大"); } pageIndex = (pageIndex - 1) * pageSize; weSalesMsg.put("offset", pageIndex); weSalesMsg.put("limit", pageSize); //记录调用参数接口日志 long diff=(Long.parseLong(endTime) - Long.parseLong(starTime))/1000/60/60; if(diff<=24){ pullQueryData(weChatMapSalesMsg); List list = mallMngChangeMapper.getSalesDetaiData(weSalesMsg); Integer total = mallMngChangeMapper.getTotalRecord(weSalesMsg); //desList = DesUtils.encode(JSON.toJSONString(list)); if(list.size()==0){ return Result.error("900054","该条件下无数据"); }else{ Map map = new HashMap<>(); map.put("total",total); map.put("rows",list); logger.debug("---------- 处理商户获取销售明细::结束,处理成功 ----------"); return Result.success(map); } }else{ logger.debug("---------- 处理商户获取销售明细::结束,【900053】请求总数或时间区间过大 ----------"); return Result.error("900053","请求总数或时间区间过大"); } }catch (Exception e){ logger.error("外部系统查询订单销售数据错误="+ JSON.toJSONString(msg),e); return Result.error("900051","参数错误"); } } /** * 记录外部调用接口参数,时间和调用方 * @param msg */ private void pullQueryData(Map msg) { Map map = new HashMap<>(); map.put("tranDirection",msg.get("merchId")); map.put("msg",msg.toString()); mallMngChangeMapper.pullQueryData(map); } /** * 插入来源于oms的库存数据 * @param inventoryDataVo */ @Override public Result inserInventory(InventoryDataVo inventoryDataVo) { try{ logger.error("插入来源于oms的库存数据"); //查询是否存在该库存信息 Integer checkStuts = inventoryDataMapper.queryOneInventory(inventoryDataVo); if(checkStuts>0){ inventoryDataMapper.updateInventory(inventoryDataVo); }else{ inventoryDataMapper.inserInventory(inventoryDataVo); } return Result.success(); }catch (Exception e){ logger.error("插入来源于oms的库存数据"+JSON.toJSONString(inventoryDataVo),e); return Result.error("1001","数据插入出错"); } } /** * 查询库存数据提供给外部系统 * @param msg * @param httpServletRequest * @return */ @Override public Result queryInventory(JSONObject msg, HttpServletRequest httpServletRequest) { try{ logger.debug("---------- 处理商户获取库存数据::开始 ----------"); //校验签名 Map weChatMapMsg = JSONObject.toJavaObject(msg, Map.class); //签名验证 String strSign = weChatMapMsg.get("sign").toString().trim(); String merchId = weChatMapMsg.get("merchId").toString().trim()==null?"":weChatMapMsg.get("merchId").toString().trim(); String timestamp = weChatMapMsg.get("timestamp").toString().trim()==null?"":weChatMapMsg.get("timestamp").toString().trim(); // String str = configMapper.getConfigValue("inventory"); if(StringUtils.isEmpty(merchId)){ return Result.error("900051","merchId为空"); } // 改为使用密钥配置 MerchantSecret merchantSecret = new MerchantSecret(); merchantSecret.setMerchSn(merchId); List merchantSecrets = merchantSecretMapper.selectMerchantSecretList(merchantSecret); if (null == merchantSecrets || merchantSecrets.isEmpty()) { return Result.error("900051","merchId参数错误"); } MerchantSecret MerchantSecret_2 = merchantSecrets.get(0); String str = MerchantSecret_2.getMd5Salt(); if(StringUtils.isEmpty(timestamp)){ return Result.error("900051","timestamp为空"); } String md5CheckCode = checkType(weChatMapMsg.get("data").toString(), timestamp, str); logger.debug("--- queryInventory md5CheckCode:", md5CheckCode); if (!strSign.trim().equals(md5CheckCode)) { return Result.error("900002", "签名错误"); } Map weDtilMsg = JSONObject.toJavaObject(JSON.parseObject(weChatMapMsg.get("data").toString()), Map.class); Integer pageIndex = Integer.parseInt(weDtilMsg.get("pageIndex")+""); pageIndex = pageIndex <= 1 ? 1 : pageIndex; Integer pageSize = Integer.parseInt(weDtilMsg.get("pageSize")+""); pageSize = pageSize <= 0 ? 1 : pageSize; pageSize = pageSize >= 500 ? 500 : pageSize; pageIndex = (pageIndex-1)*pageSize; weChatMapMsg.put("offset", pageIndex); weChatMapMsg.put("limit", pageSize); weChatMapMsg.put("merchId", merchId); weChatMapMsg.put("sign", strSign); String merchSn = weDtilMsg.get("merchSn").toString().trim()==null?"":weDtilMsg.get("merchSn").toString().trim(); if(merchSn.equals("")){ return Result.error("900001","参数错误"); } if(pageSize>3000){ return Result.error("900003","请求数量过大"); } pullQueryData(weChatMapMsg); // 数据查询 //List list = inventoryDataMapper.getInventoryData(weChatMapMsg); // todo bug_2023-03-21 此处直接拉取的oms库,需要重新设计 // todo bug_2023-03-21 虽然拉取数据存疑,但此处拉取出的数据向商户返回,其返回的字段与对外接口已经保持一致 List list = getOmsData(weDtilMsg,weChatMapMsg); // todo bug_2023-03-21 total不正确 Integer total = inventoryDataMapper.getInventoryTotal(); if(list.size()==0){ return Result.error("900004","该条件下无数据"); }else{ Map map = new HashMap<>(); map.put("total",total); map.put("invTime",DateUtils.dateToStrLong(new Date())); map.put("rows",list); logger.debug("---------- 处理商户获取库存数据::结束,处理成功 ----------"); return Result.success(map); } }catch (Exception e){ logger.error("外部系统查询库存系统条件="+JSON.toJSONString(msg),e); return Result.error("900001","参数错误"); } } //签名加密校验 public String checkType(String data,String timestamp,String sekey) { String sign = sekey+"data" + data + "timestamp" + timestamp; return Md5Utils.encryption(sign); } public List getOmsData(Map weDtilMsg,Map weChatMapMsg){ String driver=omsUtils.getOmsDriver(); String user=omsUtils.getOmsUser(); String password=omsUtils.getOmsPassword(); String url=omsUtils.getOmsUrl(); List inventoryDataPushVos = null; try{ //加载数据库驱动 Class.forName(driver); //连接数据库 Connection conn = DriverManager.getConnection(url,user,password); //创建Statement对象 Statement stmt = conn.createStatement(); String sql = "SELECT wmsi.merch_sn,ppr.prod_barcode,ppr.prod_name,wmsi.shop_sn,wim.valid_num,wmsi.shop_inve FROM wb_inve_mng wim LEFT JOIN pd_product_record ppr ON wim.sku = ppr.sku LEFT JOIN wb_merch_shop_inve wmsi ON wim.sku = wmsi.sku WHERE ppr.is_record = 1 AND ppr.is_valid = 0 AND wim.inve_status = 0 AND wim.is_valid = 0 AND wmsi.is_valid = 0 AND wim.merch_sn='"+weDtilMsg.get("merchSn")+"' limit "+weChatMapMsg.get("offset")+","+weChatMapMsg.get("limit")+""; //建立结果集 ResultSet rs = stmt.executeQuery(sql); inventoryDataPushVos =convertList(rs); //关闭结果集 rs.close(); //关闭Statement对象 stmt.close(); //关闭数据库 conn.close(); }catch(Exception e){ logger.error("查询oms库存数据出错"); } return inventoryDataPushVos; } private static List convertList(ResultSet rs) throws SQLException { List list = new ArrayList(); while (rs.next()) { InventoryDataPushVo inventoryDataPushVo = new InventoryDataPushVo(); inventoryDataPushVo.setBarcode(rs.getString("prod_barcode")); inventoryDataPushVo.setProductName(rs.getString("prod_name")); inventoryDataPushVo.setShopSn(rs.getString("shop_sn")); inventoryDataPushVo.setShopInvent(rs.getInt("shop_inve")); inventoryDataPushVo.seteMatou(rs.getInt("valid_num")); list.add(inventoryDataPushVo); } return list; } }