通过自定义 解码器来实现 不固定长度 固定帧头和帧尾的报文
public class FixedHeaderTailDecoder extends ByteToMessageDecoder {
private static final short START_DELIMITER = (short) 0x4040;
private static final short END_DELIMITER = (short) 0x2323;
private enum State {
WAIT_START,
COLLECTING
}
private State currentState = State.WAIT_START;
private int startIndex = -1;
@Override
protected void decode(ChannelHandlerContext ctx, ByteBuf in, List<Object> out) {
while (in.readableBytes() >= 2) {
switch (currentState) {
case WAIT_START:
if (in.getShort(in.readerIndex()) == START_DELIMITER) {
startIndex = in.readerIndex();
currentState = State.COLLECTING;
}
in.skipBytes(1);
break;
case COLLECTING:
if (in.getShort(in.readerIndex()) == END_DELIMITER) {
int endIndex = in.readerIndex() + 2;
int length = endIndex - startIndex;
ByteBuf completeMessage = in.retainedSlice(startIndex, length);
out.add(completeMessage);
in.readerIndex(endIndex);
currentState = State.WAIT_START;
startIndex = -1;
} else {
in.skipBytes(1);
}
break;
}
}
}
@Override
protected void handlerRemoved0(ChannelHandlerContext ctx) throws Exception {
resetState();
super.handlerRemoved0(ctx);
}
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) {
resetState();
ctx.fireExceptionCaught(cause);
}
private void resetState() {
currentState = State.WAIT_START;
startIndex = -1;
}
}