use crate::redis::Redis;
use json::{JsonValue};
use serde::{Deserialize, Serialize};
use std::collections::BTreeMap;
use std::fs;
use std::path::PathBuf;
pub mod redis;
#[derive(Clone)]
pub enum Cache {
Redis(Redis),
None,
}
impl Cache {
pub fn new(config: Config) -> Result<Self, String> {
let connection = config
.connections
.get(config.default.as_str())
.unwrap()
.clone();
Cache::login(
connection.mode,
&connection.hostname,
&connection.hostport,
&connection.userpass,
)
}
pub fn login(
cache_mode: CacheMode,
host: &str,
port: &str,
pass: &str,
) -> Result<Self, String> {
let res = match cache_mode {
CacheMode::Redis => {
let dsn = if pass.is_empty() {
format!("redis://{host}:{port}/")
} else {
format!("redis://:{pass}@{host}:{port}/")
};
Cache::Redis(Redis::connect(dsn)?)
}
};
Ok(res)
}
pub fn db(&mut self, db: i8) -> &mut Self {
match self {
Cache::Redis(e) => {
e.db(db);
}
Cache::None => {}
}
self
}
pub fn add(
&mut self,
key: &str,
value: JsonValue,
expiration_date: u64,
) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.add(key, value, expiration_date)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn get(&mut self, key: &str) -> Result<JsonValue, String> {
let res = match self {
Cache::Redis(e) => e.get(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn delete(&mut self, key: &str) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.delete(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn exists(&mut self, key: &str) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.exists(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn keys(&mut self, key: &str) -> Result<JsonValue, String> {
let res = match self {
Cache::Redis(e) => e.keys(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn set_add(&mut self, key: &str, value: JsonValue) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.set_add(key, value)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn set_get(&mut self, key: &str) -> Result<JsonValue, String> {
let res = match self {
Cache::Redis(e) => e.set_get(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn set_delete(&mut self, key: &str, value: JsonValue) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.set_delete(key, value)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn set_message_queue(&mut self, key: &str, value: JsonValue) -> Result<bool, String> {
match self {
Cache::Redis(e) => e.set_message_queue(key, value),
Cache::None => Err("error".to_string()),
}
}
pub fn get_message_queue(&mut self, key: &str) -> Result<JsonValue, String> {
match self {
Cache::Redis(e) => Ok(e.get_message_queue(key)?),
Cache::None => Err("error".to_string()),
}
}
pub fn set_object(&mut self, key: &str, field: &str, value: JsonValue) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.set_object(key, field, value)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn get_object(&mut self, key: &str) -> Result<JsonValue, String> {
let res = match self {
Cache::Redis(e) => e.get_object(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn add_hash(&mut self, key: &str, field: &str, value: JsonValue) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.add_hash(key, field, value)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn delete_hash(&mut self, key: &str, field: &str) -> Result<bool, String> {
let res = match self {
Cache::Redis(e) => e.delete_hash(key, field)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn get_hash_field_value(&mut self, key: &str, field: &str) -> Result<JsonValue, String> {
let res = match self {
Cache::Redis(e) => e.get_hash_field_value(key, field)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
pub fn get_hash_fields(&mut self, key: &str) -> Result<JsonValue, String> {
let res = match self {
Cache::Redis(e) => e.get_hash_fields(key)?,
Cache::None => return Err("error".to_string()),
};
Ok(res)
}
}
pub trait CacheBase {
fn db(&mut self, db: i8) -> &mut Self;
fn add(&mut self, key: &str, value: JsonValue, expiration_date: u64) -> Result<bool, String>;
fn get(&mut self, key: &str) -> Result<JsonValue, String>;
fn delete(&mut self, key: &str) -> Result<bool, String>;
fn exists(&mut self, key: &str) -> Result<bool, String>;
fn keys(&mut self, key: &str) -> Result<JsonValue, String>;
fn set_add(&mut self, key: &str, value: JsonValue) -> Result<bool, String>;
fn set_get(&mut self, key: &str) -> Result<JsonValue, String>;
fn set_delete(&mut self, key: &str, value: JsonValue) -> Result<bool, String>;
fn set_message_queue(&mut self, key: &str, value: JsonValue) -> Result<bool, String>;
fn get_message_queue(&mut self, key: &str) -> Result<JsonValue, String>;
fn set_object(&mut self, key: &str, field: &str, value: JsonValue) -> Result<bool, String>;
fn get_object(&mut self, key: &str) -> Result<JsonValue, String>;
fn add_hash(&mut self, key: &str, field: &str, value: JsonValue) -> Result<bool, String>;
fn get_hash_field_value(&mut self, key: &str, field: &str) -> Result<JsonValue, String>;
fn get_hash_fields(&mut self, key: &str) -> Result<JsonValue, String>;
fn delete_hash(&mut self, key: &str, field: &str) -> Result<bool, String>;
}
#[derive(Clone, Debug, Deserialize, Serialize)]
pub struct Config {
pub default: String,
pub connections: BTreeMap<String, Connection>,
}
impl Default for Config {
fn default() -> Self {
Self::new()
}
}
impl Config {
pub fn create(config_file: PathBuf) -> Config {
let data = Config::new();
match fs::read_to_string(config_file.clone()) {
Ok(e) => toml::from_str::<Config>(&e).unwrap_or_else(|_| {
if e.contains(format!("#{}", env!("CARGO_PKG_NAME")).as_str()) {
return data;
}
let toml = toml::to_string(&data).unwrap();
let toml = format!("\r\n#{}\r\n{}{}", env!("CARGO_PKG_NAME"), toml, e);
let _ = fs::write(config_file.to_str().unwrap(), toml);
data
}),
Err(_) => {
let toml = toml::to_string(&data).unwrap();
let _ = fs::write(config_file.to_str().unwrap(), toml);
data
}
}
}
pub fn new() -> Config {
let mut connections = BTreeMap::new();
connections.insert("my_name".to_string(), Connection::default());
Self {
default: "my_name".to_string(),
connections,
}
}
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct Connection {
pub mode: CacheMode,
pub hostname: String,
pub hostport: String,
pub userpass: String,
}
impl Default for Connection {
fn default() -> Self {
Self {
mode: CacheMode::Redis,
hostname: "127.0.0.1".to_string(),
hostport: "6379".to_string(),
userpass: "".to_string(),
}
}
}
impl Connection {
pub fn from(&mut self, data: JsonValue) -> &mut Connection {
self.mode = CacheMode::from(data["mode"].as_str().unwrap());
self.hostname = data["hostname"].to_string();
self.hostport = data["hostport"].to_string();
self.userpass = data["userpass"].to_string();
self
}
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub enum CacheMode {
Redis,
}
impl CacheMode {
pub fn str(&mut self) -> String {
match self {
CacheMode::Redis => "redis",
}
.to_string()
}
pub fn from(name: &str) -> Self {
match name {
"redis" => CacheMode::Redis,
_ => CacheMode::Redis,
}
}
}