PanagiotisGeorgiadis/elm-datetime/1.2.0

NOTE: the latest version is 1.3.0

DateTime

The DateTime module was introduced in order to keep track of both the Date and Time. The DateTime consists of a Day, Month, Year, Hours, Minutes, Seconds and Milliseconds. You can construct a DateTime either by using a Posix or by using an existing Date and Time combination. Otherwise you can attempt to construct a DateTime by using a combination of a RawDate and a RawClock.

type alias DateTime =
DateTime

An instant in time, composed of a Date and a Time.

Creating a DateTime

fromPosix : Posix -> DateTime

Create a DateTime from a Posix time.

fromPosix (Time.millisToPosix 0)
-- DateTime { date = Date { day = Day 1, month = Jan, year = Year 1970 }, time = Time { hours = Hour 0, minutes = Minute 0, seconds = Second 0, milliseconds = Millisecond 0 } } : DateTime


fromPosix (Time.millisToPosix 1566795954000)
-- DateTime { date = Date { day = Day 26, month = Aug, year = Year 2019 }, time = Time { hours = Hour 5, minutes = Minute 5, seconds = Second 54, milliseconds = Millisecond 0 } } : DateTime
fromRawParts : RawDate -> RawTime -> Maybe DateTime

Attempts to construct a new DateTime object from its raw constituent parts. Returns Nothing if any parts or their combination would result in an invalid DateTime.

fromRawParts { day = 26, month = Aug, year = 2019 } { hours = 12, minutes = 30, seconds = 45, milliseconds = 0 }
-- Just (DateTime { date = Date { day = Day 26, month = Aug, year = Year 2019 }, time = Time { hours = Hour 12, minutes = Minute 30, seconds = Second 45, milliseconds = Millisecond 0 }}) : Maybe DateTime


fromRawParts { day = 29, month = Feb, year = 2019 } { hours = 16, minutes = 30, seconds = 45, milliseconds = 0 }
-- Nothing : Maybe DateTime


fromRawParts { day = 15, month = Nov, year = 2019 } { hours = 24, minutes = 20, seconds = 40, milliseconds = 0 }
-- Nothing : Maybe DateTime
fromDateAndTime : Date -> Time -> DateTime

Create a DateTime by combining a Date and Time.

-- date == 26 Aug 2019
-- time == 12:30:45.000


fromDateAndTime date time
-- DateTime { date = Date { day = Day 26, month = Aug, year = Year 2019 }, time = Time { hours = Hour 12, minutes = Minute 30, seconds = Second 45, milliseconds = Millisecond 0 } } : DateTime

Conversions

toPosix : DateTime -> Posix

Converts a DateTime to a posix time. The result is relative to the Epoch. This basically means that if the DateTime provided is after the Epoch the result will be a positive posix time. Otherwise the result will be a negative posix time.

-- dateTime  == 25 Dec 2019 19:23:45.000
toPosix dateTime -- Posix 1577301825000 : Posix


-- dateTime2 == 1 Jan 1970 00:00:00.000 : Posix
toPosix dateTime2 -- Posix 0


-- dateTime3 == 8 Jan 1920 04:36:15.000
toPosix dateTime3 -- Posix -1577301825000 : Posix
toMillis : DateTime -> Int

Convers a DateTime to the equivalent milliseconds. The result is relative to the Epoch. This basically means that if the DateTime provided is after the Epoch the result will be a positive number representing the milliseconds that have elapsed since the Epoch. Otherwise the result will be a negative number representing the milliseconds required in order to reach the Epoch.

-- dateTime  == 25 Dec 2019 19:23:45.000
toMillis dateTime -- 1577301825000 : Int


-- dateTime2 == 1 Jan 1970 00:00:00.000
toMillis dateTime2 -- 0 : Int


-- dateTime3 == 8 Jan 1920 04:36:15.000
toMillis dateTime3 -- -1577301825000 : Int

Accessors

getDate : DateTime -> Date

Extract the Date from a DateTime.

-- dateTime == 25 Dec 2019 16:45:30.000
getDate dateTime -- 25 Dec 2019 : Calendar.Date
getTime : DateTime -> Time

Extract the Time from a DateTime.

-- dateTime == 25 Dec 2019 16:45:30.000
getTime dateTime -- 16:45:30.000 : Clock.Time
getYear : DateTime -> Int

