Make serde optional
This commit is contained in:
parent
2339ca5fe6
commit
dd09555537
5 changed files with 81 additions and 74 deletions
|
@ -2,7 +2,7 @@ language: rust
|
||||||
rust: stable
|
rust: stable
|
||||||
sudo: false
|
sudo: false
|
||||||
script:
|
script:
|
||||||
- cargo test --all --features "toml yaml json"
|
- cargo test --all --features "toml_config yaml_config json_config"
|
||||||
- cargo build
|
- cargo build
|
||||||
# No idea how to fix this, since we don't depend on futures-preview directly.
|
# No idea how to fix this, since we don't depend on futures-preview directly.
|
||||||
# - rustdoc --test README.md --extern irc=target/debug/libirc.rlib -L target/debug/deps --edition 2018
|
# - rustdoc --test README.md --extern irc=target/debug/libirc.rlib -L target/debug/deps --edition 2018
|
||||||
|
|
15
Cargo.toml
15
Cargo.toml
|
@ -20,11 +20,16 @@ is-it-maintained-open-issues = { repository = "aatxe/irc" }
|
||||||
members = [ "./", "irc-proto" ]
|
members = [ "./", "irc-proto" ]
|
||||||
|
|
||||||
[features]
|
[features]
|
||||||
default = ["ctcp", "toml"]
|
default = ["ctcp", "toml_config"]
|
||||||
ctcp = []
|
ctcp = []
|
||||||
nochanlists = []
|
nochanlists = []
|
||||||
json = ["serde_json"]
|
json_config = ["serde", "serde_derive", "serde_json"]
|
||||||
yaml = ["serde_yaml"]
|
toml_config = ["serde", "serde_derive", "toml"]
|
||||||
|
yaml_config = ["serde", "serde_derive", "serde_yaml"]
|
||||||
|
|
||||||
|
# Temporary transitionary features
|
||||||
|
json = ["json_config"]
|
||||||
|
yaml = ["yaml_config"]
|
||||||
|
|
||||||
[dependencies]
|
[dependencies]
|
||||||
thiserror = "1.0.2"
|
thiserror = "1.0.2"
|
||||||
|
@ -35,8 +40,8 @@ encoding = "0.2"
|
||||||
irc-proto = { version = "*", path = "irc-proto" }
|
irc-proto = { version = "*", path = "irc-proto" }
|
||||||
log = "0.4"
|
log = "0.4"
|
||||||
native-tls = "0.2"
|
native-tls = "0.2"
|
||||||
serde = { version = "1.0", features = ["derive"] }
|
serde = { version = "1.0", features = ["derive"], optional = true }
|
||||||
serde_derive = "1.0"
|
serde_derive = { version = "1.0", optional = true }
|
||||||
tokio = { version = "0.2.4", features = ["time", "net", "stream", "macros", "stream"] }
|
tokio = { version = "0.2.4", features = ["time", "net", "stream", "macros", "stream"] }
|
||||||
tokio-util = { version = "0.2.0", features = ["codec"] }
|
tokio-util = { version = "0.2.0", features = ["codec"] }
|
||||||
tokio-tls = "0.3.0"
|
tokio-tls = "0.3.0"
|
||||||
|
|
|
@ -86,9 +86,9 @@ programmatic configuration. Runtime loading is done via the function `Config::lo
|
||||||
sufficient for most IRC bots. Programmatic configuration is convenient for writing tests, but can
|
sufficient for most IRC bots. Programmatic configuration is convenient for writing tests, but can
|
||||||
also be useful when defining your own custom configuration format that can be converted to `Config`.
|
also be useful when defining your own custom configuration format that can be converted to `Config`.
|
||||||
The primary configuration format is TOML, but if you are so inclined, you can use JSON and/or YAML
|
The primary configuration format is TOML, but if you are so inclined, you can use JSON and/or YAML
|
||||||
via the optional `json` and `yaml` features respectively. At the minimum, a configuration requires
|
via the optional `json_config` and `yaml_config` features respectively. At the minimum, a configuration
|
||||||
`nickname` and `server` to be defined, and all other fields are optional. You can find detailed
|
requires `nickname` and `server` to be defined, and all other fields are optional. You can find
|
||||||
explanations of the various fields on [docs.rs][config-fields].
|
detailed explanations of the various fields on [docs.rs][config-fields].
|
||||||
|
|
||||||
[config-fields]: https://docs.rs/irc/*/irc/client/data/config/struct.Config.html#fields
|
[config-fields]: https://docs.rs/irc/*/irc/client/data/config/struct.Config.html#fields
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,5 @@
|
||||||
//! JSON configuration files using serde
|
//! JSON configuration files using serde
|
||||||
|
#[cfg(feature = "serde")]
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
use std::{
|
use std::{
|
||||||
collections::HashMap,
|
collections::HashMap,
|
||||||
|
@ -8,15 +9,15 @@ use std::{
|
||||||
};
|
};
|
||||||
use tokio::net::ToSocketAddrs;
|
use tokio::net::ToSocketAddrs;
|
||||||
|
|
||||||
#[cfg(feature = "json")]
|
#[cfg(feature = "json_config")]
|
||||||
use serde_json;
|
use serde_json;
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml_config")]
|
||||||
use serde_yaml;
|
use serde_yaml;
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
use toml;
|
use toml;
|
||||||
|
|
||||||
use crate::error::Error::InvalidConfig;
|
use crate::error::Error::InvalidConfig;
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
use crate::error::TomlError;
|
use crate::error::TomlError;
|
||||||
use crate::error::{ConfigError, Result};
|
use crate::error::{ConfigError, Result};
|
||||||
|
|
||||||
|
@ -65,127 +66,129 @@ use crate::error::{ConfigError, Result};
|
||||||
/// let config = Config::load("config.toml").unwrap();
|
/// let config = Config::load("config.toml").unwrap();
|
||||||
/// # }
|
/// # }
|
||||||
/// ```
|
/// ```
|
||||||
#[derive(Clone, Deserialize, Serialize, Default, PartialEq, Debug)]
|
#[derive(Clone, Default, PartialEq, Debug)]
|
||||||
|
#[cfg_attr(feature = "serde", derive(Serialize, Deserialize))]
|
||||||
pub struct Config {
|
pub struct Config {
|
||||||
/// A list of the owners of the client by nickname (for bots).
|
/// A list of the owners of the client by nickname (for bots).
|
||||||
#[serde(skip_serializing_if = "Vec::is_empty")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Vec::is_empty"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub owners: Vec<String>,
|
pub owners: Vec<String>,
|
||||||
/// The client's nickname.
|
/// The client's nickname.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub nickname: Option<String>,
|
pub nickname: Option<String>,
|
||||||
/// The client's NICKSERV password.
|
/// The client's NICKSERV password.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub nick_password: Option<String>,
|
pub nick_password: Option<String>,
|
||||||
/// Alternative nicknames for the client, if the default is taken.
|
/// Alternative nicknames for the client, if the default is taken.
|
||||||
#[serde(skip_serializing_if = "Vec::is_empty")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Vec::is_empty"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub alt_nicks: Vec<String>,
|
pub alt_nicks: Vec<String>,
|
||||||
/// The client's username.
|
/// The client's username.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub username: Option<String>,
|
pub username: Option<String>,
|
||||||
/// The client's real name.
|
/// The client's real name.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub realname: Option<String>,
|
pub realname: Option<String>,
|
||||||
/// The server to connect to.
|
/// The server to connect to.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub server: Option<String>,
|
pub server: Option<String>,
|
||||||
/// The port to connect on.
|
/// The port to connect on.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub port: Option<u16>,
|
pub port: Option<u16>,
|
||||||
/// The password to connect to the server.
|
/// The password to connect to the server.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub password: Option<String>,
|
pub password: Option<String>,
|
||||||
/// Whether or not to use SSL.
|
/// Whether or not to use SSL.
|
||||||
/// Clients will automatically panic if this is enabled without SSL support.
|
/// Clients will automatically panic if this is enabled without SSL support.
|
||||||
#[serde(skip_serializing_if = "is_false")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "is_false"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub use_ssl: bool,
|
pub use_ssl: bool,
|
||||||
/// The path to the SSL certificate for this server in DER format.
|
/// The path to the SSL certificate for this server in DER format.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub cert_path: Option<String>,
|
pub cert_path: Option<String>,
|
||||||
/// The path to a SSL certificate to use for CertFP client authentication in DER format.
|
/// The path to a SSL certificate to use for CertFP client authentication in DER format.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub client_cert_path: Option<String>,
|
pub client_cert_path: Option<String>,
|
||||||
/// The password for the certificate to use in CertFP authentication.
|
/// The password for the certificate to use in CertFP authentication.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub client_cert_pass: Option<String>,
|
pub client_cert_pass: Option<String>,
|
||||||
/// The encoding type used for this connection.
|
/// The encoding type used for this connection.
|
||||||
/// This is typically UTF-8, but could be something else.
|
/// This is typically UTF-8, but could be something else.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub encoding: Option<String>,
|
pub encoding: Option<String>,
|
||||||
/// A list of channels to join on connection.
|
/// A list of channels to join on connection.
|
||||||
#[serde(skip_serializing_if = "Vec::is_empty")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Vec::is_empty"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub channels: Vec<String>,
|
pub channels: Vec<String>,
|
||||||
/// User modes to set on connect. Example: "+RB -x"
|
/// User modes to set on connect. Example: "+RB -x"
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub umodes: Option<String>,
|
pub umodes: Option<String>,
|
||||||
/// The text that'll be sent in response to CTCP USERINFO requests.
|
/// The text that'll be sent in response to CTCP USERINFO requests.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub user_info: Option<String>,
|
pub user_info: Option<String>,
|
||||||
/// The text that'll be sent in response to CTCP VERSION requests.
|
/// The text that'll be sent in response to CTCP VERSION requests.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub version: Option<String>,
|
pub version: Option<String>,
|
||||||
/// The text that'll be sent in response to CTCP SOURCE requests.
|
/// The text that'll be sent in response to CTCP SOURCE requests.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub source: Option<String>,
|
pub source: Option<String>,
|
||||||
/// The amount of inactivity in seconds before the client will ping the server.
|
/// The amount of inactivity in seconds before the client will ping the server.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub ping_time: Option<u32>,
|
pub ping_time: Option<u32>,
|
||||||
/// The amount of time in seconds for a client to reconnect due to no ping response.
|
/// The amount of time in seconds for a client to reconnect due to no ping response.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub ping_timeout: Option<u32>,
|
pub ping_timeout: Option<u32>,
|
||||||
/// The length in seconds of a rolling window for message throttling. If more than
|
/// The length in seconds of a rolling window for message throttling. If more than
|
||||||
/// `max_messages_in_burst` messages are sent within `burst_window_length` seconds, additional
|
/// `max_messages_in_burst` messages are sent within `burst_window_length` seconds, additional
|
||||||
/// messages will be delayed automatically as appropriate. In particular, in the past
|
/// messages will be delayed automatically as appropriate. In particular, in the past
|
||||||
/// `burst_window_length` seconds, there will never be more than `max_messages_in_burst` messages
|
/// `burst_window_length` seconds, there will never be more than `max_messages_in_burst` messages
|
||||||
/// sent.
|
/// sent.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub burst_window_length: Option<u32>,
|
pub burst_window_length: Option<u32>,
|
||||||
/// The maximum number of messages that can be sent in a burst window before they'll be delayed.
|
/// The maximum number of messages that can be sent in a burst window before they'll be delayed.
|
||||||
/// Messages are automatically delayed as appropriate.
|
/// Messages are automatically delayed as appropriate.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub max_messages_in_burst: Option<u32>,
|
pub max_messages_in_burst: Option<u32>,
|
||||||
/// Whether the client should use NickServ GHOST to reclaim its primary nickname if it is in
|
/// Whether the client should use NickServ GHOST to reclaim its primary nickname if it is in
|
||||||
/// use. This has no effect if `nick_password` is not set.
|
/// use. This has no effect if `nick_password` is not set.
|
||||||
#[serde(skip_serializing_if = "is_false")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "is_false"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub should_ghost: bool,
|
pub should_ghost: bool,
|
||||||
/// The command(s) that should be sent to NickServ to recover a nickname. The nickname and
|
/// The command(s) that should be sent to NickServ to recover a nickname. The nickname and
|
||||||
/// password will be appended in that order after the command.
|
/// password will be appended in that order after the command.
|
||||||
/// E.g. `["RECOVER", "RELEASE"]` means `RECOVER nick pass` and `RELEASE nick pass` will be sent
|
/// E.g. `["RECOVER", "RELEASE"]` means `RECOVER nick pass` and `RELEASE nick pass` will be sent
|
||||||
/// in that order.
|
/// in that order.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub ghost_sequence: Option<Vec<String>>,
|
pub ghost_sequence: Option<Vec<String>>,
|
||||||
/// Whether or not to use a fake connection for testing purposes. You probably will never want
|
/// Whether or not to use a fake connection for testing purposes. You probably will never want
|
||||||
/// to enable this, but it is used in unit testing for the `irc` crate.
|
/// to enable this, but it is used in unit testing for the `irc` crate.
|
||||||
#[serde(skip_serializing_if = "is_false")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "is_false"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub use_mock_connection: bool,
|
pub use_mock_connection: bool,
|
||||||
/// The initial value used by the fake connection for testing. You probably will never need to
|
/// The initial value used by the fake connection for testing. You probably will never need to
|
||||||
/// set this, but it is used in unit testing for the `irc` crate.
|
/// set this, but it is used in unit testing for the `irc` crate.
|
||||||
#[serde(skip_serializing_if = "Option::is_none")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "Option::is_none"))]
|
||||||
pub mock_initial_value: Option<String>,
|
pub mock_initial_value: Option<String>,
|
||||||
|
|
||||||
/// A mapping of channel names to keys for join-on-connect.
|
/// A mapping of channel names to keys for join-on-connect.
|
||||||
#[serde(skip_serializing_if = "HashMap::is_empty")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "HashMap::is_empty"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub channel_keys: HashMap<String, String>,
|
pub channel_keys: HashMap<String, String>,
|
||||||
/// A map of additional options to be stored in config.
|
/// A map of additional options to be stored in config.
|
||||||
#[serde(skip_serializing_if = "HashMap::is_empty")]
|
#[cfg_attr(feature = "serde", serde(skip_serializing_if = "HashMap::is_empty"))]
|
||||||
#[serde(default)]
|
#[cfg_attr(feature = "serde", serde(default))]
|
||||||
pub options: HashMap<String, String>,
|
pub options: HashMap<String, String>,
|
||||||
|
|
||||||
/// The path that this configuration was loaded from.
|
/// The path that this configuration was loaded from.
|
||||||
///
|
///
|
||||||
/// This should not be specified in any configuration. It will automatically be handled by the library.
|
/// This should not be specified in any configuration. It will automatically be handled by the library.
|
||||||
#[serde(skip_serializing)]
|
#[cfg_attr(feature = "serde", serde(skip_serializing))]
|
||||||
#[doc(hidden)]
|
#[doc(hidden)]
|
||||||
pub path: Option<PathBuf>,
|
pub path: Option<PathBuf>,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(feature = "serde")]
|
||||||
fn is_false(v: &bool) -> bool {
|
fn is_false(v: &bool) -> bool {
|
||||||
!v
|
!v
|
||||||
}
|
}
|
||||||
|
@ -230,7 +233,7 @@ impl Config {
|
||||||
res.map(|config| config.with_path(path))
|
res.map(|config| config.with_path(path))
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "json")]
|
#[cfg(feature = "json_config")]
|
||||||
fn load_json<P: AsRef<Path>>(path: P, data: &str) -> Result<Config> {
|
fn load_json<P: AsRef<Path>>(path: P, data: &str) -> Result<Config> {
|
||||||
serde_json::from_str(data).map_err(|e| InvalidConfig {
|
serde_json::from_str(data).map_err(|e| InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -238,7 +241,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "json"))]
|
#[cfg(not(feature = "json_config"))]
|
||||||
fn load_json<P: AsRef<Path>>(path: P, _: &str) -> Result<Config> {
|
fn load_json<P: AsRef<Path>>(path: P, _: &str) -> Result<Config> {
|
||||||
Err(InvalidConfig {
|
Err(InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -246,7 +249,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
fn load_toml<P: AsRef<Path>>(path: P, data: &str) -> Result<Config> {
|
fn load_toml<P: AsRef<Path>>(path: P, data: &str) -> Result<Config> {
|
||||||
toml::from_str(data).map_err(|e| InvalidConfig {
|
toml::from_str(data).map_err(|e| InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -254,7 +257,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "toml"))]
|
#[cfg(not(feature = "toml_config"))]
|
||||||
fn load_toml<P: AsRef<Path>>(path: P, _: &str) -> Result<Config> {
|
fn load_toml<P: AsRef<Path>>(path: P, _: &str) -> Result<Config> {
|
||||||
Err(InvalidConfig {
|
Err(InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -262,7 +265,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml_config")]
|
||||||
fn load_yaml<P: AsRef<Path>>(path: P, data: &str) -> Result<Config> {
|
fn load_yaml<P: AsRef<Path>>(path: P, data: &str) -> Result<Config> {
|
||||||
serde_yaml::from_str(data).map_err(|e| InvalidConfig {
|
serde_yaml::from_str(data).map_err(|e| InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -270,7 +273,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "yaml"))]
|
#[cfg(not(feature = "yaml_config"))]
|
||||||
fn load_yaml<P: AsRef<Path>>(path: P, _: &str) -> Result<Config> {
|
fn load_yaml<P: AsRef<Path>>(path: P, _: &str) -> Result<Config> {
|
||||||
Err(InvalidConfig {
|
Err(InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -308,7 +311,7 @@ impl Config {
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "json")]
|
#[cfg(feature = "json_config")]
|
||||||
fn save_json<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
fn save_json<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
||||||
serde_json::to_string(self).map_err(|e| InvalidConfig {
|
serde_json::to_string(self).map_err(|e| InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -316,7 +319,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "json"))]
|
#[cfg(not(feature = "json_config"))]
|
||||||
fn save_json<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
fn save_json<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
||||||
Err(InvalidConfig {
|
Err(InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -324,7 +327,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
fn save_toml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
fn save_toml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
||||||
toml::to_string(self).map_err(|e| InvalidConfig {
|
toml::to_string(self).map_err(|e| InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -332,7 +335,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "toml"))]
|
#[cfg(not(feature = "toml_config"))]
|
||||||
fn save_toml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
fn save_toml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
||||||
Err(InvalidConfig {
|
Err(InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -340,7 +343,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml_config")]
|
||||||
fn save_yaml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
fn save_yaml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
||||||
serde_yaml::to_string(self).map_err(|e| InvalidConfig {
|
serde_yaml::to_string(self).map_err(|e| InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -348,7 +351,7 @@ impl Config {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(feature = "yaml"))]
|
#[cfg(not(feature = "yaml_config"))]
|
||||||
fn save_yaml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
fn save_yaml<P: AsRef<Path>>(&self, path: &P) -> Result<String> {
|
||||||
Err(InvalidConfig {
|
Err(InvalidConfig {
|
||||||
path: path.as_ref().to_string_lossy().into_owned(),
|
path: path.as_ref().to_string_lossy().into_owned(),
|
||||||
|
@ -561,8 +564,7 @@ impl Config {
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod test {
|
mod test {
|
||||||
use super::Config;
|
use super::{Config, Result};
|
||||||
use anyhow::Result;
|
|
||||||
use std::collections::HashMap;
|
use std::collections::HashMap;
|
||||||
|
|
||||||
#[allow(unused)]
|
#[allow(unused)]
|
||||||
|
@ -609,7 +611,7 @@ mod test {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
#[cfg(feature = "json")]
|
#[cfg(feature = "json_config")]
|
||||||
fn load_from_json() -> Result<()> {
|
fn load_from_json() -> Result<()> {
|
||||||
const DATA: &str = include_str!("client_config.json");
|
const DATA: &str = include_str!("client_config.json");
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
|
@ -620,7 +622,7 @@ mod test {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
fn load_from_toml() -> Result<()> {
|
fn load_from_toml() -> Result<()> {
|
||||||
const DATA: &str = include_str!("client_config.toml");
|
const DATA: &str = include_str!("client_config.toml");
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
|
@ -631,7 +633,7 @@ mod test {
|
||||||
}
|
}
|
||||||
|
|
||||||
#[test]
|
#[test]
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml_config")]
|
||||||
fn load_from_yaml() -> Result<()> {
|
fn load_from_yaml() -> Result<()> {
|
||||||
const DATA: &str = include_str!("client_config.yaml");
|
const DATA: &str = include_str!("client_config.yaml");
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
|
|
|
@ -94,17 +94,17 @@ pub enum Error {
|
||||||
#[derive(Debug, Error)]
|
#[derive(Debug, Error)]
|
||||||
pub enum ConfigError {
|
pub enum ConfigError {
|
||||||
/// Failed to parse as TOML.
|
/// Failed to parse as TOML.
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
#[error("invalid toml")]
|
#[error("invalid toml")]
|
||||||
InvalidToml(#[source] TomlError),
|
InvalidToml(#[source] TomlError),
|
||||||
|
|
||||||
/// Failed to parse as JSON.
|
/// Failed to parse as JSON.
|
||||||
#[cfg(feature = "json")]
|
#[cfg(feature = "json_config")]
|
||||||
#[error("invalid json")]
|
#[error("invalid json")]
|
||||||
InvalidJson(#[source] serde_json::Error),
|
InvalidJson(#[source] serde_json::Error),
|
||||||
|
|
||||||
/// Failed to parse as YAML.
|
/// Failed to parse as YAML.
|
||||||
#[cfg(feature = "yaml")]
|
#[cfg(feature = "yaml_config")]
|
||||||
#[error("invalid yaml")]
|
#[error("invalid yaml")]
|
||||||
InvalidYaml(#[source] serde_yaml::Error),
|
InvalidYaml(#[source] serde_yaml::Error),
|
||||||
|
|
||||||
|
@ -136,7 +136,7 @@ pub enum ConfigError {
|
||||||
}
|
}
|
||||||
|
|
||||||
/// A wrapper that combines toml's serialization and deserialization errors.
|
/// A wrapper that combines toml's serialization and deserialization errors.
|
||||||
#[cfg(feature = "toml")]
|
#[cfg(feature = "toml_config")]
|
||||||
#[derive(Debug, Error)]
|
#[derive(Debug, Error)]
|
||||||
pub enum TomlError {
|
pub enum TomlError {
|
||||||
/// A TOML deserialization error.
|
/// A TOML deserialization error.
|
||||||
|
|
Loading…
Reference in a new issue