修改
1 occ 消息解析资源释放 2生成protobuf设备名称解析 3添加消息处理类 4 删除老版本设备解析
This commit is contained in:
parent
43cd1bffb0
commit
c5cbe04ab8
@ -5,6 +5,7 @@ import io.netty.buffer.Unpooled;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.util.CollectionUtils;
|
||||
|
||||
@Slf4j
|
||||
public class FrameSchema {
|
||||
@ -96,6 +97,33 @@ public class FrameSchema {
|
||||
return messages;
|
||||
}
|
||||
|
||||
public static List<MessageData> decode2(ByteBuf in) throws Exception {
|
||||
in.markReaderIndex();
|
||||
List<FrameSchema> frames = new ArrayList<>();
|
||||
|
||||
frameDecode2(in, frames);
|
||||
if (CollectionUtils.isEmpty(frames)) {
|
||||
in.resetReaderIndex();
|
||||
return null;
|
||||
}
|
||||
ByteBuf buf = Unpooled.buffer();
|
||||
for (FrameSchema frame : frames) {
|
||||
buf.writeBytes(frame.packageData);
|
||||
frame.packageData.release();
|
||||
}
|
||||
try {
|
||||
List<MessageData> messages = new ArrayList<>();
|
||||
messageDecode(buf, messages);
|
||||
return messages;
|
||||
} catch (Exception e) {
|
||||
log.error("OCC消息解析异常", e);
|
||||
return null;
|
||||
} finally {
|
||||
buf.release();
|
||||
}
|
||||
}
|
||||
|
||||
@Deprecated
|
||||
public static List<MessageData> decode(ByteBuf in) throws Exception {
|
||||
in.markReaderIndex();
|
||||
boolean success = true;
|
||||
@ -103,16 +131,21 @@ public class FrameSchema {
|
||||
List<FrameSchema> frames = new ArrayList<>();
|
||||
frameDecode(in, frames);
|
||||
if (frames.size() > 0) {
|
||||
//拼装数据包
|
||||
ByteBuf buf = Unpooled.buffer();
|
||||
for (FrameSchema frame : frames) {
|
||||
buf.writeBytes(frame.packageData);
|
||||
frame.packageData.release();
|
||||
}
|
||||
//数据包解析业务
|
||||
List<MessageData> messages = new ArrayList<>();
|
||||
try {
|
||||
messageDecode(buf, messages);
|
||||
} catch (Exception e) {
|
||||
log.error("OCC消息解析异常", e);
|
||||
return null;
|
||||
} finally {
|
||||
buf.release();
|
||||
}
|
||||
return messages;
|
||||
} else {
|
||||
@ -138,7 +171,10 @@ public class FrameSchema {
|
||||
*/
|
||||
private static void messageDecode(ByteBuf buf, List<MessageData> messages) throws Exception {
|
||||
int len = buf.getUnsignedShort(0);
|
||||
ByteBuf msgBuf = buf.readBytes(len + 2);
|
||||
byte[] msgData = new byte[len + 2];
|
||||
buf.readBytes(msgData);
|
||||
ByteBuf msgBuf = Unpooled.wrappedBuffer(msgData);
|
||||
// ByteBuf msgBuf = buf.readBytes(len + 2);
|
||||
int msgId = msgBuf.getUnsignedShort(8);
|
||||
MessageId messageId = MessageId.of(msgId);
|
||||
if (messageId.equals(MessageId.UNKNOWN)) {
|
||||
@ -164,6 +200,7 @@ public class FrameSchema {
|
||||
* @param frames
|
||||
* @throws Exception
|
||||
*/
|
||||
@Deprecated
|
||||
static void frameDecode(ByteBuf in, List<FrameSchema> frames) throws Exception {
|
||||
if (in.readableBytes() < 4) {
|
||||
throw new Exception("数据不全");
|
||||
@ -172,8 +209,9 @@ public class FrameSchema {
|
||||
int totalLength = in.readUnsignedShort();
|
||||
short flag = in.readUnsignedByte();
|
||||
int contentLen = totalLength - 1;
|
||||
if (in.readableBytes() < contentLen) {
|
||||
throw new Exception("可读内容不足");
|
||||
int readables = in.readableBytes();
|
||||
if (readables < contentLen) {
|
||||
throw new Exception(String.format("可读内容不足 sysId[%s] totalLen[%s] flag[%s] contentLen[%s] readableBytes[%s]", sysId, totalLength, flag, contentLen, readables));
|
||||
}
|
||||
frames.add(new FrameSchema(sysId, in.readBytes(contentLen)));
|
||||
if (flag == Flag_Multi) {
|
||||
@ -181,6 +219,39 @@ public class FrameSchema {
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 信息帧解析
|
||||
*
|
||||
* @param in
|
||||
* @param frames
|
||||
*/
|
||||
static void frameDecode2(ByteBuf in, List<FrameSchema> frames) {
|
||||
int totalReadables = in.readableBytes();
|
||||
if (totalReadables < 4) {
|
||||
log.error("数据不全,当前可读[{}]", totalReadables);
|
||||
frames.clear();
|
||||
return;
|
||||
}
|
||||
short sysId = in.readUnsignedByte();
|
||||
int totalLength = in.readUnsignedShort();
|
||||
short flag = in.readUnsignedByte();
|
||||
int contentLen = totalLength - 1;
|
||||
int readables = in.readableBytes();
|
||||
if (readables < contentLen) {
|
||||
log.error("可读内容不足 sysId[{}] totalLen[{}] flag[{}] contentLen[{}] readableBytes[{}]", sysId, totalLength, flag, contentLen, readables);
|
||||
frames.clear();
|
||||
return;
|
||||
}
|
||||
|
||||
ByteBuf contentByte = Unpooled.buffer(contentLen);
|
||||
in.readBytes(contentByte);
|
||||
// frames.add(new FrameSchema(sysId, in.readBytes(contentLen)));
|
||||
frames.add(new FrameSchema(sysId, contentByte));
|
||||
if (flag == Flag_Multi) {
|
||||
frameDecode2(in, frames);
|
||||
}
|
||||
}
|
||||
|
||||
public void encode(ByteBuf buf) {
|
||||
buf.writeByte(this.systemId);
|
||||
buf.writeShort(this.totalLength);
|
||||
|
@ -68,7 +68,9 @@ public abstract class MessageData {
|
||||
this.version = buf.readUnsignedShort();
|
||||
this.msgId = MessageId.of(buf.readShort());
|
||||
this.decode2(buf);
|
||||
buf.release();
|
||||
} else {
|
||||
buf.release();
|
||||
throw new Exception(
|
||||
String.format("OCC消息可读字节数小于%s:readableBytes=%s", headerBytes, readableBytes));
|
||||
}
|
||||
|
@ -20,15 +20,14 @@ public class OccMessageDecoder extends ByteToMessageDecoder {
|
||||
@Override
|
||||
protected void decode(ChannelHandlerContext ctx, ByteBuf in, List<Object> out) throws Exception {
|
||||
connection.lastReceiveMessageTime = System.currentTimeMillis();
|
||||
List<MessageData> messages = FrameSchema.decode(in);
|
||||
List<MessageData> messages = FrameSchema.decode2(in);
|
||||
if (!(messages == null || messages.size() == 0)) {
|
||||
System.out.println(
|
||||
String.format(
|
||||
"收到OCC消息: %s",
|
||||
JSON.toJSONString(
|
||||
messages.get(0), Feature.PrettyFormat, Feature.FieldBased, Feature.WriteNulls)));
|
||||
MockAppContext.publish(messages);
|
||||
DeviceStatusConvertorManager.doConvertor(messages);
|
||||
|
||||
out.add(messages);
|
||||
}
|
||||
}
|
||||
|
@ -0,0 +1,25 @@
|
||||
package club.joylink.xiannccda.ats.message;
|
||||
|
||||
import club.joylink.xiannccda.ats.message.collect.DeviceStatusConvertorManager;
|
||||
import club.joylink.xiannccda.mock.message.MockAppContext;
|
||||
import io.netty.channel.ChannelHandlerContext;
|
||||
import io.netty.channel.SimpleChannelInboundHandler;
|
||||
import io.netty.util.ReferenceCountUtil;
|
||||
import java.util.Collections;
|
||||
import java.util.List;
|
||||
import org.springframework.util.CollectionUtils;
|
||||
|
||||
public class OccMessageHandler extends SimpleChannelInboundHandler<List<MessageData>> {
|
||||
|
||||
@Override
|
||||
protected void channelRead0(ChannelHandlerContext ctx, List<MessageData> msg) throws Exception {
|
||||
if (CollectionUtils.isEmpty(msg)) {
|
||||
ReferenceCountUtil.release(msg);
|
||||
return;
|
||||
|
||||
}
|
||||
MockAppContext.publish(msg);
|
||||
DeviceStatusConvertorManager.doConvertor(msg);
|
||||
}
|
||||
|
||||
}
|
@ -58,6 +58,7 @@ public class OccTcpClientConnection {
|
||||
protected void initChannel(Channel ch) {
|
||||
ch.pipeline().addLast(new OccMessageEncoder(self));
|
||||
ch.pipeline().addLast(new OccMessageDecoder(self));
|
||||
ch.pipeline().addLast(new OccMessageHandler());
|
||||
}
|
||||
});
|
||||
|
||||
|
@ -1,108 +0,0 @@
|
||||
package club.joylink.xiannccda.ats.message.line3;
|
||||
|
||||
import club.joylink.xiannccda.ats.message.line3.device.DeviceType;
|
||||
import club.joylink.xiannccda.dto.protos.LayoutGraphicsProto;
|
||||
import club.joylink.xiannccda.dto.protos.LayoutGraphicsProto.RtssGraphicStorage;
|
||||
import club.joylink.xiannccda.dto.protos.LayoutGraphicsProto.Section;
|
||||
import club.joylink.xiannccda.dto.protos.LayoutGraphicsProto.Signal;
|
||||
import club.joylink.xiannccda.dto.protos.LayoutGraphicsProto.Turnout;
|
||||
import com.google.common.collect.Maps;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Objects;
|
||||
|
||||
@Deprecated
|
||||
public abstract class DeviceNameChanger implements NameChanger {
|
||||
|
||||
|
||||
static Map<DeviceType, DeviceNameChanger> NCC_DEVICE_TYPE_NAME_MAPPER = Maps.newHashMap();
|
||||
|
||||
static {
|
||||
NCC_DEVICE_TYPE_NAME_MAPPER.put(DeviceType.DEVICE_TYPE_SWITCH, new SwitchDevice());
|
||||
NCC_DEVICE_TYPE_NAME_MAPPER.put(DeviceType.DEVICE_TYPE_SIGNAL, new SignalDevice());
|
||||
NCC_DEVICE_TYPE_NAME_MAPPER.put(DeviceType.DEVICE_TYPE_TRACK, new TrackDevice());
|
||||
}
|
||||
|
||||
private final static Map<DeviceType, List<String>> DEVICE_NAMES = Maps.newHashMap();
|
||||
|
||||
|
||||
public static void init(LayoutGraphicsProto.RtssGraphicStorage gs) {
|
||||
for (DeviceNameChanger value : NCC_DEVICE_TYPE_NAME_MAPPER.values()) {
|
||||
value.collectNames(gs);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static String findMatch(DeviceType dt, String name) {
|
||||
DeviceNameChanger nameChanger = NCC_DEVICE_TYPE_NAME_MAPPER.get(dt);
|
||||
if (Objects.nonNull(nameChanger)) {
|
||||
List<String> deviceNames = DEVICE_NAMES.get(dt);
|
||||
nameChanger.changeDeviceName(name, deviceNames);
|
||||
}
|
||||
return name;
|
||||
}
|
||||
|
||||
public static void main(String[] args) {
|
||||
// X1506_L2
|
||||
new TrackDevice().changeDeviceName("TP_2DG", List.of("P_2DG"));
|
||||
new SignalDevice().changeDeviceName("X1506_L2", List.of("X1506-L2"));
|
||||
}
|
||||
|
||||
public static class SwitchDevice extends DeviceNameChanger {
|
||||
|
||||
@Override
|
||||
public void collectNames(RtssGraphicStorage graphicStorage) {
|
||||
List<String> names = graphicStorage.getTurnoutsList().stream().map(Turnout::getCode).toList();
|
||||
DEVICE_NAMES.put(DeviceType.DEVICE_TYPE_SWITCH, names);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String changeDeviceName(String nccDeviceName, List<String> graphicNames) {
|
||||
if (nccDeviceName.length() < 3) {
|
||||
return nccDeviceName;
|
||||
}
|
||||
|
||||
String started = nccDeviceName.substring(0, 1);
|
||||
String head = nccDeviceName.substring(1, 3);
|
||||
String tail = nccDeviceName.substring(4);
|
||||
return started + tail + head;
|
||||
}
|
||||
}
|
||||
|
||||
public static class TrackDevice extends DeviceNameChanger {
|
||||
|
||||
|
||||
@Override
|
||||
public void collectNames(RtssGraphicStorage graphicStorage) {
|
||||
List<String> names = graphicStorage.getSectionList().stream().map(Section::getCode).toList();
|
||||
DEVICE_NAMES.put(DeviceType.DEVICE_TYPE_TRACK, names);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String changeDeviceName(String nccDeviceName, List<String> graphicNames) {
|
||||
if (nccDeviceName.length() < 4) {
|
||||
return nccDeviceName;
|
||||
}
|
||||
return super.changeDeviceName(nccDeviceName, graphicNames);
|
||||
}
|
||||
}
|
||||
|
||||
public static class SignalDevice extends DeviceNameChanger {
|
||||
|
||||
@Override
|
||||
public void collectNames(RtssGraphicStorage graphicStorage) {
|
||||
List<String> names = graphicStorage.getSignalsList().stream().map(Signal::getCode).toList();
|
||||
DEVICE_NAMES.put(DeviceType.DEVICE_TYPE_SIGNAL, names);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String changeDeviceName(String nccDeviceName, List<String> graphicNames) {
|
||||
if (nccDeviceName.length() <= 3) {
|
||||
return nccDeviceName;
|
||||
}
|
||||
return super.changeDeviceName(nccDeviceName.replaceAll("_", "-"), graphicNames);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -27,9 +27,17 @@ public class DeviceNameChangerManage {
|
||||
final static Table<Integer, DeviceType, List<NameChangerFilter>> CHANGER_TABLE = HashBasedTable.create();
|
||||
|
||||
public static String findMatch(DeviceType deviceType, String occName) {
|
||||
if (Objects.isNull(deviceType)) {
|
||||
log.error("错误的设备类型 type[{}]", deviceType);
|
||||
return occName;
|
||||
}
|
||||
if (Objects.isNull(occName)) {
|
||||
log.error("错误的设备名称 occName[{}]", occName);
|
||||
return occName;
|
||||
}
|
||||
List<NameChangerFilter> filters = CHANGER_TABLE.get(3, deviceType);
|
||||
if (CollectionUtils.isEmpty(filters)) {
|
||||
log.error("未找到对应的转换的occName:[{}] debiceType[{}]", occName, deviceType);
|
||||
log.error("未找到对应的转换的occName:[{}] deviceType[{}]", occName, deviceType);
|
||||
return occName;
|
||||
}
|
||||
for (NameChangerFilter filter : filters) {
|
||||
@ -38,7 +46,7 @@ public class DeviceNameChangerManage {
|
||||
return newName;
|
||||
}
|
||||
}
|
||||
log.error("不能转换的occName:[{}] debiceType[{}]", occName, deviceType);
|
||||
log.error("不能转换的occName:[{}] deviceType[{}]", occName, deviceType);
|
||||
return occName;
|
||||
}
|
||||
|
||||
|
@ -72,8 +72,9 @@ public class DeviceStatusBitmapResponse extends MessageResponse {
|
||||
DeviceType dt = deviceTypeEntity.getType();
|
||||
for (DeviceEntity deviceEntity : deviceTypeEntity.deviceList) {
|
||||
GeneratedMessageV3.Builder builder = DeviceStatusConvertor.convert(dt, deviceEntity.status);
|
||||
|
||||
DeviceStatusConvertor.fillField(builder, "id", deviceEntity.devName);
|
||||
// DeviceStatusConvertor.fillField(builder, "id", deviceEntity.devName);
|
||||
String newOccName = DeviceNameChangerManage.findMatch(dt, deviceEntity.devName);
|
||||
DeviceStatusConvertor.fillField(builder, "id", newOccName);
|
||||
DeviceStatusConvertor.convertForTrack(deviceEntity.getStatus(), builder);
|
||||
DeviceStatusConvertor.convertForPlatform(deviceEntity.getStatus(), (Objects.isNull(deviceEntity.getSpare()) ? 0 : deviceEntity.getSpare()), builder);
|
||||
DeviceStatusConvertor.convertForSwitch(Objects.isNull(deviceEntity.getSpare()) ? 0 : deviceEntity.getSpare(), builder);
|
||||
@ -117,9 +118,9 @@ public class DeviceStatusBitmapResponse extends MessageResponse {
|
||||
entity.type = DeviceType.of(buf.readShort());
|
||||
entity.objCount = buf.readShort();
|
||||
entity.deviceList = EntityParseUtil.collect(entity.objCount, buf, DeviceEntity.class);
|
||||
for (DeviceEntity de : entity.deviceList) {
|
||||
/* for (DeviceEntity de : entity.deviceList) {
|
||||
de.devName = DeviceNameChangerManage.findMatch(entity.type, de.devName);
|
||||
}
|
||||
}*/
|
||||
return entity;
|
||||
}
|
||||
}
|
||||
|
@ -82,14 +82,15 @@ public class DeviceStatusChangeResponse extends MessageResponse {
|
||||
this.devName = EntityParseUtil.convertStr(buf, 24);
|
||||
this.deviceStatus = buf.readInt();
|
||||
this.spare = buf.readInt();
|
||||
this.devName = DeviceNameChangerManage.findMatch(this.type, this.devName);
|
||||
// this.devName = DeviceNameChangerManage.findMatch(this.type, this.devName);
|
||||
}
|
||||
|
||||
@Override
|
||||
public List<Builder> generateProto() {
|
||||
GeneratedMessageV3.Builder builder = DeviceStatusConvertor.convert(this.type, this.deviceStatus);
|
||||
|
||||
DeviceStatusConvertor.fillField(builder, "id", this.devName);
|
||||
// DeviceStatusConvertor.fillField(builder, "id", this.devName);
|
||||
String occName = DeviceNameChangerManage.findMatch(this.type, this.devName);
|
||||
DeviceStatusConvertor.fillField(builder, "id", occName);
|
||||
DeviceStatusConvertor.convertForTrack(this.deviceStatus, builder);
|
||||
DeviceStatusConvertor.convertForPlatform(this.deviceStatus, Objects.isNull(this.spare) ? 0 : this.spare, builder);
|
||||
DeviceStatusConvertor.convertForSwitch(Objects.isNull(this.spare) ? 0 : this.spare, builder);
|
||||
|
@ -71,8 +71,11 @@ public class TrainIndicationInitResponse extends MessageResponse {
|
||||
builder.setWindow(window);
|
||||
if (trainCell.getDevType() != null) {
|
||||
builder.setDevType(DeviceStatusProto.DeviceType.forNumber(trainCell.getDevType().getVal()));
|
||||
|
||||
}
|
||||
builder.setDevName(StringUtils.defaultString(trainCell.getDevName(), ""));
|
||||
// builder.setDevName(StringUtils.defaultString(trainCell.getDevName(), ""));
|
||||
String occName = DeviceNameChangerManage.findMatch(trainCell.getDevType(), trainCell.getDevName());
|
||||
builder.setDevName(occName);
|
||||
|
||||
builder.setTrainIndex(StringUtils.defaultString(trainCell.getTrainIndex(), ""));
|
||||
builder.setGroupId(StringUtils.defaultString(trainCell.getGroupId(), ""));
|
||||
@ -225,7 +228,7 @@ public class TrainIndicationInitResponse extends MessageResponse {
|
||||
this.devType = DeviceType.of(devType);
|
||||
this.devName = new String(devName, MessageCons.STRING_CHARSET).trim();
|
||||
|
||||
this.devName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
// this.devName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
this.trainIndex = new String(trainIndex, MessageCons.STRING_CHARSET).trim();
|
||||
this.groupId = new String(groupId, MessageCons.STRING_CHARSET).trim();
|
||||
this.trainId = new String(trainId, MessageCons.STRING_CHARSET).trim();
|
||||
|
@ -73,7 +73,7 @@ public class TrainIndicationRemoveResponse extends MessageResponse {
|
||||
//
|
||||
this.devType = DeviceType.of(devType);
|
||||
this.devName = new String(devName, MessageCons.STRING_CHARSET).trim();
|
||||
this.devName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
// this.devName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
this.trainIndex = new String(trainIndex, MessageCons.STRING_CHARSET).trim();
|
||||
this.groupId = new String(groupId, MessageCons.STRING_CHARSET).trim();
|
||||
}
|
||||
@ -98,7 +98,9 @@ public class TrainIndicationRemoveResponse extends MessageResponse {
|
||||
if (Objects.nonNull(this.devType)) {
|
||||
trainRemove.setDeviceType(DeviceStatusProto.DeviceType.forNumber(this.devType.getVal()));
|
||||
}
|
||||
trainRemove.setDevName(StringUtils.defaultString(this.devName, ""));
|
||||
// trainRemove.setDevName(StringUtils.defaultString(this.devName, ""));
|
||||
String occName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
trainRemove.setDevName(occName);
|
||||
trainRemove.setTrainIndex(StringUtils.defaultString(this.trainIndex, ""));
|
||||
trainRemove.setGroupId(StringUtils.defaultString(this.groupId, ""));
|
||||
|
||||
|
@ -144,8 +144,9 @@ public class TrainIndicationUpdateResponse extends MessageResponse {
|
||||
if (Objects.nonNull(this.devType)) {
|
||||
train.setDevType(DeviceStatusProto.DeviceType.forNumber(this.devType.getVal()));
|
||||
}
|
||||
train.setDevName(StringUtils.defaultString(this.devName, ""));
|
||||
|
||||
// train.setDevName(StringUtils.defaultString(this.devName, ""));
|
||||
String occName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
train.setDevName(occName);
|
||||
train.setTrainIndex(StringUtils.defaultString(this.trainIndex, ""));
|
||||
train.setRollingStock(this.getRollingStock());
|
||||
train.setOtpTime(this.optTime);
|
||||
@ -213,7 +214,7 @@ public class TrainIndicationUpdateResponse extends MessageResponse {
|
||||
this.devType = DeviceType.of(devType);
|
||||
this.devName = new String(devName, MessageCons.STRING_CHARSET).trim();
|
||||
|
||||
this.devName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
// this.devName = DeviceNameChangerManage.findMatch(this.devType, this.devName);
|
||||
this.trainIndex = new String(trainIndex, MessageCons.STRING_CHARSET).trim();
|
||||
this.groupId = new String(groupId, MessageCons.STRING_CHARSET).trim();
|
||||
this.trainId = new String(trainId, MessageCons.STRING_CHARSET).trim();
|
||||
|
Loading…
Reference in New Issue
Block a user