Unix Timestamp & Date Time Guide

Code Examples In Rust


Introduction

Date and time management is a crucial aspect of many web applications, whether scheduling events, logging user activity, or displaying localized times for a global audience.
In Rust, the chrono crate remains the go-to solution for working with date-time, Unix timestamps, and time zones. However, the newer time crate has also gained popularity due to its lightweight design and focus on performance. Both libraries allow Rust developers to easily manipulate time values, perform time zone conversions, and work with timestamps in a variety of formats.


Get Current Time

Retrieving the current time is a fundamental task in software development, used in scenarios like logging, scheduling, time-stamping, and real-time processing.
In Rust, popular crates like chrono and time offer comprehensive tools to retrieve the current time, perform time-related operations, and manipulate time formats with ease.

Method:

1std::time::SystemTime::now();

Example:

1use std::time::{SystemTime, UNIX_EPOCH};
2
3fn main() {
4    // Get the current system time
5    let now = SystemTime::now();
6
7    // Convert to UNIX timestamp (seconds since epoch)
8    let duration_since_epoch = now.duration_since(UNIX_EPOCH).expect("Time went backwards");
9
10    println!("Current UNIX timestamp: {}", duration_since_epoch.as_secs());
11}

Result:

1Current UNIX timestamp: 1672284822

Get Unix Timestamp

Unix timestamps are a standard way of representing time as the number of seconds (or milliseconds) elapsed since the Unix epoch, which is January 1, 1970, at 00:00:00 UTC. They are widely used in web development for logging, scheduling, and synchronizing time across systems due to their simplicity and consistency.
In Rust, popular crates like chrono and time provide robust and efficient tools to retrieve Unix timestamps. These libraries make it easy to get the current Unix timestamp and perform conversions between Unix timestamps and other time representations.

Method:

1duration_since(UNIX_EPOCH)

Example:

1use std::time::{SystemTime, UNIX_EPOCH};
2
3fn main() {
4    // Get the current system time
5    let now = SystemTime::now();
6
7    // Convert to UNIX timestamp (seconds since epoch)
8    let duration_since_epoch = now.duration_since(UNIX_EPOCH).expect("Time went backwards");
9
10    println!("Current UNIX timestamp: {}", duration_since_epoch.as_secs());
11}

Result:

1Current UNIX timestamp: 1672284822

Construct New Time

Creating new date and time objects is a core aspect of many applications, enabling developers to represent specific moments in time, schedule events, or perform date arithmetic.
chrono and time in Rust providing easy ways to create date-time objects, modify them, and perform various time-related operations.

Method:

1// Using chrono crate
2// need to add dependencies in Cargo.toml
3// [dependencies]
4// chrono = "0.4.23"
5NaiveDate::from_ymd_op(year: i32, month: u32, day: u32)
6NaiveDate::and_hms_opt(hour: u32, min: u32, sec: u32)
7NaiveDateTime::parse_from_str

Example:

1use chrono::{NaiveDate, NaiveDateTime};
2
3fn main() {
4    // Create a specific date: yyyy-mm-dd
5    let date = NaiveDate::from_ymd_opt(2024, 10, 12).unwrap();
6
7    // Combine it with a specific time: hh:mm:ss
8    let specific_time: NaiveDateTime = date.and_hms_opt(14, 30, 0).unwrap();
9
10    println!(
11        "Specific time: {}",
12        specific_time.format("%Y-%m-%d %H:%M:%S")
13    );
14
15    // Create a specific datetime from a string
16    let time_from_str: NaiveDateTime =
17        NaiveDateTime::parse_from_str("2024-10-12 14:30:00", "%Y-%m-%d %H:%M:%S")
18            .expect("Failed to parse datetime");
19
20    println!("Specific time from string: {}", time_from_str);
21}

Result:

1Specific time: 2024-10-12 14:30:00
2Specific time from string: 2024-10-12 14:30:00

Convert Unix timestamp to Readable Date Time

