العمل مع التواريخ والوقت في Rust: تقنيات ومكتبات متقدمة

مدرب بايثون أونلاين للمبتدئين

تعلم Python بسهولة دون إرهاق نظري. حل مهام عملية مع التحقق التلقائي واكتب الكود مباشرة في المتصفح.

ابدأ الدورة

العمل المتقدم مع التواريخ والوقت في Rust: من NaiveDateTime إلى Timezone



العمل مع التواريخ والوقت — من أكثر المهام شيوعًا في تطوير الواجهة الخلفية، وتسجيل الأحداث، والأنظمة المالية، ومعالجة البيانات. في Rust، توفر المكتبة القياسية الوحدة الأساسية std::time، ولكنها غير كافية للمشاريع الجادة. على المستوى المتقدم، نلجأ إلى الكريت chrono — المعيار الفعلي للعمل مع التواريخ والوقت. في هذه المقالة، سنستعرض السيناريوهات المعقدة: العمل مع المناطق الزمنية، وتحليل التنسيقات غير القياسية، والتعامل مع الفترات الزمنية، وتحسين الأداء.



1. التثبيت والهيكل الأساسي لـ chrono



أضف التبعية في Cargo.toml:



[dependencies]chrono = { version = "0.4", features = ["serde"] }


الأنواع الأساسية في chrono للعمل المتقدم:

  • NaiveDateTime — تاريخ-وقت بدون منطقة زمنية (محلي).
  • DateTime<Tz> — تاريخ-وقت مرتبط بمنطقة زمنية (مثل Utc، Local، FixedOffset).
  • Duration — فترة زمنية (تختلف عن std::time::Duration، وتدعم القيم السالبة).
  • TimeDelta — مرادف لـ Duration في الإصدارات الجديدة.


مثال لإنشاء اللحظة الحالية في UTC والوقت المحلي:



use chrono::{Utc, Local, DateTime};

fn main() { let utc_now: DateTime<Utc> = Utc::now(); let local_now: DateTime<Local> = Local::now(); println!("UTC: {}", utc_now); println!("Local: {}", local_now);}


2. العمل مع المناطق الزمنية (Timezone)



إحدى الإمكانيات القوية لـ chrono هي دعم قاعدة بيانات Olson للمناطق الزمنية من خلال الكريت chrono-tz. يتيح ذلك العمل مع أسماء المناطق مثل "Europe/Moscow" أو "America/New_York".



قم بالتثبيت:



[dependencies]chrono = "0.4"chrono-tz = "0.8"


مثال لتحويل الوقت بين المناطق:



use chrono::{Utc, DateTime, TimeZone};use chrono_tz::Europe::Moscow;

fn main() { let utc_time: DateTime<Utc> = Utc::now(); let moscow_time = utc_time.with_timezone(&Moscow); println!("UTC: {}", utc_time); println!("Moscow: {}", moscow_time);}


نقطة مهمة: احفظ الوقت دائمًا بصيغة UTC في قاعدة البيانات، وقم بالتحويل إلى الوقت المحلي فقط عند العرض للمستخدم. هذا يمنع الارتباك مع التوقيت الصيفي/الشتوي.



2.1. العمل مع FixedOffset



إذا كنت تعرف الإزاحة الثابتة (مثل +03:00)، استخدم FixedOffset:



use chrono::{FixedOffset, DateTime, Utc};

fn main() { let offset = FixedOffset::east_opt(3 * 3600).unwrap(); // +03:00 let now_utc: DateTime<Utc> = Utc::now(); let now_offset = now_utc.with_timezone(&offset); println!("With offset +03:00: {}", now_offset);}


3. تحليل وتنسيق التواريخ (تقنيات متقدمة)



التحليل القياسي عبر parse_from_str يتطلب تنسيقًا دقيقًا. لكن في المشاريع الحقيقية، قد تختلف التنسيقات (مثل سجلات من أنظمة مختلفة). لنستعرض عدة طرق.



3.1. تنسيقات متعددة مع try_parse



استخدم التكرار عبر التنسيقات:



use chrono::NaiveDateTime;

fn parse_flexible(date_str: &str) -> Option<NaiveDateTime> { let formats = [ "%Y-%m-%d %H:%M:%S", "%d/%m/%Y %H:%M", "%Y%m%dT%H%M%S", "%b %d %Y %I:%M:%S%p", ];

for fmt in &formats { if let Ok(dt) = NaiveDateTime::parse_from_str(date_str, fmt) { return Some(dt); } } None}

fn main() { let dates = vec![ "2024-03-15 14:30:00", "15/03/2024 14:30", "2

المدونات

توصيات الكتب