Extract the Year part of a DateTime as an Int.

-- dateTime == 25 Dec 2019 16:45:30.000
getYear dateTime -- 2019 : Int
getMonth : DateTime -> Month

Extract the Month part of a DateTime as a Month.

-- dateTime == 25 Dec 2019 16:45:30.000
getMonth dateTime -- Dec : Time.Month
getDay : DateTime -> Int

Extract the Day part of DateTime as an Int.

-- dateTime == 25 Dec 2019 16:45:30.000
getDay dateTime -- 25 : Int
getHours : DateTime -> Int

Extract the Hour part of DateTime as an Int.

-- dateTime == 25 Dec 2019 16:45:30.000
getHours dateTime -- 16 : Int
getMinutes : DateTime -> Int

Extract the Minute part of DateTime as an Int.

-- dateTime == 25 Dec 2019 16:45:30.000
getMinutes dateTime -- 45 : Int
getSeconds : DateTime -> Int

Extract the Second part of DateTime as an Int.

-- dateTime == 25 Dec 2019 16:45:30.000
getSeconds dateTime -- 30 : Int
getMilliseconds : DateTime -> Int

Extract the Millisecond part of DateTime as an Int.

-- dateTime == 25 Dec 2019 16:45:30.000
getMilliseconds dateTime -- 0 : Int

Setters

setDate : Date -> DateTime -> DateTime

