Compare commits

...

3 Commits

Author SHA1 Message Date
jikstra
1ab014f96f Start implementing Ui config on top of the Config enum 2019-09-14 21:44:59 +02:00
B. Petersen
70a69d5313 cargo fmt 2019-09-13 11:02:34 +02:00
B. Petersen
056faad029 Implement set/get_ui_config and use those methods if config string starts with 'ui.' 2019-09-12 21:53:37 +02:00
7 changed files with 71 additions and 28 deletions

View File

@@ -149,11 +149,9 @@ pub unsafe extern "C" fn dc_set_config(
}
let context = &*context;
match config::Config::from_str(dc_tools::as_str(key)) {
Ok(key) => context.set_config(key, as_opt_str(value)).is_ok() as libc::c_int,
Err(_) => 0,
}
let key = dc_tools::as_str(key);
let value = as_opt_str(value);
context.set_config_from_str(key, value).is_ok() as libc::c_int
}
#[no_mangle]
@@ -168,11 +166,8 @@ pub unsafe extern "C" fn dc_get_config(
let context = &*context;
let key = config::Config::from_str(dc_tools::as_str(key)).expect("invalid key");
// TODO: Translating None to NULL would be more sensible than translating None
// to "", as it is now.
context.get_config(key).unwrap_or_default().strdup()
let key = dc_tools::as_str(key);
context.get_config_from_str(key).unwrap_or_default().strdup()
}
#[no_mangle]

View File

