How to calculate a duration between two dates in luxon?
Asked Answered
R

3

51

Luxon's documentation for the Duration.fromISO method describes it as

Create a Duration from an ISO 8601 duration string

Nowhere is mentioned the ability to create a duration based on two dates. My typical use case would be: "did the event between date ISODAT1 and ISODATE2 last more than an hour?".

What I will do is to transform the dates into a timestamp and check whether the difference is greater than 3600 (seconds), I believe however that there is a more native way to make the check.

Retirement answered 6/9, 2020 at 10:40 Comment(0)
D
84

You could use DateTime's .diff (doc)

Return the difference between two DateTimes as a Duration.

const date1 = luxon.DateTime.fromISO("2020-09-06T12:00")
const date2 = luxon.DateTime.fromISO("2019-06-10T14:00")

const diff = date1.diff(date2, ["years", "months", "days", "hours"])

console.log(diff.toObject())
<script src="https://cdn.jsdelivr.net/npm/[email protected]/build/global/luxon.min.js"></script>
Denotative answered 6/9, 2020 at 11:4 Comment(3)
Documentation linked in this answer seems to have moved to moment.github.io/luxon/#/math?id=diffsPolyphemus
@AnibeAgamah thank you, I've just updated the linkDenotative
This is the doc link of the API, also useful: moment.github.io/luxon/api-docs/index.html#datetimediffEddi
M
20

Example

const date1 = luxon.DateTime.fromISO("2020-09-06T12:00");
const date2 = luxon.DateTime.fromISO("2019-06-10T14:00");
const diff = Interval.fromDateTimes(later, now);
const diffHours = diff.length('hours');

if (diffHours > 1) {
  // ...
}

Documentation for Luxon v2.x

In the Luxon documentation they mention durations and intervals. It seems that you would be best off using Intervals and then calling the .length('hours') on the Interval if you're interested to know if something has been over an hour.

Durations

The Duration class represents a quantity of time such as "2 hours and 7 minutes".

const dur = Duration.fromObject({ hours: 2, minutes: 7 });

dur.hours;   //=> 2
dur.minutes; //=> 7
dur.seconds; //=> 0

dur.as('seconds'); //=> 7620
dur.toObject();    //=> { hours: 2, minutes: 7 }
dur.toISO();       //=> 'PT2H7M'

Intervals

Intervals are a specific period of time, such as "between now and midnight". They're really a wrapper for two DateTimes that form its endpoints.

const now = DateTime.now();
const later = DateTime.local(2020, 10, 12);
const i = Interval.fromDateTimes(now, later);

i.length()                             //=> 97098768468
i.length('years')                      //=> 3.0762420239726027
i.contains(DateTime.local(2019))       //=> true

i.toISO()       //=> '2017-09-14T04:07:11.532-04:00/2020-10-12T00:00:00.000-04:00'
i.toString()    //=> '[2017-09-14T04:07:11.532-04:00 – 2020-10-12T00:00:00.000-04:00)
Machute answered 30/8, 2021 at 18:58 Comment(4)
The irony is that on the project that got me looking into this my teammate ended up recommending we go with something like: DateTime.now().diff(DateTime.fromISO(date))Machute
In this example, what if I wanted only - if 2 hours or less? .ie. "Difference cannot be more than 2 hours"Abadan
@NikhilNanjappa I would imagine you could subtract the two dates and instantiate a duration from it, thus grabbing the hours and checking it out. Otherwise given the example above you could take two dates, and use the Interval.fromDateTimes(date1, date2).length('hours') I believe.Machute
Thanks @Machute - I did this instead which works as expected. if (durToObject.hours >= 2 && durToObject.minutes >= 1) { **Error** }Abadan
A
1

We can also convert to duration and find what OP asked did the event between date ISODAT1 and ISODATE2 last more than an hour?

// Get the hour duration between two dates
const hoursBetween = Interval.fromDateTimes(date1, date2).toDuration('hours').hours;

// Or simply check it
if(Interval.fromDateTimes(date1, date2).toDuration('hours').hours > 1) {
  // yes, it did last more than an hour
}

Luxon Doc: Luxon intervaltoduration

Avery answered 4/3 at 20:30 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.