Skip to content

Commit

Permalink
Support SystemTime before 1970
Browse files Browse the repository at this point in the history
  • Loading branch information
emwalker committed Jul 28, 2024
1 parent e44f580 commit 02d93c9
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 8 deletions.
12 changes: 8 additions & 4 deletions src/time.rs
Original file line number Diff line number Diff line change
Expand Up @@ -402,14 +402,18 @@ impl TryConvert for SystemTime {
timespec = rb_time_timespec(val.as_rb_value());
Ruby::get_unchecked().qnil()
})?;
if timespec.tv_sec >= 0 && timespec.tv_nsec >= 0 {
let mut duration = Duration::from_secs(timespec.tv_sec as _);
if timespec.tv_nsec >= 0 {
let mut duration = Duration::from_secs(timespec.tv_sec.abs() as _);
duration += Duration::from_nanos(timespec.tv_nsec as _);
Ok(Self::UNIX_EPOCH + duration)
if timespec.tv_sec >= 0 {
Ok(Self::UNIX_EPOCH + duration)
} else {
Ok(Self::UNIX_EPOCH - duration)
}
} else {
Err(Error::new(
Ruby::get_with(val).exception_arg_error(),
"time must not be negative",
"time nanos must not be negative",
))
}
}
Expand Down
31 changes: 27 additions & 4 deletions tests/time.rs
Original file line number Diff line number Diff line change
@@ -1,9 +1,30 @@
use magnus::rb_assert;
use magnus::{Error, Ruby};
use std::time::SystemTime;

#[test]
#[cfg(feature = "chrono")]
fn it_supports_chrono() {
fn test_all() {
magnus::Ruby::init(|ruby| {
test_supports_system_time(ruby)?;
#[cfg(feature = "chrono")]
test_supports_chrono(ruby)?;
Ok(())
})
.unwrap();
}

fn test_supports_system_time(ruby: &Ruby) -> Result<(), Error> {
let t = ruby.eval::<SystemTime>("Time.new(1971)").unwrap();
rb_assert!(ruby, "t.year == 1971", t);

let t = ruby.eval::<SystemTime>("Time.new(1960)").unwrap();
rb_assert!(ruby, "t.year == 1960", t);

Ok(())
}

fn test_supports_chrono(ruby: &Ruby) -> Result<(), Error> {
use chrono::{DateTime, Datelike, FixedOffset, Utc};
use magnus::rb_assert;
let ruby = unsafe { magnus::embed::init() };

let t = ruby.eval::<DateTime<Utc>>("Time.at(0, 10, :nsec)").unwrap();
assert_eq!(t.year(), 1970);
Expand Down Expand Up @@ -45,4 +66,6 @@ fn it_supports_chrono() {
assert_eq!(&dt.to_rfc3339(), "2022-05-31T09:08:00.123456789+05:30");
rb_assert!(ruby, "!dt.utc?", dt);
rb_assert!(ruby, "dt.utc_offset == 19800", dt);

Ok(())
}

0 comments on commit 02d93c9

Please sign in to comment.