use std::ffi::CString; use std::os::raw::c_char; #[link(name = "tdjson")] extern "C" { fn td_execute(request: *const c_char) -> *const c_char; } /// Отключаем логи TDLib синхронно, до создания клиента pub fn disable_tdlib_logs() { let request = r#"{"@type":"setLogVerbosityLevel","new_verbosity_level":0}"#; let c_request = CString::new(request).unwrap(); unsafe { let _ = td_execute(c_request.as_ptr()); } // Также перенаправляем логи в никуда let request2 = r#"{"@type":"setLogStream","log_stream":{"@type":"logStreamEmpty"}}"#; let c_request2 = CString::new(request2).unwrap(); unsafe { let _ = td_execute(c_request2.as_ptr()); } } /// Форматирование timestamp в время HH:MM с учётом timezone offset /// timezone_str: строка формата "+03:00" или "-05:00" pub fn format_timestamp_with_tz(timestamp: i32, timezone_str: &str) -> String { let secs = timestamp as i64; // Парсим timezone offset (например "+03:00" -> 3 часа) let offset_hours = parse_timezone_offset(timezone_str); let hours = ((secs % 86400) / 3600) as i32; let minutes = ((secs % 3600) / 60) as u32; // Применяем timezone offset let local_hours = ((hours + offset_hours) % 24 + 24) % 24; format!("{:02}:{:02}", local_hours, minutes) } /// Парсит timezone строку типа "+03:00" в количество часов fn parse_timezone_offset(tz: &str) -> i32 { // Простой парсинг "+03:00" или "-05:00" if tz.len() >= 3 { let sign = if tz.starts_with('-') { -1 } else { 1 }; let hours_str = &tz[1..3]; if let Ok(hours) = hours_str.parse::() { return sign * hours; } } 3 // fallback к MSK } /// Устаревшая функция для обратной совместимости (используется дефолтный +03:00) #[allow(dead_code)] pub fn format_timestamp(timestamp: i32) -> String { format_timestamp_with_tz(timestamp, "+03:00") } /// Форматирование timestamp в дату для разделителя pub fn format_date(timestamp: i32) -> String { use std::time::{SystemTime, UNIX_EPOCH}; let now = SystemTime::now() .duration_since(UNIX_EPOCH) .unwrap() .as_secs() as i64; let msg_day = timestamp as i64 / 86400; let today = now / 86400; if msg_day == today { "Сегодня".to_string() } else if msg_day == today - 1 { "Вчера".to_string() } else { // Простое форматирование даты let days_since_epoch = timestamp as i64 / 86400; // Приблизительный расчёт даты (без учёта високосных годов) let year = 1970 + (days_since_epoch / 365) as i32; let day_of_year = days_since_epoch % 365; let months = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]; let mut month = 0; let mut day = day_of_year as i32; for (i, &m) in months.iter().enumerate() { if day < m { month = i + 1; break; } day -= m; } format!("{:02}.{:02}.{}", day + 1, month, year) } } /// Получить день из timestamp для группировки pub fn get_day(timestamp: i32) -> i64 { timestamp as i64 / 86400 } /// Форматирование timestamp в полную дату и время (DD.MM.YYYY HH:MM) pub fn format_datetime(timestamp: i32) -> String { let secs = timestamp as i64; // Время let hours = ((secs % 86400) / 3600) as u32; let minutes = ((secs % 3600) / 60) as u32; let local_hours = (hours + 3) % 24; // MSK // Дата let days_since_epoch = secs / 86400; let year = 1970 + (days_since_epoch / 365) as i32; let day_of_year = days_since_epoch % 365; let months = [31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31]; let mut month = 1; let mut day = day_of_year as i32; for (i, &m) in months.iter().enumerate() { if day < m { month = i + 1; break; } day -= m; } format!("{:02}.{:02}.{} {:02}:{:02}", day + 1, month, year, local_hours, minutes) } /// Форматирование "был(а) онлайн" из timestamp pub fn format_was_online(timestamp: i32) -> String { use std::time::{SystemTime, UNIX_EPOCH}; let now = SystemTime::now() .duration_since(UNIX_EPOCH) .unwrap() .as_secs() as i32; let diff = now - timestamp; if diff < 60 { "был(а) только что".to_string() } else if diff < 3600 { let mins = diff / 60; format!("был(а) {} мин. назад", mins) } else if diff < 86400 { let hours = diff / 3600; format!("был(а) {} ч. назад", hours) } else { // Показываем дату let datetime = chrono::DateTime::from_timestamp(timestamp as i64, 0) .map(|dt| dt.format("%d.%m %H:%M").to_string()) .unwrap_or_else(|| "давно".to_string()); format!("был(а) {}", datetime) } }