#[derive(Clone, Eq, PartialEq, Debug, darling::FromMeta)]
#[darling(rename_all = "snake_case")]
pub enum Backend {
Node(Node),
#[cfg(any(test, feature = "drink"))]
RuntimeOnly(RuntimeOnly),
}
impl Default for Backend {
fn default() -> Self {
Backend::Node(Node::Auto)
}
}
#[derive(Clone, Eq, PartialEq, Debug, darling::FromMeta)]
pub enum Node {
#[darling(word)]
#[darling(skip)]
Auto,
Url(String),
}
impl Node {
pub fn url(&self) -> Option<String> {
std::env::var("CONTRACTS_NODE_URL").ok().or_else(|| {
match self {
Node::Auto => None,
Node::Url(url) => Some(url.clone()),
}
})
}
}
#[cfg(any(test, feature = "drink"))]
#[derive(Clone, Eq, PartialEq, Debug, darling::FromMeta)]
pub enum RuntimeOnly {
#[darling(word)]
#[darling(skip)]
Default,
Sandbox(syn::Path),
}
#[cfg(any(test, feature = "drink"))]
impl From<RuntimeOnly> for syn::Path {
fn from(value: RuntimeOnly) -> Self {
match value {
RuntimeOnly::Default => syn::parse_quote! { ::ink_e2e::MinimalSandbox },
RuntimeOnly::Sandbox(path) => path,
}
}
}
#[derive(Debug, Default, PartialEq, Eq, darling::FromMeta)]
pub struct E2EConfig {
#[darling(default)]
environment: Option<syn::Path>,
#[darling(default)]
backend: Backend,
}
impl E2EConfig {
pub fn environment(&self) -> Option<syn::Path> {
self.environment.clone()
}
pub fn backend(&self) -> Backend {
self.backend.clone()
}
}
#[cfg(test)]
mod tests {
use super::*;
use darling::{
ast::NestedMeta,
FromMeta,
};
use quote::quote;
#[test]
fn config_works_backend_runtime_only() {
let input = quote! {
environment = crate::CustomEnvironment,
backend(runtime_only),
};
let config =
E2EConfig::from_list(&NestedMeta::parse_meta_list(input).unwrap()).unwrap();
assert_eq!(
config.environment(),
Some(syn::parse_quote! { crate::CustomEnvironment })
);
assert_eq!(config.backend(), Backend::RuntimeOnly(RuntimeOnly::Default));
}
#[test]
#[should_panic(expected = "ErrorUnknownField")]
fn config_backend_runtime_only_default_not_allowed() {
let input = quote! {
backend(runtime_only(default)),
};
let config =
E2EConfig::from_list(&NestedMeta::parse_meta_list(input).unwrap()).unwrap();
assert_eq!(config.backend(), Backend::RuntimeOnly(RuntimeOnly::Default));
}
#[test]
fn config_works_runtime_only_with_custom_backend() {
let input = quote! {
backend(runtime_only(sandbox = ::ink_e2e::MinimalSandbox)),
};
let config =
E2EConfig::from_list(&NestedMeta::parse_meta_list(input).unwrap()).unwrap();
assert_eq!(
config.backend(),
Backend::RuntimeOnly(RuntimeOnly::Sandbox(
syn::parse_quote! { ::ink_e2e::MinimalSandbox }
))
);
}
#[test]
fn config_works_backend_node() {
let input = quote! {
backend(node),
};
let config =
E2EConfig::from_list(&NestedMeta::parse_meta_list(input).unwrap()).unwrap();
assert_eq!(config.backend(), Backend::Node(Node::Auto));
match config.backend() {
Backend::Node(node_config) => {
assert_eq!(node_config, Node::Auto);
temp_env::with_vars([("CONTRACTS_NODE_URL", None::<&str>)], || {
assert_eq!(node_config.url(), None);
});
temp_env::with_vars(
[("CONTRACTS_NODE_URL", Some("ws://127.0.0.1:9000"))],
|| {
assert_eq!(
node_config.url(),
Some(String::from("ws://127.0.0.1:9000"))
);
},
);
}
_ => panic!("Expected Backend::Node"),
}
}
#[test]
#[should_panic(expected = "ErrorUnknownField")]
fn config_backend_node_auto_not_allowed() {
let input = quote! {
backend(node(auto)),
};
let config =
E2EConfig::from_list(&NestedMeta::parse_meta_list(input).unwrap()).unwrap();
assert_eq!(config.backend(), Backend::Node(Node::Auto));
}
#[test]
fn config_works_backend_node_url() {
let input = quote! {
backend(node(url = "ws://0.0.0.0:9999")),
};
let config =
E2EConfig::from_list(&NestedMeta::parse_meta_list(input).unwrap()).unwrap();
match config.backend() {
Backend::Node(node_config) => {
assert_eq!(node_config, Node::Url("ws://0.0.0.0:9999".to_owned()));
temp_env::with_vars([("CONTRACTS_NODE_URL", None::<&str>)], || {
assert_eq!(node_config.url(), Some("ws://0.0.0.0:9999".to_owned()));
});
temp_env::with_vars(
[("CONTRACTS_NODE_URL", Some("ws://127.0.0.1:9000"))],
|| {
assert_eq!(
node_config.url(),
Some(String::from("ws://127.0.0.1:9000"))
);
},
);
}
_ => panic!("Expected Backend::Node"),
}
}
}