recomendaría a tiempo siempre uso UTC (GMT) en el lado del servidor (en el código subyacente, base de datos, etc), y convertir el tiempo de UTC a hora local para fines de visualización solamente. Esto significa que todas las manipulaciones de tiempo, incluido el ahorro de tiempo en la base de datos, la realización de cálculos, etc., deben realizarse con UTC.
El problema es: ¿cómo sabe el código subyacente cuál es la zona horaria del navegador del cliente? Supongamos que el usuario ingresa algún valor de fecha/hora (como 12/30/2009 14:30) en el formulario y lo envía al servidor. Suponiendo que el usuario envió la hora local, ¿cómo sabe el servidor cómo convertir este valor en UTC?
La aplicación puede solicitar al usuario que especifique la zona horaria (y la guarde en una cookie o base de datos persistente), pero requiere un esfuerzo adicional del usuario, y su aplicación debería implementar la lógica y pantallas para esto . Sería mejor si la aplicación pudiera determinar la zona horaria del cliente automáticamente.
He resuelto este problema con la ayuda de la función getTimezoneOffset de JavaScript, que es la única API que puede indicarle al servidor la diferencia horaria entre la hora local en el cliente y GMT. Como esta es una API del lado del cliente, hice lo siguiente: en el servidor, compruebe si hay una cookie de sesión personalizada que contenga el valor de compensación de tiempo, y si no está disponible, vuelva a cargar la página (solo durante las llamadas GET y no POST) con alguna lógica de JavaScript agregada para generar el desplazamiento de tiempo y guardarlo en la cookie. Desde el lado del cliente esto es casi transparente (una vez durante la sesión, recargo una página en GET). Una vez que tengo el desplazamiento en la cookie, lo aplico a las funciones de gestión del tiempo dependiendo de la dirección de la conversión de tiempo (UTC a la hora local, o hora local a UTC).
Esto puede sonar un poco complicado, y lo es, pero después de escribir funciones de ayuda, la integración de esta característica en el sitio era una cuestión de hacer una sola llamada en Load (de páginas que necesitan conversión de tiempo), y utilizando rutinas de conversión de tiempo al enviar y recuperar valores de tiempo hacia y desde el navegador. Aquí está un ejemplo de cómo se puede utilizar:
using My.Utilities.Web;
...
// Derive the form class from BaseForm instead of Page.
public class WebForm1: BaseForm
{
...
private void Page_Load(object sender, System.EventArgs e)
{
// If we only want to load the page to generate the time
// zone offset cookie, we do not need to do anything else.
if (InitializeLocalTime())
return;
// Assume that txtStartDate is a TextBox control.
if (!IsPostback)
{
// To display a date-time value, convert it from GMT (UTC)
// to local time.
DateTime startDate = GetStartDateFromDB(...);
txtStartDate.Text = FormatLocalDate(startDate);
...
}
else
{
// To save a date-time value, convert it from local
// time to GMT (UTC).
DateTime tempDate = DateTime.Parse(txtStartDate.Text);
DateTime startDate = ConvertLocalTimeToUtc(tempDate);
SaveStartDateInDB(startDate, ...);
...
}
}
...
}
Si necesita más detalles, consulte el artículo It’s About Time: Localizing Time in ASP.NET Applications (lo siento, pero no tengo un vínculo directo al artículo sobre el sitio del editor, ya que asp .netPRO restringe el acceso solo a los suscriptores pagos; sin embargo, hay enlaces a copias en PDF). Me gustaría poder publicar la muestra del artículo, pero no quiero violar los derechos de autor; sin embargo, aquí hay un project to build a helper library que tiene toda la funcionalidad y documentación necesarias (simplemente ignore las cosas que no necesita).
ACTUALIZACIÓN: El artículo ha sido publicado en línea con el proyecto de muestra publicado por el nuevo editor here.
Esta pregunta puede ser antigua y tener una respuesta aceptada, pero es bastante amplia y las respuestas solo abordan un aspecto del problema. La respuesta también es incorrecta, ya que la solución recomendada no cubre el horario de verano y utiliza 'TimeZoneInfo', que no estaba disponible en .NET 2.0 (que como requisito de esta pregunta). Recomiendo que esta pregunta sea cerrada o eliminada. –