Coder Social home page Coder Social logo

hylexus / jt-framework Goto Github PK

View Code? Open in Web Editor NEW
330.0 19.0 114.0 20.34 MB

基于Spring-Boot的JT-808协议服务端

Home Page: https://hylexus.github.io/jt-framework/

Java 96.57% JavaScript 0.02% Shell 0.02% HTML 0.05% Vue 2.48% TypeScript 0.74% SCSS 0.11%
jt-808 808 808-protocol jt-framework

jt-framework's People

Contributors

anotherme17 avatar dependabot[bot] avatar dferic avatar hylexus avatar pruidong avatar smile-forever avatar tandajian avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

jt-framework's Issues

准备把Gradle升级到7.3.3,报错

准备把Gradle升级到7.3.3,报错:

  • What went wrong:
    A problem occurred evaluating script.

Failed to apply plugin 'propdeps-maven'.
Could not create plugin of type 'PropDepsMavenPlugin'.
> Could not generate a decorated class for type PropDepsMavenPlugin.
> org/gradle/api/artifacts/maven/PomFilterContainer

在网上找propdeps-maven这个插件的资料也没有.

已经修改了两个地方:

  1. 项目根目录中build.gradle:

中的

id 'maven'

已经被修改为: id 'maven-publish'

  1. build-script\script\common-java-env-config.gradle中:

apply plugin: 'maven'

已经修改为:

apply plugin: 'maven-publish'

反转义功能异常

反转义功能异常

7E00020000978290002147029E7D017E
反转义之后最后的01没有除去。

优化建议
image

不支持2019版的消息应答?

jt-framework/jt-808-server-support/src/main/java/io/github/hylexus/jt808/codec/Encoder.java
这里下发给设备时,14和15位是0,没有版本标识
image

报文解析数据丢失问题

报文解析拓展属性数据丢失问题

msgBody 类对象Extra拓展属性丢失问题。

对象中没有E3 还有F3也无法获取到值。
debug时候 循环是能取到 E3 还有F3的值的。貌似没有set到对象中。 附件是我的 LocationUploadRequestMsgBody 类

请求报文样例:

7E020000C705019500000200B700000000000410000157B48906CA55BE00400000000020030400010401040000000002020000030200002504000000002A0200002B040000000030011E310108E306006404EC0199F37D010002020000000302000000040231380005040000000000060200000007020000000801000009020000000B020000000C020000000D020000000E0100000F0100005204000000000100020000010104000000000102020000010304000000000104020000010C020000010D020000010E020000010F02FFD801100204EE1B7E

LocationUploadRequestMsgBody 类

package com.ivyb2b.cesp.iot.entity.req;

import io.github.hylexus.jt.annotation.msg.req.Jt808ReqMsgBody;
import io.github.hylexus.jt.annotation.msg.req.basic.BasicField;
import io.github.hylexus.jt.annotation.msg.req.extra.ExtraField;
import io.github.hylexus.jt.annotation.msg.req.extra.ExtraMsgBody;
import io.github.hylexus.jt.annotation.msg.req.slice.SlicedFrom;
import io.github.hylexus.jt.annotation.msg.req.slice.SplittableField;
import io.github.hylexus.jt.data.converter.req.entity.LngLatReqMsgFieldConverter;
import io.github.hylexus.jt808.msg.RequestMsgBody;
import io.github.hylexus.jt808.msg.RequestMsgMetadata;
import io.github.hylexus.jt808.support.entity.scan.RequestMsgMetadataAware;
import lombok.Data;
import lombok.ToString;
import lombok.experimental.Accessors;

import static io.github.hylexus.jt.data.MsgDataType.*;

/**
 * @author hylexus
 * Created At 2020-01-29 12:03 下午
 */
@Data
@Accessors(chain = true)
@Jt808ReqMsgBody(msgType = 0x0200)
public class LocationUploadRequestMsgBody implements RequestMsgBody, RequestMsgMetadataAware {

    @ToString.Exclude
    private RequestMsgMetadata requestMsgMetadata;

    @Override
    public void setRequestMsgMetadata(RequestMsgMetadata metadata) {
        this.requestMsgMetadata = metadata;
    }

    // 报警标志
    @BasicField(startIndex = 0, dataType = DWORD)
    private int alarmFlag;

    // 状态
    @BasicField(startIndex = 4, dataType = DWORD)
    @SplittableField(splitPropertyValueIntoNestedBeanField = "statusInfo")
    private int status;

    private LocationUploadStatus statusInfo;

    @BasicField(startIndex = 4, dataType = BYTES, length = 4)
    private byte[] statusBytes;

    // 将上面的 status 字段的第0位取出转为 int 类型
    @SlicedFrom(sourceFieldName = "status", bitIndex = 0)
    private int accIntStatus;

    // 将上面的 status 字段的第0位取出转为 boolean 类型
    @SlicedFrom(sourceFieldName = "status", bitIndex = 0)
    private Boolean accBooleanStatus;

    // 0 北纬;1 南纬
    // 将上面的 status 字段的第2位取出转为 int 类型
    @SlicedFrom(sourceFieldName = "status", bitIndex = 2)
    private int latType;

    // 纬度(尚未除以 10^6)
    @BasicField(startIndex = 8, dataType = DWORD)
    private Integer intLat;
    // 纬度(使用转换器除以10^6转为Double类型)
    @BasicField(startIndex = 8, dataType = DWORD, customerDataTypeConverterClass = LngLatReqMsgFieldConverter.class)
    private Double lat;

    // 经度(尚未除以 10^6)
    @BasicField(startIndex = 12, dataType = DWORD)
    private Integer intLng;
    // 经度(使用转换器除以10^6转为Double类型)
    @BasicField(startIndex = 12, dataType = DWORD, customerDataTypeConverterClass = LngLatReqMsgFieldConverter.class)
    private Double lng;

    // 高度
    @BasicField(startIndex = 16, dataType = WORD)
    private Integer height;

    // 速度
    @BasicField(startIndex = 18, dataType = WORD)
    private int speed;

    // 方向
    @BasicField(startIndex = 20, dataType = WORD)
    private Integer direction;

    @BasicField(startIndex = 22, dataType = BCD, length = 6)
    private String time;

    @ExtraField(
            // 消息体中第28字节开始
            startIndex = 28,
            // 附加项长度用getExtraInfoLength返回值表示
            byteCountMethod = "getExtraInfoLength"
    )
    private ExtraInfo extraInfo;

    public int getExtraInfoLength() {
        int totalLength = this.requestMsgMetadata.getHeader().getMsgBodyLength();
        return totalLength - 28;
    }

    @Data
    // 切记@ExtraMsgBody注解不能丢
    @ExtraMsgBody(
            byteCountOfMsgId = 1, // 消息Id用1个字节表示
            byteCountOfContentLength = 1 // 附加项长度字段用1个字节表示
    )
    public static class ExtraInfo {
        @ExtraField.NestedFieldMapping(msgId = 0x01, dataType = DWORD)
        private int field0x01;

