Summary
timeflow currently provides precise formatting (via strftime-style format strings) and exact elapsed durations. A common complementary need — especially in UIs, logs, notifications, and reports — is relative human-readable formatting: expressing a point in time in natural language relative to the current moment or another reference point.
Proposed API
humanize() — relative to now
datetime.humanize()? -> String
// Examples (relative to current system time):
// "just now" (< 30 seconds ago)
// "2 minutes ago"
// "an hour ago"
// "3 days ago"
// "last month"
// "2 years ago"
// "in 5 minutes" (future)
// "in 3 days"
// "in 2 months"
humanize_relative_to(&reference) — relative to a given point
datetime.humanize_relative_to(&other_datetime)? -> String
date.humanize_relative_to(&other_date)? -> String
This is useful for displaying times relative to a known event (e.g. "3 hours after the deployment", "1 week before the deadline") without being tied to the current wall clock.
age_in_years(&reference) — for birthdate arithmetic
let birthdate = Date::new(1990, 6, 15)?;
let today = Date::now()?;
let age = birthdate.age_in_years(&today)?; // e.g. 34
Threshold Table
Suggested rounding thresholds (inspired by moment.js and timeago.rs):
| Elapsed |
Output |
| < 30s |
"just now" / "in a moment" |
| 30s – 90s |
"a minute ago" / "in a minute" |
| 90s – 45min |
"X minutes ago" |
| 45min – 90min |
"an hour ago" / "in an hour" |
| 90min – 22h |
"X hours ago" |
| 22h – 36h |
"a day ago" / "tomorrow" / "yesterday" |
| 36h – 26 days |
"X days ago" |
| 26d – 46d |
"a month ago" / "next month" |
| 46d – 11 months |
"X months ago" |
| 11m – 18m |
"a year ago" / "next year" |
| > 18 months |
"X years ago" |
Implementation Notes
humanize() calls humanize_relative_to(&Self::now()?) internally.
- The method should be available on
Date, Time, and DateTime.
- For
Date::humanize(), time-of-day granularity is not available — the threshold table should stop at "days" for Date.
- For
Time::humanize(), only intra-day units (hours, minutes, seconds) are meaningful.
- All output strings should be in English for v1. Localisation is explicitly out of scope for this issue.
humanize does not need to be configurable in v1 — the threshold table above can be hardcoded. A HumanizeOptions builder could be added later.
- This feature has no new dependencies — it uses only
Self::now() and elapsed() which already exist in timeflow.
Acceptance Criteria
Summary
timeflowcurrently provides precise formatting (viastrftime-style format strings) and exact elapsed durations. A common complementary need — especially in UIs, logs, notifications, and reports — is relative human-readable formatting: expressing a point in time in natural language relative to the current moment or another reference point.Proposed API
humanize()— relative to nowhumanize_relative_to(&reference)— relative to a given pointThis is useful for displaying times relative to a known event (e.g. "3 hours after the deployment", "1 week before the deadline") without being tied to the current wall clock.
age_in_years(&reference)— for birthdate arithmeticThreshold Table
Suggested rounding thresholds (inspired by
moment.jsandtimeago.rs):Implementation Notes
humanize()callshumanize_relative_to(&Self::now()?)internally.Date,Time, andDateTime.Date::humanize(), time-of-day granularity is not available — the threshold table should stop at "days" forDate.Time::humanize(), only intra-day units (hours, minutes, seconds) are meaningful.humanizedoes not need to be configurable in v1 — the threshold table above can be hardcoded. AHumanizeOptionsbuilder could be added later.Self::now()andelapsed()which already exist intimeflow.Acceptance Criteria
humanize()implemented onDate,Time, andDateTimehumanize_relative_to(&reference)implemented on all three typesage_in_years(&reference)implemented onDateDate::humanize()does not produce sub-day outputTime::humanize()does not produce multi-day output