# Deserialising from toml adds extra double quotes. Can I get rid of them at the time of deserializing, or should I trim it explicitly later? Thanks

**URL:** <https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570>\
**Category:** help\
**Created:** [September 21, 2022, 10:33pm UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570 "2022-09-21T22:33:50Z")\
**Posts on this page:** 13\
**Page:** 1

<div class="post-metadata">

**Author:** ![nohupped](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/nohupped/32/29200_2.png) [@nohupped](https://users.rust-lang.org/u/nohupped)\
**Post date:** [September 21, 2022, 10:33pm UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/1 "2022-09-21T22:33:50Z")

</div>

```rust
#![allow(unused)]
use std::{sync::Arc, collections::HashMap};

use serde::{Deserialize, Deserializer};
use toml::{self, Value}; // 0.5.9

fn main() {
    let toml_string = r#"[foobar]
arg = "foo"
[[foobar.skip]]
name = "foo"
attr = [["foo", "bar"], ["baz", "abc"]]
[[foobar.skip]]
name = "another_foo"
    "#;
    println!("{}",toml_string);
let foo: Custom = toml::from_str(toml_string).unwrap();
println!("Foo: {:?}", foo);
}

#[derive(Debug, Deserialize)]
pub struct Custom {
    foobar: FooBar 
}
#[derive(Debug, Deserialize)]
pub struct FooBar {
    arg: String,
    #[serde(deserialize_with = "parse_skip")]
    skip: Option<Arc<Vec<Skip>>>,
}
#[derive(Debug, Default)]
pub struct Skip {
    pub name: String,
    pub attr: Option<Arc<HashMap<String, String>>>,
}

fn parse_skip<'de, D>(deserializer: D) -> Result<Option<Arc<Vec<Skip>>>, D::Error>
where
    D: Deserializer<'de>,
{
    let mut skips: Vec<Skip> = Vec::new();
    let vals: Vec<HashMap<&str, Value>> = Deserialize::deserialize(deserializer)?;
    for val in vals.into_iter() {
        let mut skip = Skip {
            ..Default::default()
        };
        for (k, v) in val.into_iter() {
            
            if k.eq("name") {
                skip.name = v.to_string();
            }
            if k.eq("attr") && v.is_array() {
                let labels = v
                    .as_array()
                    .into_iter()
                    .filter(|l| l.len() == 2)
                    .map(|f| {
                        
                        (f[0].to_string(), f[1].to_string())
                        
                    })
                    .collect::<HashMap<String, String>>();
                skip.attr = Some(Arc::new(labels));
            }
        }
        skips.push(skip);

    }
    Ok(Some(Arc::new(skips)))
}

```

([Playground](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=31a54343abf15a896d3d93867fb0221f))

Output:

```rust
[foobar]
arg = "foo"
[[foobar.skip]]
name = "foo"
attr = [["foo", "bar"], ["baz", "abc"]]
[[foobar.skip]]
name = "another_foo"
    
Foo: Custom { foobar: FooBar { arg: "foo", skip: Some([Skip { name: "\"foo\"", attr: Some({"[\"foo\", \"bar\"]": "[\"baz\", \"abc\"]"}) }, Skip { name: "\"another_foo\"", attr: None }]) } }

```

Errors:

```rust
   Compiling playground v0.0.1 (/playground)
    Finished dev [unoptimized + debuginfo] target(s) in 1.89s
     Running `target/debug/playground`

```

Is it possible to get rid of the extra double quotes

```rust
name: "\"foo\""

```

and serialize it as

```rust
name: "foo"

```

?  
Thank you.

---

<div class="post-metadata">

**Author:** ![Heliozoa](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/heliozoa/32/16524_2.png) [@Heliozoa](https://users.rust-lang.org/u/Heliozoa)\
**Post date:** [September 21, 2022, 10:51pm UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/2 "2022-09-21T22:51:57Z")

</div>

It's your own deserializer function that adds the quotes.

```rust
fn main() {
    println!("{}", Value::String("test".to_string()));
}

```

```rust
"test"

```

`toml::Value`'s `Display` impl (which is used by `to_string`) outputs the value as it would appear in a toml file, in this case the string `foo` becomes `"foo"`. You should use `match` or `Value::as_str` instead.

---

<div class="post-metadata">

**Author:** ![nohupped](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/nohupped/32/29200_2.png) [@nohupped](https://users.rust-lang.org/u/nohupped)\
**Post date:** [September 22, 2022, 7:33am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/3 "2022-09-22T07:33:03Z")

</div>

Thank you @Heliozoa . However, my type inside the hashmap is a String, not &str and `Value::as_str` returns an `&str`, so wouldn't that require me to use `to_string()`, `to_owned()` or `format!()` to clone it as a String?

---

<div class="post-metadata">

**Author:** ![bjorn3](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/bjorn3/32/5255_2.png) [@bjorn3](https://users.rust-lang.org/u/bjorn3)\
**Post date:** [September 22, 2022, 8:37am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/4 "2022-09-22T08:37:04Z")

</div>

You should probably use `.as_str().to_owned()`. `.to_string()` uses the `Display` impl of `Value` to get the value, which prints out toml. `.as_str()` extracts an `&str` and then `.to_owned()` turns it into an owned `String`.

---

<div class="post-metadata">

**Author:** ![H2CO3](https://avatars.discourse-cdn.com/v4/letter/h/b5ac83/32.png) [@H2CO3](https://users.rust-lang.org/u/H2CO3)\
**Post date:** [September 22, 2022, 8:46am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/5 "2022-09-22T08:46:40Z")

</div>

The 30 000-foot view question is: why are you deserializing into a `Value` in the first place? Your data clearly has a schema (it's statically typed), so you should be deserializing directly into your own domain objects instead of the toml Value type.

---

<div class="post-metadata">

**Author:** ![nohupped](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/nohupped/32/29200_2.png) [@nohupped](https://users.rust-lang.org/u/nohupped)\
**Post date:** [September 22, 2022, 9:50am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/6 "2022-09-22T09:50:25Z")

</div>

Thank you. The reason for deserializing it to a `Value` is because both are different types

```rust
"attr": Array()

```

and

```rust
"name": String()

```

or am I'm doing it wrong here?

---

<div class="post-metadata">

**Author:** ![H2CO3](https://avatars.discourse-cdn.com/v4/letter/h/b5ac83/32.png) [@H2CO3](https://users.rust-lang.org/u/H2CO3)\
**Post date:** [September 22, 2022, 10:03am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/7 "2022-09-22T10:03:38Z")

</div>

You can deserialize into structs with different types of fields. In fact you are doing just that implicitly with all of the other `#[derive(Deserialize)]` impls. What are you trying to achieve that doesn't work out of the box with the derived, strongly-typed impls?

---

<div class="post-metadata">

**Author:** ![nohupped](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/nohupped/32/29200_2.png) [@nohupped](https://users.rust-lang.org/u/nohupped)\
**Post date:** [September 22, 2022, 10:04am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/8 "2022-09-22T10:04:42Z")

</div>

Thank you. Let me try that and I will update the progress here.

---

<div class="post-metadata">

**Author:** ![nohupped](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/nohupped/32/29200_2.png) [@nohupped](https://users.rust-lang.org/u/nohupped)\
**Post date:** [September 22, 2022, 9:32pm UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/9 "2022-09-22T21:32:32Z")

</div>

`to_owned` from `as_str` was producing the same output, but using `write!` macro to create a `String` from the `&str` returned by `as_str` did the trick.  
Thank you.

---

<div class="post-metadata">

**Author:** ![H2CO3](https://avatars.discourse-cdn.com/v4/letter/h/b5ac83/32.png) [@H2CO3](https://users.rust-lang.org/u/H2CO3)\
**Post date:** [September 23, 2022, 1:20am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/10 "2022-09-23T01:20:02Z")

</div>

There must be something else you are overlooking here. `<&str>::to_owned()` definitely does not add any quotes on its own.

---

<div class="post-metadata">

**Author:** ![Heliozoa](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/heliozoa/32/16524_2.png) [@Heliozoa](https://users.rust-lang.org/u/Heliozoa)\
**Post date:** [September 23, 2022, 6:29am UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/11 "2022-09-23T06:29:33Z")

</div>

> [@nohupped](#):
>
> `Value::as_str` returns an `&str`, so wouldn't that require me to use `to_string()`, `to_owned()` or `format!()` to clone it as a String?

I also mentioned `match`, because `Value` is a regular enum where the String variant contains the string: [Value in toml::value - Rust](https://docs.rs/toml/latest/toml/value/enum.Value.html)  
So you can use `match` (or `if let`) to get the string out of it

```rust
if let Value::String(s) = value {
    println!("{s}");
}
match value {
    Value::String(s) => println!("{s}"),
    _ => panic!("something else")
}

```

---

<div class="post-metadata">

**Author:** ![nohupped](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/nohupped/32/29200_2.png) [@nohupped](https://users.rust-lang.org/u/nohupped)\
**Post date:** [September 23, 2022, 4:32pm UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/12 "2022-09-23T16:32:02Z")

</div>

You're right. I was exhausted and I didn't know what I was writing. Started fresh, used `match` to cleanly parse each enums from `toml::Value` and yes, `to_owned()` doesn't add quotes. Everyone here were of great help. Thank you.

---

<div class="post-metadata">

**Author:** ![system](https://sea1.discourse-cdn.com/flex019/user_avatar/users.rust-lang.org/system/32/51372_2.png) [@system](https://users.rust-lang.org/u/system)\
**Post date:** [December 22, 2022, 4:32pm UTC](https://users.rust-lang.org/t/deserialising-from-toml-adds-extra-double-quotes-can-i-get-rid-of-them-at-the-time-of-deserializing-or-should-i-trim-it-explicitly-later-thanks/81570/13 "2022-12-22T16:32:47Z")

</div>

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.