        @ExtraField.NestedFieldMapping(msgId = 0x02, dataType = WORD)
        private int field0x02;

        @ExtraField.NestedFieldMapping(msgId = 0x03, dataType = WORD)
        private int field0x03;

        @ExtraField.NestedFieldMapping(msgId = 0x25, dataType = DWORD)
        private int field0x25;

        @ExtraField.NestedFieldMapping(msgId = 0x2A, dataType = WORD)
        private int field0x2A;

        @ExtraField.NestedFieldMapping(msgId = 0x2B, dataType = DWORD)
        private int field0x2B;

        @ExtraField.NestedFieldMapping(msgId = 0x30, dataType = BYTE)
        private byte field0x30;

        @ExtraField.NestedFieldMapping(msgId = 0x31, dataType = BYTE)
        private byte field0x31;

        @ExtraField.NestedFieldMapping(msgId = 0xE3, dataType = BCD)
        private String field0xE3;

        @ExtraField.NestedFieldMapping(msgId = 0xF3, dataType = BYTES,isNestedExtraField=true)
        private DrivingData drivingData;

//        @ExtraField.NestedFieldMapping(msgId = 0xD1, dataType = BYTE)
//        private int field0xD1;
//
//        @ExtraField.NestedFieldMapping(msgId = 0xD2, dataType = BYTE)
//        private int field0xD2;
//
//        @ExtraField.NestedFieldMapping(msgId = 0xD3, dataType = WORD)
//        private int field0xD3;
//
//        @ExtraField.NestedFieldMapping(msgId = 0xD4, dataType = WORD)
//        private int field0xD4;
//
//        @ExtraField.NestedFieldMapping(msgId = 0xD5, dataType = WORD)
//        private int field0xD5;
//
//        @ExtraField.NestedFieldMapping(msgId = 0xD6, dataType = BYTES)
//        private byte field0xD6;
    }

    @Data
    // 切记@ExtraMsgBody注解不能丢
    @ExtraMsgBody(
            byteCountOfMsgId = 2, // 消息Id用1个字节表示
            byteCountOfContentLength = 1 // 附加项长度字段用1个字节表示
    )
    public static class DrivingData{
        @ExtraField.NestedFieldMapping(msgId = 0x0002, dataType = WORD)
        private int field0x0002;

        @ExtraField.NestedFieldMapping(msgId = 0x0003, dataType = WORD)
        private int field0x0003;

        @ExtraField.NestedFieldMapping(msgId = 0x0004, dataType = WORD)
        private int field0x0004;

        @ExtraField.NestedFieldMapping(msgId = 0x0005, dataType = DWORD)
        private int field0x0005;
        @ExtraField.NestedFieldMapping(msgId = 0x0006, dataType = WORD)
        private int field0x0006;
        @ExtraField.NestedFieldMapping(msgId = 0x0007, dataType = WORD)
        private int field0x0007;
        @ExtraField.NestedFieldMapping(msgId = 0x0008, dataType = BYTE)
        private int field0x0008;
        @ExtraField.NestedFieldMapping(msgId = 0x0009, dataType = WORD)
        private int field0x0009;
        @ExtraField.NestedFieldMapping(msgId = 0x000B, dataType = WORD)
        private int field0x000B;
        @ExtraField.NestedFieldMapping(msgId = 0x000C, dataType = WORD)
        private int field0x000C;
        @ExtraField.NestedFieldMapping(msgId = 0x000D, dataType = WORD)
        private int field0x000D;
        @ExtraField.NestedFieldMapping(msgId = 0x000E, dataType = BYTE)
        private int field0x000E;
        @ExtraField.NestedFieldMapping(msgId = 0x000F, dataType = BYTE)
        private int field0x000F;
        @ExtraField.NestedFieldMapping(msgId = 0x0052, dataType = DWORD)
        private int field0x0052;

        @ExtraField.NestedFieldMapping(msgId = 0x0100, dataType = WORD)
        private int field0x0100;
        @ExtraField.NestedFieldMapping(msgId = 0x0101, dataType = DWORD)
        private int field0x0101;
        @ExtraField.NestedFieldMapping(msgId = 0x0102, dataType = WORD)
        private int field0x0102;
        @ExtraField.NestedFieldMapping(msgId = 0x0103, dataType = DWORD)
        private int field0x0103;
        @ExtraField.NestedFieldMapping(msgId = 0x0104, dataType = WORD)
        private int field0x0104;
        @ExtraField.NestedFieldMapping(msgId = 0x010C, dataType = WORD)
        private int field0x010C;
        @ExtraField.NestedFieldMapping(msgId = 0x010D, dataType = WORD)
        private int field0x010D;
        @ExtraField.NestedFieldMapping(msgId = 0x010E, dataType = WORD)
        private int field0x010E;
        @ExtraField.NestedFieldMapping(msgId = 0x010F, dataType = WORD)
        private int field0x010F;
        @ExtraField.NestedFieldMapping(msgId = 0x0110, dataType = WORD)
        private int field0x0110;


    }


    @Data
    public static class LocationUploadStatus {
        @SplittableField.BitAt(bitIndex = 0)
        private boolean accStatus; // acc开?
        @SplittableField.BitAt(bitIndex = 1)
        private int bit1; //1:定位, 0:未定义
        @SplittableField.BitAt(bitIndex = 2)
        private Boolean isSouthLat;// 是否南纬?
        @SplittableField.BitAt(bitIndex = 3)
        private Integer lngType;
        // 将第0位和第1位同时取出并转为int
        // 在此处无实际意义,只是演示可以这么使用
        @SplittableField.BitAtRange(startIndex = 0, endIndex = 1)
        private int bit0to1;
    }
}

编码问题,没有对 0x7d 转为0x7d 0x01

image

package io.github.hylexus.jt.utils;

import io.github.hylexus.jt.config.JtProtocolConstant;
import io.github.hylexus.jt.exception.MsgEscapeException;
import io.github.hylexus.oaks.utils.Bytes;
import io.netty.buffer.ByteBuf;
import lombok.extern.slf4j.Slf4j;

import java.io.ByteArrayOutputStream;
import java.io.IOException;

/**
 * @author hylexus
 * createdAt 2019/1/28
 **/
@Slf4j
public class ProtocolUtils {

    public static byte calculateCheckSum4Jt808(byte[] bs, int start, int end) {
        byte sum = bs[start];
        for (int i = start + 1; i < end; i++) {
            sum ^= bs[i];
        }
        return sum;
    }

    public static byte[] doEscape4ReceiveJt808Msg(byte[] bs, int start, int end) throws Exception {
        if (start < 0 || end > bs.length) {
            throw new ArrayIndexOutOfBoundsException("doEscape4Receive error : index out of bounds(start=" + start
                    + ",end=" + end + ",bytes length=" + bs.length + ")");
        }
        try (ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
            int i = 0;
            for (; i < start; i++) {
                outputStream.write(bs[i]);
            }
            // 最后一个字节不应该是7d,否则就是编码错误
            for (; i < end - 1; i++) {
                if (bs[i] == 0x7d && bs[i + 1] == 0x01) {
                    outputStream.write(0x7d);
                    i++;
                } else if (bs[i] == 0x7d && bs[i + 1] == 0x02) {
                    outputStream.write(0x7e);
                    i++;
                } else {
                    outputStream.write(bs[i]);
                }
            }

            // https://github.com/hylexus/jt-framework/issues/17
            for (; i < bs.length; i++) {
                outputStream.write(bs[i]);
            }
            return outputStream.toByteArray();
        } catch (IOException e) {
            throw new MsgEscapeException(e);
        }
    }

