package com.chinacreator.videoalliance.order.service; import java.text.ParseException; import java.util.Calendar; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import com.chinacreator.common.exception.BusinessException; import com.chinacreator.common.util.MD5; import com.chinacreator.common.util.UsermobUtil; import com.chinacreator.videoalliance.common.bean.AreaInfo; import com.chinacreator.videoalliance.common.bean.CPInfo; import com.chinacreator.videoalliance.common.util.AreaUtil; import com.chinacreator.videoalliance.common.util.ConfigUtil; import com.chinacreator.videoalliance.order.bean.OrderInfo; import com.chinacreator.videoalliance.order.bean.OrderLog; import com.chinacreator.videoalliance.order.bean.SPInfo; import com.chinacreator.videoalliance.order.bean.TdPreOrderidRecBean; import com.chinacreator.videoalliance.order.dao.SPDao; import com.chinacreator.videoalliance.order.dao.TcPreDao; import org.apache.commons.lang.math.NumberUtils; import org.apache.commons.lang.time.DateUtils; import org.apache.log4j.Logger; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import org.springframework.util.StringUtils; @Component public class TcPreOrderService { private static Logger log = Logger.getLogger("orderError"); @Autowired private SPDao spDao; @Autowired private TcPreDao tcPreDao; /** * 验证及解密手机号码 * @param orderInfo * @throws Exception */ private void checkUserid(OrderInfo orderInfo) throws Exception { String userid = orderInfo.getUserid(); if ((StringUtils.isEmpty(userid)) || ("null".equals(userid))) throw new BusinessException("9051", "手机号码无效", new String[0]); if (!UsermobUtil.isValid(userid)) { userid = ConfigUtil.decrypt(userid, orderInfo.getCpid()); userid = ConfigUtil.getUserid(userid, orderInfo.getCpid()); } if (!UsermobUtil.isValid(userid)) { throw new BusinessException("9052", "手机号码无效", new String[0]); } orderInfo.setUserid(userid); } /** * CPID验证 * @param orderInfo * @throws Exception */ public void checkCpInfo(OrderInfo orderInfo) throws Exception { CPInfo cpInfo = ConfigUtil.getCPInfo(orderInfo.getCpid(), null); if ((cpInfo.getStatus() != 0) && (cpInfo.getStatus() != 4)) { throw new BusinessException("9053", "该业务暂未开放,敬请期待。", new String[0]); } } /** * 验证SPID * @param orderInfo * @throws Exception */ private void checkSpInfo(OrderInfo orderInfo) throws Exception { SPInfo spInfo = getSPInfo(orderInfo); if (spInfo.getCanorder() == 1 && StringUtils.isEmpty(orderInfo.getOrderchannel())) { throw new BusinessException("9054", "该产品不支持订购操作", new String[0]); } orderInfo.setSpid(spInfo.getSpid()); } /** * 验证签名是否有效 * @param orderInfo * @param deuserid 加密的手机号码 * @throws Exception */ public void checkSign(OrderInfo orderInfo, String deuserid) throws Exception { String sign = orderInfo.getSignature(); if (StringUtils.isEmpty(sign)) { throw new BusinessException("9054", "signature不能为空"); } Map cpSpBean = tcPreDao.getCpSp(orderInfo.getCpid(),orderInfo.getSpid()); String pwd = cpSpBean.get("NETPWD").toString(); String localSign = MD5.MD5Encode(orderInfo.getOrderid() + orderInfo.getType() + orderInfo.getCpid() + orderInfo.getSpid() + deuserid + pwd + orderInfo.getTimestamp()); if (!localSign.equals(orderInfo.getSignature())) { throw new BusinessException("9054", "signature校验失败"); } } /** * 订购前验证 * @param orderInfo * @param deuserid 原始加密手机号码,用于签名验证 * @throws Exception */ public void checkOrder(OrderInfo orderInfo, String deuserid) throws Exception { checkSign(orderInfo,deuserid); checkUserid(orderInfo); checkCpInfo(orderInfo); checkSpInfo(orderInfo); String userid = orderInfo.getUserid(); //获取地市信息 AreaInfo areaInfo = getAreaInfo(userid); orderInfo.setProvince(areaInfo.getProvince()); orderInfo.setArea(areaInfo.getArea()); CPInfo cpInfo = ConfigUtil.getCPInfo(orderInfo.getCpid(), areaInfo.getProvince()); if (cpInfo == null) { throw new BusinessException("9011", "CP标识无效", new String[0]); } if(!tcPreDao.valiBusi(orderInfo)){ throw new BusinessException("9031", "不能办理非指定业务"); } } /** * 获取手机号码的地市信息 * @param userid * @return * @throws Exception */ private AreaInfo getAreaInfo(String userid) throws Exception { AreaInfo areaInfo = AreaUtil.getAreaInfoByUserid(userid); if (areaInfo == null) { areaInfo = new AreaInfo(); } return areaInfo; } /** * 获取sp信息 * @param orderInfo * @return * @throws Exception */ private SPInfo getSPInfo(OrderInfo orderInfo) throws Exception { SPInfo spInfo = null; if (StringUtils.isEmpty(orderInfo.getSpid())) spInfo = this.spDao.findDefaultByCP(orderInfo.getCpid()); else { spInfo = this.spDao.findById(orderInfo.getSpid()); } if (spInfo == null) { throw new BusinessException("9015", "产品标识符无效", new String[0]); } orderInfo.setSpid(spInfo.getSpid()); orderInfo.setMutex(spInfo.getMutex()); orderInfo.setRelationSp(spInfo.getRelationSp()); orderInfo.setPaytype(spInfo.getPaytype()); orderInfo.setErrorhandle(spInfo.getErrorhandle()); return spInfo; } /** * 获取订单关联bean * @param orderInfo * @return * @throws Exception */ private TdPreOrderidRecBean getTporBean(OrderInfo orderInfo) throws Exception{ TdPreOrderidRecBean tporBean = new TdPreOrderidRecBean(); tporBean.setId(tcPreDao.generateID()); tporBean.setArea(orderInfo.getArea()); tporBean.setOrderid(orderInfo.getOrderid()); tporBean.setProvince(orderInfo.getProvince()); tporBean.setUserid(orderInfo.getUserid()); tporBean.setCpid(orderInfo.getCpid()); tporBean.setSpid(orderInfo.getSpid()); tporBean.setLogid(orderInfo.getReorderid()); //上海权益日志报文记录表ID if(tporBean.getLogid() == null){ tporBean.setLogid(""); } if(orderInfo.getOrderchannel() != null){ tporBean.setChannel(orderInfo.getOrderchannel()); }else{ tporBean.setChannel(orderInfo.getCancelchannel()); } return tporBean; } /** * 办理业务 * @param orderInfo * @return */ public String orderBusi(OrderInfo orderInfo)throws Exception{ String errorcode = "0"; String errorinfo = "成功"; String result = "-1"; String orderPreid = tcPreDao.getPreOrderId(); orderInfo.setId(orderPreid); String currTime = tcPreDao.getCurrTime(); //业务类型:0订购,1退订,2预订购,3预退订,4预订购转换 TdPreOrderidRecBean tporBean = getTporBean(orderInfo); tporBean.setBusitype(orderInfo.getType()+""); try { //畅视2元处理流程: if(!"115".equals(orderInfo.getSpid())){ if(0 != orderInfo.getType() && 1 != orderInfo.getType()){ throw new BusinessException("80015", "参数不合法,TYPE", new String[0]); } } //有带订购ID的,要判断是否重复订单 if(orderInfo.getOrderid() != null && !"".equals(orderInfo.getId().trim()) && !"null".equals(orderInfo.getOrderid().trim())){ if(this.hasDupliOrderid(orderInfo)){//判断是否重复订单ID if(orderInfo.getType() == 0 || orderInfo.getType() == 2){ orderInfo.setStatus(0); }else{ tporBean.setBusitype("1"); orderInfo.setStatus(1); } throw new BusinessException("9110", "重复订单,不处理", new String[0]); } } //订购时在判断业务是否互斥 if(0 == orderInfo.getType() && this.hasMutual(orderInfo)){ throw new BusinessException("9117","已办理互斥业务", new String[0]); } if(0 == orderInfo.getType() || 2 == orderInfo.getType()){ //订购,预订购 orderInfo.setOrdertime(currTime); orderInfo.setEffecttime(currTime); orderInfo.setCancelchannel(""); orderInfo.setStatus(0); if("1184".equals(orderInfo.getSpid()) && "changshi".equals(orderInfo.getCpid())){ orderInfo.setEndtime(tcPreDao.endtimeMonthLastDay("24")); } String hasEffect = this.hasEffect(orderInfo, tporBean); if("1".equals(hasEffect)){//订购表已是订购状态 throw new BusinessException("9115","已有订购关系,不能重复订购", new String[0]); }else if("2".equals(hasEffect) && "115".equals(orderInfo.getSpid())){//预订购表已是订购状态,只有广东腾讯2元才判断预订购 throw new BusinessException("9116","已有预订购关系,不能重复订购", new String[0]); } tporBean.setOrdertime(currTime); orderInfo.setStatus(0); if(0 == orderInfo.getType()){//订购 tporBean.setBusitype("0"); //订购 tcPreDao.order(orderInfo); }else{//预订购 tporBean.setBusitype("2");//预订购 tporBean.setOrderpreid(orderPreid); tcPreDao.orderPre(orderInfo); } }else if(1 == orderInfo.getType()){//退订 String endtime = tcPreDao.getEndDayOfCurrentMonth(); orderInfo.setCanceltime(currTime); orderInfo.setOrderchannel(""); orderInfo.setStatus(1); orderInfo.setEndtime(endtime); tporBean.setBusitype("1"); //退订 String hasEffect = this.hasEffect(orderInfo, tporBean); if("0".equals(hasEffect)){//订购表和预订购表无订购状态的数据 throw new BusinessException("9118","未订购,不能退订", new String[0]); }else if("3".equals(hasEffect)){//订购表和预订购表无订购状态的数据 throw new BusinessException("9118","预订购正在处理,不能退订", new String[0]); } tporBean.setCanceltime(currTime); if("1".equals(hasEffect)){//订购表已是订购状态 tcPreDao.cancelOrder(orderInfo); }else if("2".equals(hasEffect) && "115".equals(orderInfo.getSpid())){//预订购表已是订购状态,只有广东腾讯才有预退订 tporBean.setBusitype("3"); //预退订 tcPreDao.cancelOrderPre(orderInfo); }else{//有预订购,但不是广东腾讯2元(SPID不是115) throw new BusinessException("9118","未订购,不能退订", new String[0]); } } result = "0"; } catch (Exception e) { e.printStackTrace(); log.error("error=>orderid: "+orderInfo.getOrderid()+". userid: "+orderInfo.getUserid()+",cpid: "+orderInfo.getCpid()+". spid: "+orderInfo.getSpid()+",订购出现异常,"+e); errorcode = "8000"; errorinfo ="系统忙"; if ((e instanceof BusinessException)) { errorcode = ((BusinessException) e).getCode(); errorinfo = ((BusinessException) e).getMessage(); if(errorinfo.length()>200){ errorinfo = errorinfo.substring(0, 200); } } if(!errorcode.equals("9999")){ throw e; } } finally { tporBean.setResultcode(errorcode); tporBean.setResultinfo(errorinfo); tcPreDao.addOrderRec(tporBean); tcPreDao.updShInPaInfo(tporBean); //更新上海权益2元报文表(如果可以更新的话) saveLog(orderInfo, errorcode, errorinfo); } return result; } /** * 查询本地订购关系表/预订购表当前是否存在订购状态 * @param orderInfo * @return 0无订购,1订购关系表有订购,2预订购表有订购 * @throws Exception */ private String hasEffect(OrderInfo orderInfo, TdPreOrderidRecBean tporBean) throws Exception{ String hasEffect = "0"; //[{ORDERIDA=2019052, AREA=长沙, SPID=1167, PROVINCE=湖南, ID=201905241107578658666, ORDERCHANNEL=t, STATUS=1, ORDERTIME=20190524104129, USERID=18673197465, CPID=youtu}] //查询用户本地订购关系表未失效的订购数据 List list = tcPreDao.findOrderRelaAll(orderInfo.getUserid()); if(list != null && list.size()>0){//本地有订购关系 for(HashMap hm : list){ if(orderInfo.getCpid().equals(hm.get("CPID")) && orderInfo.getSpid().equals(hm.get("SPID")) && "0".equals(hm.get("STATUS"))){ hasEffect = "1"; break; } if(orderInfo.getCpid().equals(hm.get("CPID")) && orderInfo.getSpid().equals(hm.get("SPID")) && "1".equals(hm.get("STATUS")) && hm.get("CANCELTIME") == null){ hasEffect = "1"; break; } } } if("0".equals(hasEffect)){ //查询预订购表是否有订购状态的数据 list = tcPreDao.findPreOrderRelaAll(orderInfo.getUserid()); if(list != null && list.size()>0){//本地有订购关系 for(HashMap hm : list){ if(orderInfo.getCpid().equals(hm.get("CPID")) && orderInfo.getSpid().equals(hm.get("SPID")) && "0".equals(hm.get("STATUS")) && ("1".equals(hm.get("SYNSTATUS")) ||"2".equals(hm.get("SYNSTATUS")))){ //未同步或正在同步 hasEffect = "2"; if(orderInfo.getType() == 1){ //如果是退订,设置预订购表ID tporBean.setOrderpreid(hm.get("ID")+""); if("2".equals(hm.get("SYNSTATUS"))){ hasEffect = "3"; //正在同步,不能退订 } } break; } } } } return hasEffect; } /** * 判断业务是否互斥 * @param orderInfo * @throws Exception */ private boolean hasMutual(OrderInfo orderInfo) throws Exception{ boolean result = false; try { //[{ORDERIDA=2019052, AREA=长沙, SPID=1167, PROVINCE=湖南, ID=201905241107578658666, ORDERCHANNEL=t, STATUS=1, ORDERTIME=20190524104129, USERID=18673197465, CPID=youtu}] //查询用户本地订购关系表未失效的订购数据 List list = tcPreDao.findOrderRelaAll(orderInfo.getUserid()); if (list != null && list.size() > 0) { if (!StringUtils.isEmpty(orderInfo.getMutex())) { String[] mutexSpids = orderInfo.getMutex().trim().split(","); for (String mutexSpid : mutexSpids) { for (HashMap hm : list) { if (!hm.get("SPID").equals(orderInfo.getSpid()) && hm.get("SPID").equals(mutexSpid) && !"2".equals(hm.get("STATUS"))) { result = true; break; } } } } } } catch (Exception e) { log.error("查询互斥订购关系出现异常,"+e.getMessage()); e.printStackTrace(); throw new BusinessException("9021", "查询互斥订购关系出现异常,"+e.getMessage(), new String[0]); } return result; } /** * 判断是否有相同订单 * @param orderInfo * @return true是,false否 */ private boolean hasDupliOrderid(OrderInfo orderInfo) throws Exception{ boolean result = false; try { //[{AREA=长沙, ORDERID=20190524103510000001, ORDERLOGID=1111111111111111, PROVINCE=湖南, ID=201905241043108658661, RESULTINFO=成功, STATUS=0, RESULTCODE=0, ORDERTIME=20190524104125, USERID=18673197465}] List list = tcPreDao.findOrderId(orderInfo.getOrderid()); System.out.println(list); if(list != null && list.size() > 0){ for(HashMap bean : list){ if(orderInfo.getOrderid().equals(bean.get("ORDERID"))){ result = true; break; } } } } catch (Exception e) { e.printStackTrace(); log.error("判断是否有相同订单出现异常,"+e.getMessage()); e.printStackTrace(); throw new BusinessException("9022", "查判断是否有相同订单出现异常,"+e.getMessage(), new String[0]); } return result; } public String getEndTime(String endTimeStr) throws ParseException { Calendar calendar = Calendar.getInstance(); Date date = DateUtils.parseDate(endTimeStr.substring(0, 8), new String[] { "yyyyMMdd" }); calendar.setTime(date); String day = calendar.getActualMaximum(Calendar.DAY_OF_MONTH) + ""; String year = calendar.get(Calendar.YEAR) + ""; String month = calendar.get(Calendar.MONTH) + 1 < 10 ? "0" + (calendar.get(Calendar.MONTH) + 1) : calendar.get(Calendar.MONTH) + 1 + ""; return year + month + day + "235959"; } /** * 写订购日志 * @param orderInfo * @param errorcode * @param errorinfo */ public void saveLog(OrderInfo orderInfo, String errorcode, String errorinfo) { OrderLog orderLog = new OrderLog(); orderLog.setApptype(orderInfo.getApptype()); orderLog.setArea(orderInfo.getArea()); orderLog.setChannel(orderInfo.getOrderchannel()); orderLog.setOrderstatus(orderInfo.getOrderstatus()); orderLog.setStatus(orderInfo.getStatus()); orderLog.setCpid(orderInfo.getCpid()); orderLog.setIsexperience(orderInfo.getIsexperience()); orderLog.setOrdertype(orderInfo.getOrdertype() + ""); orderLog.setProvince(orderInfo.getProvince()); orderLog.setArea(orderInfo.getArea()); orderLog.setSpid(orderInfo.getSpid()); orderLog.setUserid(orderInfo.getUserid()); orderLog.setErrorcode(errorcode); orderLog.setErrorinfo(errorinfo); if(!orderInfo.getTimes().isEmpty()){ orderLog.setTimes((System.currentTimeMillis()-NumberUtils.toLong(orderInfo.getTimes()))+""); } this.tcPreDao.addOrderLog(orderLog); } }