Rust AppView - highly experimental!
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

fix: blob deserialization? maybe? idk

+77 -1
+77 -1
lexica/src/lib.rs
··· 32 32 } 33 33 34 34 /// Blob type for CBOR deserialization (CAR files, native Cid type) 35 - #[derive(Clone, Debug, Deserialize, Serialize)] 35 + /// Now includes lenient deserialization to handle: 36 + /// - Missing size field (defaults to 0) 37 + /// - Multiple CID field formats (ref as Cid, ref as bytes, legacy cid field) 38 + /// - Schema variations in CAR files 39 + #[derive(Clone, Debug, Serialize)] 36 40 #[serde(tag = "$type")] 37 41 #[serde(rename = "blob")] 38 42 #[serde(rename_all = "camelCase")] ··· 42 46 #[serde(serialize_with = "utils::cid_as_link")] 43 47 pub cid: Cid, 44 48 pub size: i32, 49 + } 50 + 51 + impl<'de> Deserialize<'de> for Blob { 52 + fn deserialize<D>(deserializer: D) -> Result<Self, D::Error> 53 + where 54 + D: serde::Deserializer<'de>, 55 + { 56 + use serde::de::{Error, MapAccess, Visitor}; 57 + use std::fmt; 58 + 59 + struct BlobVisitor; 60 + 61 + impl<'de> Visitor<'de> for BlobVisitor { 62 + type Value = Blob; 63 + 64 + fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result { 65 + formatter.write_str("a blob object with mimeType and ref/cid fields") 66 + } 67 + 68 + fn visit_map<A>(self, mut map: A) -> Result<Self::Value, A::Error> 69 + where 70 + A: MapAccess<'de>, 71 + { 72 + let mut mime_type: Option<String> = None; 73 + let mut cid: Option<Cid> = None; 74 + let mut size: Option<i32> = None; 75 + 76 + while let Some(key) = map.next_key::<String>()? { 77 + match key.as_str() { 78 + "$type" => { 79 + // Skip $type field 80 + let _: serde::de::IgnoredAny = map.next_value()?; 81 + } 82 + "mimeType" => { 83 + mime_type = Some(map.next_value()?); 84 + } 85 + "ref" => { 86 + // Try to deserialize ref field as Cid (native CBOR format) 87 + cid = Some(map.next_value()?); 88 + } 89 + "cid" => { 90 + // Legacy format: direct cid field 91 + if cid.is_none() { 92 + cid = Some(map.next_value()?); 93 + } else { 94 + let _: serde::de::IgnoredAny = map.next_value()?; 95 + } 96 + } 97 + "size" => { 98 + size = Some(map.next_value()?); 99 + } 100 + _ => { 101 + // Ignore unknown fields 102 + let _: serde::de::IgnoredAny = map.next_value()?; 103 + } 104 + } 105 + } 106 + 107 + let mime_type = mime_type.ok_or_else(|| A::Error::missing_field("mimeType"))?; 108 + let cid = cid.ok_or_else(|| A::Error::missing_field("ref or cid"))?; 109 + let size = size.unwrap_or(0); // Default to 0 if missing 110 + 111 + Ok(Blob { 112 + mime_type, 113 + cid, 114 + size, 115 + }) 116 + } 117 + } 118 + 119 + deserializer.deserialize_map(BlobVisitor) 120 + } 45 121 } 46 122 47 123 /// Blob type for JSON deserialization (Slingshot, string CID or {$link: "cid"} format)