    public static byte[] doEscape4SendJt808Msg(byte[] bs, int start, int end) throws IOException {
        if (start < 0 || end > bs.length) {
            throw new ArrayIndexOutOfBoundsException("doEscape4Send error : index out of bounds(start=" + start
                    + ",end=" + end + ",bytes length=" + bs.length + ")");
        }
        try (ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
            for (int i = 0; i < start; i++) {
                outputStream.write(bs[i]);
            }
            for (int i = start; i <= end; i++) {
                if (bs[i] == 0x7e) {
                    outputStream.write(0x7d);
                    outputStream.write(0x02);
                }else if (bs[i] == 0x7d){
                    // 应该添加此条件 
                    //https://github.com/hylexus/jt-framework/issues/26
                    outputStream.write(0x7d);
                    outputStream.write(0x01);
                } else {
                    outputStream.write(bs[i]);
                }
            }
            // https://github.com/hylexus/jt-framework/issues/17
            for (int i = end + 1; i < bs.length; i++) {
                outputStream.write(bs[i]);
            }
            return outputStream.toByteArray();
        } catch (IOException e) {
            throw new MsgEscapeException(e);
        }
    }

    public static String bytes2String(byte[] bytes, int start, int length) {
        return bytes2String(bytes, start, length, null);
    }

    public static String bytes2String(byte[] bytes, int start, int length, String defaultVal) {
        try {
            return new String(Bytes.subSequence(bytes, start, length), JtProtocolConstant.JT_808_STRING_ENCODING);
        } catch (Exception e) {
            log.error(e.getMessage(), e);
            return defaultVal;
        }
    }

    public static byte[] byteBufToByteArray(ByteBuf buf, int length) {
        byte[] tmp = new byte[length];
        buf.readBytes(tmp);
        return tmp;
    }
}

image

openFeign和jt808出现的异常

环境

spring-cloud-starter-openfeign 2.2.5.RELEASE

jt-808-server-spring-boot-stater 1.0.10-RELEASE

出现的异常

2021-01-07 10:27:14.382 ERROR 3135 --- [msg-processor-0] r.CustomReflectionBasedRequestMsgHandler : An unexpected exception occurred while invoke ExceptionHandler

java.lang.reflect.InvocationTargetException: null
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_265]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_265]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_265]
at java.lang.reflect.Method.invoke(Method.java:498) ~[na:1.8.0_265]
at io.github.hylexus.jt808.handler.impl.exception.ExceptionHandlerMethodExceptionHandler.handleException(ExceptionHandlerMethodExceptionHandler.java:47) ~[jt-808-server-support-1.0.10-RELEASE.jar:1.0.10-RELEASE]
at io.github.hylexus.jt808.handler.impl.exception.DelegateExceptionHandler.handleException(DelegateExceptionHandler.java:55) ~[jt-808-server-support-1.0.10-RELEASE.jar:1.0.10-RELEASE]
at io.github.hylexus.jt808.handler.impl.reflection.CustomReflectionBasedRequestMsgHandler.doProcess(CustomReflectionBasedRequestMsgHandler.java:80) ~[jt-808-server-support-1.0.10-RELEASE.jar:1.0.10-RELEASE]
at io.github.hylexus.jt808.handler.AbstractMsgHandler.handleMsg(AbstractMsgHandler.java:36) [jt-808-server-support-1.0.10-RELEASE.jar:1.0.10-RELEASE]
at io.github.hylexus.jt808.queue.listener.AbstractRequestMsgQueueListener.consumeMsg(AbstractRequestMsgQueueListener.java:65) [jt-808-server-support-1.0.10-RELEASE.jar:1.0.10-RELEASE]
at io.github.hylexus.jt808.queue.listener.LocalEventBusListener.listen(LocalEventBusListener.java:42) [jt-808-server-support-1.0.10-RELEASE.jar:1.0.10-RELEASE]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_265]
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) ~[na:1.8.0_265]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[na:1.8.0_265]
at java.lang.reflect.Method.invoke(Method.java:498) ~[na:1.8.0_265]
at com.google.common.eventbus.Subscriber.invokeSubscriberMethod(Subscriber.java:87) [guava-29.0-jre.jar:na]
at com.google.common.eventbus.Subscriber$SynchronizedSubscriber.invokeSubscriberMethod(Subscriber.java:144) [guava-29.0-jre.jar:na]
at com.google.common.eventbus.Subscriber$1.run(Subscriber.java:72) [guava-29.0-jre.jar:na]
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149) [na:1.8.0_265]
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624) [na:1.8.0_265]
at java.lang.Thread.run(Thread.java:748) [na:1.8.0_265]
Caused by: io.netty.channel.StacklessClosedChannelException: null
at io.netty.channel.AbstractChannel$AbstractUnsafe.write(Object, ChannelPromise)(Unknown Source) ~[netty-all-4.1.52.Final.jar:4.1.52.Final]

怎么出现的

在@Jt808RequestMsgHandlerMapping
先调用openFeign里的方法(调用其它微服务)
再调用Jt808Session.sendMsgToClient就出错..
都是第一次发送出错。

第一次以后又都正常

附加信息,增加不带注解的属性。null错误

/**
 * 符加信息
 */
@Data
public class ExtraInfo {
    /**
     * 信息ID
     */
    @BasicField(startIndex = 0,dataType = BYTE)
    private Integer id;

    /**
     * 内容长度
     */
    @BasicField(order = 1,startIndex = 1,dataType = BYTE)
    private Integer length;

    /**
     * 符加信息内容
     */
    @BasicField(order = 2,startIndex = 2,dataType = BYTES,byteCountMethod = "getLength")
    private byte[] rawBytes;

    /**
     * rawBytes转成具体内容保存在这里
     */
    private Object content;
}

private object content增加这个属性就会出null Error

2021-01-14 16:05:12.765 ERROR 7186 --- [ntLoopGroup-3-1] omReflectionBasedRequestMsgBodyConverter : null

java.lang.NullPointerException: null
	at io.github.hylexus.jt.codec.decode.FieldDecoder.processListDataType(FieldDecoder.java:180) ~[jt-core-1.0.10-RELEASE.jar:1.0.10-RELEASE]
	at io.github.hylexus.jt.codec.decode.FieldDecoder.processBasicFieldInternal(FieldDecoder.java:132) ~[jt-core-1.0.10-RELEASE.jar:1.0.10-RELEASE]
	at io.github.hylexus.jt.codec.decode.FieldDecoder.processBasicField(FieldDecoder.java:98) ~[jt-core-1.0.10-RELEASE.jar:1.0.10-RELEASE]

