Obtener la fecha y hora actual en Elixir

83

Esta parece una pregunta realmente tonta, pero ¿cómo se obtiene y muestra la fecha u hora actual en Elixir? Intenté revisar los documentos pero no pude encontrar nada. ¿Necesito usar una función Erlang?

Graham Conzett
fuente

Respuestas:

56

Para responder a su pregunta de manera más específica (¡aunque realmente aprecio la recomendación de Onorio de usar Timex!), Puede obtener la fecha y hora actual de la lib estándar de Erlang usando :calendar.universal_time()o :calendar.local_time(). Hay una serie de funciones útiles para trabajar con el datetimetipo de Erlang en el calendarmódulo, pero son algo limitadas y no le proporcionan nada para analizar o formatear fechas, que es donde entra Timex.

bitwalker
fuente
1
Excelente respuesta, gracias a ambos y definitivamente revisaré Timex.
Graham Conzett
17

NaiveDateTime

Si no le importa la zona horaria y solo desea una fecha y hora puras, use NaiveDateTime:

NaiveDateTime.utc_now
# => ~N[2017-11-30 20:49:54.660724]

Fecha y hora

Si también desea los detalles de la zona horaria, utilice DateTime, que también devolverá cosas como el nombre de la zona horaria, el desplazamiento UTC, el desplazamiento STD y la abreviatura de la zona horaria:

DateTime.utc_now
# => %DateTime{calendar: Calendar.ISO, day: 30, hour: 20, microsecond: {667345, 6}, minute: 51, month: 11, second: 58, std_offset: 0, time_zone: "Etc/UTC", utc_offset: 0, year: 2017, zone_abbr: "UTC"}

Luego, también puede llamar to_date/1y to_time/1desde estos módulos para obtener los valores de fecha y hora específicos de las estructuras de fecha y hora.

Sheharyar
fuente
12

Creo que tu mejor opción es usar la biblioteca timex de Paul Schoenfelder (también conocida como BitWalker) para Elixir. La biblioteca está aquí: https://github.com/bitwalker/timex y puede obtener el paquete en hex.pm https://hex.pm/packages/timex . Paul brindó amablemente una buena explicación de cómo usar la biblioteca en la página Léame de ese repositorio de github.

Podría hacer llamadas a las bibliotecas nativas de Erlang, pero creo que la biblioteca de Paul es superior cuando se trata de Elixir.

Onorio Catenacci
fuente
5
¡Gracias por la recomendación Onorio! Para cualquiera que lea esto, estoy muy abierto a las contribuciones para que podamos hacer que Timex sea la biblioteca de referencia para la fecha / hora en Elixir, y tal vez algún día fusionarla con la biblioteca estándar de Elixir si debería estar a la par. Si está interesado en ayudar, envíeme un mensaje o sumérjase en el rastreador de problemas en GitHub y envíe algunas solicitudes de extracción.
bitwalker
1
@bitwalker Sí, Erlang / Elixir tiene muchas cosas que hacer para la fecha / hora lib. Y espero que Timex también se pueda fusionar con Elixir :)
Tony Han
11

Depende del formato en el que lo desee.

Puede usar cualquier función en la biblioteca estándar de Erlang de Elixir. Tradicionalmente, obtendría el tiempo con la now/0función:

iex(1)> :erlang.now
{1487, 549978, 29683}

Eso representa time_t1,487,549,978.29683, que son 19 minutos, 38.29683 segundos después de la medianoche UTC del lunes 20 de febrero de 2017.

Sin embargo, desde Erlang / OTP 18, esa función está obsoleta; una de las razones es que Erlang garantiza que el valor de retorno aumentará con cada llamada. Si lo llama en un bucle cerrado en una máquina lo suficientemente rápido como para llamarlo más de una vez por microsegundo, la marca de tiempo devuelta se adelantará al tiempo real.

El reemplazo es una API con más precisión y control . La interfaz principal de esta nueva API es la os:system_time/0función, que devuelve el tiempo de época en una unidad definida por el sistema:

iex(2)> :os.system_time
1487549978296838000

Sin system_time/1embargo, puede solicitar una unidad específica con :

iex(3)> :os.system_time(:millisecond)
1487549978296

Desde Elixir 1.2, esas funciones también han estado disponibles en el Systemmódulo nativo :

iex(4)> System.system_time(:second)
1487549978

Para una interfaz más amigable pero aún nativa de Elixir, use el calendarmódulo, que le dará tuplas:

iex(5)> :calendar.universal_time
{{2017, 2, 20}, {0, 19, 38}}

Desde la 1.3, Elixir también ha tenido su propio conjunto de módulos para manipular fechas y horas: Datey DateTime. Puede usar sus funciones para obtener la fecha u hora actual así:

iex(6)> Date.utc_today
~D[2017-02-20]
iex(7)> DateTime.utc_now
#DateTime<2017-02-20 00:19:38.29683Z>
Mark Reed
fuente
8

Para obtener la cantidad de milisegundos (marca de tiempo de Unix):

DateTime.utc_now() |> DateTime.to_unix(:millisecond)
Sam Houston
fuente
1
Buen Sam, justo lo que estaba buscando;)
Dennis
7

También puede usar :os.timestamp\0, que regresa {megaseconds, seconds, microseconds}de UTC. :os.timestamp |> :calendar.now_to_datetimele dará ahora en {{YYYY, MM, DD}, {HH, MM, SS}}formato estándar erlang .

G Amini
fuente
3
Y para poner eso en una marca de tiempo POSIX / UNIX: michal.muskala.eu/2015/07/30/unix-timestamps-in-elixir.html
Henrik N
6

Si necesita lidiar con el horario de verano o las zonas horarias, hice una biblioteca para eso: Calendario .

Para obtener la hora actual, usaría, por ejemplo, Calendar.DateTime.now("America/Los_Angeles")la hora actual en Los Ángeles o Calendar.DateTime.now_utcla hora actual en UTC.

Lau
fuente
2

Para obtener la marca de tiempo de Unix

DateTime.to_unix(DateTime.utc_now)
radzserg
fuente
0

Bueno, Timex al rescate generalmente, sin embargo, algunos de los siguientes trucos pueden ser de ayuda:

{erl_date, erl_time} = :calendar.local_time()
# {{2020, 11, 19}, {0, 6, 36}}

{:ok, time} = Time.from_erl(erl_time)
# {:ok, ~T[00:06:36]}

{:ok, date} = Date.from_erl(erl_date)
# {:ok, ~D[2020-11-19]}

Calendar.strftime(time, "%c", preferred_datetime: "%H:%M:%S")
# "00:06:36"


Calendar.strftime(date, "%c", preferred_datetime: "%m-%d-%Y")
# "11-19-2020"
Mikhail Chuprynski
fuente