Your suggested approach is flawed in that the current offset from the client's browser is only going to apply to the current date and time. In reality, time zone offsets change over time within a given time zone. You cannot just take a singular offset from one point in time and expect to use it to convert other dates and times to the same time zone. Instead, you need to use the string that identifies the time zone, not an offset from that zone.
As an example, consider the Eastern time zone in the United States. For part of the year, it uses UTC-5, and we call it Eastern Standard Time (EST). In another other part of the year, it uses UTC-4, and we call it Eastern Daylight Time (EDT). This time zone is identified by either the IANA time zone ID "America/New_York"
, or the Windows time zone ID "Eastern Standard Time"
(which covers the entire zone, both EST and EDT despite its wording).
So, break this problem apart into a few steps:
In JavaScript, identify the users's IANA time zone (America/New_York
):
If you are targeting modern web browsers, you can call this function:
Intl.DateTimeFormat().resolvedOptions().timeZone
If you need to support older web browsers, you can use jsTimeZoneDetect, or moment.tz.guess()
from Moment-Timezone.
Send that string to your web server through whatever mechinsm you like (form post, XHR, fetch, etc.)
In your .NET code, receive that string and use it to reference the time zone and do the conversion. You have two options:
You can use Noda Time, passing the IANA time zone ID to DateTimeZoneProviders.Tzdb
as shown in the example on the home page.
You can use .NET's built-in TimeZoneInfo
object. If you're running .NET Core on non-Windows systems (Linux, OSX, etc.) you can just pass the IANA time zone ID to TimeZoneInfo.FindSystemTimeZoneById
. If you are on Windows, you'll need to first convert it to a Windows time zone ID ("Eastern Standard Time"
). You can use TZConvert.GetTimeZoneInfo
from my TimeZoneConverter library.
Once you have either a DateTimeZone
from Noda Time, or a TimeZoneInfo
object, you can use the methods on it to convert UTC values to local time values for that time zone. Each of these will apply the correct offset for the point in time being converted.
I'll also say, many applications simply ask the user to choose their time zone from a dropdown list and save it in a user profile. As long as you're storing a time zone identifier string and not just a numeric offset, this approach is perfectly acceptable to replace steps 1 and 2 above.