出错代码定位
类:io.github.hylexus.jt.codec.decode.FieldDecoder

方法:processListDataType

final BasicField itemAnnotation = itemFieldMetadata.getAnnotation(BasicField.class);
遍历到content时,itemAnnotion 是null

[Question] Logo

Hi there this is the author of vuepress-theme-hope. though vuepress hope logo is used in demo, but I would suggest you to replace it in production. Maybe you can create a logo of your own.

No [MsgConverter] found for msgType

`

package io.github.hylexus.jt808.dispatcher;

import io.github.hylexus.jt.data.msg.MsgType;
import io.github.hylexus.jt808.converter.RequestMsgBodyConverter;
import io.github.hylexus.jt808.msg.RequestMsgBody;
import io.github.hylexus.jt808.msg.RequestMsgWrapper;
import io.github.hylexus.jt808.support.RequestMsgBodyConverterMapping;
import lombok.extern.slf4j.Slf4j;

import java.util.Optional;

/**

  • @author hylexus

  • createdAt 2019/1/24
    **/
    @slf4j
    public abstract class AbstractRequestMsgDispatcher implements RequestMsgDispatcher {

    private RequestMsgBodyConverterMapping msgConverterMapping;

    public AbstractRequestMsgDispatcher(RequestMsgBodyConverterMapping msgConverterMapping) {
    this.msgConverterMapping = msgConverterMapping;
    }

    public void doDispatch(RequestMsgWrapper wrapper) throws Exception {

     final Optional<RequestMsgBody> subMsg = tryParseMsgBody(wrapper);
     if (!subMsg.isPresent()) {
         return;
     }
    
     wrapper.setBody(subMsg.get());
     this.doBroadcast(wrapper);
    

    }

    private Optional tryParseMsgBody(RequestMsgWrapper wrapper) {
    final MsgType msgType = wrapper.getMetadata().getMsgType();
    final Optional<RequestMsgBodyConverter<? extends RequestMsgBody>> converterInfo = this.msgConverterMapping.getConverter(msgType);
    if (!converterInfo.isPresent()) {
    log.error("No [MsgConverter] found for msgType {}", msgType);
    return Optional.empty();
    }

     final RequestMsgBodyConverter<? extends RequestMsgBody> msgBodyConverter = converterInfo.get();
     final Optional<? extends RequestMsgBody> subMsg = msgBodyConverter.convert2Entity(wrapper.getMetadata());
     if (!subMsg.isPresent()) {
         log.debug("[MsgConverter] return empty(). converter:{}", msgBodyConverter.getClass());
         return Optional.empty();
     }
    
     final RequestMsgBody requestMsgBody = subMsg.get();
     return Optional.of(requestMsgBody);
    

    }

    public abstract void doBroadcast(RequestMsgWrapper wrapper) throws Exception;
    }
    `

HI,我是发现的编码、解码转义有BUG的

public static byte[] doEscape4ReceiveJt808Msg(byte[] bs, int start, int end) throws Exception {
if (start < 0 || end > bs.length) {
throw new ArrayIndexOutOfBoundsException("doEscape4Receive error : index out of bounds(start=" + start
+ ",end=" + end + ",bytes length=" + bs.length + ")");
}
try (ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
for (int i = 0; i < start; i++) {
outputStream.write(bs[i]);
}
for (int i = start; i < end - 1; i++) {
if (bs[i] == 0x7d && bs[i + 1] == 0x01) {
outputStream.write(0x7d);
i++;
} else if (bs[i] == 0x7d && bs[i + 1] == 0x02) {
outputStream.write(0x7e);
i++;
} else {
outputStream.write(bs[i]);
}
}
if (bs[end - 1] == 0x7d && bs[end] == 0x01) {
outputStream.write(0x7d);
} else if (bs[end - 1] == 0x7d && bs[end] == 0x02) {
outputStream.write(0x7e);
} else {
for (int i = end - 1; i < bs.length; i++) {
outputStream.write(bs[i]);
}
}
return outputStream.toByteArray();
}
}

报文解析错误

如下报文解析错误:

7E0200005B01234567891000110000000000000000020A3AAC067EAA2400000000000022083117155601040000014A30011D310100EB31000C00B28986049401208044782200060089FFFFFFFE000600C5FFFFFFE7000B00D801CC0090050FEC20C7000400B71D00947E

异常信息:

2022-09-06 11:31:29.978 [nioEventLoopGroup-5-1] ERROR jt-808.channel.dispatcher - 
java.lang.IndexOutOfBoundsException: index: 12, length: 91 (expected: range(0, 25))
	at io.netty.buffer.AbstractByteBuf.checkRangeBounds(AbstractByteBuf.java:1390)
	at io.netty.buffer.AbstractByteBuf.checkIndex0(AbstractByteBuf.java:1397)
	at io.netty.buffer.PooledSlicedByteBuf.slice(PooledSlicedByteBuf.java:106)
	at io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.decode(DefaultJt808MsgDecoder.java:57)
	at io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:53)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
	at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:327)
	at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:314)
	at io.netty.handler.codec.ByteToMessageDecoder.callDecode(ByteToMessageDecoder.java:435)
	at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:279)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
	at io.netty.handler.timeout.IdleStateHandler.channelRead(IdleStateHandler.java:286)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
	at io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
	at io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:166)
	at io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:722)
	at io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:658)
	at io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:584)
	at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:496)
	at io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:995)
	at io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	at java.base/java.lang.Thread.run(Thread.java:833)
2022-09-06 11:31:29.980 [nioEventLoopGroup-5-1] ERROR jt-808.request.decoder - Received unknown msg, msgId = 43556(0xaa24). ignore.
2022-09-06 11:31:29.980 [nioEventLoopGroup-5-1] ERROR jt-808.channel.dispatcher - 
io.github.hylexus.jt.exception.JtIllegalStateException: Received unknown msg, msgId=43556
	at io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.lambda$parseMsgType$0(DefaultJt808MsgDecoder.java:91)
	at java.base/java.util.Optional.orElseThrow(Optional.java:403)
	at io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.parseMsgType(DefaultJt808MsgDecoder.java:89)
	at io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.decode(DefaultJt808MsgDecoder.java:52)
	at io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:53)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
	at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:327)
	at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:299)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
	at io.netty.handler.timeout.IdleStateHandler.channelRead(IdleStateHandler.java:286)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
	at io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
	at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
	at io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
	at io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:166)
	at io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:722)
	at io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:658)
	at io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:584)
	at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:496)
	at io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:995)
	at io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	at java.base/java.lang.Thread.run(Thread.java:833)


厂商解释:

"中间出现7E的情况这个是属于正常情况,而且设备上传的时候都是将中间出现的7E转义成7D02上传的,只是说你解析的时候需要转义回7E进行解析"

"数据都是实时发送,刚好数据发到有7E的字节那设备就会去进行转义,本来这个7E就算一个字节的,又不是一个没有的字节"

请问这种怎么处理?谢谢.

