rmpv/encode/
value.rs

1use std::io::Write;
2
3use rmp::encode::{write_nil, write_bool, write_uint, write_sint, write_f32, write_f64, write_str,
4                  write_bin, write_array_len, write_map_len, write_ext_meta};
5
6use crate::{Integer, IntPriv, Utf8String, Value};
7use super::Error;
8
9/// Encodes and attempts to write the most efficient representation of the given Value.
10///
11/// # Note
12///
13/// All instances of `ErrorKind::Interrupted` are handled by this function and the underlying
14/// operation is retried.
15pub fn write_value<W>(wr: &mut W, val: &Value) -> Result<(), Error>
16    where W: Write
17{
18    match *val {
19        Value::Nil => {
20            write_nil(wr).map_err(|err| Error::InvalidMarkerWrite(err))?;
21        }
22        Value::Boolean(val) => {
23            write_bool(wr, val).map_err(|err| Error::InvalidMarkerWrite(err))?;
24        }
25        Value::Integer(Integer { n }) => {
26            match n {
27                IntPriv::PosInt(n) => {
28                    write_uint(wr, n)?;
29                }
30                IntPriv::NegInt(n) => {
31                    write_sint(wr, n)?;
32                }
33            }
34        }
35        Value::F32(val) => {
36            write_f32(wr, val)?;
37        }
38        Value::F64(val) => {
39            write_f64(wr, val)?;
40        }
41        Value::String(Utf8String { ref s }) => {
42            match *s {
43                Ok(ref val) => write_str(wr, &val)?,
44                Err(ref err) => write_bin(wr, &err.0)?,
45            }
46        }
47        Value::Binary(ref val) => {
48            write_bin(wr, &val)?;
49        }
50        Value::Array(ref vec) => {
51            write_array_len(wr, vec.len() as u32)?;
52            for v in vec {
53                write_value(wr, v)?;
54            }
55        }
56        Value::Map(ref map) => {
57            write_map_len(wr, map.len() as u32)?;
58            for &(ref key, ref val) in map {
59                write_value(wr, key)?;
60                write_value(wr, val)?;
61            }
62        }
63        Value::Ext(ty, ref data) => {
64            write_ext_meta(wr, data.len() as u32, ty)?;
65            wr.write_all(data).map_err(|err| Error::InvalidDataWrite(err))?;
66        }
67    }
68
69    Ok(())
70}