From 5f644cf8f8207e4fd4fba387e01f2a66e01145e9 Mon Sep 17 00:00:00 2001 From: Jason Mobarak Date: Fri, 28 Aug 2020 14:45:47 -0700 Subject: [PATCH] json2json: maintain fields other than "data" [INFRA-266] If we're running json2json and there are fields in the input struct other than "data" we need to maintain those fields. The use case here is for HITL, where there's metadata (a "time" field) that needs to be kept. --- .../targets/resources/sbp2json-cargo.toml | 1 + rust/sbp/src/sbp2json.rs | 24 +++++----- rust/sbp2json/Cargo.toml | 3 +- rust/sbp2json/tests/common/mod.rs | 4 +- rust/sbp2json/tests/test_round_trips.rs | 48 ++++++++++++++++++- test_data/serial-link.log.json | 10 ++++ 6 files changed, 74 insertions(+), 16 deletions(-) create mode 100644 test_data/serial-link.log.json diff --git a/generator/sbpg/targets/resources/sbp2json-cargo.toml b/generator/sbpg/targets/resources/sbp2json-cargo.toml index bd690c9c60..01d8fd9017 100644 --- a/generator/sbpg/targets/resources/sbp2json-cargo.toml +++ b/generator/sbpg/targets/resources/sbp2json-cargo.toml @@ -25,6 +25,7 @@ features = ["sbp2json"] [dev-dependencies] sha2 = "0.8" hex = "0.4" +serde_json = "1.0" [profile.release] lto = true diff --git a/rust/sbp/src/sbp2json.rs b/rust/sbp/src/sbp2json.rs index 97f69706ed..3388f89d64 100644 --- a/rust/sbp/src/sbp2json.rs +++ b/rust/sbp/src/sbp2json.rs @@ -191,7 +191,7 @@ fn add_common_fields<'a>( /// etc). to the outputted JSON object. fn write_sbp_json_value( float_compat: bool, - rewrap_data: bool, + rewrap_data: Option, base64_payload: &mut String, common_sbp: &dyn SBPMessage, slice: &[u8], @@ -200,12 +200,12 @@ fn write_sbp_json_value( ) -> Result<()> { let value = unpack(value); let value = add_common_fields(common_sbp, slice, value.unwrap(), base64_payload); - let data_wrapped; - let value = if rewrap_data { - data_wrapped = json!({ "data": value }); - &data_wrapped + let value = if let Some(mut rewrap_data) = rewrap_data { + let data_obj = rewrap_data.as_object_mut().unwrap(); + data_obj.insert("data".into(), value.clone()); + rewrap_data } else { - value + value.clone() }; if float_compat { let io_ref = Rc::get_mut(stream).expect("could not get output stream"); @@ -223,18 +223,18 @@ fn write_sbp_json_value( /// The Swift console stores SBP JSON in the "data" field of a JSON object, if this field is /// present then we should unpack the SPB JSON from it. -fn unwrap_data_obj<'a>(value: &'a Value) -> (&'a Value, bool) { +fn unwrap_data_obj<'a>(value: &'a Value) -> (&'a Value, Option) { if !value.is_object() { - return (value, false); + return (value, None); } let map = value.as_object().unwrap(); if map.contains_key("payload") { - return (value, false); + return (value, None); } if !map.contains_key("data") { - return (value, false); + return (value, None); } - (map.get("data").unwrap(), true) + (map.get("data").unwrap(), Some(value.clone())) } /// Unwrap and return the "payload" key from a JSON object, if it exists. @@ -454,7 +454,7 @@ pub fn sbp2json_read_loop( let mut value = serde_json::to_value(&msg)?; write_sbp_json_value( float_compat, - false, + None, &mut base64_payload, common_sbp, slice, diff --git a/rust/sbp2json/Cargo.toml b/rust/sbp2json/Cargo.toml index 996a6bb4d6..62f6c5efa6 100644 --- a/rust/sbp2json/Cargo.toml +++ b/rust/sbp2json/Cargo.toml @@ -25,6 +25,7 @@ features = ["sbp2json"] [dev-dependencies] sha2 = "0.8" hex = "0.4" +serde_json = "1.0" [profile.release] lto = true @@ -40,4 +41,4 @@ path = "src/json2sbp.rs" [[bin]] name = "json2json" -path = "src/json2json.rs" \ No newline at end of file +path = "src/json2json.rs" diff --git a/rust/sbp2json/tests/common/mod.rs b/rust/sbp2json/tests/common/mod.rs index e954e4df5b..96243f8124 100644 --- a/rust/sbp2json/tests/common/mod.rs +++ b/rust/sbp2json/tests/common/mod.rs @@ -12,7 +12,7 @@ use sha2::{Digest, Sha256}; use sbp::sbp2json::Result; -fn find_project_root() -> Option { +pub fn find_project_root() -> Option { let exe = env::current_exe(); assert!(exe.is_ok()); let mut path = exe.unwrap(); @@ -32,7 +32,7 @@ fn find_project_root() -> Option { return None; } -struct DeleteTestOutput { +pub struct DeleteTestOutput { files: Vec, } diff --git a/rust/sbp2json/tests/test_round_trips.rs b/rust/sbp2json/tests/test_round_trips.rs index c6a6af7f1b..91755d57f3 100644 --- a/rust/sbp2json/tests/test_round_trips.rs +++ b/rust/sbp2json/tests/test_round_trips.rs @@ -1,11 +1,13 @@ use std::boxed::Box; +use std::fs::File; use std::io::prelude::*; +use std::io::BufReader; use std::rc::Rc; #[macro_use] mod common; -use common::{test_round_trip, ThirdTransform}; +use common::{find_project_root, test_round_trip, DeleteTestOutput, ThirdTransform}; use sbp::sbp2json::json2json_read_loop; use sbp::sbp2json::json2sbp_read_loop; @@ -80,3 +82,47 @@ fn test_json2json() -> Result<()> { third_transform, ) } + +#[test] +fn test_json2json_maintain_fields() -> Result<()> { + let mut del_test_output = DeleteTestOutput::new(); + + let root = find_project_root().unwrap(); + let root = root.as_path(); + + let output_path = root.join("test_data/serial-link.log.json.output"); + + { + let input_path = root.join("test_data/serial-link.log.json"); + let mut input_file = File::open(input_path).expect("could not open input file"); + + del_test_output.add_test_output(&output_path); + + let output_file = File::create(&output_path).expect("could not create output file"); + + let mut output_file: Rc> = Rc::new(Box::new(output_file)); + + assert!(json2json_read_loop(false, false, &mut input_file, &mut output_file).is_ok()); + } + + let mut message_count = 0; + + { + let output_file = File::open(output_path).expect("could not open input file"); + let output_file = BufReader::new(output_file); + + for line in output_file.lines() { + let value: serde_json::Value = serde_json::from_str(&line.unwrap()).unwrap(); + assert!(value.is_object()); + + let value = value.as_object().unwrap(); + assert!(value.contains_key("time")); + + message_count += 1; + } + } + + assert_eq!(message_count, 10); + + Ok(()) +} diff --git a/test_data/serial-link.log.json b/test_data/serial-link.log.json new file mode 100644 index 0000000000..f144613a8b --- /dev/null +++ b/test_data/serial-link.log.json @@ -0,0 +1,10 @@ +{"time":"2020-08-28T20:02:28.43443402Z","data":{"length":82,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIGNoYW5nZWQ6IGVuYWJsZV9icm9hZGNhc3QgPSAwLCBicm9hZGNhc3QgcG9ydCA9IDU2NjY2LCBvZmZzZXQgPSAtMzIuMTU5Nw==","crc":15453}} +{"time":"2020-08-28T20:02:28.454301488Z","data":{"length":82,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIGNoYW5nZWQ6IGVuYWJsZV9icm9hZGNhc3QgPSAwLCBicm9hZGNhc3QgcG9ydCA9IDU2NjY2LCBvZmZzZXQgPSAtMzIuMTU5Nw==","crc":15453}} +{"time":"2020-08-28T20:02:28.464622847Z","data":{"length":34,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIHdhdGNoZWQ6IG50cmlwX2VuYWJsZT0gMA==","crc":21196}} +{"time":"2020-08-28T20:02:28.474422726Z","data":{"length":82,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIGNoYW5nZWQ6IGVuYWJsZV9icm9hZGNhc3QgPSAwLCBicm9hZGNhc3QgcG9ydCA9IDU2NjY2LCBvZmZzZXQgPSAtMzIuMTU5Nw==","crc":15453}} +{"time":"2020-08-28T20:02:28.484696224Z","data":{"length":34,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIHdhdGNoZWQ6IG50cmlwX2VuYWJsZT0gMA==","crc":21196}} +{"time":"2020-08-28T20:02:28.494474444Z","data":{"length":82,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIGNoYW5nZWQ6IGVuYWJsZV9icm9hZGNhc3QgPSAwLCBicm9hZGNhc3QgcG9ydCA9IDU2NjY2LCBvZmZzZXQgPSAtMzIuMTU5Nw==","crc":15453}} +{"time":"2020-08-28T20:02:28.504458866Z","data":{"length":34,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIHdhdGNoZWQ6IG50cmlwX2VuYWJsZT0gMA==","crc":21196}} +{"time":"2020-08-28T20:02:28.515197572Z","data":{"length":82,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIGNoYW5nZWQ6IGVuYWJsZV9icm9hZGNhc3QgPSAwLCBicm9hZGNhc3QgcG9ydCA9IDU2NjY2LCBvZmZzZXQgPSAtMzIuMTU5Nw==","crc":15453}} +{"time":"2020-08-28T20:02:28.524860578Z","data":{"length":34,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIHdhdGNoZWQ6IG50cmlwX2VuYWJsZT0gMA==","crc":21196}} +{"time":"2020-08-28T20:02:28.534466535Z","data":{"length":82,"preamble":85,"sender":44432,"msg_type":1025,"payload":"B1NldHRpbmdzIGNoYW5nZWQ6IGVuYWJsZV9icm9hZGNhc3QgPSAwLCBicm9hZGNhc3QgcG9ydCA9IDU2NjY2LCBvZmZzZXQgPSAtMzIuMTU5Nw==","crc":15453}}