Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Conversation

@ShoyuVanilla
Copy link

Currently, the following code panics on unwrapping an err: Error("invalid type: map, expected message prefix byte", line: 1, column: 1):

#[test]
fn legacy_msg_deserialize_with_serde_json() {
    let legacy_msg =
       solana_message::VersionedMessage::Legacy(solana_message::legacy::Message::new(&[], None));
    let serialized = serde_json::to_string(&legacy_msg).unwrap();
    let deserialized: solana_message::VersionedMessage = serde_json::from_str(&serialized).unwrap(); // 💥
}

This is because when serializing legacy messages the serializer don't insert version prefix explicitly

Self::Legacy(message) => {
let mut seq = serializer.serialize_tuple(1)?;
seq.serialize_element(message)?;
seq.end()
}
Self::V0(message) => {
let mut seq = serializer.serialize_tuple(2)?;
seq.serialize_element(&MESSAGE_VERSION_PREFIX)?;
seq.serialize_element(message)?;
seq.end()
}

but when deserializing, the deserializer implicitly reads the first byte of LegacyMessage into a version prefix.

fn visit_seq<A>(self, mut seq: A) -> Result<VersionedMessage, A::Error>
where
A: SeqAccess<'de>,
{
let prefix: MessagePrefix = seq
.next_element()?
.ok_or_else(|| de::Error::invalid_length(0, &self))?;

In bincode deserialization scenario this causes no problem but with serde_json, it causes funny error that the very string that serialized from a VersionedMessage::Legacy cannot be deserialized to itself, because serde_json expects Int but it encounters {, the first byte of serialized LegacyMessage as a serde_json::Value::Map.

@ShoyuVanilla ShoyuVanilla requested a review from a team as a code owner September 10, 2025 05:53
enum PrefixOrLegacy {
Prefix(MessagePrefix),
Legacy(LegacyMessage),
}
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We cannot use this or other branching with deserialize_any for bincode as it doesn't support deserialize_any, so apply this iff the given deserializer is human readable.

@apfitzge apfitzge requested a review from jstarry September 10, 2025 12:52
@ShoyuVanilla
Copy link
Author

Though I can workaround this issue but it's a bit irritating in my codebase 😅 Could this be reviewed or merged?

@ShoyuVanilla
Copy link
Author

@jstarry Sorry for the ping! I was wondering if this PR could be reviewed, or if this change isn’t something the project wants to pursue. I’m currently working on a project that performs serialization/deserialization on transactions, and this issue has required me to implement a custom serializer/deserializer 😅

@jstarry
Copy link
Contributor

jstarry commented Oct 15, 2025

@ShoyuVanilla apologies on the delay, been backed up on code reviews for awhile. I like this fix but I think we should go further and fix the json string representation of versioned messages as well. Does this fix work for you? #381

@ShoyuVanilla
Copy link
Author

@ShoyuVanilla apologies on the delay, been backed up on code reviews for awhile. I like this fix but I think we should go further and fix the json string representation of versioned messages as well. Does this fix work for you? #381

Yeah, that works fine. Thanks!

@ShoyuVanilla
Copy link
Author

Closing in favor of #381

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants