2008-08-15 15 views

Respuesta

36

Tienes que almacenar en UTC; si no lo haces, tu informe histórico y tu comportamiento durante cosas como Horario de verano se ... gracioso. GMT es una hora local, sujeta a Horario de verano relativo a UTC (que no es).

La presentación a usuarios en diferentes zonas horarias puede ser un verdadero bastardo si está almacenando la hora local. Es fácil ajustarse a lo local si sus datos brutos están en UTC: simplemente agregue el desplazamiento de su usuario y ¡listo!

Joel habló sobre esto en uno de los podcasts (de forma aproximada) - dijo a store your data in the highest resolution possible (busque 'fidelidad'), porque siempre puede enviarlo cuando se apaga nuevamente. Es por eso que digo almacenarlo como UTC, como la hora local que necesita ajustar para cualquiera que no esté en esa zona horaria, y eso es mucho trabajo duro. Y necesita almacenar si, por ejemplo, los ahorros de luz diurna entraron en vigencia cuando almacenó el tiempo. Yuk.

A menudo en las bases de datos en el pasado he almacenado dos: UTC para ordenar, hora local para mostrar. De esta forma, ni el usuario ni la computadora se confunden.

Ahora, en cuanto a la pantalla: Claro, puede hacer lo de "hace 3 minutos", pero solo si almacena UTC; de lo contrario, los datos ingresados ​​en diferentes zonas horarias harán cosas como mostrar como "-4 horas atrás ", que asustará a la gente. Si va a mostrar una hora real, a las personas les encanta tenerla en su hora local, y si los datos se ingresan en varias zonas horarias, solo puede hacerlo con facilidad si está almacenando UTC.

+0

Pero, supongamos que tiene un sistema de reservas, y reserva una habitación en una zona horaria con horario de verano a las 3 p.m. Cuando ocurre DST, el desplazamiento entre GMT y la zona horaria de la sala de reuniones cambia en una hora. De repente, la reunión se reserva en otro momento. –

+0

No importa, no me había dado cuenta de que convertiría la hora en el desplazamiento DST del momento en que se produjo la reunión, por lo que siempre estaría en el desplazamiento correcto. –

+0

No, GMT no tiene horario de verano. Si estamos siendo pedantes, tampoco UTC es una zona horaria. GMT se basa en el tiempo solar medio en Greenwich. UTC se basa en el Tiempo Atómico (TAI) ajustado por un número entero de segundos (piense en segundos intercalares) para permanecer cerca de la fase solar de la Tierra, aunque pueden diferir en hasta 0.9 segundos. Tendría que seguir reuniéndose durante bastantes años para que el tiempo de rotación de la Tierra cambie de manera apreciable, pero es por eso que la complejidad existe aquí. – mc0e

1

Personalmente, no veo ninguna razón para no almacenar todo en GMT y luego uso la zona horaria local de los usuarios para mostrar la hora en lo que se refiere a ellos.

Si desea mostrar la hora relativa, obviamente todavía necesita tiempo y hacer una traducción, pero si desea hacer la traducción, creo que GMT sigue siendo su mejor opción.

+0

el problema es, ¿a qué hora utilizan los procesos automatizados al comunicar, por ejemplo, las fechas límite a las personas? ¿almacena la zona horaria de los usuarios tal como la decidieron y la utilizan en todas las comunicaciones? – DevelopingChris

0

Me gusta almacenar en GMT y mostrar solo datos relativos ("hace unos 10 segundos", "5 meses atrás"). Los usuarios no necesitan ver marcas de tiempo reales para la mayoría de los casos de uso.

Sin duda hay excepciones, y una aplicación individual puede tener muchas de ellas, por lo que no puede ser una respuesta "única". Las cosas que necesitan una sólida capacidad de auditoría (por ejemplo, la votación) y los sistemas en los que el tiempo forma parte del dominio del discurso (astronomía, investigación científica) pueden exigir que se muestren marcas de tiempo verdaderas al usuario.

La mayoría de las aplicaciones, sin embargo, son más fáciles de entender con un tiempo relativamente simple.

1

Así que ejecuté un pequeño experimento con el servidor MSSQL.

Creé una tabla y agregué una fila con la zona horaria localizada actual (Australia). Luego cambié mi fecha y hora para ser GMT y agregué otra fila.

Incluso aunque esas filas se agregaron con una separación de alrededor de 10 segundos, aparecen en el servidor SQL como si estuvieran separadas por 10 horas.

Si nada más, al menos me dice que debería estar almacenando las fechas de manera concomitante, lo que para mí, agrega peso al argumento para almacenarlas como GMT.

+0

almacenarlos con un desplazamiento incrustado, también podría significar, 2 columnas, tiempo gmt y personas elegidas compensación, no la forma automatizada sqlserver o la máquina cliente. – DevelopingChris

1