@@ -550,9 +550,8 @@ pub unsafe fn dc_cmdline(context: &Context, line: &str) -> Result<(), failure::E
}
"get" => {
ensure!(!arg1.is_empty(), "Argument <key> missing.");
let key = config::Config::from_str(&arg1)?;
let val = context.get_config(key);
println!("{}={:?}", key, val);
let val = context.get_config_from_str(&arg1);
println!("{}={:?}", &arg1.to_string(), val);
}
"info" => {
println!("{}", to_string(dc_get_info(context)));

View File

@@ -495,7 +495,7 @@ unsafe fn handle_cmd(line: &str, ctx: Arc<RwLock<Context>>) -> Result<ExitResult
configure(&ctx.read().unwrap());
}
"oauth2" => {
if let Some(addr) = ctx.read().unwrap().get_config(config::Config::Addr) {
if let Some(addr) = ctx.read().unwrap().get_config(&config::Config::Addr) {
let oauth2_url = dc_get_oauth2_url(
&ctx.read().unwrap(),
&addr,

View File

@@ -1,3 +1,5 @@
use std::str::FromStr;
use strum::{EnumProperty, IntoEnumIterator};
use strum_macros::{AsRefStr, Display, EnumIter, EnumProperty, EnumString};
@@ -8,9 +10,11 @@ use crate::error::Error;
use crate::job::*;
use crate::stock::StockMessage;
pub const CONFIG_UI_PREFIX: &str = "ui.";
/// The available configuration keys.
#[derive(
Debug, Clone, Copy, PartialEq, Eq, Display, EnumString, AsRefStr, EnumIter, EnumProperty,
Debug, Clone, PartialEq, Eq, Display, EnumString, AsRefStr, EnumIter, EnumProperty,
)]
#[strum(serialize_all = "snake_case")]
pub enum Config {
@@ -65,11 +69,17 @@ pub enum Config {
SysMsgsizeMaxRecommended,
#[strum(serialize = "sys.config_keys")]
SysConfigKeys,
Ui(String)
}
impl Context {
pub fn get_config_from_str(&self, key: &str) -> Option<String> {
self.get_config(&config_from_str(key))
}
/// Get a configuration key. Returns `None` if no value is set, and no default value found.
pub fn get_config(&self, key: Config) -> Option<String> {
pub fn get_config(&self, key: &Config) -> Option<String> {
let value = match key {
Config::Selfavatar => {
let rel_path = self.sql.get_config(self, key);
@@ -78,6 +88,7 @@ impl Context {
Config::SysVersion => Some((&*DC_VERSION_STR).clone()),
Config::SysMsgsizeMaxRecommended => Some(format!("{}", 24 * 1024 * 1024 / 4 * 3)),
Config::SysConfigKeys => Some(get_config_keys_string()),
Config::Ui(key) => self.sql.get_config(self, format!("{}{}", CONFIG_UI_PREFIX, key)),
_ => self.sql.get_config(self, key),
};
@@ -92,6 +103,13 @@ impl Context {
}
}
pub fn set_config_from_str(&self, key: &str, value: Option<&str>) -> Result<(), &str> {
if self.sql.set_config(self, config_from_str(key), value).is_err() {
return Err("Sql error");
}
Ok(())
}
/// Set the given config key.
/// If `None` is passed as a value the value is cleared and set to the default if there is one.
pub fn set_config(&self, key: Config, value: Option<&str>) -> Result<(), Error> {
@@ -125,7 +143,11 @@ impl Context {
};
self.sql.set_config(self, key, val)
}
},
Config::Ui(key) => {
let key = format!("{}{}", CONFIG_UI_PREFIX, key);
self.sql.set_config(self, key, value)
},
_ => self.sql.set_config(self, key, value),
}
}
@@ -142,12 +164,23 @@ fn get_config_keys_string() -> String {
format!(" {} ", keys)
}
fn config_from_str(key: &str) -> Result<Config, &str> {
if key.starts_with(CONFIG_UI_PREFIX) {
Config::Ui(key[CONFIG_UI_PREFIX.len()-1..].to_string())
} else {
if let Ok(config) = Config::from_str(key) {
config
} else {
Err("invalid key")
}
}
}
#[cfg(test)]
mod tests {
use super::*;
use std::str::FromStr;
use std::string::ToString;
use crate::test_utils::*;
#[test]
fn test_to_string() {
@@ -165,4 +198,20 @@ mod tests {
fn test_default_prop() {
assert_eq!(Config::ImapFolder.get_str("default"), Some("INBOX"));
}
#[test]
fn test_config_from_str() {
assert_eq!(config_from_str("addr"), Config::Addr);
assert_eq!(config_from_str("addrxyz"), None);
}
#[test]
fn test_get_config_from_str() {
let t = dummy_context();
assert_eq!(t.ctx.set_config_from_str("addr", Some("foo@bar.bar")), Ok(()));
assert_eq!(t.ctx.get_config_from_str("addr").unwrap(), "foo@bar.bar");
assert_eq!(t.ctx.set_config_from_str("ui.desktop.some_string", Some("foobar")), Ok(()));
assert_eq!(t.ctx.get_config_from_str("ui.desktop.some_string").unwrap(), "foobar");
}
}

View File

@@ -146,7 +146,7 @@ impl Contact {
name: context.stock_str(StockMessage::SelfMsg).into(),
authname: "".into(),
addr: context
.get_config(Config::ConfiguredAddr)
.get_config(&Config::ConfiguredAddr)
.unwrap_or_default(),
blocked: false,
origin: Origin::Unknown,
@@ -257,7 +257,7 @@ impl Contact {
let addr_normalized = addr_normalize(addr.as_ref());
let addr_self = context
.get_config(Config::ConfiguredAddr)
.get_config(&Config::ConfiguredAddr)
.unwrap_or_default();
if addr_normalized == addr_self {
@@ -295,7 +295,7 @@ impl Contact {
let addr = addr_normalize(addr.as_ref());
let addr_self = context
.get_config(Config::ConfiguredAddr)
.get_config(&Config::ConfiguredAddr)
.unwrap_or_default();
if addr == addr_self {
@@ -456,7 +456,7 @@ impl Contact {
query: Option<impl AsRef<str>>,
) -> Result<Vec<u32>> {
let self_addr = context
.get_config(Config::ConfiguredAddr)
.get_config(&Config::ConfiguredAddr)
.unwrap_or_default();
let mut add_self = false;
@@ -499,7 +499,7 @@ impl Contact {
},
)?;
let self_name = context.get_config(Config::Displayname).unwrap_or_default();
let self_name = context.get_config(&Config::Displayname).unwrap_or_default();
let self_name2 = context.stock_str(StockMessage::SelfMsg);
if let Some(query) = query {
@@ -765,7 +765,7 @@ impl Contact {
/// using dc_set_config(context, "selfavatar", image).
pub fn get_profile_image(&self, context: &Context) -> Option<PathBuf> {
if self.id == DC_CONTACT_ID_SELF {
if let Some(p) = context.get_config(Config::Selfavatar) {
if let Some(p) = context.get_config(&Config::Selfavatar) {
return Some(PathBuf::from(p));
}
}
@@ -1026,7 +1026,7 @@ pub fn addr_cmp(addr1: impl AsRef<str>, addr2: impl AsRef<str>) -> bool {
pub fn addr_equals_self(context: &Context, addr: impl AsRef<str>) -> bool {
if !addr.as_ref().is_empty() {
let normalized_addr = addr_normalize(addr.as_ref());
if let Some(self_addr) = context.get_config(Config::ConfiguredAddr) {
if let Some(self_addr) = context.get_config(&Config::ConfiguredAddr) {
return normalized_addr == self_addr;
}
}

View File

@@ -1025,7 +1025,7 @@ unsafe fn contains_report(mime: *mut mailmime) -> bool {
/// [Config::ConfiguredAddr] is configured, this address is returned.
pub fn ensure_secret_key_exists(context: &Context) -> Result<String> {
let self_addr = context
.get_config(Config::ConfiguredAddr)
.get_config(&Config::ConfiguredAddr)
.ok_or(format_err!(concat!(
"Failed to get self address, ",
"cannot ensure secret key if not configured."

View File

@@ -128,7 +128,7 @@ unsafe fn stress_functions(context: &Context) {
free(fn1 as *mut libc::c_void);
}
let res = context.get_config(config::Config::SysConfigKeys).unwrap();
let res = context.get_config(&config::Config::SysConfigKeys).unwrap();
assert!(!res.contains(" probably_never_a_key "));
assert!(res.contains(" addr "));