package com.stylefeng.guns.modular.system.service.impl;
|
|
import com.alibaba.fastjson.JSON;
|
import com.alibaba.fastjson.JSONObject;
|
import com.baomidou.mybatisplus.mapper.EntityWrapper;
|
import com.baomidou.mybatisplus.service.impl.ServiceImpl;
|
import com.stylefeng.guns.core.util.ToolUtil;
|
import com.stylefeng.guns.modular.smallLogistics.model.OrderLogistics;
|
import com.stylefeng.guns.modular.smallLogistics.server.IOrderLogisticsService;
|
import com.stylefeng.guns.modular.specialTrain.model.OrderPrivateCar;
|
import com.stylefeng.guns.modular.specialTrain.server.IOrderPrivateCarService;
|
import com.stylefeng.guns.modular.system.dao.DriverActivityHistoryMapper;
|
import com.stylefeng.guns.modular.system.dao.DriverActivityOnlineMapper;
|
import com.stylefeng.guns.modular.system.dao.DriverOnlineMapper;
|
import com.stylefeng.guns.modular.system.model.*;
|
import com.stylefeng.guns.modular.system.service.IDriverAssessmentService;
|
import com.stylefeng.guns.modular.system.service.IDriverOnlineService;
|
import com.stylefeng.guns.modular.system.service.IDriverService;
|
import com.stylefeng.guns.modular.system.service.IDriverWorkService;
|
import com.stylefeng.guns.modular.system.util.PushUtil;
|
import com.stylefeng.guns.modular.system.util.RedisUtil;
|
import com.stylefeng.guns.modular.system.util.TextToSpeechUtil;
|
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.stereotype.Service;
|
|
import javax.annotation.Resource;
|
import java.io.BufferedReader;
|
import java.io.IOException;
|
import java.io.InputStreamReader;
|
import java.text.SimpleDateFormat;
|
import java.util.*;
|
import java.util.stream.Collectors;
|
|
@Service
|
public class DriverOnlineServiceImpl extends ServiceImpl<DriverOnlineMapper, DriverOnline> implements IDriverOnlineService {
|
|
@Resource
|
private DriverOnlineMapper driverOnlineMapper;
|
|
@Autowired
|
private RedisUtil redisUtil;
|
|
@Autowired
|
private IDriverWorkService driverWorkService;
|
|
@Autowired
|
private IDriverAssessmentService driverAssessmentService;
|
|
@Autowired
|
private IDriverService driverService;
|
|
@Resource
|
private DriverActivityOnlineMapper driverActivityOnlineMapper;
|
|
@Resource
|
private DriverActivityHistoryMapper driverActivityHistoryMapper;
|
|
@Autowired
|
private IOrderPrivateCarService orderPrivateCarService;
|
|
@Autowired
|
private IOrderLogisticsService orderLogisticsService;
|
|
@Autowired
|
private PushUtil pushUtil;
|
|
|
|
|
|
/**
|
* 添加数据
|
* @param driverId
|
* @throws Exception
|
*/
|
@Override
|
public void addDriverOnline(Integer driverId) throws Exception {
|
DriverWork driverWork = driverWorkService.selectOne(new EntityWrapper<DriverWork>().eq("driverId", driverId).eq("state", 1));
|
if(null == driverWork){//非上班状态不记录
|
for (int i = 1; i < 5; i++) {
|
redisUtil.remove("ONLINE_" + i + "_" + driverId);
|
}
|
return;
|
}
|
String[] split1 = driverWork.getType().split(",");
|
for (String ty : split1) {
|
//查询数据及条件判断
|
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
|
DriverOnline query = driverOnlineMapper.query(driverId, sdf.format(new Date()), Integer.valueOf(ty), 0);//正常记录数据
|
DriverOnline query1 = null;//考勤范围内的数据
|
DriverAssessment driverAssessment = driverAssessmentService.selectOne(new EntityWrapper<DriverAssessment>()
|
.eq("companyId", driverService.selectById(driverId).getCompanyId()));
|
Date s = null;
|
Date e = null;
|
long now = System.currentTimeMillis();
|
if(null != driverAssessment){//在考勤范围内记录数据
|
SimpleDateFormat sdf1 = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
|
String[] split = driverAssessment.getAssessment().split(" - ");
|
s = sdf1.parse(sdf.format(new Date()) + " " + split[0]);
|
e = sdf1.parse(sdf.format(new Date()) + " " + split[1]);
|
if(now > s.getTime() && now <= e.getTime()){
|
query1 = driverOnlineMapper.query(driverId, sdf.format(new Date()), Integer.valueOf(ty), 1);
|
}
|
}
|
|
//开始修改数据
|
if(query != null){
|
String value = redisUtil.getValue("ONLINE_" + ty + "_" + driverId);
|
if(ToolUtil.isEmpty(value)){
|
redisUtil.setStrValue("ONLINE_" + ty + "_" + driverId, String.valueOf(now / 1000));//存入秒
|
return;
|
}
|
Long ss = (now / 1000) - Long.valueOf(value);
|
if(ss.longValue() >= 600){//间隔时间大于10分钟则为离线
|
redisUtil.remove("ONLINE_" + ty + "_" + driverId);
|
return;
|
}
|
|
query.setDuration(query.getDuration() + ss);
|
driverOnlineMapper.updateById(query);
|
|
//记录考勤范围内的数据
|
if(null != s && null != e && now > s.getTime() && now <= e.getTime()){
|
if(null != query1){
|
query1.setDuration(query1.getDuration() + ss);
|
driverOnlineMapper.updateById(query1);
|
}else{
|
query1 = new DriverOnline();
|
query1.setDriverId(driverId);
|
query1.setType(Integer.valueOf(ty));
|
query1.setDate(new Date());
|
query1.setAssessment(1);
|
query1.setDuration(ss);
|
driverOnlineMapper.insert(query1);
|
}
|
}
|
}else{
|
DriverOnline driverOnline = new DriverOnline();
|
driverOnline.setDriverId(driverId);
|
driverOnline.setType(Integer.valueOf(ty));
|
driverOnline.setDate(new Date());
|
driverOnline.setAssessment(0);
|
driverOnline.setDuration(0L);
|
driverOnlineMapper.insert(driverOnline);
|
}
|
redisUtil.setStrValue("ONLINE_" + ty + "_" + driverId, String.valueOf(now / 1000));//存入秒
|
}
|
}
|
|
|
@Override
|
public void addDriverOnline1(Integer driverId) throws Exception {
|
DriverWork driverWork = driverWorkService.selectOne(new EntityWrapper<DriverWork>().eq("driverId", driverId).eq("state", 1));
|
if(null == driverWork){//非上班状态不记录
|
return;
|
}
|
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
|
List<DriverActivityHistory> driverActivityHistories = driverActivityHistoryMapper.selectList(new EntityWrapper<DriverActivityHistory>().eq("driverId", driverId)
|
.eq("type", 3).eq("carryOut", 1).last(" and day = '" + sdf.format(new Date()) + "' and driverActivityId in (select id from t_driver_activity where status = 3 and now() between startTime and endTime)"));
|
//生成每个活动从开始上班到当前时间的时长记录
|
for (DriverActivityHistory driverActivityHistory : driverActivityHistories) {
|
String value = redisUtil.getValue("driverActivity_" + driverId + "_" + driverActivityHistory.getId());
|
if(ToolUtil.isNotEmpty(value)){
|
JSONObject jsonObject = JSON.parseObject(value);
|
Long startTime = jsonObject.getLong("startTime");
|
long time = System.currentTimeMillis() - startTime;
|
redisUtil.setStrValue("driverActivity_" + driverId + "_" + driverActivityHistory.getId(), "{\"startTime\":" + startTime + ", \"time\":" + time + "}", 172800);
|
}else{
|
long time = System.currentTimeMillis() - driverWork.getStartTime().getTime();
|
redisUtil.setStrValue("driverActivity_" + driverId + "_" + driverActivityHistory.getId(), "{\"startTime\":" + driverWork.getStartTime().getTime() + ", \"time\":" + time + "}", 172800);
|
}
|
}
|
}
|
|
/**
|
* 获取给定日期范围的在线时长
|
* @param driverId
|
* @param assessment
|
* @param start yyyy-MM-dd
|
* @param end yyyy-MM-dd
|
* @return
|
*/
|
@Override
|
public Integer querySumTime(Integer driverId, Integer assessment, Date start, Date end) {
|
return driverOnlineMapper.querySumTime(driverId, assessment, start, end);
|
}
|
|
|
/**
|
* 定时检测司机是否连续接单
|
*/
|
@Override
|
public void deductionDuration() {
|
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
|
String format = sdf.format(new Date());
|
List<DriverActivityHistory> driverActivityHistories = driverActivityHistoryMapper.selectList(new EntityWrapper<DriverActivityHistory>().eq("DATE_FORMAT(day, '%Y-%m-%d')", format).eq("type", 3).eq("carryOut", 1));
|
List<Integer> collect = driverActivityHistories.stream().map(DriverActivityHistory::getDriverId).collect(Collectors.toList());
|
if(collect.size() == 0){
|
return;
|
}
|
for (DriverActivityHistory driverActivityHistory : driverActivityHistories) {
|
DriverWork driverWork = driverWorkService.selectOne(new EntityWrapper<DriverWork>().eq("driverId", driverActivityHistory.getDriverId()).eq("state", 1));
|
if(null == driverWork){
|
continue;
|
}
|
DriverActivityOnline driverActivityOnline = driverActivityOnlineMapper.selectById(driverActivityHistory.getActivityId());
|
DriverOnline driverOnline = this.selectOne(new EntityWrapper<DriverOnline>().eq("DATE_FORMAT(date, '%Y-%m-%d')", format)
|
.eq("driverId", driverActivityHistory.getDriverId()).eq("type", driverActivityOnline.getType()));
|
if(null == driverOnline){
|
continue;
|
}
|
Integer driverId = driverOnline.getDriverId();
|
Driver driver1 = driverService.selectById(driverId);
|
long m = Double.valueOf(driverActivityOnline.getOfflineTime() * 3600000L).longValue();
|
|
//找出最后一次接单的时间
|
long mm = 0L;
|
OrderPrivateCar orderPrivateCar = orderPrivateCarService.selectOne(new EntityWrapper<OrderPrivateCar>().eq("driverId", driverId).eq("isDelete", 1).ne("state", 10));
|
Date snatchOrderTime = null;
|
if(null != orderPrivateCar){
|
snatchOrderTime = orderPrivateCar.getSnatchOrderTime();
|
mm = snatchOrderTime.getTime();
|
}
|
OrderLogistics orderLogistics = orderLogisticsService.selectOne(new EntityWrapper<OrderLogistics>().eq("driverId", driverId).eq("isDelete", 1).ne("state", 10));
|
if(null != orderLogistics && (null == snatchOrderTime || snatchOrderTime.before(orderLogistics.getSnatchOrderTime()))){
|
mm = orderLogistics.getSnatchOrderTime().getTime();
|
}
|
|
//超时不接单,直接将之前的在线时长清零
|
//推送司机下班提醒
|
if((System.currentTimeMillis() - mm) >= m){
|
this.deleteById(driverOnline.getId());
|
driverWork.setState(2);
|
driverWork.setEndTime(new Date());
|
driverWorkService.updateById(driverWork);
|
Driver driver = driverService.selectById(driverWork.getDriverId());
|
driver.setState(1);
|
driverService.updateById(driver);
|
Integer language = driver.getLanguage();
|
|
String msg = language == 1 ? "您已连续" + driverActivityOnline.getOfflineTime() + "小时未接单,系统将强制更改您的状态为:下班" :
|
language == 2 ? "You have not been accepting orders for " + driverActivityOnline.getOfflineTime() + " hour(s) System will change your state to Off-work" :
|
"Vous n’acceptez pas de commandes depuis " + driverActivityOnline.getOfflineTime() + " heure(s) Le système changera votre état en Hors travail";
|
String fileName = "OffLine" + driver.getId() + ".mp3";
|
String audioUrl = null;
|
try {
|
audioUrl = TextToSpeechUtil.create(language == 1 ? "cmn-CN" : language == 2 ? "en-US" : "fr-FR", msg, fileName);
|
} catch (Exception e) {
|
throw new RuntimeException(e);
|
}
|
Map<String, String> map = new HashMap<>();
|
map.put("msg", msg);
|
map.put("audioUrl", audioUrl);
|
pushUtil.afterWork(driverOnline.getDriverId(), 2, map);
|
|
//定时任务删除语音文件
|
new Timer().schedule(new TimerTask() {
|
@Override
|
public void run() {
|
Process process = null;
|
try {
|
process = Runtime.getRuntime().exec("sudo rm -rf /home/igotechgh/nginx/html/files/audio/" + fileName);
|
} catch (IOException e) {
|
throw new RuntimeException(e);
|
}
|
if (process != null) {
|
process.destroy();
|
}
|
}
|
}, 30000);
|
}
|
|
}
|
|
|
}
|
|
|
@Override
|
public void deductionDuration1() {
|
SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
|
List<DriverActivityHistory> driverActivityHistories = driverActivityHistoryMapper.selectList(new EntityWrapper<DriverActivityHistory>()
|
.eq("type", 3).eq("carryOut", 1).last(" and day = '" + sdf.format(new Date()) + "' and driverActivityId in (select id from t_driver_activity where status = 3 and now() between startTime and endTime)"));
|
for (DriverActivityHistory driverActivityHistory : driverActivityHistories) {
|
DriverWork driverWork = driverWorkService.selectOne(new EntityWrapper<DriverWork>().eq("driverId", driverActivityHistory.getDriverId()).eq("state", 1));
|
if(null == driverWork){
|
continue;
|
}
|
DriverActivityOnline driverActivityOnline = driverActivityOnlineMapper.selectById(driverActivityHistory.getActivityId());
|
//在线连续xx小时不接单,司机下线,时长不计入总累计时长
|
int m = Double.valueOf(driverActivityOnline.getOfflineTime() * 60).intValue();
|
String value = redisUtil.getValue("driverActivity_" + driverActivityHistory.getDriverId() + "_" + driverActivityHistory.getId());
|
if(ToolUtil.isEmpty(value)){
|
continue;
|
}
|
JSONObject jsonObject = JSON.parseObject(value);
|
//开始记录时长的时间开始时间戳
|
Long startTime = jsonObject.getLong("startTime");
|
//在线时长累计
|
Long time = jsonObject.getLong("time") / 60000;
|
int count1 = orderPrivateCarService.selectCount(new EntityWrapper<OrderPrivateCar>().eq("driverId", driverActivityHistory.getDriverId())
|
.eq("isDelete", 1).ne("state", 10).last(" and UNIX_TIMESTAMP(snatchOrderTime) > " + (startTime) / 1000));
|
int count2 = orderLogisticsService.selectCount(new EntityWrapper<OrderLogistics>().eq("driverId", driverActivityHistory.getDriverId())
|
.eq("isDelete", 1).ne("state", 10).last(" and UNIX_TIMESTAMP(snatchOrderTime) > " + (startTime) / 1000));
|
|
Driver driver = driverService.selectById(driverWork.getDriverId());
|
//阶段时间累计时长超过设定时长且没有接单,不计入累计总时长(司机服务中不下班)
|
if(m <= time && count1 + count2 == 0 && driver.getState() != 3){
|
//司机下班,清空当前阶段的累计时长
|
driverWork.setState(2);
|
driverWork.setEndTime(new Date());
|
driverWorkService.updateById(driverWork);
|
driver.setState(1);
|
driverService.updateById(driver);
|
redisUtil.remove("driverActivity_" + driverActivityHistory.getDriverId() + "_" + driverActivityHistory.getId());
|
Integer language = driver.getLanguage();
|
|
String msg = language == 1 ? "您已连续" + driverActivityOnline.getOfflineTime() + "小时未接单,系统将强制更改您的状态为:下班" :
|
language == 2 ? "You have not been accepting orders for " + driverActivityOnline.getOfflineTime() + " hour(s) System will change your state to Off-work" :
|
"Vous n’acceptez pas de commandes depuis " + driverActivityOnline.getOfflineTime() + " heure(s) Le système changera votre état en Hors travail";
|
String fileName = "OffLine" + driver.getId() + ".mp3";
|
String audioUrl = null;
|
try {
|
audioUrl = TextToSpeechUtil.create(language == 1 ? "cmn-CN" : language == 2 ? "en-US" : "fr-FR", msg, fileName);
|
} catch (Exception e) {
|
throw new RuntimeException(e);
|
}
|
Map<String, String> map = new HashMap<>();
|
map.put("msg", msg);
|
map.put("audioUrl", audioUrl);
|
pushUtil.afterWork(driverWork.getDriverId(), 2, map);
|
|
//定时任务删除语音文件
|
new Timer().schedule(new TimerTask() {
|
@Override
|
public void run() {
|
Process process = null;
|
try {
|
process = Runtime.getRuntime().exec("sudo rm -rf /home/igotechgh/nginx/html/files/audio/" + fileName);
|
} catch (IOException e) {
|
throw new RuntimeException(e);
|
}
|
if (process != null) {
|
process.destroy();
|
}
|
}
|
}, 30000);
|
}
|
//阶段时间累计有新的订单,计入累计总时长,重置新的开始统计时间戳
|
if(m <= time && count1 + count2 > 0){
|
DriverOnline driverOnline = this.selectOne(new EntityWrapper<DriverOnline>().eq("DATE_FORMAT(date, '%Y-%m-%d')", sdf.format(new Date()))
|
.eq("driverId", driverActivityHistory.getDriverId()));
|
if(null == driverOnline){
|
driverOnline = new DriverOnline();
|
driverOnline.setDriverId(driverActivityHistory.getDriverId());
|
driverOnline.setDate(new Date());
|
driverOnline.setDuration(time * 60);
|
driverOnline.setInsertTime(new Date());
|
this.insert(driverOnline);
|
}else{
|
driverOnline.setDuration(driverOnline.getDuration() + (time * 60));
|
this.updateById(driverOnline);
|
}
|
redisUtil.setStrValue("driverActivity_" + driverActivityHistory.getDriverId() + "_" + driverActivityHistory.getId(), "{\"startTime\":" + System.currentTimeMillis() + ", \"time\":" + 0 + "}", 172800);
|
}
|
}
|
}
|
}
|