Packages

Momento is an Elixir port of Moment.js for the purpose of parsing, validating, manipulating, and formatting dates.

Current section

Files

Jump to
momento lib date.ex
Raw

lib/date.ex

defmodule Momento.Date do
@spec date() :: DateTime.t
def date, do: DateTime.from_unix!(:erlang.system_time(:nano_seconds), :nanoseconds)
@spec date(DateTime.t) :: DateTime.t
def date(%DateTime{} = arg), do: arg
# TODO: Add timezone support
@spec date(String.t) :: DateTime.t
def date(arg) when is_bitstring(arg) do
cond do
# ISO8601 - "2016-04-20T15:05:13.991Z"
Regex.match?(~r/^[0-9]{4}-[0-9]{2}-[0-9]{2}[tT\s][0-9]{2}:[0-9]{2}:[0-9]{2}\.[0-9]{3}[zZ]$/, arg) ->
with [date, time] <- String.split(arg, "T"),
[year, month, day] <- String.split(date, "-"),
[hour, minute, seconds] <- String.split(time, ":"),
[second, milliseconds] <- String.split(seconds, "."),
[millisecond, _] <- String.split(milliseconds, "Z")
do
%DateTime{
year: String.to_integer(year),
month: String.to_integer(month),
day: String.to_integer(day),
hour: String.to_integer(hour),
minute: String.to_integer(minute),
second: String.to_integer(second),
microsecond: {String.to_integer(millisecond) * 1000, 6},
std_offset: 0,
utc_offset: 0,
time_zone: "Etc/UTC",
zone_abbr: "UTC"
}
end
# ISO date - "2016-04-20"
Regex.match?(~r/^[0-9]{4}-[0-9]{2}-[0-9]{2}$/, arg) ->
with [year, month, day] <- String.split(arg, "-")
do
%DateTime{
year: String.to_integer(year),
month: String.to_integer(month),
day: String.to_integer(day),
hour: 0,
minute: 0,
second: 0,
microsecond: {0, 6},
std_offset: 0,
utc_offset: 0,
time_zone: "Etc/UTC",
zone_abbr: "UTC"
}
end
true -> {:error, "Unknown date format."}
end
end
# Unix epoch
@spec date(integer) :: {:ok, DateTime.t}
def date(s) when is_integer(s) and s > 999999999999999999, do: DateTime.from_unix(s, :nanoseconds)
def date(s) when is_integer(s) and s > 999999999999999, do: DateTime.from_unix(s, :microseconds)
def date(s) when is_integer(s) and s > 999999999999, do: DateTime.from_unix(s, :milliseconds)
def date(s) when is_integer(s) and s > 999999999, do: DateTime.from_unix(s, :seconds)
@spec date(integer) :: DateTime.t
def date!(s), do: ({:ok, datetime} = date(s); datetime)
end