....
This commit is contained in:
103
actix_mvc_app/src/utils/mod.rs
Normal file
103
actix_mvc_app/src/utils/mod.rs
Normal file
@@ -0,0 +1,103 @@
|
||||
use chrono::{DateTime, TimeZone, Utc};
|
||||
use tera::{self, Function, Result, Value};
|
||||
|
||||
/// Registers custom Tera functions
|
||||
pub fn register_tera_functions(tera: &mut tera::Tera) {
|
||||
tera.register_function("now", NowFunction);
|
||||
tera.register_function("format_date", FormatDateFunction);
|
||||
}
|
||||
|
||||
/// Tera function to get the current date/time
|
||||
#[derive(Clone)]
|
||||
pub struct NowFunction;
|
||||
|
||||
impl Function for NowFunction {
|
||||
fn call(&self, args: &std::collections::HashMap<String, Value>) -> Result<Value> {
|
||||
let format = match args.get("format") {
|
||||
Some(val) => match val.as_str() {
|
||||
Some(s) => s,
|
||||
None => "%Y-%m-%d %H:%M:%S",
|
||||
},
|
||||
None => "%Y-%m-%d %H:%M:%S",
|
||||
};
|
||||
|
||||
let now = Utc::now();
|
||||
|
||||
// Special case for just getting the year
|
||||
if args.get("year").and_then(|v| v.as_bool()).unwrap_or(false) {
|
||||
return Ok(Value::String(now.format("%Y").to_string()));
|
||||
}
|
||||
|
||||
Ok(Value::String(now.format(format).to_string()))
|
||||
}
|
||||
}
|
||||
|
||||
/// Tera function to format a date
|
||||
#[derive(Clone)]
|
||||
pub struct FormatDateFunction;
|
||||
|
||||
impl Function for FormatDateFunction {
|
||||
fn call(&self, args: &std::collections::HashMap<String, Value>) -> Result<Value> {
|
||||
let timestamp = match args.get("timestamp") {
|
||||
Some(val) => match val.as_i64() {
|
||||
Some(ts) => ts,
|
||||
None => {
|
||||
return Err(tera::Error::msg(
|
||||
"The 'timestamp' argument must be a valid timestamp",
|
||||
))
|
||||
}
|
||||
},
|
||||
None => {
|
||||
return Err(tera::Error::msg(
|
||||
"The 'timestamp' argument is required",
|
||||
))
|
||||
}
|
||||
};
|
||||
|
||||
let format = match args.get("format") {
|
||||
Some(val) => match val.as_str() {
|
||||
Some(s) => s,
|
||||
None => "%Y-%m-%d %H:%M:%S",
|
||||
},
|
||||
None => "%Y-%m-%d %H:%M:%S",
|
||||
};
|
||||
|
||||
// Convert timestamp to DateTime using the non-deprecated method
|
||||
let datetime = match DateTime::from_timestamp(timestamp, 0) {
|
||||
Some(dt) => dt,
|
||||
None => {
|
||||
return Err(tera::Error::msg(
|
||||
"Failed to convert timestamp to datetime",
|
||||
))
|
||||
}
|
||||
};
|
||||
|
||||
Ok(Value::String(datetime.format(format).to_string()))
|
||||
}
|
||||
}
|
||||
|
||||
/// Formats a date for display
|
||||
pub fn format_date(date: &DateTime<Utc>, format: &str) -> String {
|
||||
date.format(format).to_string()
|
||||
}
|
||||
|
||||
/// Truncates a string to a maximum length and adds an ellipsis if truncated
|
||||
pub fn truncate_string(s: &str, max_length: usize) -> String {
|
||||
if s.len() <= max_length {
|
||||
s.to_string()
|
||||
} else {
|
||||
format!("{}...", &s[0..max_length])
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
use super::*;
|
||||
|
||||
#[test]
|
||||
fn test_truncate_string() {
|
||||
assert_eq!(truncate_string("Hello", 10), "Hello");
|
||||
assert_eq!(truncate_string("Hello, world!", 5), "Hello...");
|
||||
assert_eq!(truncate_string("", 5), "");
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user