Deserializing untagged enum
Closed this issue · 2 comments
nrempel commented
Hey there, thanks for the great library!
I'm trying to deserialize a response from a BitTorrent DHT node into a struct and it doesn't seem to be working.
#[derive(Debug, Deserialize)]
struct FindNodeMessage {
nodes: ByteBuf,
id: ByteBuf
}
#[derive(Debug, Deserialize)]
#[serde(untagged)]
enum KRPCResponse {
FindNode(HashMap<String, ByteBuf>), // This works
FindNodeMessage // This does not
}
#[derive(Debug, Deserialize)]
struct KRPCMessage {
#[serde(rename = "t")]
transaction_id: String,
#[serde(rename = "y")]
type_code: String,
#[serde(rename = "v")]
version: Option<String>,
#[serde(rename = "r")]
response: KRPCResponse,
ip: KRPCContact,
}
Deserializing a message using a HashMap like so works and deserializes as:
KRPCMessage { transaction: Transaction { transaction_id: "aa", query_type: "find_node" }, type_code: "r", version: None, response: FindNode({"nodes": [93, 101, 79, 45, 25, 26, 197, 167, 246, 22, 101, 238, 245, 85, 188, 171, 110, 179, 216, 93, 5, 228, 97, 34, 149, 166, 170, 182, 234, 101, 136, 213, 240, 153, 181, 187, 203, 158, 139, 11, 31, 153, 142, 9, 114, 125, 86, 106, 90, 74, 16, 19, 83, 129, 143, 215, 102, 244, 214, 162, 186, 37, 67, 68, 24, 59, 1, 217, 68, 5, 36, 212, 220, 134, 218, 173, 198, 32, 25, 9, 30, 150, 42, 154, 117, 155, 51, 132, 149, 148, 155, 72, 230, 211, 185, 32, 69, 62, 98, 209, 58, 57, 26, 225, 174, 77, 165, 81, 230, 153, 163, 175, 49, 68, 234, 35, 21, 66, 181, 23, 71, 48, 93, 22, 31, 207, 146, 12, 26, 225, 60, 35, 251, 120, 230, 24, 123, 25, 223, 226, 69, 129, 144, 79, 193, 11, 62, 160, 248, 37, 61, 44, 168, 20, 43, 107, 199, 145, 77, 17, 48, 91, 183, 216, 125, 175, 67, 62, 84, 201, 132, 63, 30, 140, 68, 129, 89, 235, 199, 80, 31, 146, 133, 35, 244, 214, 174, 82, 144, 73, 241, 241, 187, 233, 235, 179, 166, 219, 60, 135, 12, 225, 109, 61, 111, 237, 83, 25, 244, 161, 141, 160, 210, 44, 187, 231, 197, 53, 57, 230, 165, 69, 58, 144, 226, 26, 84, 177, 87, 5, 215, 227, 33, 114, 177, 153, 51, 234, 16, 133, 208, 243, 200, 108, 119, 141, 142, 249, 83, 181, 246, 20, 121, 134, 5, 187, 75, 126, 117, 37, 158, 138, 67, 246, 173, 132, 117, 134, 219, 1, 157, 84, 193, 13, 229, 190, 162, 255, 87, 246, 75, 64, 8, 195, 196, 145, 36, 118, 64, 201, 86, 226, 200, 187, 197, 251, 67, 101, 115, 143, 234, 39, 73, 65, 220, 174, 5, 142, 116, 29, 26, 225, 153, 100, 94, 183, 103, 15, 145, 158, 57, 178, 136, 198, 228, 186, 108, 209, 249, 58, 8, 40, 177, 180, 240, 33, 196, 145, 92, 218, 108, 248, 136, 36, 61, 70, 248, 14, 50, 201, 194, 111, 155, 31, 156, 252, 174, 118, 185, 172, 44, 42, 224, 181, 26, 110, 116, 96, 101, 235, 156, 69, 90, 15, 35, 219, 26, 3, 37, 89, 48, 10, 19, 179, 68, 194, 243, 37, 196, 145, 78, 4, 24, 7, 50, 140, 106, 116, 253, 251, 133, 18, 180, 187, 167, 123, 90, 66, 156, 150, 188, 24, 76, 127, 82, 65], "id": [50, 245, 78, 105, 115, 81, 255, 74, 236, 41, 205, 186, 171, 242, 251, 227, 70, 124, 194, 103]}), ip: 67.215.246.10:6881 }
However, try to deserialize into the FindNodeMessage
struct always fails:
#[derive(Debug, Deserialize)]
#[serde(untagged)]
enum KRPCResponse {
FindNodeMessage // Try to use struct
}
Error: value: Deserialize("data did not match any variant of untagged enum KRPCResponse")
Am I missing something here?
Thank you!
bluk commented
Is the enum correct? Should it be:
#[derive(Debug, Deserialize)]
#[serde(untagged)]
enum KRPCResponse {
FindNodeMessage(FindNodeMessage)
}
instead? I don't think the variant name indicates the actual type used to deserialize to.
nrempel commented
That works! Thank you for the help.
mod find_node;
#[derive(Debug, Deserialize)]
#[serde(untagged)]
enum KRPCResponse {
FindNode(find_node::FindNodeMessage)
}
Being new to Rust I got tripped up by the enum syntax and thought I was referencing the struct. Good to go now :)