diff options
author | Ryan Leckey <ryan@launchbadge.com> | 2017-06-22 14:14:29 -0700 |
---|---|---|
committer | Ryan Leckey <ryan@launchbadge.com> | 2017-06-22 14:30:51 -0700 |
commit | 2b438ed9b53fee5689032f3b5fcdda8d15becd5f (patch) | |
tree | 48374e66a6594c7d11d19fe38f7e23df731b52be /src/file | |
parent | 04d3ee8f70337e4899932b92262fbeec2dbb1bd9 (diff) |
Add builder API to Config
Diffstat (limited to 'src/file')
-rw-r--r-- | src/file/format/json.rs | 30 | ||||
-rw-r--r-- | src/file/format/mod.rs | 6 | ||||
-rw-r--r-- | src/file/format/toml.rs | 26 | ||||
-rw-r--r-- | src/file/format/yaml.rs | 34 | ||||
-rw-r--r-- | src/file/mod.rs | 32 | ||||
-rw-r--r-- | src/file/source/file.rs | 17 | ||||
-rw-r--r-- | src/file/source/mod.rs | 7 | ||||
-rw-r--r-- | src/file/source/string.rs | 5 |
8 files changed, 94 insertions, 63 deletions
diff --git a/src/file/format/json.rs b/src/file/format/json.rs index 4a94943..290e17d 100644 --- a/src/file/format/json.rs +++ b/src/file/format/json.rs @@ -4,25 +4,27 @@ use std::collections::HashMap; use std::error::Error; use value::{Value, ValueKind}; -pub fn parse(uri: Option<&String>, text: &str, namespace: Option<&String>) -> Result<HashMap<String, Value>, Box<Error>> { +pub fn parse(uri: Option<&String>, + text: &str, + namespace: Option<&String>) + -> Result<HashMap<String, Value>, Box<Error>> { // Parse a JSON object value from the text let mut root: serde_json::Value = serde_json::from_str(text)?; // Limit to namespace if let Some(namespace) = namespace { root = serde_json::Value::Object(match root { - serde_json::Value::Object(ref mut table) => { - if let Some(serde_json::Value::Object(table)) = table.remove(namespace) { - table - } else { - serde_json::Map::new() - } - } + serde_json::Value::Object(ref mut table) => { + if let Some(serde_json::Value::Object(table)) = + table.remove(namespace) { + table + } else { + serde_json::Map::new() + } + } - _ => { - serde_json::Map::new() - } - }); + _ => serde_json::Map::new(), + }); }; // TODO: Have a proper error fire if the root of a file is ever not a Table @@ -70,8 +72,6 @@ fn from_json_value(uri: Option<&String>, value: &serde_json::Value) -> Value { Value::new(uri, ValueKind::Array(l)) } - serde_json::Value::Null => { - Value::new(uri, ValueKind::Nil) - } + serde_json::Value::Null => Value::new(uri, ValueKind::Nil), } } diff --git a/src/file/format/mod.rs b/src/file/format/mod.rs index 287b9b4..3fc15a6 100644 --- a/src/file/format/mod.rs +++ b/src/file/format/mod.rs @@ -55,7 +55,11 @@ impl FileFormat { // TODO: pub(crate) #[doc(hidden)] #[allow(unused_variables)] - pub fn parse(&self, uri: Option<&String>, text: &str, namespace: Option<&String>) -> Result<HashMap<String, Value>, Box<Error>> { + pub fn parse(&self, + uri: Option<&String>, + text: &str, + namespace: Option<&String>) + -> Result<HashMap<String, Value>, Box<Error>> { match *self { #[cfg(feature = "toml")] FileFormat::Toml => toml::parse(uri, text, namespace), diff --git a/src/file/format/toml.rs b/src/file/format/toml.rs index 633f39e..2df1fca 100644 --- a/src/file/format/toml.rs +++ b/src/file/format/toml.rs @@ -4,25 +4,27 @@ use std::collections::{HashMap, BTreeMap}; use std::error::Error; use value::{Value, ValueKind}; -pub fn parse(uri: Option<&String>, text: &str, namespace: Option<&String>) -> Result<HashMap<String, Value>, Box<Error>> { +pub fn parse(uri: Option<&String>, + text: &str, + namespace: Option<&String>) + -> Result<HashMap<String, Value>, Box<Error>> { // Parse a TOML value from the provided text let mut root: toml::Value = toml::from_str(text)?; // Limit to namespace if let Some(namespace) = namespace { root = toml::Value::Table(match root { - toml::Value::Table(ref mut table) => { - if let Some(toml::Value::Table(table)) = table.remove(namespace) { - table - } else { - BTreeMap::new() - } - } + toml::Value::Table(ref mut table) => { + if let Some(toml::Value::Table(table)) = + table.remove(namespace) { + table + } else { + BTreeMap::new() + } + } - _ => { - BTreeMap::new() - } - }); + _ => BTreeMap::new(), + }); } // TODO: Have a proper error fire if the root of a file is ever not a Table diff --git a/src/file/format/yaml.rs b/src/file/format/yaml.rs index 7c3dd71..b1afce7 100644 --- a/src/file/format/yaml.rs +++ b/src/file/format/yaml.rs @@ -6,7 +6,10 @@ use std::collections::{BTreeMap, HashMap}; use std::mem; use value::{Value, ValueKind}; -pub fn parse(uri: Option<&String>, text: &str, namespace: Option<&String>) -> Result<HashMap<String, Value>, Box<Error>> { +pub fn parse(uri: Option<&String>, + text: &str, + namespace: Option<&String>) + -> Result<HashMap<String, Value>, Box<Error>> { let mut docs = yaml::YamlLoader::load_from_str(text)?; // Designate root @@ -21,18 +24,17 @@ pub fn parse(uri: Option<&String>, text: &str, namespace: Option<&String>) -> Re // Limit to namespace if let Some(namespace) = namespace { root = yaml::Yaml::Hash(match root { - yaml::Yaml::Hash(ref mut table) => { - if let Some(yaml::Yaml::Hash(table)) = table.remove(&yaml::Yaml::String(namespace.clone())) { - table - } else { - BTreeMap::new() - } - } + yaml::Yaml::Hash(ref mut table) => { + if let Some(yaml::Yaml::Hash(table)) = + table.remove(&yaml::Yaml::String(namespace.clone())) { + table + } else { + BTreeMap::new() + } + } - _ => { - BTreeMap::new() - } - }); + _ => BTreeMap::new(), + }); }; // TODO: Have a proper error fire if the root of a file is ever not a Table @@ -47,7 +49,9 @@ pub fn parse(uri: Option<&String>, text: &str, namespace: Option<&String>) -> Re fn from_yaml_value(uri: Option<&String>, value: &yaml::Yaml) -> Value { match *value { yaml::Yaml::String(ref value) => Value::new(uri, ValueKind::String(value.clone())), - yaml::Yaml::Real(ref value) => Value::new(uri, ValueKind::Float(value.parse::<f64>().unwrap())), + yaml::Yaml::Real(ref value) => { + Value::new(uri, ValueKind::Float(value.parse::<f64>().unwrap())) + } 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) => { @@ -70,9 +74,7 @@ fn from_yaml_value(uri: Option<&String>, value: &yaml::Yaml) -> Value { Value::new(uri, ValueKind::Array(l)) } - yaml::Yaml::Null => { - Value::new(uri, ValueKind::Nil) - } + yaml::Yaml::Null => Value::new(uri, ValueKind::Nil), // TODO: how should we BadValue? _ => { diff --git a/src/file/mod.rs b/src/file/mod.rs index 7fc25c8..671f579 100644 --- a/src/file/mod.rs +++ b/src/file/mod.rs @@ -10,6 +10,7 @@ use std::path::Path; use self::source::FileSource; pub use self::format::FileFormat; +#[derive(Clone, Debug)] pub struct File<T> where T: FileSource { @@ -70,12 +71,19 @@ impl<T: FileSource> File<T> { } } -impl<T: FileSource> Source for File<T> { +impl<T: FileSource> Source for File<T> + where T: 'static, + T: Sync + Send +{ + fn clone_into_box(&self) -> Box<Source + Send + Sync> { + Box::new((*self).clone()) + } + fn collect(&self) -> Result<HashMap<String, Value>> { // Coerce the file contents to a string - let (uri, contents, format) = match self.source.resolve(self.format).map_err(|err| { - ConfigError::Foreign(err) - }) { + let (uri, contents, format) = match self.source + .resolve(self.format) + .map_err(|err| ConfigError::Foreign(err)) { Ok((uri, contents, format)) => (uri, contents, format), Err(error) => { @@ -88,13 +96,13 @@ impl<T: FileSource> Source for File<T> { }; // Parse the string using the given format - let result = format.parse(uri.as_ref(), &contents, self.namespace.as_ref()).map_err(|cause| { - ConfigError::FileParse { - uri: uri, - cause: cause - } - }); - - result + format + .parse(uri.as_ref(), &contents, self.namespace.as_ref()) + .map_err(|cause| { + ConfigError::FileParse { + uri: uri, + cause: cause, + } + }) } } diff --git a/src/file/source/file.rs b/src/file/source/file.rs index 79f46bf..426c0b5 100644 --- a/src/file/source/file.rs +++ b/src/file/source/file.rs @@ -3,7 +3,7 @@ use std::result; use std::error::Error; use std::path::{PathBuf, Path}; -use ::file::format::ALL_EXTENSIONS; +use file::format::ALL_EXTENSIONS; use std::io::{self, Read}; use std::fs; use std::env; @@ -13,6 +13,7 @@ use source::Source; use super::{FileFormat, FileSource}; /// Describes a file sourced from a file +#[derive(Clone, Debug)] pub struct FileSourceFile { /// Basename of configuration file name: String, @@ -30,7 +31,9 @@ impl FileSourceFile { } } - fn find_file(&self, format_hint: Option<FileFormat>) -> Result<(PathBuf, FileFormat), Box<Error>> { + fn find_file(&self, + format_hint: Option<FileFormat>) + -> Result<(PathBuf, FileFormat), Box<Error>> { // Build expected configuration file let mut basename = PathBuf::new(); @@ -47,7 +50,11 @@ impl FileSourceFile { Some(format) => Ok((filename, format)), None => { for (format, extensions) in ALL_EXTENSIONS.iter() { - if extensions.contains(&filename.extension().unwrap_or_default().to_string_lossy().as_ref()) { + if extensions.contains(&filename + .extension() + .unwrap_or_default() + .to_string_lossy() + .as_ref()) { return Ok((filename, *format)); } } @@ -90,7 +97,9 @@ impl FileSourceFile { } impl FileSource for FileSourceFile { - fn resolve(&self, format_hint: Option<FileFormat>) -> Result<(Option<String>, String, FileFormat), Box<Error>> { + fn resolve(&self, + format_hint: Option<FileFormat>) + -> Result<(Option<String>, String, FileFormat), Box<Error>> { // Find file let (filename, format) = self.find_file(format_hint)?; diff --git a/src/file/source/mod.rs b/src/file/source/mod.rs index 89f1a3c..67e2cf1 100644 --- a/src/file/source/mod.rs +++ b/src/file/source/mod.rs @@ -1,12 +1,15 @@ pub mod file; pub mod string; +use std::fmt::Debug; use std::error::Error; use source::Source; use super::FileFormat; /// Describes where the file is sourced -pub trait FileSource { - fn resolve(&self, format_hint: Option<FileFormat>) -> Result<(Option<String>, String, FileFormat), Box<Error>>; +pub trait FileSource: Debug + Clone { + fn resolve(&self, + format_hint: Option<FileFormat>) + -> Result<(Option<String>, String, FileFormat), Box<Error>>; } diff --git a/src/file/source/string.rs b/src/file/source/string.rs index 922e46c..70101d6 100644 --- a/src/file/source/string.rs +++ b/src/file/source/string.rs @@ -6,6 +6,7 @@ use source::Source; use super::{FileSource, FileFormat}; /// Describes a file sourced from a string +#[derive(Clone, Debug)] pub struct FileSourceString(String); impl<'a> From<&'a str> for FileSourceString { @@ -15,7 +16,9 @@ impl<'a> From<&'a str> for FileSourceString { } impl FileSource for FileSourceString { - fn resolve(&self, format_hint: Option<FileFormat>) -> Result<(Option<String>, String, FileFormat), Box<Error>> { + fn resolve(&self, + format_hint: Option<FileFormat>) + -> Result<(Option<String>, String, FileFormat), Box<Error>> { Ok((None, self.0.clone(), format_hint.expect("from_str requires a set file format"))) } } |