前言中不允许有内容

下载源代码并按照配置弄好,运行gradlew clean build后,报Could not parse POM “...” 前言中不允许有内容.
image

netty报错 "refCnt: 0, decrement: 1"

nested exception is io.netty.util.IllegalReferenceCountException: refCnt: 0, decrement: 1] with root cause
io.netty.util.IllegalReferenceCountException: refCnt: 0, decrement: 1
at io.netty.util.internal.ReferenceCountUpdater.toLiveRealRefCnt(ReferenceCountUpdater.java:74)
at io.netty.util.internal.ReferenceCountUpdater.release(ReferenceCountUpdater.java:138)
at io.netty.buffer.AbstractReferenceCountedByteBuf.release(AbstractReferenceCountedByteBuf.java:100)
at io.netty.buffer.CompositeByteBuf.addComponent0(CompositeByteBuf.java:307)
at io.netty.buffer.CompositeByteBuf.addComponent(CompositeByteBuf.java:265)
at io.netty.buffer.CompositeByteBuf.addComponent(CompositeByteBuf.java:222)
at io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgEncoder.buildPackage(DefaultJt808MsgEncoder.java:93)
at io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgEncoder.encode(DefaultJt808MsgEncoder.java:54)
at io.github.hylexus.jt.jt808.spec.impl.DefaultJt808CommandSender.encode(DefaultJt808CommandSender.java:29)
at io.github.hylexus.jt.jt808.spec.impl.AbstractJt808CommandSender.sendCommandAndWaitingForReply(AbstractJt808CommandSender.java:35)

有没有qq群可以用来交流

有没有qq群可以用来交流()

idea 201801版本 无法编译该项目
错误:
java.lang.AbstractMethodError: org.jetbrains.plugins.gradle.tooling.util.ModuleComponentIdentifierImpl.getModuleIdentifier()Lorg/gradle/api/artifacts/ModuleIdentifier;

gradle降级到 4.10.3-bin也会报另外的错
Could not get unknown property 'archiveClassifier' for task ':jt-808-server-spring-boot-stater:sourcesJar' of type org.gradle.api.tasks.bundling.Jar.

archiveClassifier应该5.0+的属性。

完善消息下发功能

完善消息下发功能

消息下发功能太简单

1、消息下发可直接下发对象到终端(自动对象转换HEX)
2、消息下发应答处理-应可直接转换为定义的resquest对象。
3、应答消息可考虑放置redis等中,考虑下集群部署问题。

DWORD显示应该是有问题的。

DWORD,如果用Integer去接收,超过0x7f_ff_ff_ff的,Interger就会显示负数。Integer的最大值是0x7f_ff_ff_ff
虽然底层是一样的bit.但显示出来就是错误的。可以用Long去接收

附加信息。length的类型只能是Integer

/**
 * 符加信息
 */
@Data
public class ExtraInfo {
    /**
     * 信息ID
     */
    @BasicField(startIndex = 0,dataType = BYTE)
    private Short id;

    /**
     * 内容长度
     */
    @BasicField(order = 1,startIndex = 1,dataType = BYTE)
    private Short length;

    /**
     * 符加信息内容
     */
    @BasicField(order = 2,startIndex = 2,dataType = BYTES,byteCountMethod = "getLength")
    private byte[] rawBytes;
}

length的类型是BYTE,我用Short去接收,

byteCountMethod = "getLength" 会强转Short到Integer

2021-01-14 16:18:29.615 ERROR 7370 --- [ntLoopGroup-3-1] omReflectionBasedRequestMsgBodyConverter : java.lang.Short cannot be cast to java.lang.Integer

java.lang.ClassCastException: java.lang.Short cannot be cast to java.lang.Integer
	at io.github.hylexus.jt.codec.decode.FieldDecoder.getLengthFromByteCountMethod(FieldDecoder.java:276) ~[jt-core-1.0.10-RELEASE.jar:1.0.10-RELEASE]
	at io.github.hylexus.jt.codec.decode.FieldDecoder.getBasicFieldLength(FieldDecoder.java:244) ~[jt-core-1.0.10-RELEASE.jar:1.0.10-RELEASE]
	at io.github.hylexus.jt.codec.decode.FieldDecoder.processListDataType(FieldDecoder.java:180) ~[jt-core-1.0.10-RELEASE.jar:1.0.10-RELEASE]

出错代码定位

    private <T> Integer getLengthFromByteCountMethod(T instance, Method lengthMethod)
            throws IllegalAccessException, InvocationTargetException {

        return (Integer) lengthMethod.invoke(instance);
    }

内存泄漏:LEAK: ByteBuf.release() was not called before it's garbage-collected

