Protobuf反序列化异常
Protobuf deserialize exception
尝试在 Java 中使用 protobuf 反序列化消息并出现以下异常。
原因:com.google.protobuf.InvalidProtocolBufferException:解析协议消息时,输入在字段中间意外结束。这可能意味着输入已被截断或嵌入的消息错误报告了自己的长度。
在 com.google.protobuf.InvalidProtocolBufferException.truncatedMessage(InvalidProtocolBufferException.java:86)
在 com.google.protobuf.CodedInputStream$ArrayDecoder.readRawLittleEndian64(CodedInputStream.java:1179)
在 com.google.protobuf.CodedInputStream$ArrayDecoder.readFixed64(CodedInputStream.java:791)
在 com.google.protobuf.UnknownFieldSet$Builder.mergeFieldFrom(UnknownFieldSet.java:534)
在 com.google.protobuf.GeneratedMessageV3.parseUnknownFieldProto3(GeneratedMessageV3.java:305)
我已经手动解码了你的字符串,我同意图书馆的说法:你的信息被截断了。我 猜测 这是因为您使用的是基于字符串的 API,并且数据中有一个零字节 - 许多文本 API 看到一个零字节 (NUL
在 ASCII 术语中)表示字符串的结尾。
细目如下:
\n=10=field 1, length prefix - I'm assuming this is a string
\x14=20
"id:article:v1:964000"
(22 bytes used for field 1)
\x12=18=field 2, length prefix - I'm assuming this is a sub-messssage
$=36
\n=10=field 1, length prefix - I'm assuming this is a string
\x10=16
"predicted_topics"
(18 bytes used for field 2.1)
\x12=18=field 2, length prefix - I'm assuming this is a string
\x06=6
"IS/biz"
(8 bytes used for field 2.2)
\x1a=26=field 3, length prefix - I'm assuming this is "bytes"
\x08=8
\xf0
l
\x8f
\xde
p
\x9f
\xe4
(unexpected EOF)
最后,我们试图解码最内层消息的 8 个字节,但只剩下 7 个字节。我知道这不是子消息,因为这会导致标签无效,而且它看起来不像 UTF-8,所以我假设这是一个 bytes
字段(但坦率地说它不是没关系:我们需要 8 个字节,而我们只有 7 个)。
我的猜测是 bytes
字段中的最后一个字节为零;如果我们假设末尾缺少 \x00
,那么字段 2.3 是 10 个字节,我们已经占了 18+8+10=36 个字节,这将使子消息(字段 2)完整。 在 外部子消息之后可能还有更多缺失数据 - 我无法知道。
所以:确保您没有使用基于文本的 API 和二进制数据。
尝试在 Java 中使用 protobuf 反序列化消息并出现以下异常。
原因:com.google.protobuf.InvalidProtocolBufferException:解析协议消息时,输入在字段中间意外结束。这可能意味着输入已被截断或嵌入的消息错误报告了自己的长度。 在 com.google.protobuf.InvalidProtocolBufferException.truncatedMessage(InvalidProtocolBufferException.java:86) 在 com.google.protobuf.CodedInputStream$ArrayDecoder.readRawLittleEndian64(CodedInputStream.java:1179) 在 com.google.protobuf.CodedInputStream$ArrayDecoder.readFixed64(CodedInputStream.java:791) 在 com.google.protobuf.UnknownFieldSet$Builder.mergeFieldFrom(UnknownFieldSet.java:534) 在 com.google.protobuf.GeneratedMessageV3.parseUnknownFieldProto3(GeneratedMessageV3.java:305)
我已经手动解码了你的字符串,我同意图书馆的说法:你的信息被截断了。我 猜测 这是因为您使用的是基于字符串的 API,并且数据中有一个零字节 - 许多文本 API 看到一个零字节 (NUL
在 ASCII 术语中)表示字符串的结尾。
细目如下:
\n=10=field 1, length prefix - I'm assuming this is a string
\x14=20
"id:article:v1:964000"
(22 bytes used for field 1)
\x12=18=field 2, length prefix - I'm assuming this is a sub-messssage
$=36
\n=10=field 1, length prefix - I'm assuming this is a string
\x10=16
"predicted_topics"
(18 bytes used for field 2.1)
\x12=18=field 2, length prefix - I'm assuming this is a string
\x06=6
"IS/biz"
(8 bytes used for field 2.2)
\x1a=26=field 3, length prefix - I'm assuming this is "bytes"
\x08=8
\xf0
l
\x8f
\xde
p
\x9f
\xe4
(unexpected EOF)
最后,我们试图解码最内层消息的 8 个字节,但只剩下 7 个字节。我知道这不是子消息,因为这会导致标签无效,而且它看起来不像 UTF-8,所以我假设这是一个 bytes
字段(但坦率地说它不是没关系:我们需要 8 个字节,而我们只有 7 个)。
我的猜测是 bytes
字段中的最后一个字节为零;如果我们假设末尾缺少 \x00
,那么字段 2.3 是 10 个字节,我们已经占了 18+8+10=36 个字节,这将使子消息(字段 2)完整。 在 外部子消息之后可能还有更多缺失数据 - 我无法知道。
所以:确保您没有使用基于文本的 API 和二进制数据。