rustsystemtime

How to access as_secs in SystemTime? "no method named `as_secs` found for enum Result"


I'm using std::time::SystemTime. My goal is to make a struct with a field called timestamp and store the time in seconds.

I saw this example which works correctly:

use std::time::SystemTime;

match SystemTime::now().duration_since(SystemTime::UNIX_EPOCH) {
    Ok(n) => println!("1970-01-01 00:00:00 UTC was {} seconds ago!", n.as_secs()),
    Err(_) => panic!("SystemTime before UNIX EPOCH!"),
}

When I try this code I get an error:

use std::time::SystemTime;

let n = SystemTime::now().duration_since(SystemTime::UNIX_EPOCH);
println!("{}", n.as_secs());
error[E0599]: no method named `as_secs` found for enum `std::result::Result<std::time::Duration, std::time::SystemTimeError>` in the current scope
 --> src/main.rs:5:22
  |
5 |     println!("{}", n.as_secs());
  |                      ^^^^^^^ method not found in `std::result::Result<std::time::Duration, std::time::SystemTimeError>`

What am I doing wrong?


Solution

  • Read the error:

    no method named `...` found for type `Result<...>`
    

    So, we look at Result:

    Result is a type that represents either success (Ok) or faliure (Err)

    See the std::result module for documentation details.

    So, we know that SystemTime::duration_since(&self, _) returns a Result, meaning it could possibly have failed. Reading the docs:

    Returns an Err if earlier is later than self, and the error contains how far from self the time is.

    So, we just have to unwrap, expect, or match on it to get the possibility of an error out:

    use std::time::SystemTime;
    
    // Unwrapping
    let n = SystemTime::now().duration_since(SystemTime::UNIX_EPOCH)
        .unwrap(); // Will panic if it is not `Ok`.
    
    // Expecting
    let n = SystemTime::now().duration_since(SystemTime::UNIX_EPOCH)
        .expect("Invalid time comparison"); // Will panic with error message
            // if it is not `Ok`.
    
    // Matching
    let n = SystemTime::now().duration_since(SystemTime::UNIX_EPOCH);
    match n {
        Ok(x) => { /* Use x */ },
        Err(e) => { /* Process Error e */ },
    }
    
    // Fallibly Destructuring:
    let n = SystemTime::now().duration_since(SystemTime::UNIX_EPOCH);
    if let Ok(x) = n {
        /* Use x */
    } else {
        /* There was an error. */
    }