[ ERROR] [2022-03-20 15:01:33.939] io.netty.util.ResourceLeakDetector [319] [808-msg-processor-13]- LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information.
Recent access records:
Created at:
io.netty.buffer.PooledByteBufAllocator.newDirectBuffer(PooledByteBufAllocator.java:385)
io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:187)
io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:178)
io.netty.buffer.AbstractByteBufAllocator.ioBuffer(AbstractByteBufAllocator.java:139)
io.netty.channel.DefaultMaxMessagesRecvByteBufAllocator$MaxMessageHandle.allocate(DefaultMaxMessagesRecvByteBufAllocator.java:114)
io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:150)
io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:719)
io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:655)
io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:581)
io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:493)
io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:989)
io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
java.base/java.lang.Thread.run(Thread.java:834)
[ ERROR] [2022-03-20 15:01:33.941] io.netty.util.ResourceLeakDetector [319] [808-msg-processor-13]- LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information.
Recent access records:
Created at:
io.netty.buffer.PooledByteBufAllocator.newDirectBuffer(PooledByteBufAllocator.java:385)
io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:187)
io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:173)
io.netty.buffer.AbstractByteBufAllocator.buffer(AbstractByteBufAllocator.java:107)
io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgBytesProcessor.doEscapeForReceive(DefaultJt808MsgBytesProcessor.java:53)
io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.decode(DefaultJt808MsgDecoder.java:44)
io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:53)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:324)
io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:296)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
io.netty.handler.timeout.IdleStateHandler.channelRead(IdleStateHandler.java:286)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:166)
io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:719)
io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:655)
io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:581)
io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:493)
io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:989)
io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
java.base/java.lang.Thread.run(Thread.java:834)
[ ERROR] [2022-03-20 15:01:33.943] io.netty.util.ResourceLeakDetector [319] [808-msg-processor-13]- LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information.
Recent access records:
Created at:
io.netty.buffer.PooledByteBufAllocator.newDirectBuffer(PooledByteBufAllocator.java:385)
io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:187)
io.netty.buffer.AbstractByteBufAllocator.directBuffer(AbstractByteBufAllocator.java:173)
io.netty.buffer.AbstractByteBufAllocator.buffer(AbstractByteBufAllocator.java:107)
io.github.hylexus.jt.jt808.support.annotation.codec.Jt808AnnotationBasedEncoder.encodeMsgBody(Jt808AnnotationBasedEncoder.java:86)
io.github.hylexus.jt.jt808.support.annotation.codec.Jt808AnnotationBasedEncoder.encodeAndWriteToResponse(Jt808AnnotationBasedEncoder.java:53)
io.github.hylexus.jt.jt808.support.dispatcher.handler.result.Jt808ResponseBodyHandlerResultHandler.doHandleResult(Jt808ResponseBodyHandlerResultHandler.java:57)
io.github.hylexus.jt.jt808.support.dispatcher.handler.result.Jt808ResponseBodyHandlerResultHandler.handleResult(Jt808ResponseBodyHandlerResultHandler.java:45)
io.github.hylexus.jt.jt808.support.dispatcher.Jt808DispatcherHandler.handleResult(Jt808DispatcherHandler.java:121)
io.github.hylexus.jt.jt808.support.dispatcher.Jt808DispatcherHandler.processHandlerResult(Jt808DispatcherHandler.java:96)
io.github.hylexus.jt.jt808.support.dispatcher.Jt808DispatcherHandler.handleRequest(Jt808DispatcherHandler.java:62)
io.github.hylexus.jt.jt808.spec.impl.request.queue.AbstractJt808RequestMsgQueueListener.consumeMsg(AbstractJt808RequestMsgQueueListener.java:56)
io.github.hylexus.jt.jt808.spec.impl.request.queue.LocalEventBusListener.listen(LocalEventBusListener.java:39)
jdk.internal.reflect.GeneratedMethodAccessor39.invoke(Unknown Source)
java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
java.base/java.lang.reflect.Method.invoke(Method.java:566)
com.google.common.eventbus.Subscriber.invokeSubscriberMethod(Subscriber.java:91)
com.google.common.eventbus.Subscriber$SynchronizedSubscriber.invokeSubscriberMethod(Subscriber.java:150)
com.google.common.eventbus.Subscriber$1.run(Subscriber.java:76)
java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
java.base/java.lang.Thread.run(Thread.java:834)
[ ERROR] [2022-03-20 15:01:33.947] io.netty.util.ResourceLeakDetector [319] [808-msg-processor-13]- LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information.
Recent access records:
Created at:
io.netty.buffer.AbstractByteBufAllocator.compositeDirectBuffer(AbstractByteBufAllocator.java:223)
io.netty.buffer.AbstractByteBufAllocator.compositeDirectBuffer(AbstractByteBufAllocator.java:218)
io.netty.buffer.AbstractByteBufAllocator.compositeBuffer(AbstractByteBufAllocator.java:193)
io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgEncoder.buildPackage(DefaultJt808MsgEncoder.java:91)
io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgEncoder.encode(DefaultJt808MsgEncoder.java:54)
io.github.hylexus.jt.jt808.support.dispatcher.handler.result.Jt808ResponseBodyHandlerResultHandler.doHandleResult(Jt808ResponseBodyHandlerResultHandler.java:59)
io.github.hylexus.jt.jt808.support.dispatcher.handler.result.Jt808ResponseBodyHandlerResultHandler.handleResult(Jt808ResponseBodyHandlerResultHandler.java:45)
io.github.hylexus.jt.jt808.support.dispatcher.Jt808DispatcherHandler.handleResult(Jt808DispatcherHandler.java:121)
io.github.hylexus.jt.jt808.support.dispatcher.Jt808DispatcherHandler.processHandlerResult(Jt808DispatcherHandler.java:96)
io.github.hylexus.jt.jt808.support.dispatcher.Jt808DispatcherHandler.handleRequest(Jt808DispatcherHandler.java:62)
io.github.hylexus.jt.jt808.spec.impl.request.queue.AbstractJt808RequestMsgQueueListener.consumeMsg(AbstractJt808RequestMsgQueueListener.java:56)
io.github.hylexus.jt.jt808.spec.impl.request.queue.LocalEventBusListener.listen(LocalEventBusListener.java:39)
jdk.internal.reflect.GeneratedMethodAccessor39.invoke(Unknown Source)
java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
java.base/java.lang.reflect.Method.invoke(Method.java:566)
com.google.common.eventbus.Subscriber.invokeSubscriberMethod(Subscriber.java:91)
com.google.common.eventbus.Subscriber$SynchronizedSubscriber.invokeSubscriberMethod(Subscriber.java:150)
com.google.common.eventbus.Subscriber$1.run(Subscriber.java:76)
java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
java.base/java.lang.Thread.run(Thread.java:834)
[ ERROR] [2022-03-20 15:01:33.951] io.netty.util.ResourceLeakDetector [319] [808-msg-processor-13]- LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information.
Recent access records:
Created at:
io.netty.buffer.AbstractByteBufAllocator.compositeDirectBuffer(AbstractByteBufAllocator.java:223)
io.netty.buffer.AbstractByteBufAllocator.compositeBuffer(AbstractByteBufAllocator.java:201)
io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgBytesProcessor.doEscapeForReceive(DefaultJt808MsgBytesProcessor.java:66)
io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.decode(DefaultJt808MsgDecoder.java:44)
io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:53)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:324)
io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:296)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
io.netty.handler.timeout.IdleStateHandler.channelRead(IdleStateHandler.java:286)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:166)
io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:719)
io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:655)
io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:581)
io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:493)
io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:989)
io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
java.base/java.lang.Thread.run(Thread.java:834)

io.netty.util.ResourceLeakDetector : LEAK: ByteBuf.release() was not called before it's garbage-collected

<dependency> //依赖版本
	<groupId>io.github.hylexus.jt</groupId>
	<artifactId>jt-808-server-spring-boot-starter</artifactId>
	<version>2.1.1</version>
</dependency>

具体报错日志

2024-01-15T00:50:42.120+08:00 ERROR 1786 --- [ntLoopGroup-4-4] io.netty.util.ResourceLeakDetector       : LEAK: ByteBuf.release() was not called before it's garbage-collected. See https://netty.io/wiki/reference-counted-objects.html for more information.
Recent access records: 
#1:
	io.github.hylexus.jt.jt808.support.utils.JtProtocolUtils.release(JtProtocolUtils.java:214)
	io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:50)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:444)
	io.netty.channel.AbstractChannelHandlerContext.access$600(AbstractChannelHandlerContext.java:61)
	io.netty.channel.AbstractChannelHandlerContext$7.run(AbstractChannelHandlerContext.java:425)
	io.netty.util.concurrent.AbstractEventExecutor.runTask(AbstractEventExecutor.java:173)
	io.netty.util.concurrent.DefaultEventExecutor.run(DefaultEventExecutor.java:66)
	io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:997)
	io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	java.base/java.lang.Thread.run(Thread.java:1583)
