package com.hx.phip.controller.appointment;
|
|
import com.alibaba.fastjson.JSONArray;
|
import com.alibaba.fastjson.JSONObject;
|
import com.hx.common.BaseController;
|
import com.hx.exception.TipsException;
|
import com.hx.mybatisTool.SqlSentence;
|
import com.hx.phiappt.common.OperatorConstants;
|
import com.hx.phiappt.common.RoleType;
|
import com.hx.phiappt.constants.tool.appointment.TransferUtil;
|
import com.hx.phiappt.constants.tool.appointment.autoMate.AppAutoMateHandleUtil;
|
import com.hx.phiappt.constants.tool.appointment.autoMate.AppAutoMateV5Util;
|
import com.hx.phiappt.dao.mapper.*;
|
import com.hx.phiappt.model.*;
|
import com.hx.phiappt.vo.ApponintmentVo;
|
import com.hx.phiappt.vo.ProjectVo;
|
import com.hx.phiappt.vo.ShopWorkTimeVo;
|
import com.hx.phiappt.vo.appointment.autoMate.AppAutoMateVo;
|
import com.hx.phip.service.EmployeeRoleService;
|
import com.hx.phip.service.SystemParameterService;
|
import com.hx.resultTool.Result;
|
import com.hx.util.DateUtil;
|
import com.hx.util.StringUtils;
|
import com.hz.his.dto.appointment.AppointmentAutoMateDto;
|
import org.slf4j.Logger;
|
import org.slf4j.LoggerFactory;
|
import org.springframework.web.bind.annotation.RequestBody;
|
import org.springframework.web.bind.annotation.RequestMapping;
|
import org.springframework.web.bind.annotation.RestController;
|
|
import javax.annotation.Resource;
|
import java.util.*;
|
import java.util.stream.Collectors;
|
|
/**
|
* author:fhx
|
* Date:2021/3/24 18:43
|
*/
|
@RestController
|
@RequestMapping("/appointment/autoMate")
|
public class AppAutoMateController extends BaseController {
|
private final Logger logger = LoggerFactory.getLogger(AppAutoMateController.class);
|
|
@Resource
|
private SystemParameterService systemParameterService;
|
@Resource
|
private EmployeeRoleService employeeRoleService;
|
|
/** 自动匹配 - 混合项目 */
|
@RequestMapping("/addApply/blend")
|
public Result addApplyBland(@RequestBody AppointmentAutoMateDto dto)
|
{
|
logger.info("预约自动匹配请求参数:{}", JSONObject.toJSONString(dto));
|
if(dto.getOpType() == null){
|
throw new TipsException("操作人类型为空!");
|
}
|
|
if(StringUtils.isEmpty(dto.getShopId())) {
|
throw new TipsException("请选择门店");
|
}
|
|
Shop shop = commonService.selectOneByKey(ShopMapper.class, dto.getShopId());
|
if(shop == null) {
|
throw new TipsException("找不到门店");
|
}
|
|
if(StringUtils.isEmpty(dto.getUserId())) {
|
throw new TipsException("请选择用户");
|
}
|
|
Map<String, Object> values = new HashMap<>();
|
SqlSentence sqlSentence = new SqlSentence();
|
sqlSentence.setM(values);
|
StringBuilder sql = new StringBuilder();
|
|
values.put("userId", dto.getUserId());
|
sqlSentence.setSqlSentence(" select u.*, cu.depId as shopId from user u left join corp_user cu on cu.id = u.hisCorpUserId WHERE u.id = #{m.userId} ");
|
|
User user = commonService.selectOne(UserMapper.class, sqlSentence);
|
if(user == null) {
|
throw new TipsException("找不到用户");
|
}
|
|
Employee doctor = null;
|
String doctorId = dto.getDoctorId();
|
if(!StringUtils.isEmpty(doctorId)) {
|
values.put("id", doctorId);
|
values.put("roleUniqueStr", RoleType.UNIQUE_STR_DOCTOR);
|
sql.setLength(0);
|
sql.append(" select e.*, r.shopId from employee e ")
|
.append(" left join employee_role r on r.employeeId = e.id ")
|
.append(" WHERE e.id = #{m.id} and r.roleUniqueStr = #{m.roleUniqueStr} and e.isDel = 0 ")
|
.append(" group by r.roleUniqueStr ");
|
sqlSentence.setSqlSentence(sql.toString());
|
doctor = commonService.selectOne(EmployeeMapper.class, sqlSentence);
|
if(doctor == null)
|
{
|
throw new TipsException("找不到医生");
|
}
|
}else{
|
doctorId = null;
|
}
|
|
if(StringUtils.isEmpty(dto.getArriveDate(), dto.getStartTime())) {
|
throw new TipsException("请选择到店日期和时间");
|
}
|
|
if(dto.getVisitType() == null) {
|
throw new TipsException("请选择就诊类型");
|
}
|
|
if(dto.getAppType() == null) {
|
throw new TipsException("请选择预约类型");
|
}
|
|
Integer waitDuration = dto.getWaitDuration();
|
if(waitDuration == null || waitDuration < 0){
|
waitDuration = 0;
|
}
|
|
Integer palsyDuration = dto.getPalsyDuration();
|
if(palsyDuration == null || palsyDuration < 0){
|
palsyDuration = 0;
|
}
|
|
|
if(dto.getSpecialUser() == null){
|
dto.setSpecialUser(Appointment.NO);
|
}
|
|
if(dto.getIsMicApprove() == null){
|
dto.setIsMicApprove(BaseEntity.NO);
|
}
|
|
if(dto.getIsSwitch() == null){
|
dto.setIsSwitch(BaseEntity.NO);
|
}
|
|
if(dto.getRealMzTime() == null){
|
dto.setRealMzTime(0);
|
}
|
|
//推荐匹配数量为空,则默认2
|
if(dto.getMateNum() == null){
|
dto.setMateNum(2);
|
}
|
|
//术前时间
|
int sqTime = 0;
|
|
LinkedHashMap<String, ProjectVo> pMap = new LinkedHashMap<>();
|
Map<String, Integer> pNumMap = new HashMap<>();
|
Map<String, Integer> pZlMap = new HashMap<>();
|
List<Project> projectList = new ArrayList<>();
|
String [] projectIdsArr = null;
|
String [] projectNamesArr = null;
|
int isDevice = 0;
|
|
//是否再生项目
|
String zsProjectId = "";
|
boolean isZsP = false;
|
//是否有非生美项目
|
boolean isNotSm = false;
|
|
//复查可以不选项目
|
if(StringUtils.isEmpty(dto.getProjectJson()) && dto.getAppType() != Appointment.APP_TYPE_REVIEW)
|
{
|
throw new TipsException("请选择项目");
|
|
}else {
|
//再生项目逻辑,目前写死一个项目
|
SystemParameter sp = systemParameterService.selectOneByName(SystemParameter.KEY_CRM_APPOINTMENT_PROJECT_ID);
|
if(sp != null && StringUtils.noNull(sp.getParamValue())){
|
zsProjectId = sp.getParamValue();
|
}
|
|
JSONArray pArr = JSONArray.parseArray(dto.getProjectJson());
|
int len = pArr.size();
|
JSONObject temp ;
|
String id ;
|
int num ;
|
Project p ;
|
projectIdsArr = new String[len];
|
projectNamesArr = new String[len];
|
|
for(int i = 0;i < len;i ++)
|
{
|
temp = pArr.getJSONObject(i);
|
id = temp.getString("id");
|
num = temp.getIntValue("num");
|
if(StringUtils.isEmpty(id) || num <= 0)
|
{
|
throw new TipsException("请选择正确项目和数量");
|
}
|
p = commonService.selectOneByKey(ProjectMapper.class, id);
|
if(p == null || p.getIsDel().equals(BaseEntity.YES) || p.getIsUp().equals(BaseEntity.NO))
|
{
|
throw new TipsException("找不到项目或者项目下架");
|
}
|
projectList.add(p);
|
|
pMap.put(id, new ProjectVo(p, num, dto.getShopId()));
|
pNumMap.put(id, num);
|
//判断治疗时间等于0,则默认5分钟
|
pZlMap.put(id, p.getUseDuration() == null ? 0 : p.getUseDuration());
|
//获取最大的术前准备时间
|
if(p.getReadyDuration() > sqTime){
|
sqTime = p.getReadyDuration();
|
}
|
projectIdsArr[i] = id;
|
projectNamesArr[i] = p.getName();
|
|
if(p.getIsDevice().equals(BaseEntity.YES)){
|
isDevice++;
|
}
|
|
if(!isNotSm && p.getIsLifeBeauty().equals(BaseEntity.NO)){
|
isNotSm = true;
|
}
|
|
if(zsProjectId.equals(id)){
|
if(num > 1){
|
throw new TipsException("再生项目数量不能大于1!");
|
}
|
isZsP = true;
|
}
|
}
|
}
|
|
//判断如果包含了再生项目,
|
if(isZsP && projectList.size() > 1){
|
throw new TipsException("预约项目里面有再生项目,不能和其他项目同时预约!");
|
}
|
|
if(isNotSm && StringUtils.isEmpty(doctorId)){
|
throw new TipsException("预约包含非生美项目,需选择预约医生!");
|
}
|
|
/////////////////////////////////////////////////
|
//逻辑1
|
//1.通过客户类型和客户等级查询出面诊、沟通、手续时间(默认5分钟)
|
int mzTime = 15;
|
int gtTime = 5;
|
// int sxTime = 5;
|
sql.setLength(0);
|
sql.append(" select * from cure_set_time ");
|
sql.append(" where isDel = #{m.isDel} and appType = #{m.appType} and userLevel = #{m.userLevel}");
|
values.put("isDel", BaseEntity.NO);
|
values.put("appType", dto.getAppType());
|
values.put("userLevel", user.getUserLevel());
|
sqlSentence.setSqlSentence(sql.toString());
|
|
List<CureSetTime> cList = commonService.selectList(CureSetTimeMapper.class, sqlSentence);
|
if(cList != null && cList.size() > 0){
|
for(CureSetTime cst : cList){
|
if(cst.getSetType() == CureSetTime.SET_TYPE_COM){
|
mzTime = cst.getDuration(); //面诊
|
}
|
// else if(cst.getSetType() == CureSetTime.SET_TYPE_COMMUNICATE){
|
// gtTime = cst.getDuration(); //沟通
|
// }
|
// else if(cst.getSetType() == CureSetTime.SET_TYPE_PROCEDURES){
|
// sxTime = cst.getDuration(); //手续
|
// }
|
}
|
}
|
|
if(mzTime > dto.getRealMzTime()){
|
waitDuration = 0;
|
}
|
|
//判断沟通或手续是否为空,不为空就使用传值的
|
gtTime = dto.getComDuration() != null ? dto.getComDuration() : gtTime;
|
//术前时间(分钟) = 秒 /60
|
sqTime = sqTime / 60;
|
|
//2.选择项目的治疗时间
|
//通过项目id和医生id查询判断是否有对应的医生项目治疗时间
|
int zlTime = 0;
|
int thisTime ;
|
|
//医生id不为空
|
if(!StringUtils.isEmpty(doctorId) && projectIdsArr != null){
|
sql.setLength(0);
|
sql.append("select * from doctor_project_cure_time where isDel = #{m.isDel} and doctorId = #{m.doctorId} and projectId = #{m.projectId}");
|
sqlSentence.setSqlSentence(sql.toString());
|
values.put("doctorId", doctorId);
|
DoctorProjectCureTime ct;
|
|
for(String projectId : projectIdsArr){
|
values.put("projectId", projectId);
|
ct = commonService.selectOne(DoctorProjectCureTimeMapper.class, sqlSentence);
|
if(ct != null){
|
//设定的时间 * 数量
|
thisTime = ct.getDuration() * pNumMap.get(projectId);
|
}else{
|
//项目治疗时间(秒) / 60 * 数量
|
thisTime = (pZlMap.get(projectId) / 60 * pNumMap.get(projectId));
|
}
|
zlTime += thisTime;
|
pMap.get(projectId).setZlTime(thisTime);
|
}
|
}else{
|
for(String projectId : projectIdsArr){
|
//项目治疗时间(秒) / 60 * 数量
|
thisTime = (pZlMap.get(projectId) / 60 * pNumMap.get(projectId));
|
zlTime += thisTime;
|
pMap.get(projectId).setZlTime(thisTime);
|
}
|
}
|
|
//用户操作时,对应个别时间为0
|
if(dto.getOpType() == OperatorConstants.OP_TYPE_USER){
|
// mzTime = 0;
|
//默认标准轮匹配的实际面诊时长=系统面诊时长
|
dto.setRealMzTime(mzTime);
|
gtTime = 0;
|
// sqTime = 0;
|
waitDuration = 0;
|
}
|
//再生项目时,其他时间都为0
|
else if(isZsP){
|
mzTime = 0;
|
gtTime = 0;
|
palsyDuration = 0;
|
sqTime = 0;
|
waitDuration = 0;
|
}
|
|
|
|
// //总时长 = 面诊 + 沟通 + 敷麻 + 术前 + 准备等待 + 治疗
|
// int duration = mzTime + gtTime + palsyDuration + sqTime + waitDuration + zlTime;
|
|
//////////////////////////////////////////////////////////
|
//逻辑2
|
Date st = DateUtil.parseString_1(dto.getArriveDate() + " " + dto.getStartTime() + ":00");
|
|
//减去沟通时间
|
String dayStr = DateUtil.formatDate(st);
|
String projectIds = org.apache.commons.lang3.StringUtils.join(projectIdsArr, ",");
|
String projectNames = org.apache.commons.lang3.StringUtils.join(projectNamesArr, "|");
|
|
List<ApponintmentVo> aVoList = new ArrayList<>();
|
JSONObject json = new JSONObject();
|
|
Employee cu = null;
|
//判断操作人是员工时
|
if(dto.getOpType() == OperatorConstants.OP_TYPE_EMPLOYEE && StringUtils.noNull(dto.getOpRoleId())){
|
cu = employeeRoleService.selectEmployeeById(dto.getOpRoleId());
|
}
|
|
String err;
|
|
//非MIC、非勾选转疗、且不是用户所属顾问门店的预约,才检查转疗限制逻辑
|
if(dto.getIsMicApprove() == BaseEntity.NO
|
&& dto.getIsSwitch() == BaseEntity.NO
|
&& !StringUtils.isEmpty(user.getShopId())
|
&& !dto.getShopId().equals(user.getShopId())){
|
|
err = TransferUtil.checkTransferNotAccepted(commonService
|
, user, shop, st, doctor, cu, projectList);
|
if(err != null){
|
throw new TipsException(err);
|
}
|
|
//修改为转疗
|
dto.setIsSwitch(BaseEntity.YES);
|
}
|
|
//-----迁移到新增/修改预约进行判断
|
Integer occupySwitch = dto.getIsSwitch();
|
//检查是否不占用转疗名额
|
if(BaseEntity.YES.equals(occupySwitch)){
|
occupySwitch = TransferUtil.checkTransferNotOccupy(commonService
|
, user.getUserLevel(), dto.getShopId() , st, doctorId
|
, cu , projectList);
|
}
|
|
//非MIC检查下是否符合要求
|
if(dto.getIsMicApprove() == BaseEntity.NO){
|
//先检查下对应条件是否符合要求:1项目类型、2门店预约人数、3门店最大转疗人数、4检查设备、5医生预约人数
|
err = AppAutoMateHandleUtil.checkLimit(commonService, shop, doctorId, st, dayStr, projectIdsArr, dto.getIsSwitch(), occupySwitch, dto.getAptId());
|
|
if(!StringUtils.isEmpty(err)) {
|
json.put("list", aVoList);
|
json.put("sqTime", sqTime);
|
json.put("zlTime", zlTime);
|
json.put("mzTime", mzTime);
|
json.put("isSwitch", dto.getIsSwitch());
|
json.put("occupySwitch", occupySwitch);
|
json.put("errMsg", err);
|
return Result.success(json);
|
}
|
}
|
|
//处理项目可预约时间
|
List<Date> canAppList = AppAutoMateHandleUtil.getProjectCanAppTime(commonService, projectList, st);
|
// List<Date> canAppList = null;
|
|
//医生时间
|
List<DoctorTime> doctorTimeList = AppAutoMateHandleUtil.selectDoctorTime(commonService, dto.getShopId(), doctorId, dayStr, dto.getAptId());
|
//过滤出医生的预约占用的特殊用户时间
|
List<DoctorTime> specialTimeList = new ArrayList<>();
|
if(dto.getSpecialUser() == Appointment.YES){
|
specialTimeList = doctorTimeList.stream()
|
.filter(s->s.getSpecialUser() == Appointment.YES
|
&& s.getApptType() != DoctorTime.APPT_TYPE_NONE)
|
.collect(Collectors.toList());
|
}
|
|
//判断如果是mic通用
|
if(dto.getIsMicApprove() == BaseEntity.YES){
|
return Result.success(AppAutoMateHandleUtil.MICList(commonService
|
, aVoList, st, dto.getRealMzTime(), gtTime, palsyDuration
|
, sqTime, zlTime, waitDuration, projectIds, projectNames
|
,isDevice, dto.getShopId(), dayStr, dto.getAptId(), pMap, specialTimeList));
|
}
|
|
//没有医生为全部生美项目
|
if(StringUtils.isEmpty(doctorId)){
|
return Result.success(AppAutoMateHandleUtil.SMList(commonService, aVoList, st, dto.getRealMzTime(), gtTime, palsyDuration
|
, sqTime, zlTime, waitDuration, projectIds, projectNames
|
,isDevice, dto.getShopId(), dayStr, dto.getAptId(), pMap, dto.getIsSwitch(),occupySwitch, canAppList
|
, specialTimeList));
|
}
|
|
|
//查询当天是否有活动日
|
values.put("shopId", dto.getShopId());
|
values.put("dayStr", dayStr);
|
sqlSentence.setSqlSentence("select * from activity_day where isDel = #{m.isDel} and shopId = #{m.shopId} and dayStr = #{m.dayStr}");
|
ActivityDay activityDay = commonService.selectOne(ActivityDayMapper.class, sqlSentence);
|
|
//门店营业时间
|
ShopWorkTimeVo shopWorkTimeVo = new ShopWorkTimeVo(shop, dayStr);
|
// //初始日期(存储判断)
|
// String initDayStr = dayStr;
|
// //初始开始时间(如09:00)
|
// String initStartTime = dto.getStartTime();
|
|
TreeMap<String, Integer> timeMap = null;
|
|
// 医生id为空返回门店时间
|
// if(StringUtils.isEmpty(doctorId)){
|
// timeMap = AppAutoMateV5Util.shopWorkTimeSet(shopWorkTimeVo);
|
// }
|
|
|
//门店特殊时间
|
List<ShopTime> shopTimeList = AppAutoMateHandleUtil.selectShopTime(commonService, dto.getShopId(), dayStr, dto.getAppType(), user.getUserLevel(), user.getStarLevel());
|
|
//时间处理次数:1第一轮医生正常时间、2第二轮医生开头5分钟可预约、3第三轮医生结束5分钟可预约
|
int handleNum = 1;
|
//向上还是向下:0标准1向下2向上(向下或向上中间可加等待时间)
|
int upOrDown = 0;
|
//按天分隔类型:0不分隔、1上午、2下午
|
int daySpaceType = dto.isDaySpace() ? 1 : 0;
|
|
//第一轮匹配
|
AppAutoMateVo mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
err = mateData.getErrMsg();
|
if(timeMap == null || timeMap.size() <= 0){
|
throw new TipsException("当前预约医生预约日期无排班时间,无法选择系统推荐时间,请重新选择预约医生");
|
}
|
|
////////////////////////////////////////////////////////////////////////
|
//判断用户选择的时间是否符合
|
|
//是否走扣减处理(默认true),即扣减医生上下5分钟逻辑
|
boolean deductHandle = true;
|
//如果是是再生项目、或预约特殊类型为特殊客户,则不走扣减处理
|
if(isZsP || dto.getSpecialUser() == Appointment.YES){
|
deductHandle = false;
|
}
|
|
ApponintmentVo aVo = null;
|
// ApponintmentVo aVo2 = null;
|
String deviceErr = null;
|
|
//从医生可用时间里面,拼接出当天最小可以时间
|
Date minStartTime = DateUtil.parseString_1(dto.getArriveDate() + " " + timeMap.keySet().iterator().next() + ":00");
|
Date upStratTime = st;
|
|
Calendar cs = Calendar.getInstance();
|
|
//判断是否有项目可预约时间限制
|
int isCanApp = canAppList == null || canAppList.size() < 2 ? 0 : 1;
|
|
//查询医生某个时间段有多少治疗数量sql
|
sql.setLength(0);
|
sql.append(" select COUNT(1) from doctor_time where ")
|
.append(" where isDel = 0 and shopId = '").append(dto.getShopId()).append("' ")
|
.append(" and apptType = 2 and timeType in (2, 3) ")
|
.append(" and ( #{m.zlStartTime} BETWEEN startTime and endTime ")
|
.append(" or #{m.zlEndTime} BETWEEN startTime and endTime) ");
|
String doctorTimeAppNumSql = sql.toString();
|
|
//超过2个停止循环
|
while(aVoList.size() < dto.getMateNum() && StringUtils.isEmpty(err)){
|
//每次匹配都判断一下是否要做上下午时间处理
|
mateData = AppAutoMateHandleUtil.handleTimeToDaySpace(timeMap, dto.getArriveDate(), daySpaceType, palsyDuration, st);
|
timeMap = mateData.getTimeMap();
|
st = mateData.getStartTime(); //如果是上下午区分的,时间开始时间要重新获取才能符合上下午时间的分隔
|
// logger.info("开始时间:{}", DateUtil.formatDate_2(st));
|
// logger.info("daySpaceType:{}", daySpaceType);
|
// logger.info("upOrDown:{}", upOrDown);
|
// logger.info("handleNum:{}", handleNum);
|
// logger.info("时间:{}", JSONObject.toJSONString(timeMap));
|
|
//判断如果时特殊客户预约,且非第一次处理和没有符合的时间,则直接提示不继续处理
|
if(upOrDown == 0){
|
//标准轮(使用实际面诊时长)
|
aVo = AppAutoMateV5Util.getAppTimeBlend(timeMap, upStratTime, gtTime, dto.getRealMzTime(), palsyDuration, sqTime, zlTime, waitDuration, pMap, isCanApp);
|
} else if(upOrDown == 1){
|
//向下匹配预约时间(使用配置的面诊时长)
|
aVo = AppAutoMateV5Util.getAppTimeByDownV2(timeMap, st, gtTime, mzTime, palsyDuration, sqTime, zlTime, 0, 50, pMap, isCanApp);
|
}else if(upOrDown == 2){
|
//向上匹配预约时间(使用配置的面诊时长)
|
aVo = AppAutoMateV5Util.getAppTimeByUpV2(timeMap, upStratTime, gtTime, mzTime, palsyDuration, sqTime, zlTime, 0, 50, pMap, isCanApp);
|
}
|
|
//为空,表示当天已经没有时间段可以预约
|
if(aVo == null && upOrDown != 0)
|
{
|
if (aVoList.size() < dto.getMateNum() && handleNum == 1 && deductHandle) {
|
//第二轮(治疗开始时间+10分钟)
|
handleNum = 2;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
} else if (aVoList.size() < dto.getMateNum() && handleNum == 2 && deductHandle) {
|
//第三轮(治疗结束时间-10分钟)
|
handleNum = 3;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
}
|
//如果是处理到:向上处理+没满足2个+(第三轮后 或 非扣减处理),则跑向下处理(+等待时间)
|
else if(upOrDown == 2 && aVoList.size() < dto.getMateNum() && (handleNum == 3 || !deductHandle)) {
|
//修改向上匹配时间
|
upOrDown = 1;
|
handleNum = 1;
|
//还原正常时间先
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
|
// } else if(upOrDown == 2 && handleNum == 3){
|
}
|
//判断如果上午分隔时间执行完,则进行下午分隔处理
|
else if(daySpaceType == 1){
|
daySpaceType = 2;
|
//重置标准匹配时间
|
upOrDown = 0;
|
handleNum = 1;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
}else {
|
if(StringUtils.isEmpty(err)){
|
err = mateData.getErrMsg();
|
}
|
if(StringUtils.isEmpty(err) && dto.getSpecialUser() == Appointment.YES && StringUtils.noNull(doctorId)){
|
err = "(特殊用户预约)系统匹配不到医生可用时间!";
|
}else if(StringUtils.isEmpty(err)){
|
err = deviceErr != null ? deviceErr : "系统匹配不到医生可用时间,或项目有可预约时间限制";
|
}
|
break;
|
|
}
|
}
|
else if(aVo != null)
|
{
|
//判断开始时间是否小于门店开始时间
|
boolean isSmaller = aVo.getStartTime().compareTo(shopWorkTimeVo.getmStartTime()) == -1;
|
|
deviceErr = null;
|
//判断需不需要设备判断,不需要不检查设备逻辑
|
if(isDevice > 0){
|
//检查设备时间
|
deviceErr = AppAutoMateHandleUtil.checkDevice(commonService, dto.getShopId(), dayStr, aVo, dto.getAptId());
|
}
|
|
if(StringUtils.isEmpty(deviceErr) && !isSmaller)
|
{
|
//判断活动日不为空,并且匹配时间不超过活动日时间
|
if(activityDay != null
|
&& aVo.getStartTime().compareTo(activityDay.getStartTime()) > -1
|
&& aVo.getEndTime().compareTo(activityDay.getEndTime()) < 1)
|
{
|
aVo.setActivityDayId(activityDay.getId());
|
}
|
|
boolean isCustomerNum=true;
|
if(shop.getSameTimeCustomerNum()!=null &&shop.getSameTimeCustomerNum()>0){
|
values.put("zlStartTime", aVo.getZlStartTime());
|
values.put("zlEndTime", aVo.getEndTime());
|
sqlSentence.setSqlSentence(doctorTimeAppNumSql);
|
int count = commonService.selectCountSql(sqlSentence);
|
logger.info("=====================预约订单自动获取时间===========当前时间段的订单数:"+count);
|
logger.info(DateUtil.formatDate_2(aVo.getZlStartTime())+"=="+DateUtil.formatDate_2(aVo.getEndTime())+"=="+shop.getSameTimeCustomerNum()+"=="+count);
|
if(count>=shop.getSameTimeCustomerNum()){
|
isCustomerNum=false;
|
}
|
}
|
|
if(isCustomerNum){
|
//判断相同向下匹配
|
if(aVoList.size() > 0)
|
{
|
//遍历判断匹配时间是否重复,
|
boolean isRepeat = false;
|
for(ApponintmentVo apponintmentVo : aVoList){
|
if(
|
(apponintmentVo.getStartTime().compareTo(aVo.getStartTime()) == 0 && apponintmentVo.getEndTime().compareTo(aVo.getEndTime()) == 0)
|
// || (aVo2.getMzStartTime().compareTo(aVo.getMzStartTime()) == 0 && aVo2.getMzEndTime().compareTo(aVo.getMzEndTime()) == 0)
|
// || (aVo2.getZlStartTime().compareTo(aVo.getZlStartTime()) ==0 && aVo2.getEndTime().compareTo(aVo.getEndTime()) == 0)
|
){
|
isRepeat = true;
|
break;
|
}
|
}
|
|
//不重复则,存储对应可用
|
if(!isRepeat){
|
aVo.setHandleNum(handleNum);
|
aVo.setUpOrDown(upOrDown);
|
aVo.setProjectIds(projectIds);
|
aVo.setProjectNames(projectNames);
|
aVo.handleTips(handleNum, upOrDown);
|
aVo.setDaySpaceType(daySpaceType);
|
aVoList.add(aVo);
|
//进入则表示上午已有1个,重置标准匹配下午时间
|
if(daySpaceType == 1){
|
daySpaceType = 2;
|
upOrDown = 0;
|
handleNum = 1;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
continue;
|
}else if(daySpaceType == 2){
|
//如果是下午分隔的可以跳过
|
break;
|
}
|
}else{
|
//重复则向下匹配
|
upOrDown = 1;
|
}
|
}else{
|
aVo.setHandleNum(handleNum);
|
aVo.setUpOrDown(upOrDown);
|
aVo.setProjectIds(projectIds);
|
aVo.setProjectNames(projectNames);
|
aVo.handleTips(handleNum, upOrDown);
|
aVo.setDaySpaceType(daySpaceType);
|
aVoList.add(aVo);
|
//进入则表示上午已有1个,重置标准匹配下午时间
|
if(daySpaceType == 1){
|
daySpaceType = 2;
|
upOrDown = 0;
|
handleNum = 1;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
continue;
|
}else if(daySpaceType == 2){
|
//如果是下午分隔的可以跳过
|
break;
|
}
|
}
|
|
|
}
|
}
|
|
//如果检查返回有不符合的条件
|
if(upOrDown == 1 && aVoList.size() < dto.getMateNum()){
|
//向下
|
//已面诊开始时间为开头加5分钟重新判断
|
cs.setTime(aVo.getMzStartTime());
|
// cs.setTime(aVo.getEndTime());
|
cs.add(Calendar.MINUTE, 5);
|
st = cs.getTime();
|
}
|
// else if(upOrDown == 2 && aVoList.size() == 1){
|
// break;
|
else if(upOrDown == 2 && aVoList.size() < dto.getMateNum()){
|
//向上
|
//已初始向上开始时间为开头减5分钟重新判断
|
cs.setTime(aVo.getMzStartTime());
|
cs.add(Calendar.MINUTE, -5);
|
upStratTime = cs.getTime();
|
// st = cs.getTime();
|
//开始时间小于医生最小工作时间时
|
if(upStratTime.compareTo(minStartTime) < 0 ){
|
upOrDown = 1;
|
handleNum = 1;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
}
|
}
|
|
// dayStr = DateUtil.formatDate(st);
|
}
|
|
//判断标准匹配处理
|
if(upOrDown == 0){
|
|
//标准匹配没有跑上下减5分钟逻辑,且还没走到第三轮和走扣减逻辑
|
if(aVo == null && handleNum < 3 && deductHandle){
|
|
if (handleNum == 1 && deductHandle) {
|
//第二轮(治疗开始时间+10分钟)
|
handleNum = 2;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
} else if (handleNum == 2 && deductHandle) {
|
//第二轮(治疗结束时间-10分钟)
|
handleNum = 3;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
}
|
} else {
|
//标准匹配又符合的 或 已走完第三轮 或不走扣减逻辑,则向下匹配重新匹配
|
upStratTime = aVo != null ? aVo.getMzStartTime() : st;
|
handleNum = 1;
|
upOrDown = 2;
|
mateData = AppAutoMateHandleUtil.handleTime(commonService, shopWorkTimeVo, activityDay, projectIdsArr, doctorTimeList, shopTimeList
|
, doctorId, dto.getShopId(), handleNum, canAppList);
|
timeMap = mateData.getTimeMap();
|
}
|
}
|
}
|
|
json.put("list", aVoList);
|
json.put("sqTime", sqTime);
|
json.put("zlTime", zlTime);
|
json.put("mzTime", mzTime);
|
json.put("isSwitch", dto.getIsSwitch());
|
json.put("occupySwitch", occupySwitch);
|
|
if(!StringUtils.isEmpty(err)){
|
json.put("errMsg", err);
|
}else{
|
json.put("errMsg", deviceErr);
|
}
|
logger.info("预约匹配返回结果:{}", json.toString());
|
return Result.success(json);
|
}
|
|
|
|
}
|