summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Orchard <if_coding@fastmail.com>2021-07-28 22:52:15 -0700
committerDavid Orchard <if_coding@fastmail.com>2021-08-15 10:31:18 -0700
commitfc8cf0ed674cbb495df1baff34d4b832ca5fad3c (patch)
treea83c82ff11399ebd2da8d7ae58da31b7f295998c
parent62c84297e5340d717d89c5c0b36ed86dd5ad9d2f (diff)
Use LinkedHashMap in place of HashMap
-rw-r--r--Cargo.toml1
-rw-r--r--examples/async_source/main.rs5
-rw-r--r--examples/glob/src/main.rs14
-rw-r--r--examples/simple/src/main.rs6
-rw-r--r--examples/watch/src/main.rs4
-rw-r--r--src/builder.rs23
-rw-r--r--src/config.rs12
-rw-r--r--src/de.rs5
-rw-r--r--src/env.rs6
-rw-r--r--src/file/format/hjson.rs8
-rw-r--r--src/file/format/ini.rs8
-rw-r--r--src/file/format/json.rs8
-rw-r--r--src/file/format/json5.rs8
-rw-r--r--src/file/format/mod.rs8
-rw-r--r--src/file/format/ron.rs8
-rw-r--r--src/file/format/toml.rs8
-rw-r--r--src/file/format/yaml.rs8
-rw-r--r--src/file/mod.rs6
-rw-r--r--src/path/mod.rs10
-rw-r--r--src/source.rs22
-rw-r--r--src/value.rs10
-rw-r--r--tests/async_builder.rs3
-rw-r--r--tests/errors.rs3
-rw-r--r--tests/file_hjson.rs4
-rw-r--r--tests/file_json.rs4
-rw-r--r--tests/file_json5.rs4
-rw-r--r--tests/file_ron.rs4
-rw-r--r--tests/file_toml.rs4
-rw-r--r--tests/file_yaml.rs4
-rw-r--r--tests/get.rs15
-rw-r--r--tests/legacy/errors.rs3
-rw-r--r--tests/legacy/file_hjson.rs4
-rw-r--r--tests/legacy/file_json.rs4
-rw-r--r--tests/legacy/file_ron.rs4
-rw-r--r--tests/legacy/file_toml.rs4
-rw-r--r--tests/legacy/file_yaml.rs4
-rw-r--r--tests/legacy/get.rs15
-rw-r--r--tests/legacy/merge.rs5
-rw-r--r--tests/merge.rs5
39 files changed, 144 insertions, 137 deletions
diff --git a/Cargo.toml b/Cargo.toml
index f72389f..68e6617 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -35,6 +35,7 @@ serde-hjson = { version = "0.9", default-features = false, optional = true }
rust-ini = { version = "0.17", optional = true }
ron = { version = "0.6", optional = true }
json5_rs = { version = "0.3", optional = true, package = "json5" }
+linked-hash-map = { version = "0.5.4", features = ["serde_impl"] }
[dev-dependencies]
serde_derive = "1.0.8"
diff --git a/examples/async_source/main.rs b/examples/async_source/main.rs
index 10befe0..6c836a3 100644
--- a/examples/async_source/main.rs
+++ b/examples/async_source/main.rs
@@ -1,4 +1,5 @@
-use std::{collections::HashMap, error::Error};
+use linked_hash_map::LinkedHashMap;
+use std::error::Error;
use config::{builder::AsyncState, AsyncSource, ConfigBuilder, ConfigError, FileFormat};
@@ -56,7 +57,7 @@ struct HttpSource {
#[async_trait]
impl AsyncSource for HttpSource {
- async fn collect(&self) -> Result<HashMap<String, config::Value>, ConfigError> {
+ async fn collect(&self) -> Result<LinkedHashMap<String, config::Value>, ConfigError> {
reqwest::get(&self.uri)
.await
.map_err(|e| ConfigError::Foreign(Box::new(e)))? // error conversion is possible from custom AsyncSource impls
diff --git a/examples/glob/src/main.rs b/examples/glob/src/main.rs
index b3183ef..c85f86e 100644
--- a/examples/glob/src/main.rs
+++ b/examples/glob/src/main.rs
@@ -1,5 +1,5 @@
use std::path::Path;
-use std::collections::HashMap;
+use std::collections::LinkedHashMap;
use config::*;
use glob::glob;
@@ -14,9 +14,9 @@ fn main() {
.merge(File::from(Path::new("conf/05-some.yml"))).unwrap()
.merge(File::from(Path::new("conf/99-extra.json"))).unwrap();
- // Print out our settings (as a HashMap)
+ // Print out our settings (as a LinkedHashMap)
println!("\n{:?} \n\n-----------",
- settings.try_into::<HashMap<String, String>>().unwrap());
+ settings.try_into::<LinkedHashMap<String, String>>().unwrap());
// Option 2
// --------
@@ -28,9 +28,9 @@ fn main() {
File::from(Path::new("conf/99-extra.json"))])
.unwrap();
- // Print out our settings (as a HashMap)
+ // Print out our settings (as a LinkedHashMap)
println!("\n{:?} \n\n-----------",
- settings.try_into::<HashMap<String, String>>().unwrap());
+ settings.try_into::<LinkedHashMap<String, String>>().unwrap());
// Option 3
// --------
@@ -43,7 +43,7 @@ fn main() {
.collect::<Vec<_>>())
.unwrap();
- // Print out our settings (as a HashMap)
+ // Print out our settings (as a LinkedHashMap)
println!("\n{:?} \n\n-----------",
- settings.try_into::<HashMap<String, String>>().unwrap());
+ settings.try_into::<LinkedHashMap<String, String>>().unwrap());
}
diff --git a/examples/simple/src/main.rs b/examples/simple/src/main.rs
index 1c7ddb7..698401a 100644
--- a/examples/simple/src/main.rs
+++ b/examples/simple/src/main.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use std::collections::LinkedHashMap;
fn main() {
let mut settings = config::Config::default();
@@ -9,7 +9,7 @@ fn main() {
// Eg.. `APP_DEBUG=1 ./target/app` would set the `debug` key
.merge(config::Environment::with_prefix("APP")).unwrap();
- // Print out our settings (as a HashMap)
+ // Print out our settings (as a LinkedHashMap)
println!("{:?}",
- settings.try_into::<HashMap<String, String>>().unwrap());
+ settings.try_into::<LinkedHashMap<String, String>>().unwrap());
}
diff --git a/examples/watch/src/main.rs b/examples/watch/src/main.rs
index a197390..9e676ad 100644
--- a/examples/watch/src/main.rs
+++ b/examples/watch/src/main.rs
@@ -1,5 +1,5 @@
use config::*;
-use std::collections::HashMap;
+use std::collections::LinkedHashMap;
use std::sync::RwLock;
use notify::{RecommendedWatcher, DebouncedEvent, Watcher, RecursiveMode};
use std::sync::mpsc::channel;
@@ -20,7 +20,7 @@ fn show() {
.read()
.unwrap()
.clone()
- .try_into::<HashMap<String, String>>()
+ .try_into::<LinkedHashMap<String, String>>()
.unwrap());
}
diff --git a/src/builder.rs b/src/builder.rs
index bb88f44..65f49ae 100644
--- a/src/builder.rs
+++ b/src/builder.rs
@@ -1,5 +1,6 @@
+use linked_hash_map::LinkedHashMap;
+use std::iter::IntoIterator;
use std::str::FromStr;
-use std::{collections::HashMap, iter::IntoIterator};
use crate::error::Result;
use crate::source::AsyncSource;
@@ -87,8 +88,8 @@ use crate::{config::Config, path::Expression, source::Source, value::Value};
/// ```
#[derive(Debug, Clone, Default)]
pub struct ConfigBuilder<St: BuilderState> {
- defaults: HashMap<Expression, Value>,
- overrides: HashMap<Expression, Value>,
+ defaults: LinkedHashMap<Expression, Value>,
+ overrides: LinkedHashMap<Expression, Value>,
state: St,
}
@@ -120,8 +121,8 @@ pub struct DefaultState {
/// Refer to [`ConfigBuilder`] for similar API sample usage or to the examples folder of the crate, where such a source is implemented.
#[derive(Debug, Clone, Default)]
pub struct AsyncConfigBuilder {
- defaults: HashMap<Expression, Value>,
- overrides: HashMap<Expression, Value>,
+ defaults: LinkedHashMap<Expression, Value>,
+ overrides: LinkedHashMap<Expression, Value>,
sources: Vec<SourceType>,
}
@@ -244,11 +245,11 @@ impl ConfigBuilder<DefaultState> {
}
fn build_internal(
- defaults: HashMap<Expression, Value>,
- overrides: HashMap<Expression, Value>,
+ defaults: LinkedHashMap<Expression, Value>,
+ overrides: LinkedHashMap<Expression, Value>,
sources: &[Box<dyn Source + Send + Sync>],
) -> Result<Config> {
- let mut cache: Value = HashMap::<String, Value>::new().into();
+ let mut cache: Value = LinkedHashMap::<String, Value>::new().into();
// Add defaults
for (key, val) in defaults.into_iter() {
@@ -322,11 +323,11 @@ impl ConfigBuilder<AsyncState> {
}
async fn build_internal(
- defaults: HashMap<Expression, Value>,
- overrides: HashMap<Expression, Value>,
+ defaults: LinkedHashMap<Expression, Value>,
+ overrides: LinkedHashMap<Expression, Value>,
sources: &[SourceType],
) -> Result<Config> {
- let mut cache: Value = HashMap::<String, Value>::new().into();
+ let mut cache: Value = LinkedHashMap::<String, Value>::new().into();
// Add defaults
for (key, val) in defaults.into_iter() {
diff --git a/src/config.rs b/src/config.rs
index b9c64b4..6302c45 100644
--- a/src/config.rs
+++ b/src/config.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::fmt::Debug;
use crate::builder::{ConfigBuilder, DefaultState};
@@ -16,8 +16,8 @@ use crate::value::{Table, Value};
/// them according to the source's priority.
#[derive(Clone, Debug)]
pub struct Config {
- defaults: HashMap<path::Expression, Value>,
- overrides: HashMap<path::Expression, Value>,
+ defaults: LinkedHashMap<path::Expression, Value>,
+ overrides: LinkedHashMap<path::Expression, Value>,
sources: Vec<Box<dyn Source + Send + Sync>>,
/// Root of the cached configuration.
@@ -83,7 +83,7 @@ impl Config {
#[deprecated(since = "0.12.0", note = "please use 'ConfigBuilder' instead")]
pub fn refresh(&mut self) -> Result<&mut Config> {
self.cache = {
- let mut cache: Value = HashMap::<String, Value>::new().into();
+ let mut cache: Value = LinkedHashMap::<String, Value>::new().into();
// Add defaults
for (key, val) in self.defaults.iter() {
@@ -181,7 +181,7 @@ impl Config {
self.get(key).and_then(Value::into_bool)
}
- pub fn get_table(&self, key: &str) -> Result<HashMap<String, Value>> {
+ pub fn get_table(&self, key: &str) -> Result<LinkedHashMap<String, Value>> {
self.get(key).and_then(Value::into_table)
}
@@ -212,7 +212,7 @@ impl Source for Config {
Box::new((*self).clone())
}
- fn collect(&self) -> Result<HashMap<String, Value>> {
+ fn collect(&self) -> Result<LinkedHashMap<String, Value>> {
self.cache.clone().into_table()
}
}
diff --git a/src/de.rs b/src/de.rs
index a7a6fb4..7d66896 100644
--- a/src/de.rs
+++ b/src/de.rs
@@ -1,4 +1,5 @@
-use std::collections::{HashMap, VecDeque};
+use linked_hash_map::LinkedHashMap;
+use std::collections::VecDeque;
use std::iter::Enumerate;
use serde::de;
@@ -199,7 +200,7 @@ struct MapAccess {
}
impl MapAccess {
- fn new(table: HashMap<String, Value>) -> Self {
+ fn new(table: LinkedHashMap<String, Value>) -> Self {
MapAccess {
elements: table.into_iter().collect(),
}
diff --git a/src/env.rs b/src/env.rs
index 3d95e17..2e48701 100644
--- a/src/env.rs
+++ b/src/env.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::env;
use crate::error::*;
@@ -79,8 +79,8 @@ impl Source for Environment {
Box::new((*self).clone())
}
- fn collect(&self) -> Result<HashMap<String, Value>> {
- let mut m = HashMap::new();
+ fn collect(&self) -> Result<LinkedHashMap<String, Value>> {
+ let mut m = LinkedHashMap::new();
let uri: String = "the environment".into();
let separator = self.separator.as_deref().unwrap_or("");
diff --git a/src/file/format/hjson.rs b/src/file/format/hjson.rs
index f94b1d3..a61afef 100644
--- a/src/file/format/hjson.rs
+++ b/src/file/format/hjson.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use crate::value::{Value, ValueKind};
@@ -6,14 +6,14 @@ use crate::value::{Value, ValueKind};
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
// Parse a JSON object value from the text
// TODO: Have a proper error fire if the root of a file is ever not a Table
let value = from_hjson_value(uri, &serde_hjson::from_str(text)?);
match value.kind {
ValueKind::Table(map) => Ok(map),
- _ => Ok(HashMap::new()),
+ _ => Ok(LinkedHashMap::new()),
}
}
@@ -30,7 +30,7 @@ fn from_hjson_value(uri: Option<&String>, value: &serde_hjson::Value) -> Value {
serde_hjson::Value::Bool(value) => Value::new(uri, ValueKind::Boolean(value)),
serde_hjson::Value::Object(ref table) => {
- let mut m = HashMap::new();
+ let mut m = LinkedHashMap::new();
for (key, value) in table {
m.insert(key.clone(), from_hjson_value(uri, value));
diff --git a/src/file/format/ini.rs b/src/file/format/ini.rs
index b45695a..47f3499 100644
--- a/src/file/format/ini.rs
+++ b/src/file/format/ini.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use ini::Ini;
@@ -8,13 +8,13 @@ use crate::value::{Value, ValueKind};
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
- let mut map: HashMap<String, Value> = HashMap::new();
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+ let mut map: LinkedHashMap<String, Value> = LinkedHashMap::new();
let i = Ini::load_from_str(text)?;
for (sec, prop) in i.iter() {
match sec {
Some(sec) => {
- let mut sec_map: HashMap<String, Value> = HashMap::new();
+ let mut sec_map: LinkedHashMap<String, Value> = LinkedHashMap::new();
for (k, v) in prop.iter() {
sec_map.insert(
k.to_owned(),
diff --git a/src/file/format/json.rs b/src/file/format/json.rs
index 87a6e61..a6a9443 100644
--- a/src/file/format/json.rs
+++ b/src/file/format/json.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use crate::value::{Value, ValueKind};
@@ -6,14 +6,14 @@ use crate::value::{Value, ValueKind};
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
// Parse a JSON object value from the text
// TODO: Have a proper error fire if the root of a file is ever not a Table
let value = from_json_value(uri, &serde_json::from_str(text)?);
match value.kind {
ValueKind::Table(map) => Ok(map),
- _ => Ok(HashMap::new()),
+ _ => Ok(LinkedHashMap::new()),
}
}
@@ -34,7 +34,7 @@ fn from_json_value(uri: Option<&String>, value: &serde_json::Value) -> Value {
serde_json::Value::Bool(value) => Value::new(uri, ValueKind::Boolean(value)),
serde_json::Value::Object(ref table) => {
- let mut m = HashMap::new();
+ let mut m = LinkedHashMap::new();
for (key, value) in table {
m.insert(key.clone(), from_json_value(uri, value));
diff --git a/src/file/format/json5.rs b/src/file/format/json5.rs
index ea3390f..952b265 100644
--- a/src/file/format/json5.rs
+++ b/src/file/format/json5.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use crate::error::{ConfigError, Unexpected};
@@ -13,13 +13,13 @@ pub enum Val {
Float(f64),
String(String),
Array(Vec<Val>),
- Object(HashMap<String, Val>),
+ Object(LinkedHashMap<String, Val>),
}
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
match json5_rs::from_str::<Val>(text)? {
Val::String(ref value) => Err(Unexpected::Str(value.clone())),
Val::Integer(value) => Err(Unexpected::Integer(value)),
@@ -29,7 +29,7 @@ pub fn parse(
Val::Null => Err(Unexpected::Unit),
Val::Object(o) => match from_json5_value(uri, Val::Object(o)).kind {
ValueKind::Table(map) => Ok(map),
- _ => Ok(HashMap::new()),
+ _ => Ok(LinkedHashMap::new()),
},
}
.map_err(|err| ConfigError::invalid_root(uri, err))
diff --git a/src/file/format/mod.rs b/src/file/format/mod.rs
index 53bacf6..55d1c7a 100644
--- a/src/file/format/mod.rs
+++ b/src/file/format/mod.rs
@@ -2,7 +2,7 @@
// BUG: ? For some reason this doesn't do anything if I try and function scope this
#![allow(unused_mut)]
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use crate::value::Value;
@@ -62,8 +62,8 @@ pub enum FileFormat {
lazy_static! {
#[doc(hidden)]
// #[allow(unused_mut)] ?
- pub static ref ALL_EXTENSIONS: HashMap<FileFormat, Vec<&'static str>> = {
- let mut formats: HashMap<FileFormat, Vec<_>> = HashMap::new();
+ pub static ref ALL_EXTENSIONS: LinkedHashMap<FileFormat, Vec<&'static str>> = {
+ let mut formats: LinkedHashMap<FileFormat, Vec<_>> = LinkedHashMap::new();
#[cfg(feature = "toml")]
formats.insert(FileFormat::Toml, vec!["toml"]);
@@ -107,7 +107,7 @@ impl FileFormat {
self,
uri: Option<&String>,
text: &str,
- ) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+ ) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
match self {
#[cfg(feature = "toml")]
FileFormat::Toml => toml::parse(uri, text),
diff --git a/src/file/format/ron.rs b/src/file/format/ron.rs
index f7dbce3..a527d6f 100644
--- a/src/file/format/ron.rs
+++ b/src/file/format/ron.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use crate::value::{Value, ValueKind};
@@ -6,12 +6,12 @@ use crate::value::{Value, ValueKind};
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
let value = from_ron_value(uri, ron::from_str(text)?)?;
match value.kind {
ValueKind::Table(map) => Ok(map),
- _ => Ok(HashMap::new()),
+ _ => Ok(LinkedHashMap::new()),
}
}
@@ -56,7 +56,7 @@ fn from_ron_value(
Ok((key, value))
})
- .collect::<Result<HashMap<_, _>, _>>()?;
+ .collect::<Result<LinkedHashMap<_, _>, _>>()?;
ValueKind::Table(map)
}
diff --git a/src/file/format/toml.rs b/src/file/format/toml.rs
index c7c5972..5468d97 100644
--- a/src/file/format/toml.rs
+++ b/src/file/format/toml.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use crate::value::{Value, ValueKind};
@@ -6,14 +6,14 @@ use crate::value::{Value, ValueKind};
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
// Parse a TOML value from the provided text
// TODO: Have a proper error fire if the root of a file is ever not a Table
let value = from_toml_value(uri, &toml::from_str(text)?);
match value.kind {
ValueKind::Table(map) => Ok(map),
- _ => Ok(HashMap::new()),
+ _ => Ok(LinkedHashMap::new()),
}
}
@@ -25,7 +25,7 @@ fn from_toml_value(uri: Option<&String>, value: &toml::Value) -> Value {
toml::Value::Boolean(value) => Value::new(uri, value),
toml::Value::Table(ref table) => {
- let mut m = HashMap::new();
+ let mut m = LinkedHashMap::new();
for (key, value) in table {
m.insert(key.clone(), from_toml_value(uri, value));
diff --git a/src/file/format/yaml.rs b/src/file/format/yaml.rs
index 2526395..246758a 100644
--- a/src/file/format/yaml.rs
+++ b/src/file/format/yaml.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::error::Error;
use std::fmt;
use std::mem;
@@ -10,7 +10,7 @@ use crate::value::{Value, ValueKind};
pub fn parse(
uri: Option<&String>,
text: &str,
-) -> Result<HashMap<String, Value>, Box<dyn Error + Send + Sync>> {
+) -> Result<LinkedHashMap<String, Value>, Box<dyn Error + Send + Sync>> {
// Parse a YAML object from file
let mut docs = yaml::YamlLoader::load_from_str(text)?;
let root = match docs.len() {
@@ -26,7 +26,7 @@ pub fn parse(
match value.kind {
ValueKind::Table(map) => Ok(map),
- _ => Ok(HashMap::new()),
+ _ => Ok(LinkedHashMap::new()),
}
}
@@ -40,7 +40,7 @@ fn from_yaml_value(uri: Option<&String>, value: &yaml::Yaml) -> Value {
yaml::Yaml::Integer(value) => Value::new(uri, ValueKind::Integer(value)),
yaml::Yaml::Boolean(value) => Value::new(uri, ValueKind::Boolean(value)),
yaml::Yaml::Hash(ref table) => {
- let mut m = HashMap::new();
+ let mut m = LinkedHashMap::new();
for (key, value) in table {
if let Some(k) = key.as_str() {
m.insert(k.to_owned(), from_yaml_value(uri, value));
diff --git a/src/file/mod.rs b/src/file/mod.rs
index b00a271..02fd51f 100644
--- a/src/file/mod.rs
+++ b/src/file/mod.rs
@@ -1,7 +1,7 @@
mod format;
pub mod source;
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::path::{Path, PathBuf};
use crate::error::*;
@@ -99,7 +99,7 @@ where
Box::new((*self).clone())
}
- fn collect(&self) -> Result<HashMap<String, Value>> {
+ fn collect(&self) -> Result<LinkedHashMap<String, Value>> {
// Coerce the file contents to a string
let (uri, contents, format) = match self
.source
@@ -110,7 +110,7 @@ where
Err(error) => {
if !self.required {
- return Ok(HashMap::new());
+ return Ok(LinkedHashMap::new());
}
return Err(error);
diff --git a/src/path/mod.rs b/src/path/mod.rs
index d58a6f2..04c424c 100644
--- a/src/path/mod.rs
+++ b/src/path/mod.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::str::FromStr;
use crate::error::*;
@@ -135,7 +135,7 @@ impl Expression {
),
_ => {
- *value = HashMap::<String, Value>::new().into();
+ *value = LinkedHashMap::<String, Value>::new().into();
if let ValueKind::Table(ref mut map) = value.kind {
Some(
@@ -186,7 +186,7 @@ impl Expression {
ValueKind::Table(_) => {}
_ => {
- *root = HashMap::<String, Value>::new().into();
+ *root = LinkedHashMap::<String, Value>::new().into();
}
}
@@ -195,7 +195,7 @@ impl Expression {
// Pull out another table
let mut target = if let ValueKind::Table(ref mut map) = root.kind {
map.entry(id.clone())
- .or_insert_with(|| HashMap::<String, Value>::new().into())
+ .or_insert_with(|| LinkedHashMap::<String, Value>::new().into())
} else {
unreachable!();
};
@@ -224,7 +224,7 @@ impl Expression {
_ => {
// Didn't find a table. Oh well. Make a table and do this anyway
- *parent = HashMap::<String, Value>::new().into();
+ *parent = LinkedHashMap::<String, Value>::new().into();
Expression::Identifier(key.clone()).set(parent, value);
}
diff --git a/src/source.rs b/src/source.rs
index 831e4c4..7d257d0 100644
--- a/src/source.rs
+++ b/src/source.rs
@@ -1,4 +1,4 @@
-use std::collections::HashMap;
+use linked_hash_map::LinkedHashMap;
use std::fmt::Debug;
use std::str::FromStr;
@@ -13,8 +13,8 @@ pub trait Source: Debug {
fn clone_into_box(&self) -> Box<dyn Source + Send + Sync>;
/// Collect all configuration properties available from this source and return
- /// a HashMap.
- fn collect(&self) -> Result<HashMap<String, Value>>;
+ /// a LinkedHashMap.
+ fn collect(&self) -> Result<LinkedHashMap<String, Value>>;
/// Collects all configuration properties to a provided cache.
fn collect_to(&self, cache: &mut Value) -> Result<()> {
@@ -55,8 +55,8 @@ pub trait AsyncSource: Debug + Sync {
// Sync is supertrait due to https://docs.rs/async-trait/0.1.50/async_trait/index.html#dyn-traits
/// Collects all configuration properties available from this source and return
- /// a HashMap as an async operations.
- async fn collect(&self) -> Result<HashMap<String, Value>>;
+ /// a LinkedHashMap as an async operations.
+ async fn collect(&self) -> Result<LinkedHashMap<String, Value>>;
/// Collects all configuration properties to a provided cache.
async fn collect_to(&self, cache: &mut Value) -> Result<()> {
@@ -86,8 +86,8 @@ impl Source for Vec<Box<dyn Source + Send + Sync>> {
Box::new((*self).clone())
}
- fn collect(&self) -> Result<HashMap<String, Value>> {
- let mut cache: Value = HashMap::<String, Value>::new().into();
+ fn collect(&self) -> Result<LinkedHashMap<String, Value>> {
+ let mut cache: Value = LinkedHashMap::<String, Value>::new().into();
for source in self {
source.collect_to(&mut cache)?;
@@ -106,8 +106,8 @@ impl Source for [Box<dyn Source + Send + Sync>] {
Box::new(self.to_owned())
}