This commit is contained in:
Lemon
2024-09-03 08:50:14 +08:00
43 changed files with 2604 additions and 1023 deletions

View File

@@ -3,6 +3,8 @@ package com.jsowell.pile.domain;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.jsowell.common.annotation.Excel;
import com.jsowell.common.core.domain.BaseEntity;
import lombok.Getter;
import lombok.Setter;
import org.apache.commons.lang3.builder.ToStringBuilder;
import org.apache.commons.lang3.builder.ToStringStyle;
@@ -14,6 +16,8 @@ import java.util.Date;
* @author jsowell
* @date 2022-08-26
*/
@Getter
@Setter
public class PileBasicInfo extends BaseEntity {
private static final long serialVersionUID = 1L;
@@ -52,9 +56,9 @@ public class PileBasicInfo extends BaseEntity {
private String secretKey;
/**
* 软件协议1-云快充2-永联)
* 软件协议1-云快充; 2-永联; 3-友电
*/
@Excel(name = "软件协议", readConverterExp = "1=-云快充2-永联")
@Excel(name = "软件协议", readConverterExp = "1=-云快充; 2-永联; 3-友电")
private String softwareProtocol;
/**
@@ -107,131 +111,6 @@ public class PileBasicInfo extends BaseEntity {
*/
private String delFlag;
public void setId(Long id) {
this.id = id;
}
public Long getId() {
return id;
}
public void setSn(String sn) {
this.sn = sn;
}
public String getSn() {
return sn;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public void setBusinessType(String businessType) {
this.businessType = businessType;
}
public String getBusinessType() {
return businessType;
}
public void setSoftwareProtocol(String softwareProtocol) {
this.softwareProtocol = softwareProtocol;
}
public String getSoftwareProtocol() {
return softwareProtocol;
}
public void setProductionDate(Date productionDate) {
this.productionDate = productionDate;
}
public Date getProductionDate() {
return productionDate;
}
public void setLicenceId(Long licenceId) {
this.licenceId = licenceId;
}
public Long getLicenceId() {
return licenceId;
}
public void setModelId(Long modelId) {
this.modelId = modelId;
}
public Long getModelId() {
return modelId;
}
public void setSimId(Long simId) {
this.simId = simId;
}
public Long getSimId() {
return simId;
}
public void setMerchantId(Long merchantId) {
this.merchantId = merchantId;
}
public Long getMerchantId() {
return merchantId;
}
public void setStationId(Long stationId) {
this.stationId = stationId;
}
public Long getStationId() {
return stationId;
}
public void setFaultReason(String faultReason) {
this.faultReason = faultReason;
}
public String getFaultReason() {
return faultReason;
}
public void setDelFlag(String delFlag) {
this.delFlag = delFlag;
}
public String getDelFlag() {
return delFlag;
}
public String getSecretKey() {
return secretKey;
}
public void setSecretKey(String secretKey) {
this.secretKey = secretKey;
}
public static long getSerialVersionUID() {
return serialVersionUID;
}
@Override
public Date getCreateTime() {
return createTime;
}
public void setCreateTime(Date createTime) {
this.createTime = createTime;
}
@Override
public String toString() {
return new ToStringBuilder(this, ToStringStyle.JSON_STYLE)

View File

@@ -1,5 +1,6 @@
package com.jsowell.pile.domain.ebike;
import com.jsowell.common.YouDianUtils;
import com.jsowell.common.util.BytesUtil;
import com.jsowell.pile.domain.ebike.deviceupload.*;
import lombok.Getter;
@@ -41,6 +42,8 @@ public abstract class AbsEBikeMessage {
return new EBikeMessageCmd04(header, length, physicalId, messageId, command, null, checksum, new EBikeMessageCmd04.ConfirmOrder(dataBytes));
case "06":
return new EBikeMessageCmd06(header, length, physicalId, messageId, command, null, checksum, new EBikeMessageCmd06.PowerHeartbeat(dataBytes));
case "12":
return new EBikeMessageCmd12(header, length, physicalId, messageId, command, null, checksum);
case "20":
return new EBikeMessageCmd20(header, length, physicalId, messageId, command, null, checksum, new EBikeMessageCmd20.DeviceRegister(dataBytes));
case "21":
@@ -73,7 +76,7 @@ public abstract class AbsEBikeMessage {
// 读取物理ID
byte[] physicalIdBytes = Arrays.copyOfRange(messageBytes, 5, 9);
int physicalId = BytesUtil.bytesToIntLittle(physicalIdBytes);
int physicalId = YouDianUtils.convertToPhysicalId(physicalIdBytes);
// 读取消息ID
byte[] messageIdBytes = Arrays.copyOfRange(messageBytes, 9, 11);

View File

@@ -9,8 +9,9 @@ import lombok.extern.slf4j.Slf4j;
@Slf4j
public enum EBikeCommandEnum {
// HEARTBEAT("01", "设备心跳包"),
HOST_GET_SERVER_TIME("12", "主机获取服务器时间", EBikeMessageCmd12.class),
REGISTRATION("20", "设备注册包", EBikeMessageCmd20.class),
GET_SERVER_TIME("22", "设备获取服务器时间", EBikeMessageCmd22.class),
DEVICE_GET_SERVER_TIME("22", "设备获取服务器时间", EBikeMessageCmd22.class),
HEARTBEAT_2("21", "设备心跳包", EBikeMessageCmd21.class),
CARD_OPERATION("02", "刷卡操作", EBikeMessageCmd02.class),
SETTLEMENT_UPLOAD("03", "结算消费信息上传", EBikeMessageCmd03.class),

View File

@@ -0,0 +1,34 @@
package com.jsowell.pile.domain.ebike.deviceupload;
import com.jsowell.common.util.bean.SerializationUtil;
import com.jsowell.pile.domain.ebike.AbsEBikeMessage;
import lombok.Getter;
import lombok.Setter;
/**
* 主机获取服务器时间0x12
* 此命令主机每次上电后就会发送直至服务器应答后就停止发送。如服务器无应答则每隔3分钟发送一次请求
* 每12小时从服务器获取一次时间如服务器不应答则每隔3分钟发送一次请求
* 不带RTC模块的主机不会发送此命令
* DE 5C A9 5F转小端模式=0x5FA95CDE=1604934878=2020-11-09 23:14:38
*/
@Getter
@Setter
public class EBikeMessageCmd12 extends AbsEBikeMessage {
public EBikeMessageCmd12(String header, int length, int physicalId, int messageId, String command, Object payload, int checksum) {
super(header, length, physicalId, messageId, command, payload, checksum);
}
@Override
public void parsePayload(byte[] dataBytes) {
}
@Override
public byte[] getMessageBytes() {
byte[] serialize = SerializationUtil.serialize(this);
return serialize;
}
}

View File

@@ -42,7 +42,7 @@ public class EBikeMessageCmd20 extends AbsEBikeMessage {
/**
* 端口数量 表示设备总共有多少个端口
*/
private String portNumber;
private int portNumber;
/**
* 虚拟ID需要内部组网的设备的本地地址如485、LORA系列如不需组网的设备默认为00
@@ -66,7 +66,7 @@ public class EBikeMessageCmd20 extends AbsEBikeMessage {
public DeviceRegister(byte[] dataBytes) {
this.firmwareVersion = BytesUtil.bytesToIntLittle(Arrays.copyOfRange(dataBytes, 0, 2)) * 0.01 + "";
this.portNumber = BytesUtil.bytesToIntLittle(Arrays.copyOfRange(dataBytes, 2, 3)) + "";
this.portNumber = BytesUtil.bytesToIntLittle(Arrays.copyOfRange(dataBytes, 2, 3));
this.virtualId = BytesUtil.bytesToIntLittle(Arrays.copyOfRange(dataBytes, 3, 4)) + "";
this.deviceType = BytesUtil.printHexBinary(Arrays.copyOfRange(dataBytes, 4, 5));
this.workMode = BytesUtil.bcd2StrLittle(Arrays.copyOfRange(dataBytes, 5, 6));

View File

@@ -62,6 +62,8 @@ public class EBikeMessageCmd21 extends AbsEBikeMessage {
*/
private List<String> portStatus;
private List<String> statusDescList;
/**
* 信号强度指分机与主机之间的无线信号强度如LORA信号。00则为有线组网或无信号强度功能
*/
@@ -79,13 +81,21 @@ public class EBikeMessageCmd21 extends AbsEBikeMessage {
byte[] statusBytes = BytesUtil.copyBytes(dataBytes, 3, this.portNumber);
List<String> statusList = Lists.newArrayList();
List<String> statusDescList = Lists.newArrayList();
for (byte statusByte : statusBytes) {
int status = BytesUtil.bytesToIntLittle(new byte[]{statusByte});
statusList.add(PortStatusEnum.getDescriptionByValue(status));
statusList.add(String.valueOf(status));
statusDescList.add(PortStatusEnum.getDescriptionByValue(status));
}
this.portStatus = statusList;
this.rssi = BytesUtil.bcd2StrLittle(Arrays.copyOfRange(dataBytes, dataBytes.length - 2, dataBytes.length - 1));
this.temperature = BytesUtil.bcd2StrLittle(Arrays.copyOfRange(dataBytes, dataBytes.length - 1, dataBytes.length));
this.statusDescList = statusDescList;
this.rssi = BytesUtil.bytesToIntLittle(Arrays.copyOfRange(dataBytes, dataBytes.length - 2, dataBytes.length - 1)) + "";
//
int i = BytesUtil.bytesToIntLittle(Arrays.copyOfRange(dataBytes, dataBytes.length - 1, dataBytes.length));
if (i > 65) {
i = i - 65;
}
this.temperature = i + "";
}
}

View File

@@ -2,6 +2,7 @@ package com.jsowell.pile.service;
import com.jsowell.common.core.domain.ykc.RealTimeMonitorData;
import com.jsowell.pile.domain.PileBasicInfo;
import com.jsowell.pile.domain.ebike.deviceupload.EBikeMessageCmd20;
import com.jsowell.pile.dto.*;
import com.jsowell.pile.thirdparty.ConnectorInfo;
import com.jsowell.pile.thirdparty.EquipmentInfo;
@@ -221,4 +222,10 @@ public interface PileBasicInfoService {
String startPersonalPileCharging(StartPersonPileDTO dto);
void startupResult(ReservationChargingStartupResult chargingStartupResult);
/**
* 注册电单车桩
* @param message
*/
void registrationEBikePile(EBikeMessageCmd20 message);
}

View File

@@ -1,6 +1,5 @@
package com.jsowell.pile.service.impl;
import com.alibaba.fastjson2.JSON;
import com.google.common.collect.Maps;
import com.jsowell.common.constant.CacheConstants;
import com.jsowell.common.core.redis.RedisCache;
@@ -25,17 +24,22 @@ public class AdapayCallbackRecordServiceImpl implements AdapayCallbackRecordServ
@Autowired
private RedisCache redisCache;
/**
* 接收到支付回调记录保存到数据库
* paymentId添加了唯一约束, 如果存在则报错
* @param callbackRecord
*/
@Override
public void saveAdapayCallbackRecord(AdapayCallbackRecord callbackRecord) {
AdapayCallbackRecord adapayCallbackRecord = selectByPaymentId(callbackRecord.getPaymentId());
if (adapayCallbackRecord != null) {
return;
}
try {
adapayCallbackRecordMapper.insert(callbackRecord);
} catch (Exception e) {
log.error("saveAdapayCallbackRecord:{}, error", JSON.toJSONString(callbackRecord), e);
}
// AdapayCallbackRecord adapayCallbackRecord = selectByPaymentId(callbackRecord.getPaymentId());
// if (adapayCallbackRecord != null) {
// return;
// }
// try {
// } catch (Exception e) {
// log.error("saveAdapayCallbackRecord:{}, error", JSON.toJSONString(callbackRecord), e);
// }
adapayCallbackRecordMapper.insert(callbackRecord);
}
/**

View File

@@ -3872,7 +3872,7 @@ public class OrderBasicInfoServiceImpl implements OrderBasicInfoService {
.payMode(OrderPayRecordEnum.WHITELIST_PAYMENT.getValue())
.payAmount(payAmount)
.acquirer(AcquirerEnum.LOCAL.getValue())
.createBy("system")
.createBy(Constants.SYSTEM)
.createTime(DateUtils.getNowDate())
.delFlag(DelFlagEnum.NORMAL.getValue())
.build();

View File

@@ -11,13 +11,11 @@ import com.jsowell.common.core.domain.ykc.YKCFrameTypeCode;
import com.jsowell.common.core.redis.RedisCache;
import com.jsowell.common.enums.DelFlagEnum;
import com.jsowell.common.enums.lianlian.LianLianPileStatusEnum;
import com.jsowell.common.enums.ykc.PileConnectorDataBaseStatusEnum;
import com.jsowell.common.enums.ykc.PileConnectorStatusEnum;
import com.jsowell.common.enums.ykc.PileStatusEnum;
import com.jsowell.common.enums.ykc.ReturnCodeEnum;
import com.jsowell.common.enums.ykc.*;
import com.jsowell.common.exception.BusinessException;
import com.jsowell.common.util.*;
import com.jsowell.pile.domain.*;
import com.jsowell.pile.domain.ebike.deviceupload.EBikeMessageCmd20;
import com.jsowell.pile.dto.*;
import com.jsowell.pile.mapper.PileBasicInfoMapper;
import com.jsowell.pile.service.*;
@@ -27,6 +25,8 @@ import com.jsowell.pile.thirdparty.ConnectorInfo;
import com.jsowell.pile.thirdparty.EquipmentInfo;
import com.jsowell.pile.thirdparty.ZDLConnectorInfo;
import com.jsowell.pile.thirdparty.ZDLEquipmentInfo;
import com.jsowell.pile.transaction.dto.PileTransactionDTO;
import com.jsowell.pile.transaction.service.TransactionService;
import com.jsowell.pile.util.UserUtils;
import com.jsowell.pile.vo.base.MerchantInfoVO;
import com.jsowell.pile.vo.base.PileInfoVO;
@@ -83,6 +83,9 @@ public class PileBasicInfoServiceImpl implements PileBasicInfoService {
@Autowired
private RedisCache redisCache;
@Autowired
private TransactionService pileTransactionService;
@Value("${baseurl.prefix}")
private String BASE_URL_PREFIX;
@@ -1249,4 +1252,59 @@ public class PileBasicInfoServiceImpl implements PileBasicInfoService {
wxAppletRemoteService.reservationStartupResultSendMsg(memberVO.getOpenId(), startTime, endTime, startUpResult, failReason);
}
}
/**
* 注册电单车桩
* @param message
*/
@Override
public void registrationEBikePile(EBikeMessageCmd20 message) {
// 根据物理id(桩编号)查询桩信息
PileBasicInfo pileBasicInfo = this.selectPileBasicInfoBySN(message.getPhysicalId() + "");
if (pileBasicInfo != null) {
return;
}
List<PileBasicInfo> basicInfoList = Lists.newArrayList();
List<PileConnectorInfo> connectorInfoList = Lists.newArrayList();
// 组装pile_basic_info表数据
PileBasicInfo basicInfo = new PileBasicInfo();
// 桩编号
String sn = message.getPhysicalId() + "";
basicInfo.setSn(sn);
basicInfo.setBusinessType(Constants.ONE); // 经营类型 1-运营桩2-个人桩
basicInfo.setSoftwareProtocol(Constants.THREE); // 软件协议
basicInfo.setMerchantId(Long.valueOf("1")); // 运营商id 默认1
basicInfo.setStationId(Long.valueOf("2")); // 站点id
basicInfo.setModelId(null); // 型号id
basicInfo.setProductionDate(new Date()); // 生产日期
basicInfo.setLicenceId(null); // TODO 证书编号
basicInfo.setSimId(null); // TODO sim卡
basicInfo.setRemark(null); // 备注
basicInfo.setCreateBy(Constants.SYSTEM); // 创建人
basicInfo.setDelFlag(DelFlagEnum.NORMAL.getValue()); // 删除标识
basicInfoList.add(basicInfo);
EBikeMessageCmd20.DeviceRegister deviceRegister = message.getDeviceRegister();
int portNumber = deviceRegister.getPortNumber();
PileConnectorInfo connectorInfo;
for (int i = 1; i < portNumber + 1; i++) {
// 组装pile_connector_info表数据
connectorInfo = new PileConnectorInfo();
connectorInfo.setPileSn(sn); // sn号
String connectorCode = String.format("%1$02d", i);
connectorInfo.setPileConnectorCode(sn + connectorCode); // 枪口号
connectorInfo.setStatus(Constants.ZERO); //状态,默认 0-离网
connectorInfo.setCreateBy(Constants.SYSTEM); // 创建人
connectorInfo.setDelFlag(DelFlagEnum.NORMAL.getValue()); // 删除标识
connectorInfoList.add(connectorInfo);
}
// 批量入库
PileTransactionDTO transactionDTO = PileTransactionDTO.builder()
.pileBasicInfoList(basicInfoList)
.pileConnectorInfoList(connectorInfoList)
.build();
pileTransactionService.doCreatePileTransaction(transactionDTO);
}
}

View File

@@ -455,6 +455,17 @@ public class PileConnectorInfoServiceImpl implements PileConnectorInfoService {
infoVO.setRatedPower(pileModelInfoVO.getRatedPower());
infoVO.setRatedCurrent(pileModelInfoVO.getRatedCurrent());
infoVO.setRatedVoltage(pileModelInfoVO.getRatedVoltage());
String chargePortType;
if (StringUtils.equals(Constants.TWO, pileModelInfoVO.getChargerPileType())) {
chargePortType = Constants.THREE;
} else {
if (StringUtils.equals(Constants.ONE, pileModelInfoVO.getSpeedType())) {
chargePortType = Constants.ONE;
} else {
chargePortType = Constants.TWO;
}
}
infoVO.setChargePortType(chargePortType);
}
connectorInfoList.add(infoVO);
}
@@ -682,14 +693,14 @@ public class PileConnectorInfoServiceImpl implements PileConnectorInfoService {
* @return true离线
*/
public boolean checkPileOffLine(String pileSn) {
// 获取桩最后连接时间,最后连接到平台的时间在1分钟之前,判定为离线
// 获取桩最后连接时间,最后连接到平台的时间在3分钟之前,判定为离线
String lastConnectionTime = redisCache.getCacheObject(CacheConstants.PILE_LAST_CONNECTION + pileSn);
if (StringUtils.isBlank(lastConnectionTime)) {
// 没有最后连接时间,返回离线
return true;
}
long l = DateUtils.intervalTime(lastConnectionTime, DateUtils.getDateTime());
return l >= 1L;
return l > 3L;
}
/**

View File

@@ -5,7 +5,6 @@ import com.jsowell.common.util.DateUtils;
import com.jsowell.common.util.StringUtils;
import com.jsowell.pile.domain.PileMemberRelation;
import com.jsowell.pile.mapper.PileMemberRelationMapper;
import com.jsowell.pile.service.PileConnectorInfoService;
import com.jsowell.pile.service.PileMemberRelationService;
import com.jsowell.pile.vo.uniapp.customer.MemberVO;
import org.springframework.beans.factory.annotation.Autowired;
@@ -24,8 +23,6 @@ public class PileMemberRelationServiceImpl implements PileMemberRelationService
@Autowired
private PileMemberRelationMapper pileMemberRelationMapper;
@Autowired
private PileConnectorInfoService pileConnectorInfoService;
/**
* 查询桩与用户绑定关系
*

View File

@@ -581,7 +581,7 @@ public class PileReservationInfoServiceImpl implements PileReservationInfoServic
pileReservationInfo.setFreq("daily");
pileReservationInfo.setStatus(Constants.ZERO);
pileReservationInfo.setCreateTime(DateUtils.getNowDate());
pileReservationInfo.setCreateBy("system");
pileReservationInfo.setCreateBy(Constants.SYSTEM);
pileReservationInfo.setDelFlag(DelFlagEnum.NORMAL.getValue());
pileReservationInfoMapper.insert(pileReservationInfo);
log.info("未查询到个人桩预约信息, 初始化个人桩预约信息:{}", JSON.toJSONString(pileReservationInfo));

View File

@@ -762,11 +762,13 @@ public abstract class AbstractProgramLogic implements InitializingBean {
// 余额支付最大下发200
BigDecimal defaultAmount = Constants.BALANCE_PAY_MAX_AMOUNT;
if (totalAccountAmount.compareTo(defaultAmount) < 0) {
principalBalancePay = memberVO.getPrincipalBalance();
giftBalancePay = memberVO.getGiftBalance();
// 总余额小于200下发全部余额
principalBalancePay = memberVO.getPrincipalBalance(); // 本金余额全部支付
giftBalancePay = memberVO.getGiftBalance(); // 赠送金额全部支付
} else {
principalBalancePay = defaultAmount.min(memberVO.getPrincipalBalance());
giftBalancePay = defaultAmount.subtract(principalBalancePay);
// 总余额大于200下发200
principalBalancePay = defaultAmount.min(memberVO.getPrincipalBalance()); // 本金余额与200取最小值
giftBalancePay = defaultAmount.subtract(principalBalancePay); // defaultAmount - principalBalancePay 为赠送金支付金额
}
Map<String, BigDecimal> resultMap = Maps.newHashMap();
resultMap.put("principalBalancePay", principalBalancePay);

View File

@@ -46,6 +46,11 @@ public class ConnectorInfoVO {
*/
private String chargingType;
/**
* 充电接口类型 1-快充2-慢充3-电单车
*/
private String chargePortType;
/**
* 额定功率
*/

View File

@@ -60,6 +60,11 @@ public class PileInfoVO {
*/
private String speedType;
/**
* 充电接口类型 1-快充2-慢充3-电单车
*/
private String chargePortType;
/**
* 枪口编号
*/

View File

@@ -11,21 +11,25 @@ import lombok.NoArgsConstructor;
import java.util.List;
/**
* 小程序充电桩详情页VO
* 小程序
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
@Builder
public class PileConnectorVO {
public class AppletPileDetailVO {
// 充电信息列表
// 充电信息
private PileInfoVO pileInfo;
// 充电枪口信息列表
private List<ConnectorInfoVO> connectorInfoList;
// 计费模板信息
// private BillingTemplateVO billingTemplate;
// 充电桩信息
private PileInfoVO pileInfo;
// 运营商信息
private MerchantInfoVO merchantInfo;

View File

@@ -55,5 +55,8 @@ public class PileConnectorDetailVO {
*/
private String softwareProtocol;
/**
* 充电接口类型 1-快充2-慢充3-电单车
*/
private String chargePortType;
}

View File

@@ -132,4 +132,9 @@ public class PileDetailVO {
* 型号名称
*/
private String modelName;
/**
* 充电接口类型 1-快充2-慢充3-电单车
*/
private String chargePortType;
}

View File

@@ -47,7 +47,7 @@ public class PileModelInfoVO {
private String ratedVoltage;
/**
* 充电类型
* 充电类型 1-快充2-慢充)
*/
private String speedType;