Skip to content

Commit

Permalink
Allow any supported type when reading JSON array elements or object v…
Browse files Browse the repository at this point in the history
…alues
  • Loading branch information
zargony committed Oct 7, 2024
1 parent 2b18ae0 commit 4eeaaaa
Show file tree
Hide file tree
Showing 3 changed files with 14 additions and 11 deletions.
2 changes: 1 addition & 1 deletion firmware/src/config.rs
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,7 @@ impl FromJson for Config {
) -> Result<Self, json::Error<R::Error>> {
let mut this = Self::default();
reader
.read_object(|k, v| match k.as_str() {
.read_object(|k, v: json::Value| match &*k {
"wifi-ssid" => this.wifi_ssid = v.try_into().unwrap(),
"wifi-password" => this.wifi_password = v.try_into().unwrap(),
_ => (),
Expand Down
19 changes: 11 additions & 8 deletions firmware/src/json/reader.rs
Original file line number Diff line number Diff line change
Expand Up @@ -69,17 +69,17 @@ impl<R: BufRead> Reader<R> {
/// A JSON object is read and parsed key by key. The given closure is called for every key
/// value pair as it is parsed. This doesn't need to allocate memory for all keys and values of
/// the object, just for one key value pair at a time.
pub async fn read_object(
pub async fn read_object<T: FromJson>(
&mut self,
mut f: impl FnMut(String, Value),
mut f: impl FnMut(String, T),
) -> Result<(), Error<R::Error>> {
self.trim().await?;
self.expect(b'{').await?;
loop {
self.trim().await?;
let key = self.read_string().await?;
self.expect(b':').await?;
let value = self.read_any().await?;
let value = self.read().await?;
f(key, value);
self.trim().await?;
match self.peek().await? {
Expand All @@ -97,11 +97,14 @@ impl<R: BufRead> Reader<R> {
/// A JSON array is read and parsed element by element. The given closure is called for every
/// element as it is parsed. This doesn't need to allocate memory for all elements of the
/// array, just for one element at a time.
pub async fn read_array(&mut self, mut f: impl FnMut(Value)) -> Result<(), Error<R::Error>> {
pub async fn read_array<T: FromJson>(
&mut self,
mut f: impl FnMut(T),
) -> Result<(), Error<R::Error>> {
self.trim().await?;
self.expect(b'[').await?;
loop {
let elem = self.read_any().await?;
let elem = self.read().await?;
f(elem);
self.trim().await?;
match self.peek().await? {
Expand Down Expand Up @@ -414,7 +417,7 @@ mod tests {
) -> Result<Self, Error<R::Error>> {
let mut test = Self::default();
reader
.read_object(|k, v| match k.as_str() {
.read_object(|k, v: Value| match &*k {
"foo" => test.foo = v.try_into().unwrap(),
"bar" => test.bar = v.try_into().unwrap(),
"baz" => test.baz = v.try_into().unwrap(),
Expand Down Expand Up @@ -470,7 +473,7 @@ mod tests {
async fn read_object() {
let json = r#"{"foo": "hi", "bar": 42, "baz": true}"#;
let mut values = Vec::new();
let collect = |k, v| values.push((k, v));
let collect = |k, v: Value| values.push((k, v));
assert_eq!(reader(json).read_object(collect).await, Ok(()));
assert_eq!(values.len(), 3);
assert_eq!(values[0].0, "foo");
Expand All @@ -485,7 +488,7 @@ mod tests {
async fn read_array() {
let json = "[1, 2, 3, 4]";
let mut values = Vec::new();
let collect = |v| values.push(v);
let collect = |v: Value| values.push(v);
assert_eq!(reader(json).read_array(collect).await, Ok(()));
assert_eq!(values.len(), 4);
assert_eq!(values[0], Value::Integer(1));
Expand Down
4 changes: 2 additions & 2 deletions firmware/src/json/writer.rs
Original file line number Diff line number Diff line change
Expand Up @@ -385,7 +385,7 @@ mod tests {
let mut writer = writer();
let res = writer.$method($($value)?).await;
let json = String::from_utf8(writer.into_inner()).unwrap();
assert_eq!(res.map(|()| json.as_str()), $json)
assert_eq!(res.map(|()| &*json), $json)
}};
}

Expand Down Expand Up @@ -476,7 +476,7 @@ mod tests {
.await;
let json = String::from_utf8(writer.into_inner()).unwrap();
assert_eq!(
res.map(|()| json.as_str()),
res.map(|()| &*json),
Ok(r#"{"foo": "hi", "bar": 42, "baz": true}"#)
);
}
Expand Down

0 comments on commit 4eeaaaa

Please sign in to comment.