#2:
	io.netty.buffer.AdvancedLeakAwareByteBuf.getByte(AdvancedLeakAwareByteBuf.java:155)
	io.github.hylexus.jt.utils.HexStringUtils.encodeHex(HexStringUtils.java:23)
	io.github.hylexus.jt.utils.HexStringUtils.byteBufToString(HexStringUtils.java:58)
	io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.decode(DefaultJt808MsgDecoder.java:47)
	io.github.hylexus.jt.jt808.support.dispatcher.impl.SimpleJt808RequestProcessor.processJt808Request(SimpleJt808RequestProcessor.java:43)
	io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:48)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:444)
	io.netty.channel.AbstractChannelHandlerContext.access$600(AbstractChannelHandlerContext.java:61)
	io.netty.channel.AbstractChannelHandlerContext$7.run(AbstractChannelHandlerContext.java:425)
	io.netty.util.concurrent.AbstractEventExecutor.runTask(AbstractEventExecutor.java:173)
	io.netty.util.concurrent.DefaultEventExecutor.run(DefaultEventExecutor.java:66)
	io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:997)
	io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	java.base/java.lang.Thread.run(Thread.java:1583)
#3:
	io.netty.buffer.AdvancedLeakAwareByteBuf.getByte(AdvancedLeakAwareByteBuf.java:155)
	io.github.hylexus.jt.utils.HexStringUtils.encodeHex(HexStringUtils.java:23)
	io.github.hylexus.jt.utils.HexStringUtils.byteBufToString(HexStringUtils.java:58)
	io.github.hylexus.jt.jt808.support.codec.impl.DefaultJt808MsgDecoder.decode(DefaultJt808MsgDecoder.java:42)
	io.github.hylexus.jt.jt808.support.dispatcher.impl.SimpleJt808RequestProcessor.processJt808Request(SimpleJt808RequestProcessor.java:43)
	io.github.hylexus.jt.jt808.support.netty.Jt808DispatchChannelHandlerAdapter.channelRead(Jt808DispatchChannelHandlerAdapter.java:48)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:444)
	io.netty.channel.AbstractChannelHandlerContext.access$600(AbstractChannelHandlerContext.java:61)
	io.netty.channel.AbstractChannelHandlerContext$7.run(AbstractChannelHandlerContext.java:425)
	io.netty.util.concurrent.AbstractEventExecutor.runTask(AbstractEventExecutor.java:173)
	io.netty.util.concurrent.DefaultEventExecutor.run(DefaultEventExecutor.java:66)
	io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:997)
	io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	java.base/java.lang.Thread.run(Thread.java:1583)
#4:
	Hint: 'Jt808NettyHandlerAdapter' will handle the message from this point.
	io.netty.channel.DefaultChannelPipeline.touch(DefaultChannelPipeline.java:116)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:417)
	io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:412)
	io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:346)
	io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:333)
	io.netty.handler.codec.ByteToMessageDecoder.callDecode(ByteToMessageDecoder.java:454)
	io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:290)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:444)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:420)
	io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:412)
	io.netty.handler.timeout.IdleStateHandler.channelRead(IdleStateHandler.java:286)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:442)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:420)
	io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:412)
	io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:440)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:420)
	io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
	io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:166)
	io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:788)
	io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:724)
	io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:650)
	io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:562)
	io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:997)
	io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	java.base/java.lang.Thread.run(Thread.java:1583)
Created at:
	io.netty.buffer.SimpleLeakAwareByteBuf.unwrappedDerived(SimpleLeakAwareByteBuf.java:144)
	io.netty.buffer.SimpleLeakAwareByteBuf.readRetainedSlice(SimpleLeakAwareByteBuf.java:67)
	io.netty.buffer.AdvancedLeakAwareByteBuf.readRetainedSlice(AdvancedLeakAwareByteBuf.java:108)
	io.netty.handler.codec.DelimiterBasedFrameDecoder.decode(DelimiterBasedFrameDecoder.java:270)
	io.netty.handler.codec.DelimiterBasedFrameDecoder.decode(DelimiterBasedFrameDecoder.java:215)
	io.netty.handler.codec.ByteToMessageDecoder.decodeRemovalReentryProtection(ByteToMessageDecoder.java:529)
	io.netty.handler.codec.ByteToMessageDecoder.callDecode(ByteToMessageDecoder.java:468)
	io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:290)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:444)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:420)
	io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:412)
	io.netty.handler.timeout.IdleStateHandler.channelRead(IdleStateHandler.java:286)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:442)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:420)
	io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:412)
	io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:440)
	io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:420)
	io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
	io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:166)
	io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:788)
	io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:724)
	io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:650)
	io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:562)
	io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:997)
	io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
	io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
	java.base/java.lang.Thread.run(Thread.java:1583)
: 7 leak records were discarded because they were duplicates
: 140 leak records were discarded because the leak record count is targeted to 4. Use system property io.netty.leakDetection.targetRecords to increase the limit.

关于完善查询终端参数应答【0x0104】

终端参数项数据格式中参数值一项描述及要求:
若为多值参数,则消息中使用多个相同ID的参数项,如调度中心电话号码;
目前可能存在多msgId相同的情况,解析会出现被覆盖问题。

下发终端设置指令异常

JDK: 17

实体类定义:

import io.github.hylexus.jt.jt808.support.annotation.msg.resp.Jt808ResponseBody;
import io.github.hylexus.jt.jt808.support.annotation.msg.resp.ResponseField;
import io.github.hylexus.jt.jt808.support.data.MsgDataType;
import io.netty.buffer.ByteBuf;
import lombok.Data;
import lombok.experimental.Accessors;

import java.util.List;

import static io.github.hylexus.jt.jt808.support.data.MsgDataType.*;

/**
 * Created At 2019-10-16 10:43 下午
 *
 * <p>Ref: https://github.com/hylexus/jt-framework/blob/master/samples/jt-808-server-sample-debug/
 * src/main/java/io/github/hylexus/jt/jt808/samples/debug/entity/resp/RespTerminalSettings.java
 *
 * @author hylexus
 */
@Data
@Accessors(chain = true)
@Jt808ResponseBody(msgId = 0x8103, desc = "设置终端参数")
public class RespTerminalSettings {

  @ResponseField(order = 1, dataType = BYTE)
  private int totalParamCount;

  @ResponseField(order = 2, dataType = MsgDataType.LIST)
  private List<ParamItem> paramList;

  @Data
  @Accessors(chain = true)
  public static class ParamItem {
    @ResponseField(order = 1, dataType = DWORD)
    private int msgId;

    @ResponseField(order = 2, dataType = BYTE)
    private int bytesCountOfContentLength;

    @ResponseField(order = 3, dataType = BYTES)
    private ByteBuf msgContent;

    public ParamItem() {}

    public ParamItem(int msgId, ByteBuf msgContent) {
      this.msgId = msgId;
      this.msgContent = msgContent;
      this.bytesCountOfContentLength = msgContent.readableBytes();
    }
  }
}

