cfg_std! {
pub mod _log;
#[allow(unused_imports)]
pub use _log::*;
}
use e_utils::{CResult, Result};
#[cfg(feature = "std")]
pub use log::LevelFilter;
use serde::{Deserialize, Serialize};
use std::{borrow::Cow, str::FromStr};
pub trait AutoLevelRes<T, S: Serialize> {
fn print(self, add: &str, tag: S) -> Self;
fn eprint(self, add: &str, tag: S) -> Self;
}
pub trait AutoLevel<A: Serialize> {
fn print(&self, tag: A, level: Level) -> bool;
}
impl<S: AsRef<str>, A: Serialize> AutoLevel<A> for S {
fn print(&self, tag: A, level: Level) -> bool {
let data = self.as_ref();
match level {
Level::Trace => trace!(tag:tag, data),
Level::Debug => debug!(tag:tag, data),
Level::Info => info!(tag:tag, data),
Level::Warn => warn!(tag:tag, data),
Level::Error => error!(tag:tag, data),
Level::Off => return false,
};
true
}
}
impl<T, S: Serialize> AutoLevelRes<T, S> for CResult<T> {
fn print(self, add: &str, tag: S) -> Self {
match &self {
CResult::Ok(_x) => info!(tag:tag, add),
CResult::Err(x) => warn!(tag:tag, "{}: {}", add, x),
};
self
}
fn eprint(self, add: &str, tag: S) -> Self {
match &self {
CResult::Ok(_x) => info!(tag:tag, add),
CResult::Err(x) => error!(tag:tag, "{}: {}", add, x,),
};
self
}
}
impl<T, S: Serialize> AutoLevelRes<T, S> for Result<T> {
fn print(self, add: &str, tag: S) -> Self {
match &self {
Ok(_x) => info!(tag:tag, add),
Err(x) => warn!(tag:tag, "{}: {}", add, x,),
};
self
}
fn eprint(self, add: &str, tag: S) -> Self {
match &self {
Ok(_x) => info!(tag:tag, add),
Err(x) => error!(tag:tag, "{}: {}", add, x,),
};
self
}
}
#[derive(Clone, Debug, Deserialize, Serialize)]
pub enum LevelTag {
Unknow,
File,
Log,
System,
Permissions,
Ui,
Database,
Other(Cow<'static, str>),
}
impl Default for LevelTag {
fn default() -> Self {
LevelTag::Unknow
}
}
#[derive(Clone, Copy, Debug, PartialEq, Eq, PartialOrd, Ord, Deserialize, Serialize)]
pub enum Level {
Off,
Error,
Warn,
Info,
Debug,
Trace,
}
impl Default for Level {
fn default() -> Self {
Self::Info
}
}
#[derive(Deserialize, Serialize, Debug)]
pub struct LevelData<T: Serialize, S: Serialize> {
pub msg: T,
pub tag: S,
}
impl<T: Serialize, S: Serialize> LevelData<T, S> {
pub fn to_string(&self) -> String {
serde_json::to_string(self).unwrap_or_default()
}
}
impl Level {
pub fn add<T, S>(&self, msg: T, tag: S) -> bool
where
T: Serialize,
S: Serialize,
{
match self {
Level::Off => return false,
Level::Error => error!(tag:tag,msg),
Level::Warn => warn!(tag:tag,msg),
Level::Info => info!(tag:tag,msg),
Level::Debug => debug!(tag:tag,msg),
Level::Trace => trace!(tag:tag,msg),
}
true
}
}
#[cfg(feature = "std")]
impl From<LevelFilter> for Level {
fn from(value: LevelFilter) -> Self {
match value {
LevelFilter::Off => Level::Off,
LevelFilter::Debug => Level::Debug,
LevelFilter::Info => Level::Info,
LevelFilter::Trace => Level::Trace,
LevelFilter::Error => Level::Error,
LevelFilter::Warn => Level::Warn,
}
}
}
impl Level {
#[cfg(feature = "std")]
pub fn to_level_filter(&self) -> LevelFilter {
match self {
Level::Off => LevelFilter::Off,
Level::Trace => LevelFilter::Trace,
Level::Debug => LevelFilter::Debug,
Level::Info => LevelFilter::Info,
Level::Warn => LevelFilter::Warn,
Level::Error => LevelFilter::Error,
}
}
pub fn to_string(&self) -> String {
self.to_level_filter().to_string()
}
}
impl core::fmt::Display for Level {
fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
write!(f, "{}", self.to_string())
}
}
#[cfg(feature = "std")]
impl From<&str> for Level {
fn from(s: &str) -> Self {
let level: Level = LevelFilter::from_str(s).unwrap_or(LevelFilter::Off).into();
level
}
}
impl From<String> for Level {
fn from(s: String) -> Self {
s.as_str().into()
}
}