MS Dynamics almacena GMT y luego a un nivel de usuario conoce su zona de tiempo relativa a GMT. Luego muestra elementos en su zona horaria.

Solo pensé en tirar eso porque ese es un grupo bastante grande en MS y así es como decidieron manejarlo.

0

Suelo usar el tiempo de Unix. no necesariamente seguro en el futuro, pero funciona bastante bien.

0

Siempre almacenar en GMT (o UTC). Desde allí, es fácil convertirlo a cualquier valor de zona horaria local.

5

Josh está completamente correcto arriba, pero tengo una advertencia sutil para explicar. Este es un caso sin una respuesta correcta sobre eventos futuros y zonas horarias.

Considere el caso de una cita recurrente. Ocurre en GMT 0000 (por simplicidad), que es 1200 NZST (hora estándar de Nueva Zelanda) y 1000 AEST en Sydney Australia.

Cuando el horario de verano entra en vigencia en una zona, ¿qué debería ocurrirle a la cita? En caso de que:

1a. Si el cambio de TZ está en la zona de el "propietario" de la cita (¿quién lo reservó) luego intenta permanecer en la misma hora del reloj de escritorio (por ejemplo, 10:00 am)?
1b. Si el cambio TZ se encuentra en una de las zonas del otro de los asistentes reunión entonces no hay cambio

Consecuencias: Se mueve para todos los demás, de forma inesperada, debido a los propietarios de cambio TZ, pero se mantiene "la reunión de 10 a.m. "en lo que respecta al propietario .

'2. Como arriba, pero invertido.

Consecuencias: Se mueve para el propietario de la reunión (la reunión de las 10am se convierte en la reunión de las 9am, o v/v), lo que puede esperarse pero es inconveniente. Permanece en el mismo tiempo de reloj de escritorio para los demás asistentes hasta que pasan por su propia transición TZ.

Ninguno es perfecto. Considere el caso de dos citas, una reservada por la persona A que ocurre a las 10 a.m. hora local, la otra reservada por la persona B con la persona A como asistente que ocurre a las 9 a. M. Si la persona A y la persona B se encuentran en diferentes TZ, un cambio en el horario de verano podría hacer que se dupliquen.

Si su mente está un poco inclinada en este punto, entonces lo entiendo muy bien.

El punto detrás de este ejemplo es que para realizar correctamente alguno de estos comportamientos, no solo debe conocer la versión UTC de la hora local, sino la TZ (y no el desplazamiento) en que se encontraba el propietario cuando lo reservaron . De lo contrario, no tiene más remedio que tomar la opción 2, en silencio, sin siquiera informar a nadie que las cosas han cambiado ya que las horas GMT no cambian y solo cambia la presentación ... ¿verdad? (no, esta es la trampa, la presentación importa cuando su reunión de las 10am se mueve sola)

Tengo que darle crédito a mi colega y amigo Jason Pollock por esta idea.Lea his view here, y el seguimiento que trata iCal and VTIMEZONE aquí.

+0

Outlook Mobile se confunde exactamente con este error de comportamiento. Las citas telefónicas cambian cuando cambio la zona activa. – devstuff

+0

@devstuff - Las citas que cambian cuando selecciona una zona horaria diferente no es lo que se describe. Lo que se describe es que la zona horaria en sí misma ha cambiado (debido a los cambios legislados en el horario de verano) y, por lo tanto, ya no existe la zona horaria en la que originalmente se describieron los datos. es decir, los tiempos han cambiado en la misma zona horaria. – Mark

12

La respuesta, como siempre, es "depende".

Depende de lo que está describiendo con el tiempo y cómo se le proporcionaron los datos. La clave para decidir cómo almacenar valores de tiempo es decidir si está perdiendo información al descartar la zona horaria, así como tampoco sorprender a sus usuarios.

Definir los datos en tiempo UTC_t es una ventaja definitiva: es una sola int, lo que permite una clasificación rápida y un almacenamiento sencillo.

que ver el problema como la subdivisión en áreas específicas:

  1. datos históricos
  2. futuro, los datos a corto plazo
  3. futuro, datos a largo plazo

Con las siguientes subclases en cada uno:

  1. Sys Siempre tem
  2. usuario proporcionada

Veamos uno a la vez.

Sistema proporcionado: Recomendaría ejecutar sistemas en UTC, luego evita el problema de la zona horaria y, una vez más, no se ve pérdida de información (siempre es UTC).

datos históricos: Estas son cosas como los archivos de registro del sistema, estadísticas de procesos, seguimiento, fechas/horas de comentarios, etc. Los datos no va a cambiar, y el descriptor de zona horaria no va a cambiar de manera retroactiva. Para este tipo de datos, no se pierde información al almacenar la información en UTC independientemente de la zona horaria en la que se haya proporcionado. Por lo tanto, descarte la zona horaria.