调用:

    /**
   * 设置终端参数
   *
   * @param terminalId 终端id,第一位为0的手机号
   * @param msgId 消息id
   * @param msgValue 消息内容(类型需要与消息id对应的一致)
   */
  public void terminalParamSetting(String terminalId, int msgId, Object msgValue) {
    final RespTerminalSettings param = new RespTerminalSettings();
    var msgVal = ByteBufAllocator.DEFAULT.buffer();
    final int carColorSet = 0x0084;
    if (TERMINAL_SET_TYPE_LIST.contains(msgId)) {
      msgVal = ByteBufAllocator.DEFAULT.buffer().writeBytes(String.valueOf(msgValue).getBytes());
    } else if (msgId == carColorSet) {
      msgVal =
          ByteBufAllocator.DEFAULT.buffer().writeByte(Integer.parseInt(String.valueOf(msgValue)));
    } else {
      msgVal =
          ByteBufAllocator.DEFAULT.buffer().writeInt(Integer.parseInt(String.valueOf(msgValue)));
    }

    final List<RespTerminalSettings.ParamItem> paramList = new ArrayList<>(1);
    paramList.add(new RespTerminalSettings.ParamItem(msgId, msgVal));

    param.setTotalParamCount(paramList.size());
    final var session = sessionManager.findByTerminalId(terminalId);
    if (session.isEmpty()) {
      return;
    }
    final int nextFlowId = session.get().nextFlowId();
    final Jt808CommandKey commandKey =
        Jt808CommandKey.of(terminalId, BuiltinJt808MsgType.CLIENT_COMMON_REPLY, nextFlowId);

    final Object resp;
    try {
      resp = commandSender.sendCommandAndWaitingForReply(commandKey, param, 20L, TimeUnit.SECONDS);
      log.info("RESP::::::: {}", resp);
    } catch (InterruptedException e) {
      e.printStackTrace();
    }
  }

异常信息: nested exception is io.github.hylexus.jt.exception.JtIllegalArgumentException: java.util.List should be Iterable
异常触发位置:

报警标志怎么知道具体含义?

您好,框架解析了报警标志为数字,请问怎么知道数字对应的具体含义呢?比如: 4096 , 谢谢!


public class BuiltinMsg0200V2013 {
    // (1). byte[0,4)  DWORD 报警标志
    @RequestField(order = 1, startIndex = 0, dataType = DWORD)
    private long alarmFlag;

ExtraMsgBody注解解析异常

ExtraMsgBody注解解析异常

PassthroughPack 的byteCountOfMsgId实际定义的值为2,但是现在好像是默认值 1。 看看这块bean装箱有什么问题

请求报文:090000249782900021470379F02003160734200102010305300239B20546040000000005450400000000200316193912DB

@io.github.hylexus.jt.annotation.msg.req.extra.ExtraField(length=0, byteCountOfContentLength=1, byteCountMethod=getContentLength, byteCountOfMsgId=1, startIndex=11)

image

image

package com.ivyb2b.cesp.iot.dto.req;

import io.github.hylexus.jt.annotation.msg.req.Jt808ReqMsgBody;
import io.github.hylexus.jt.annotation.msg.req.basic.BasicField;
import io.github.hylexus.jt.annotation.msg.req.extra.ExtraField;
import io.github.hylexus.jt.annotation.msg.req.extra.ExtraMsgBody;
import io.github.hylexus.jt808.msg.RequestMsgBody;
import io.github.hylexus.jt808.msg.RequestMsgMetadata;
import io.github.hylexus.jt808.support.entity.scan.RequestMsgMetadataAware;
import lombok.Data;
import lombok.ToString;
import lombok.experimental.Accessors;

import static io.github.hylexus.jt.data.MsgDataType.*;

/**
 * @Description 数据上行透传(0x0900)
 * @Author wsy
 * @Date 2020-03-11 14:04
 * @Version 1.0
 **/

@Data
@Accessors(chain = true)
@Jt808ReqMsgBody(msgType = 0x0900)
public class PassthroughPack implements RequestMsgBody, RequestMsgMetadataAware {

    @ToString.Exclude
    private RequestMsgMetadata requestMsgMetadata;

    @Override
    public void setRequestMsgMetadata(RequestMsgMetadata metadata) {
        this.requestMsgMetadata = metadata;
    }

    /**
     * 透传消息类型
     * GNSS模块详细定位数据 0x00
     * 道路运输证IC卡信息	0x0B
     * 串口1透传	0x41
     * 串口2透传	0x42
     * 用户自定义透传	0xF0-0xF7
     * OBD数据透传	0XF4
     * 行车数据透传	0Xf8
     * 用户自定义透传	0xF9-0xFF
     */
    @BasicField(startIndex = 0, dataType = BYTE)
    private int msgType;

    @BasicField(startIndex = 1, dataType = BCD, length = 6)
    private String time;
    /**
     * 数据类型
     * 0x00:实时数据;
     * 0x01:补传数据
     */
    @BasicField(startIndex = 7, dataType = BYTE)
    private int dataType;

    /**
     * 车辆类型
     * 0x01:商用车;
     * 0x02:乘用车
     */
    @BasicField(startIndex = 8, dataType = BYTE)
    private int vehicleType;


    /**
     * 消息子类
     * 0x01:OBD数据流上报;
     * 0x02:故障码数据上报;
     * 0x03:告警数据及驾驶行为数据上报;
     * 0x04:行程报告数据上报;
     * 0x05:终端下位机日志数据上报;
     * 0x06:CAN学习采集数据上传;
     * 0x07:支持数据流ID列表上报;
     * 0x08:支持车辆控制ID列表上报;
     * 0x09:支持告警及驾驶行为数据ID列表上报
     * 0x0A:车辆关键数据上传
     * 0x0B:VIN码上报
     * 0x0C:体检数据上报
     * 0x0D:设备自检数据上报
     */
    @BasicField(startIndex = 9, dataType = BYTE)
    private int childMsgType;

    /**
     * 数据总数
     */
    @BasicField(startIndex = 10, dataType = BYTE)
    private int totalMsg;

    /**
     * 透传消息内容(子内容)
     */
    @BasicField(startIndex = 11, dataType = BYTES,byteCountMethod = "getContentLength")
    private byte[] content;

    public int getContentLength() {
        int totalLength = this.requestMsgMetadata.getHeader().getMsgBodyLength();
        return totalLength - 11;
    }

    @ExtraField(
            // 消息体中第11字节开始
            startIndex = 11,
            // 附加项长度用getExtraInfoLength返回值表示
            byteCountMethod = "getContentLength"
    )
    private ExtraData extraData;

    @Data
    // 切记@ExtraMsgBody注解不能丢
    @ExtraMsgBody(
            byteCountOfMsgId = 2, // 消息Id用2个字节表示
            byteCountOfContentLength = 1 // 附加项长度字段用1个字节表示
    )
    public static class ExtraData {
        /**
         * 电压 mV
         */
        @ExtraField.NestedFieldMapping(msgId = 0x0530, dataType = WORD)
        private int field0x0530;
        /**
         * 累计里程 km  y=x/10;精度:0.1
         */
        @ExtraField.NestedFieldMapping(msgId = 0x0546, dataType = DWORD)
        private int field0x0546;

        @ExtraField.NestedFieldMapping(msgId = 0x0545, dataType = DWORD)
        private int field0x0545;

      }
    }

是否支持JDK 8?

我们公司现在还是用的JDK 8,这个是否支持?如果不支持,需要做哪些工作来适配?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.