Sets the Date part of a [DateTime#DateTime].

-- date == 26 Aug 2019
-- dateTime == 25 Dec 2019 16:45:30.000
setDate date dateTime -- 26 Aug 2019 16:45:30.000
setTime : Time -> DateTime -> DateTime

Sets the Time part of a [DateTime#DateTime].

-- dateTime == 25 Dec 2019 16:45:30.000
setTime Clock.midnight dateTime -- 25 Dec 2019 00:00:00.000
setYear : Int -> DateTime -> Maybe DateTime

Attempts to set the Year part of a Calendar.Date in a DateTime.

-- dateTime == 29 Feb 2020 15:30:30.000
setYear 2024 dateTime -- Just (29 Feb 2024 15:30:30.000) : Maybe DateTime


setYear 2019 dateTime -- Nothing : Maybe DateTime
setMonth : Month -> DateTime -> Maybe DateTime

Attempts to set the Month part of a Calendar.Date in a DateTime.

-- dateTime == 31 Jan 2019 15:30:30.000
setMonth Aug dateTime -- Just (31 Aug 2019 15:30:30.000) : Maybe DateTime


setMonth Apr dateTime -- Nothing : Maybe DateTime
setDay : Int -> DateTime -> Maybe DateTime

Attempts to set the Day part of a Calendar.Date in a DateTime.

-- dateTime == 31 Jan 2019 15:30:30.000
setDay 25 dateTime -- Just (25 Jan 2019 15:30:30.000) : Maybe DateTime


setDay 32 dateTime -- Nothing : Maybe DateTime
setHours : Int -> DateTime -> Maybe DateTime

Attempts to set the Hours part of a Clock.Time in a DateTime.

-- dateTime == 2 Jul 2019 12:00:00.000
setHours 23 dateTime -- Just (2 Jul 2019 23:00:00.000) : Maybe DateTime


setHours 24 dateTime -- Nothing : Maybe DateTime
setMinutes : Int -> DateTime -> Maybe DateTime

Attempts to set the Minutes part of a Clock.Time in a DateTime.

-- dateTime == 2 Jul 2019 12:00:00.000
setMinutes 36 dateTime -- Just (2 Jul 2019 12:36:00.000) : Maybe DateTime


setMinutes 60 dateTime -- Nothing : Maybe DateTime
setSeconds : Int -> DateTime -> Maybe DateTime

Attempts to set the Seconds part of a Clock.Time in a DateTime.

-- dateTime == 2 Jul 2019 12:00:00.000
setSeconds 20 dateTime -- Just (2 Jul 2019 12:00:20.000) : Maybe DateTime


setSeconds 60 dateTime -- Nothing : Maybe DateTime
setMilliseconds : Int -> DateTime -> Maybe DateTime

Attempts to set the Milliseconds part of a Clock.Time in a DateTime.

-- dateTime == 2 Jul 2019 12:00:00.000
setMilliseconds 589 dateTime -- Just (2 Jul 2019 12:00:00.589) : Maybe DateTime


setMilliseconds 1000 dateTime -- Nothing : Maybe DateTime

Increment values

incrementYear : DateTime -> DateTime

Increments the Year in a given DateTime while preserving the Month, and Day parts. The Time related parts will remain the same.

-- dateTime  == 31 Jan 2019 15:30:45.100
incrementYear dateTime -- 31 Jan 2020 15:30:45.100 : DateTime


-- dateTime2 == 29 Feb 2020 15:30:45.100
incrementYear dateTime2 -- 28 Feb 2021 15:30:45.100 : DateTime

Note: In the first example, incrementing the Year causes no changes in the Month and Day parts. On the second example we see that the Day part is different than the input. This is because the resulting date in the DateTime would be an invalid date ( 29th of February 2021 ). As a result of this scenario we fall back to the last valid day of the given Month and Year combination.

incrementMonth : DateTime -> DateTime

Increments the Month in a given DateTime. It will also roll over to the next year where applicable. The Time related parts will remain the same.

-- dateTime  == 15 Sep 2019 15:30:45.100
incrementMonth dateTime -- 15 Oct 2019 15:30:45.100 : DateTime


-- dateTime2 == 15 Dec 2019 15:30:45.100
incrementMonth dateTime2 -- 15 Jan 2020 15:30:45.100 : DateTime


-- dateTime3 == 30 Jan 2019 15:30:45.100
incrementMonth dateTime3 -- 28 Feb 2019 15:30:45.100 : DateTime

Note: In the first example, incrementing the Month causes no changes in the Year and Day parts while on the second example it rolls forward the 'Year'. On the last example we see that the Day part is different than the input. This is because the resulting date would be an invalid one ( 31st of February 2019 ). As a result of this scenario we fall back to the last valid day of the given Month and Year combination.

incrementDay : DateTime -> DateTime

Increments the Day in a given DateTime. Will also increment Month and Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
incrementDay dateTime -- 26 Aug 2019 15:30:45.100 : DateTime


-- dateTime2 == 31 Dec 2019 15:30:45.100
incrementDay dateTime2 -- 1 Jan 2020 15:30:45.100 : DateTime
incrementHours : DateTime -> DateTime

Increments the Hours in a given DateTime. Will also increment Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
incrementHours dateTime -- 25 Aug 2019 16:30:45.100 : DateTime


-- dateTime2 == 31 Dec 2019 23:00:00.000
incrementHours dateTime2 -- 1 Jan 2020 00:00:00.000 : DateTime
incrementMinutes : DateTime -> DateTime

Increments the Minutes in a given DateTime. Will also increment Hours, Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
incrementMinutes dateTime -- 25 Aug 2019 15:31:45.100 : DateTime


-- dateTime2 == 31 Dec 2019 23:59:00.000
incrementMinutes dateTime2 -- 1 Jan 2020 00:00:00.000 : DateTime
incrementSeconds : DateTime -> DateTime

Increments the Seconds in a given DateTime. Will also increment Minutes, Hours, Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
incrementSeconds dateTime -- 25 Aug 2019 15:30:46.100 : DateTime


-- dateTime2 == 31 Dec 2019 23:59:59.000
incrementSeconds dateTime2 -- 1 Jan 2020 00:00:00.000 : DateTime
incrementMilliseconds : DateTime -> DateTime

Increments the Milliseconds in a given DateTime. Will also increment Seconds, Minutes, Hours, Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
incrementMilliseconds dateTime -- 25 Aug 2019 15:30:45:101 : DateTime


-- dateTime2 == 31 Dec 2019 23:59:59.999
incrementMilliseconds dateTime2 -- 1 Jan 2020 00:00:00.000 : DateTime

Decrement values

decrementYear : DateTime -> DateTime

Decrements the Year in a given DateTime while preserving the Month and Day. The Time related parts will remain the same.

-- dateTime  == 31 Jan 2019 15:30:45.100
decrementYear dateTime -- 31 Jan 2018 15:30:45.100 : DateTime


-- dateTime2 == 29 Feb 2020 15:30:45.100
decrementYear dateTime2 -- 28 Feb 2019 15:30:45.100 : DateTime

Note: In the first example, decrementing the Year causes no changes in the Month and Day parts. On the second example we see that the Day part is different than the input. This is because the resulting date in the DateTime would be an invalid date ( 29th of February 2019 ). As a result of this scenario we fall back to the last valid day of the given Month and Year combination.

decrementMonth : DateTime -> DateTime

Decrements the Month in a given DateTime. It will also roll backwards to the previous year where applicable. The Time related parts will remain the same.

-- dateTime  == 15 Sep 2019 15:30:45.100
decrementMonth dateTime -- 15 Aug 2019 15:30:45.100 : DateTime


-- dateTime2 == 15 Jan 2020 15:30:45.100
decrementMonth dateTime2 -- 15 Dec 2019 15:30:45.100 : DateTime


-- dateTime3 == 31 Dec 2019 15:30:45.100
decrementMonth dateTime3 -- 30 Nov 2019 15:30:45.100 : DateTime

Note: In the first example, decrementing the Month causes no changes in the Year and Day parts while on the second example it rolls backwards the Year. On the last example we see that the Day part is different than the input. This is because the resulting date would be an invalid one ( 31st of November 2019 ). As a result of this scenario we fall back to the last valid day of the given Month and Year combination.

decrementDay : DateTime -> DateTime

Decrements the Day in a given DateTime. Will also decrement Month and Year where applicable.

-- dateTime  == 27 Aug 2019 15:30:45.100
decrementDay dateTime -- 26 Aug 2019 15:30:45.100 : DateTime


-- dateTime2 == 1 Jan 2020 15:30:45.100
decrementDay dateTime2 -- 31 Dec 2019 15:30:45.100 : DateTime
decrementHours : DateTime -> DateTime

Decrements the Hours in a given DateTime. Will also decrement Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
decrementHours dateTime -- 25 Aug 2019 14:30:45.100 : DateTime


-- dateTime2 == 1 Jan 2020 00:00:00.000
decrementHours dateTime2 -- 31 Dec 2019 23:00:00.000 : DateTime
decrementMinutes : DateTime -> DateTime

Decrements the Minutes in a given DateTime. Will also decrement Hours, Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
decrementMinutes dateTime -- 25 Aug 2019 15:29:45.100 : DateTime


-- dateTime2 == 1 Jan 2020 00:00:00.000
decrementMinutes dateTime2 -- 31 Dec 2019 23:59:00.000 : DateTime
decrementSeconds : DateTime -> DateTime

Decrements the Seconds in a given DateTime. Will also decrement Minutes, Hours, Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
decrementSeconds dateTime -- 25 Aug 2019 15:30:44.100 : DateTime


-- dateTime2 == 1 Jan 2020 00:00:00.000
decrementSeconds dateTime2 -- 31 Dec 2019 23:59:59.000 : DateTime
decrementMilliseconds : DateTime -> DateTime

Decrements the Milliseconds in a given DateTime. Will also decrement Seconds, Minutes, Hours, Day, Month, Year where applicable.

-- dateTime  == 25 Aug 2019 15:30:45.100
decrementMilliseconds dateTime -- 25 Aug 2019 15:30:45.099 : DateTime


-- dateTime2 == 1 Jan 2020 00:00:00.000
decrementMilliseconds dateTime2 -- 31 Dec 2019 23:59:59.999 : DateTime

Compare values

compare : DateTime -> DateTime -> Order

Compares the two given DateTimes and returns an Order.

-- past   == 25 Aug 2019 12:15:45.250
-- future == 26 Aug 2019 12:15:45.250
compare past past -- EQ : Order


compare past future -- LT : Order


compare future past -- GT : Order
compareDates : DateTime -> DateTime -> Order

Compares the Date part of two given DateTime and returns an Order.

-- dateTime  == 25 Aug 2019 12:15:45.250
-- dateTime2 == 25 Aug 2019 21:00:00.000
-- dateTime3 == 26 Aug 2019 12:15:45.250
compare dateTime dateTime2 -- EQ : Order


compare dateTime dateTime3 -- LT : Order


compare dateTime3 dateTime2 -- GT : Order
compareTime : DateTime -> DateTime -> Order

Compares the Time part of two given DateTime and returns an Order.

-- dateTime  == 25 Aug 2019 12:15:45.250
-- dateTime2 == 25 Aug 2019 21:00:00.000
-- dateTime3 == 26 Aug 2019 12:15:45.250
compare dateTime dateTime3 -- EQ : Order


compare dateTime dateTime2 -- LT : Order


compare dateTime2 dateTime3 -- GT : Order

Utilities

getTimezoneOffset : Zone -> Posix -> Int

Returns the Timezone Offset in Milliseconds. This function can be used in order to form a DateTime that actually matches each users local DateTime.

dateTime =
    DateTime.fromPosix posix


offset =
    DateTime.getTimezoneOffset zone posix


zonedDateTime =
    DateTime.fromPosix (posix + offset)


-- zone == GMT+1100
-- posix == 1554660000000 -- 2019-04-07 18:00:00 UTC
-- dateTime == 2019-04-07 18:00:00 UTC
-- zonedDateTime == 2019-04-08 05:00:00 GMT+1100

The above example shows the difference between getting a DateTime in UTC and in GMT+1100.

Note: Timezones ( and local times ) should only be used for date representation purposes and never for storing or modeling. If you use getTimezoneOffset for constructing a local today DateTime, remember to convert it back to UTC when storing it in a database.

getDateRange : DateTime -> DateTime -> Time -> List DateTime

Returns an incrementally sorted DateTime list based on the start and end DateTime parameters. The Time parts of the resulting list will be equal to the Time argument that was provided. The resulting list will include both start and end dates.

-- start       == 26 Feb 2020 12:30:45.000
-- end         == 1  Mar 2020 16:30:45.000
-- defaultTime == 21:00:00.000


getDateRange start end defaultTime
-- [ 26 Feb 2020 21:00:00.000, 27 Feb 2020 21:00:00.000, 28 Feb 2020 21:00:00.000, 29 Feb 2020 21:00:00.000, 1 Mar 2020 21:00:00.000 ] : List DateTime
getDatesInMonth : DateTime -> List DateTime

Returns a list of DateTimes for the given Year and Month combination. The Time parts of the resulting list will be equal to the Time portion of the DateTime that was provided.

-- dateTime == 26 Aug 2019 21:00:00.000


getDatesInMonth dateTime
--   [ 1  Aug 2019  21:00:00.000
--   , 2  Aug 2019  21:00:00.000
--   , 3  Aug 2019  21:00:00.000
--   ...
--   , 29 Aug 2019 21:00:00.000
--   , 30 Aug 2019 21:00:00.000
--   , 31 Aug 2019 21:00:00.000
--   ] : List DateTime
getDayDiff : DateTime -> DateTime -> Int

Returns the difference in days between two DateTimes. We can have a negative difference of days as can be seen in the examples below.

-- dateTime  == 24 Aug 2019 12:00:00.000
-- dateTime2 == 24 Aug 2019 21:00:00.000
-- dateTime3 == 26 Aug 2019 15:45:00.000
getDayDiff dateTime dateTime2 -- 0 : Int


getDayDiff dateTime dateTime3 -- 2  : Int


getDayDiff dateTime3 dateTime -- -2 : Int
getWeekday : DateTime -> Weekday

Returns the weekday of a specific DateTime.

-- dateTime == 26 Aug 2019 12:30:45.000
getWeekday dateTime -- Mon : Weekday
isLeapYear : DateTime -> Bool

Checks if the Year part of the given DateTime is a leap year.

-- dateTime  == 25 Dec 2019 21:00:00.000
isLeapYear dateTime -- False


-- dateTime2 == 25 Dec 2020 12:00:00.000
isLeapYear dateTime2 -- True
sort : List DateTime -> List DateTime

Sorts incrementally a list of DateTime.

-- dateTime  == 26 Aug 1920 12:30:45.000
-- dateTime2 == 26 Aug 1920 21:00:00.000
-- dateTime3 == 1  Jan 1970 00:00:00.000
-- dateTime4 == 1  Jan 1970 14:40:20.120
-- dateTime5 == 25 Dec 2020 14:40:20.120
-- dateTime6 == 25 Dec 2020 14:40:20.150


sort [ dateTime4, dateTime2, dateTime6, dateTime5, dateTime, dateTime3 ]
-- [ 26 Aug 1920 12:30:45.000
-- , 26 Aug 1920 21:00:00.000
-- , 1  Jan 1970 00:00:00.000
-- , 1  Jan 1970 14:40:20.120
-- , 25 Dec 2020 14:40:20.120
-- , 25 Dec 2020 14:40:20.120
-- ] : List DateTime