Futuro, datos a largo plazo: Estos son eventos que están lo suficientemente lejos en el futuro o seguirán sucediendo. Si se mantienen el tiempo suficiente, las descripciones de la zona horaria están garantizadas. Un buen ejemplo de este tipo de datos es "La reunión de gestión semanal". Se trata de datos que se ingresan una vez y se espera que continúen funcionando a perpetuidad. Para estos valores, es importante determinar si se trata de un sistema o un usuario. Para los datos proporcionados por el usuario, el tiempo debe almacenarse con la zona horaria del creador, cualquier otra cosa da como resultado la pérdida de información. ¡Esta pérdida de información se hace evidente cuando la definición de la zona horaria cambia y se muestra la hora al creador que tiene un valor completamente diferente!

Como ha indicado Bwooce, existe cierta confusión cuando el creador y el espectador se encuentran en diferentes zonas horarias. En ese caso, esperaría que la aplicación indique qué valores de tiempo se han movido debido a un cambio de zona horaria desde sus ubicaciones anteriores.

Futuro, Datos a Corto Plazo: Estos son datos que rápidamente se volverán históricos, o solo válidos por un corto período de tiempo. Los ejemplos pueden ser temporizadores de intervalos, transiciones de clasificación, etc. Para estos datos, dado que la probabilidad de que la definición cambie entre la creación del valor y el tiempo que pasa a ser histórica, es posible salirse con la caída de la zona horaria.Sin embargo, descubrí que estos valores tienen la mala costumbre de convertirse en "datos futuros a largo plazo".

Una vez que haya decidido almacenar la zona horaria, se debe tener cuidado con la forma en que se almacena.

  • No almacene la zona horaria como un desplazamiento, o el descriptor completo.

Si almacena una zona horaria como un desplazamiento, ¿qué hace si la zona horaria cambia? ¿Pasas por el sistema y haces un cambio general en los datos existentes? Si lo hace, ahora ha hecho que los valores históricos sean incorrectos. Buenos ejemplos de esta falla son Oracle e iCal. Oracle almacena información de zona horaria como un desplazamiento de UTC e iCal incluye el descriptor completo para la zona horaria de creación.

  • Lo almacena como un nombre.

Esto permite la definición de la zona horaria para cambiar sin tener que modificar los valores existentes que tiene. Hace que la clasificación sea más difícil, ya que cualquier índice que se genere puede no ser válido si los datos de la zona horaria cambian.

Si los desarrolladores continúan almacenando todo en UTC, independientemente de la zona horaria, seguiremos viendo los problemas que hemos visto con el último lote de cambios de zona horaria.

En una organización, las secretarias tenían que imprimir los calendarios de sus equipos antes de la fecha de ahorro de luz del día, y luego imprimirlos de nuevo después del cambio. Finalmente, compararon los dos y volvieron a crear todas las citas que se habían movido. Por supuesto, se perdieron varias, y hubo varias semanas de dolor hasta que se alcanzó la fecha de ahorro de luz del día anterior y los tiempos volvieron a ser correctos.

1

prefiero almacenar todo con la zona horaria. el cliente puede decidir, de qué manera debe presentarse más adelante. mi biblioteca favorita para la conversión es PostgreSQL-Database.

2

Almacenar todo en GMT/UTC me parece más lógico. A continuación, puede mostrar la fecha y la hora en cada zona horaria que desee.

Unos ceveats:

  1. Si una vez solamente se especifica como un tiempo de reloj pared y que es la representación que lleva , entonces no es un tiempo absolutamente especificado. Debe (y no puede) convertirlo en cualquier representación de GMT. P.EJ. 9:00 AM cada mañana. En otras palabras: esto no es (fecha) hora.
  2. Si guarda una fecha y hora de un futuro cita, debe utilizar el compensar a GMT especificado por la zona horaria de entrada y la el momento en el tiempo en sí . Entonces, si se trata de una cita en verano, hecha en invierno, p. europa occidental, es +2: 00, aunque la compensación normal (en invierno) es +1: 00. Esto resolverá el problema del calendario que Bwooce mencionó.
  3. Por supuesto, el mismo que se aplica a utilizando el derecho compensar al convertir a GMT aplica al convertir de nuevo a una fecha y hora en particular, cualquier zona horaria.

Afortunadamente, cuando se utiliza correctamente, el tipo DateTime (.NET) se ocupa de todos los detalles sangrientos de guardar calendarios, etc. para usted y todo esto debería ser muy fácil cuando sepa cómo funciona.

1

Echa un vistazo aquí, el w3c ha hecho un excelente trabajo respondiendo la pregunta.

Mire los casos de uso.

http://www.w3.org/TR/timezone/

Nota que recomiendan datetimes almacenan como UTC no GMT, GMT está sujeto a horario de verano.

Cuestiones relacionadas