Unix timestamps, representing the number of seconds since the Unix epoch (January 1, 1970, at 00:00:00 UTC), are commonly used in programming for their simplicity and efficiency.
However, they are not human-readable, making it necessary to convert them into a readable date and time format for display, logging, or reporting purposes
In Rust, converting Unix timestamps to a readable date-time format can be done efficiently using chrono and time. These libraries allow you to easily convert Unix timestamps to structured date-time objects and format them in a way that is meaningful and understandable to users.

Method:

1// use chrono::DateTime
2// need to add dependencies in Cargo.toml
3// [dependencies]
4// chrono = "0.4.23"
5DateTime::from_timestamp((secs: i64, nsecs: u32)

Example:

1use chrono::DateTime;
2
3fn main() {
4    // Example Unix timestamp (seconds since Unix epoch)
5    let unix_timestamp: i64 = 1_700_000_000;
6
7    // Convert Unix timestamp to DateTime
8    let datetime: DateTime<chrono::Utc> =
9        DateTime::from_timestamp(unix_timestamp, 0).expect("Invalid timestamp");
10
11    // Print the result
12    let formatted = datetime.format("%d-%m-%Y %H:%M:%S");
13    println!("Readable UTC datetime: {}", formatted);
14}

Result:

1Readable datetime: 14-11-2023 22:13:20

Convert Date Time to Unix timestamp

Converting date-time objects into Unix timestamps is a common operation, often required for storing time values, performing calculations, or interacting with APIs and databases that use Unix time.
In Rust, chrono and time provide powerful tools for converting date-time values into Unix timestamps. These libraries enable developers to easily convert time-related objects to Unix timestamps and perform date-time arithmetic efficiently.

Method:

1// use chrono::DateTime
2// need to add dependencies in Cargo.toml
3// [dependencies]
4// chrono = "0.4.23"
5timestamp()
6timestamp_millis()
7timestamp_micros()
8timestamp_nanos_opt()

Example:

1use chrono::{DateTime, NaiveDateTime, TimeZone, Utc};
2
3fn main() {
4    // Define a specific date and time
5    let naive_datetime = NaiveDateTime::parse_from_str("2024-10-12 14:30:00", "%Y-%m-%d %H:%M:%S")
6        .expect("Failed to parse datetime");
7
8    // Convert NaiveDateTime to a timestamp (seconds since Unix epoch)
9    let unix_timestamp = naive_datetime.and_utc().timestamp();
10
11    println!("Unix timestamp: {}", unix_timestamp);
12
13    let dt: DateTime<Utc> = Utc.with_ymd_and_hms(2015, 5, 15, 0, 0, 0).unwrap();
14    println!(
15        "Unix timestamp in nanoseconds: {}",
16        dt.timestamp_nanos_opt().unwrap()
17    );
18}

Result:

1Unix timestamp: 1728743400
2Unix timestamp in nanoseconds: 1431648000000000000

Change Time Zone

Timezones play a critical role in applications that work with global users or time-sensitive data across different regions.
chrono and time in Rust provide powerful tools for working with time zones in a flexible and efficient way. These libraries support time zone-aware date-time objects, conversions between time zones, and formatting date-time values in a localized manner.

Method:

1// use chrono::DateTime
2// need to add dependencies in Cargo.toml
3// [dependencies]
4// chrono = "0.4.23"
5
6// parse a date time string with timezone
7DateTime::parse_from_rfc3339(s: &str)
8
9// Convert to another timezone
10DateTime<Tz>.with_timezone(tz: &Tz2)

Example:

1use chrono::{DateTime, FixedOffset, Local, NaiveDateTime, TimeZone, Utc};
2
3fn main() {
4    // Create a NaiveDateTime (timezone-agnostic)
5    let naive_datetime: NaiveDateTime =
6        NaiveDateTime::parse_from_str("2024-10-12 14:30:00", "%Y-%m-%d %H:%M:%S")
7            .expect("Failed to parse datetime");
8
9    // Convert to UTC
10    let utc_datetime: DateTime<Utc> = Utc.from_utc_datetime(&naive_datetime);
11    println!("UTC time: {}", utc_datetime);
12
13    // Convert to a fixed offset (+05:30, e.g., India Standard Time)
14    let fixed_offset: FixedOffset =
15        FixedOffset::east_opt(5 * 3600 + 30 * 60).expect("Invalid offset");
16    let ist_datetime: DateTime<FixedOffset> = utc_datetime.with_timezone(&fixed_offset);
17    println!("IST time: {}", ist_datetime);
18
19    // Convert to local time
20    let local_datetime: DateTime<Local> = utc_datetime.with_timezone(&Local);
21    println!("Local time: {}", local_datetime);
22
23    // Parse a datetime string with a specific time zone
24    let datetime_with_tz: DateTime<FixedOffset> =
25        DateTime::parse_from_rfc3339("2024-10-12T14:30:00+05:30")
26            .expect("Failed to parse datetime");
27
28    println!("Parsed time with timezone: {}", datetime_with_tz);
29
30    // Convert to UTC
31    let utc_datetime_parsed: DateTime<Utc> = datetime_with_tz.with_timezone(&chrono::Utc);
32    println!("Converted to UTC: {}", utc_datetime_parsed);
33}

Result:

1UTC time: 2024-10-12 14:30:00 UTC
2IST time: 2024-10-12 20:00:00 +05:30
3Local time: 2024-10-12 22:30:00 +08:00
4Parsed time with timezone: 2024-10-12 14:30:00 +05:30
5Converted to UTC: 2024-10-12 09:00:00 UTC

Time Addition and Subtraction

Date-time addition and subtraction are essential operations for many time-based applications.
In Rust, date-time arithmetic is made easy and efficient with chrono and time. These libraries offer support for performing arithmetic operations on date-time objects, such as adding or subtracting specific durations (e.g., days, hours, minutes), calculating the difference between two time points, and handling overflow or underflow in time units.

Method:

1// use chrono::Duration, directly add and subtract
2// need to add dependencies in Cargo.toml
3// [dependencies]
4// chrono = "0.4.23"
5chrono::Duration
6
7// use std::time::Instant
8// calc time cost
9Instant.elapsed()

Example:

1use chrono::{Duration, Utc};
2use std::time::Instant;
3
4fn main() {
5    // Get the current UTC time
6    let utc_now = Utc::now();
7    println!("Current UTC datetime: {}", utc_now);
8
9    // Add 2 days and 3 hours
10    let added_time = utc_now + Duration::days(2) + Duration::hours(3);
11    println!("After adding 2 days and 3 hours: {}", added_time);
12
13    // Subtract 1 week
14    let subtracted_time = utc_now - Duration::weeks(1);
15    println!("After subtracting 1 week: {}", subtracted_time);
16
17    // Calc time cost
18    // Start the timer
19    let start = Instant::now();
20
21    // Example of some code whose execution time you want to measure
22    let _: u64 = (1..=1_000_000).sum();
23
24    // Measure elapsed time
25    let duration = start.elapsed();
26
27    // Print the result
28    println!("Time taken: {:?}", duration);
29}

Result:

1Current UTC datetime: 2024-12-12 16:02:23.262434200 UTC
2After adding 2 days and 3 hours: 2024-12-14 19:02:23.262434200 UTC
3After subtracting 1 week: 2024-12-05 16:02:23.262434200 UTC
4Time taken: 4.9823ms

Pause or sleep for a specific time

Pausing or delaying the execution of a program is a common requirement in various applications, such as implementing retries, creating animations, scheduling tasks, or rate-limiting requests.
Rust provides two main methods for sleeping: one for blocking operations in synchronous programs using std::thread::sleep, and another for non-blocking sleep in asynchronous programs using tokio::time::sleep or async-std. Both approaches allow you to pause execution for a specified duration.

Method:

1// use std::thread::sleep
2std::thread::sleep(dur: Duration)

Example:

1use std::{thread, time};
2
3fn main() {
4    println!("Sleeping for 2 seconds...");
5
6    // Sleep for 2 seconds
7    let duration: time::Duration = time::Duration::new(2, 0); // 2 seconds, 0 nanoseconds
8    thread::sleep(duration);
9
10    println!("Awoke after 2 seconds!");
11}

Result:

1Sleeping for 2 seconds...
2Awoke after 2 seconds!