package com.template.controller;
import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.toolkit.ObjectUtils;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.seewo.open.sdk.DefaultSeewoClient;
import com.seewo.open.sdk.SeewoClient;
import com.seewo.open.sdk.auth.Account;
import com.template.api.SmartVisitorControllerAPI;
import com.template.common.utils.CommonUtil;
import com.template.common.utils.RequestUtils;
import com.template.common.utils.TimeExchange;
import com.template.common.utils.paramUtils;
import com.template.config.ParkConfig;
import com.template.config.SeewoConfig;
import com.template.model.enumModel.*;
import com.template.model.pojo.*;
import com.template.model.request.otherAppointmentRequest;
import com.template.model.request.parentsAppointmentRequest;
import com.template.model.request.turnOnTheDeviceRequest;
import com.template.model.result.CommonResult;
import com.template.model.result.PageUtils;
import com.template.model.seewo.HomeSchoolServiceSendNoteToKidParam;
import com.template.model.seewo.HomeSchoolServiceSendNoteToKidRequest;
import com.template.model.seewo.HomeSchoolServiceSendNoteToKidResult;
import com.template.model.vo.*;
import com.template.services.SmartAuthorGroupService;
import com.template.services.SmartQrcodeService;
import com.template.services.SmartUserService;
import com.template.services.SmartVisitorService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.validation.BindingResult;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import javax.annotation.Resource;
import java.net.URLDecoder;
import java.util.*;
import java.util.stream.Collectors;
import static com.template.common.utils.AesTestOne.decrypt;
/**
*
* 前端控制器
*
*
* @author ceshi
* @since 2023-12-04
*/
@RestController
public class SmartVisitorController implements SmartVisitorControllerAPI {
@Autowired
private SmartAuthorGroupService smartAuthorGroupService;
@Autowired
private SmartVisitorService smartVisitorService;
@Autowired
private SmartQrcodeService smartQrcodeService;
@Autowired
private SmartUserService smartUserService;
@Resource
private SeewoConfig seewoConfig;
@Resource
private ParkConfig parkConfig;
/**
* 新增访客预约
*
* @param smartApply 访客预约数据
* @param bindingResult
* @return
*/
@Override
public CommonResult insertSmartVisitor(SmartVisitor smartApply, BindingResult bindingResult) {
if (bindingResult.hasErrors()) {
String st = paramUtils.getParamError(bindingResult);
return CommonResult.fail(st);
}
int result = smartVisitorService.insertSmartVisitor(smartApply);
return result > 0 ? CommonResult.ok("添加成功") : CommonResult.fail("添加失败");
}
/**
* 更新访客预约
*
* @param sa 访客预约数据
* @param bindingResult
* @return
*/
@Override
public CommonResult updateSmartVisitorById(SmartVisitor sa, BindingResult bindingResult) {
if (bindingResult.hasErrors()) {
String st = paramUtils.getParamError(bindingResult);
return CommonResult.fail(st);
}
int result = smartVisitorService.updateSmartVisitor(sa);
return result > 0 ? CommonResult.ok("修改成功") : CommonResult.fail("修改失败");
}
/**
* 访客预约分页数据查询
*
* @param currentPage 当前页数
* @param pageCount 一页数据条数
* @param name 查询名称
* @return
*/
@Override
public CommonResult queryPageSmartVisitor(int currentPage, int pageCount, String name) {
PageUtils result = smartVisitorService.queryPageSmartVisitors(currentPage, pageCount, name);
return CommonResult.ok(result);
}
@Override
public CommonResult deleteSmartVisitorById(int id) {
SmartVisitor data = smartVisitorService.getSmartById(id);
if (data == null) {
return CommonResult.fail("当前数据不存在,删除失败!");
}
//审核通过就不能删除
if(data.getStatu().intValue() == eApproveStatu.Pushed.getValue()){
return CommonResult.fail("无法删除已审核通过的访客数据");
}
//已审核通过的数据不能删除 那么就不需要进行下面这些操作
//region 推送到希沃班牌,通知访客记录取消
//endregion
//region 删除百胜中的访客数据
//endregion
int result = smartVisitorService.deleteSmartVisitorById(id);
return result > 0 ? CommonResult.ok("删除成功") : CommonResult.fail("删除失败");
}
@Override
public CommonResult parentsAppointment(parentsAppointmentRequest par, BindingResult bindingResult) {
if (bindingResult.hasErrors()) {
String st = paramUtils.getParamError(bindingResult);
return CommonResult.fail(st);
}
//参数判断 判断受访学生信息是否为空
if (par.getStudents() == null) {
return CommonResult.fail("请选择受访学生");
}
if (par.getStudents().size() <= 0) {
return CommonResult.fail("请选择受访学生");
}
//根据用户ID查询相关信息
SmartUser su = smartUserService.getSmartById(par.getUserId());
if (su == null) {
return CommonResult.fail("当前用户信息不合法,无法进行预约!");
}
String startTime = par.getVisitorTime();
String endTime = TimeExchange.getEndOfDayStr(TimeExchange.StringToDate(startTime, "yyyy-MM-dd HH:mm:ss"));
//要进行家长数据重复判断
//那是不是第二次预约的时间不能在那个可访问的时间段内
//例如:比如,第一次约了7:00-10:00;那第二次:6:00-7:30 或 8:11-13:00都不行
Integer count = smartVisitorService.queryVisitorCount(su.getIdCard(), startTime, endTime);
if (count > 0) {
return CommonResult.fail("该时间段已预约,请勿重复预约!");
}
List svs = new ArrayList<>();
for (AffiliateUserVo student : par.getStudents()) {
SmartVisitor sv = new SmartVisitor();
sv.setUserId(par.getUserId());
sv.setUserName(su.getName());
sv.setUserPhone(su.getPhone());
sv.setUserNumber(su.getIdCard());
sv.setPeerNum(par.getPeerNum());
//sv.setCarNum(par.getCarNum());家长预约不能填写车牌号
sv.setVisitReason(par.getVisitReason());
sv.setStatu(eApproveStatu.Audit.getValue());
sv.setVisitorTime(TimeExchange.StringToDate(par.getVisitorTime(), "yyyy-MM-dd HH:mm:ss"));
sv.setVisitorDeadline(TimeExchange.StringToDate(TimeExchange.TimeDesH(sv.getVisitorTime(), 4), "yyyy-MM-dd HH:mm:ss"));
sv.setRespondent(student.getId());
sv.setResponcode(student.getCardNo());
sv.setRespondentName(student.getName());
//将第一个受访学生的部门ID带过去
sv.setDepartmentId(student.getDepartmentId());
sv.setVisitorType(eVisitorType.Parent.getValue());
svs.add(sv);
}
boolean result = smartVisitorService.insertVisitorBatch(svs);
return result ? CommonResult.ok("预约成功,等待审批通过") : CommonResult.fail("预约失败");
}
@Override
public CommonResult otherAppointment(otherAppointmentRequest oar, BindingResult bindingResult) {
if (bindingResult.hasErrors()) {
String st = paramUtils.getParamError(bindingResult);
return CommonResult.fail(st);
}
//根据用户ID查询相关信息
SmartUser su = smartUserService.getSmartById(oar.getUserId());
if (su == null) {
return CommonResult.fail("当前用户信息不合法,无法进行预约!");
}
String startTime = oar.getVisitorTime();
String endTime = TimeExchange.getEndOfDayStr(TimeExchange.StringToDate(startTime, "yyyy-MM-dd HH:mm:ss"));
//要进行访客数据重复判断
//那是不是第二次预约的时间不能在那个可访问的时间段内
//例如:比如,第一次约了7:00-10:00;那第二次:6:00-7:30 或 8:11-13:00都不行
Integer count = smartVisitorService.queryVisitorCount(su.getIdCard(), startTime, endTime);
if (count > 0) {
return CommonResult.fail("该时间段已预约,请勿重复预约!");
}
SmartVisitor sv = new SmartVisitor();
sv.setUserId(oar.getUserId());
sv.setUserName(oar.getUserName());
sv.setUserPhone(oar.getUserPhone());
sv.setUserNumber(oar.getUserCard());
sv.setPeerNum(oar.getPeerNum());
sv.setCarNum(oar.getCarNum());
sv.setVisitReason(oar.getVisitReason());
sv.setStatu(eApproveStatu.Audit.getValue());
sv.setVisitorTime(TimeExchange.StringToDate(startTime, "yyyy-MM-dd HH:mm:ss"));
sv.setVisitorDeadline(TimeExchange.StringToDate(endTime, "yyyy-MM-dd HH:mm:ss"));
sv.setRespondentName(oar.getRespondentName());
sv.setRespondentPhone(oar.getRespondentPhone());
sv.setVisitorType(eVisitorType.Other.getValue());
int result = smartVisitorService.insertSmartVisitor(sv);
return result > 0 ? CommonResult.ok("预约成功,等待审批通过") : CommonResult.ok("预约失败");
}
@Override
public CommonResult appointmentPageRecord(int currentPage, int pageCount, Integer userId, int type, String createStartTime, String createEndTime, String keyWord, String visitorStartTime, String visitorEndTime) {
PageUtils result = smartVisitorService.smartVisitorPageByUserId(currentPage, pageCount, userId, type, createStartTime, createEndTime, keyWord, visitorStartTime, visitorEndTime);
return CommonResult.ok(result);
}
/**
* 访客记录审核
*
* @param id 数据ID
* @param type 操作类型:
* 同意,并推送:1
* 拒绝:2
* @return
*/
@Override
@Transactional(rollbackFor = {Exception.class})
public CommonResult examineRecord(int id, int type) throws Exception {
SmartVisitor visitor = smartVisitorService.getSmartById(id);
if (visitor == null) {
return CommonResult.fail("访客记录已失效,审核失败!");
}
//审核处理后的数据不能再处理判断
if(visitor.getStatu().intValue() != eApproveStatu.Audit.getValue()){
return CommonResult.fail("该记录已被操作过,请勿重复操作");
}
try {
if (type == eExamineStatu.Agree.getValue()) {
visitor.setStatu(eApproveStatu.Pushed.getValue());
//家长访客预约才需要将消息推送到希沃电子班牌
if (visitor.getVisitorType().intValue() == eVisitorType.Parent.getValue()) {
String content = visitor.getRespondentName() + "你的家长将于" + TimeExchange.chineseDateTime(visitor.getVisitorTime()) + "到校!";
//将预约信息推送到希沃班牌
CommonResult seewo = pushInfo(visitor.getUserPhone(), visitor.getResponcode(), content);
if (!seewo.getCode().equals("200")) {
throw new Exception("审核失败");
}
}
//将数据写入门禁系统逻辑
else {
//家长不能使用车牌系统 其他的可以使用车牌逻辑
if (!ObjectUtils.isEmpty(visitor.getCarNum())) {
String appId = parkConfig.getAppId();
String carNo = visitor.getCarNum();
String parkKey = parkConfig.getParkKey();
String rand = String.valueOf(Math.random());
String reserveTime = TimeExchange.DateToString(visitor.getVisitorTime(), "yyyy-MM-dd HH:mm:ss");
String reserveEndTime = TimeExchange.DateToString(visitor.getVisitorDeadline(), "yyyy-MM-dd HH:mm:ss");
String version = "v1.0";
String appSecret = parkConfig.getAppSecret();
String url = parkConfig.getUrl() + "Inform/Reservation";
JSONObject jsonobject = new JSONObject();
jsonobject.put("appid", appId);
jsonobject.put("carNo", carNo);
jsonobject.put("parkKey", parkKey);
jsonobject.put("rand", rand);
jsonobject.put("reserveEndTime", reserveEndTime);
jsonobject.put("reserveTime", reserveTime);
jsonobject.put("version", "v1.0");
//appid=ymdd36ed157ac423e2&carNo=赣U123659&parkKey=wdcmq9rc&rand=9.94995525689689966&reserveEndTime=2023-12-22 20:12:10&reserveTime=2023-12-21 18:12:10&version=v1.0&50596cd243dc4547b4c05f01f8ea02a4
String md5Str = "appid=" + appId + "&carNo=" + carNo + "&parkKey=" + parkKey + "&rand=" + rand + "&reserveEndTime=" + reserveEndTime + "&reserveTime=" + reserveTime + "&version=" + version + "&" + appSecret;
String sign = CommonUtil.MD5(md5Str);
//sign签名
jsonobject.put("sign", sign);
//返回的结果中 code为1表示成功
String result = RequestUtils.httpPost(url, jsonobject.toJSONString());
System.out.println(result);
if (!result.contains("预约成功")) {
throw new Exception("审核失败");
}
ObjectMapper objectMapper = new ObjectMapper();
BsReservationVo reservation = objectMapper.readValue(result, BsReservationVo.class);
visitor.setBsOrderNo(reservation.getData().getReOrderNo());
}
}
} else if (type == eExamineStatu.Refused.getValue()) {
visitor.setStatu(eApproveStatu.Refused.getValue());
}
int result = smartVisitorService.updateSmartVisitor(visitor);
if (result <= 0) {
throw new Exception("审核失败");
}
} catch (Exception e) {
throw new Exception("审核失败");
}
return CommonResult.ok("审核成功");
}
/**
* 将预约信息推送到希沃电子班牌
*
* @param parentPhone 预约手机号(家长手机号 在希沃中学生会和家长手机号绑定 可以绑定多个家长)
* @param studentCode 学生编号 希沃中的学生编号和万载系统中的一致
* @param content 消息内容
* @return
*/
public CommonResult pushInfo(String parentPhone, String studentCode, String content) {
//初始化客户端
SeewoClient seewoClient = new DefaultSeewoClient(new Account(seewoConfig.getAppId(), seewoConfig.getAppSecret()));
HomeSchoolServiceSendNoteToKidParam param = new HomeSchoolServiceSendNoteToKidParam();
//响应体,MimeType为 application/json
HomeSchoolServiceSendNoteToKidParam.RequestBody requestBody = HomeSchoolServiceSendNoteToKidParam.RequestBody.builder()
.build();
param.setRequestBody(requestBody);
//query
HomeSchoolServiceSendNoteToKidParam.Query query = HomeSchoolServiceSendNoteToKidParam.Query.builder()
.appId(seewoConfig.getAppId())
.schoolUid(seewoConfig.getSchoolId())
.senderPhone(parentPhone)
.studentCode(studentCode)
.type(1)
.content(content)
.autoRegister(0)
.build();
requestBody.setQuery(query);
param.setRequestBody(requestBody);
HomeSchoolServiceSendNoteToKidRequest request = new HomeSchoolServiceSendNoteToKidRequest(param);
System.out.println("入参:" + request);
//如果想要调用沙箱环境,请通过设置 request 对象的 serverUrl 属性,如:
//request.setServerUrl("https://openapi.test.seewo.com")
//执行请求,如果想获取到com.seewo.open.sdk.HttpResponse对象,请调用 seewoClient.execute 方法
HomeSchoolServiceSendNoteToKidResult result = seewoClient.invoke(request);
System.out.println("出参:" + result);
if (!result.getMessage().equals("success")) {
CommonResult.fail();
}
return CommonResult.ok();
}
/**
* 获取到访代办数据
*
* @param userId
* @return
*/
@Override
public CommonResult visitingAgencys(int currentPage, int pageCount, int userId, int type) {
SmartUser user = smartUserService.getSmartById(userId);
if (user == null) {
return CommonResult.fail("当前用户数据无效,获取到访数据失败");
}
if (user.getIdentityId().intValue() != eIdentityStatu.Teacher.getValue()) {
return CommonResult.fail("非教师身份无法获取到访数据");
}
//是否是管理员
String whereSql = null;
//获取的权限组数据
List authorGroups = smartAuthorGroupService.smartAuthorGroup(user.getId());
for (SmartAuthorGroup authorGroup : authorGroups) {
List applyIds = Arrays.asList(authorGroup.getApplyId().split(","));
//菜单表中7是访客预约
long appointCount = applyIds.stream().filter(e -> e.equals("7")).count();
if (appointCount > 0) {
whereSql = "visitor_type = 2";
break;
}
}
List studentIds = null;
//班主任
if (user.getDuties().intValue() == eDuties.ClassTeacher.getValue()) {
//班级ID
Integer schoolClass = user.getSchoolClass();
//获取该班级下的所有学生ID数据
List students = smartUserService.queryStudentBySchoolClass(user.getSchoolClass());
if (students == null) {
return CommonResult.fail("当前身份下不存在学生信息");
}
studentIds = students.stream().map(SmartUser::getId).collect(Collectors.toList());
}
PageUtils result = new PageUtils(null, 0, pageCount, currentPage);
if (whereSql == null && studentIds == null) {
return CommonResult.ok(result);
}
result = smartVisitorService.queryVisitorPageDatas(currentPage, pageCount, type, studentIds, studentIds != null && whereSql != null ? "or " + whereSql : whereSql);
return CommonResult.ok(result);
}
@Override
public TurnOnDeviceVo turnOnTheDevice(turnOnTheDeviceRequest data) throws JsonProcessingException {
TurnOnDeviceVo result = new TurnOnDeviceVo();
//region 参数判断
if (data == null) {
result.setResultcode(2);
result.setMessage("扫码参数不能为空");
result.setActionName("qrCodePush");
return result;
}
if (data.getActionName() == null) {
result.setResultcode(2);
result.setMessage("指令不能为空");
result.setActionName("qrCodePush");
return result;
}
if (!data.getActionName().equals("qrCodePush")) {
result.setResultcode(2);
result.setMessage("指令错误");
result.setActionName("qrCodePush");
return result;
}
if (data.getData() == null) {
result.setResultcode(2);
result.setMessage("二维码内容不能为空");
result.setActionName("qrCodePush");
return result;
}
ObjectMapper objectMapper = new ObjectMapper();
qrCodeVo codeVo = objectMapper.readValue(data.getData(), qrCodeVo.class);
if (codeVo == null) {
result.setResultcode(2);
result.setMessage("二维码内容不能为空");
result.setActionName("qrCodePush");
return result;
}
if (codeVo.getQrCode() == null) {
result.setResultcode(2);
result.setMessage("二维码内容不能为空");
result.setActionName("qrCodePush");
return result;
}
if (data.getDeviceno() == null) {
result.setResultcode(2);
result.setMessage("设备编号不能为空");
result.setActionName("qrCodePush");
return result;
}
if (data.getVersion() == null) {
result.setResultcode(2);
result.setMessage("版本不能为空");
result.setActionName("qrCodePush");
return result;
}
//endregion
//解码逻辑
QrcodeImageVo qiv = objectMapper.readValue(codeVo.getQrCode(), QrcodeImageVo.class);
SmartUser user = smartUserService.getSmartById(qiv.getId());
if (user == null) {
result.setResultcode(2);
result.setMessage("用户身份无效,刷码失败");
result.setActionName("qrCodePush");
return result;
}
//目前二维码一分钟内有效
//过期:(时间戳 + 有效期分钟数)<= 当前时间
//时间戳转时间
Date dateNow = TimeExchange.StringToDate(TimeExchange.TimeRangeI10(qiv.getTimestamp(), 1), "yyyy-MM-dd HH:mm:ss");
if (dateNow.compareTo(new Date()) < 0) {
result.setResultcode(2);
result.setMessage("身份码已过期");
result.setActionName("qrCodePush");
return result;
}
//成功后将刷码记录存储到数据表中
SmartQrcode sq = new SmartQrcode();
sq.setUserId(0);
sq.setSourceCode(data.getData());
sq.setIsSuccess(1);
int insertResult = smartQrcodeService.insertSmartQrcode(sq);
if (insertResult <= 0) {
result.setResultcode(2);
result.setMessage("新增刷码记录失败");
result.setActionName("qrCodePush");
return result;
}
result.setResultcode(1);
result.setMessage("成功");
result.setActionName("qrCodePush");
return result;
}
}