如何在Rust中将serde_json::Value转换为prost_types::Struct?
实现serde_json::Value到prost_types::Struct的转换及可用Crate推荐
手动实现方案
你可以通过递归处理serde_json::Value的不同变体,将其映射为prost_types对应的类型:
use prost_types::{Struct, Value, ListValue}; use serde_json::{Value as JsonValue, Map}; fn to_struct(json: JsonValue) -> Struct { let mut fields = std::collections::BTreeMap::new(); if let JsonValue::Object(obj) = json { for (key, val) in obj { fields.insert(key, to_prost_value(val)); } } Struct { fields } } fn to_prost_value(json_val: JsonValue) -> Value { match json_val { JsonValue::Null => Value { kind: Some(Value::Kind::NullValue(0)) }, JsonValue::Bool(b) => Value { kind: Some(Value::Kind::BoolValue(b)) }, JsonValue::Number(num) => { if let Some(int_val) = num.as_i64() { Value { kind: Some(Value::Kind::Int64Value(int_val)) } } else if let Some(uint_val) = num.as_u64() { Value { kind: Some(Value::Kind::Uint64Value(uint_val)) } } else if let Some(float_val) = num.as_f64() { Value { kind: Some(Value::Kind::DoubleValue(float_val)) } } else { // 处理无法识别的数字类型,默认转为Null Value { kind: Some(Value::Kind::NullValue(0)) } } }, JsonValue::String(s) => Value { kind: Some(Value::Kind::StringValue(s)) }, JsonValue::Array(arr) => { let values = arr.into_iter().map(to_prost_value).collect(); Value { kind: Some(Value::Kind::ListValue(ListValue { values })) } }, JsonValue::Object(obj) => { let struct_val = to_struct(JsonValue::Object(obj)); Value { kind: Some(Value::Kind::StructValue(struct_val)) } }, } }
代码说明
to_struct专门处理JSON对象,将键值对转换为Struct的fields集合to_prost_value递归处理所有JSON值类型:- 布尔值、字符串直接映射到对应Protobuf类型
- 数字优先尝试转为整数类型,再降级为浮点数
- JSON数组转为
ListValue,嵌套对象递归转为Struct - Null值对应Protobuf的
NullValue
现成Crate方案
可以直接使用prost-json这个Crate,它封装了完整的转换逻辑:
步骤1:添加依赖
在Cargo.toml中加入:
[dependencies] prost-json = "0.4" serde_json = "1.0" prost-types = "0.12"
步骤2:使用转换方法
use prost_json::ValueExt; use serde_json::Value as JsonValue; use prost_types::Struct; fn to_struct(json: JsonValue) -> Struct { json.into() }
prost-json实现了From/Into trait,直接通过类型转换就能完成双向映射,无需手动处理递归逻辑。
内容的提问来源于stack exchange,提问作者Yang Bo
相关产品推荐
相关产品推荐

