3

We've got a webjob that runs on .Net Framework 4.7.1 and that performs a datetime conversion from DateTimeOffset.UtcNow to Chile continental time (that is if I'm not mistaken "Pacific SA Standard Time").

When running this webjob locally (in a Windows 10 machine) it works correctly and performs the conversion applying the DST, but when deployed to an Azure App Service this doesn't work anymore, and the final DateTime is always one hour later than the current official time.

I initially switched from TimeZoneInfo.ConvertTimeBySystemTimeZoneId to TimeZoneInfo.ConvertTimeFromUtcunder the assumption that the first doesn't consider DST but that didn't work;

then I've tried switching "wrong" my own PC, changing my timezone to 'UTC_dstoff' and disabling in the 'Adjust date/time' menu the options 'Adjust for daylight saving time automatically' and also 'Set time automatically' but it still works as expected locally;

last thing I've tried was to change the timezone to the App Service using the environment variable WEBSITE_TIME_ZONE to 'Pacific SA Standard Time' and it wasn't conclussive. I would say it initially seemed to have worked but after some more changes of timezone it starting adding one hour again.

This can be reproduced with the following lines:

var timeZoneId = "Pacific SA Standard Time";
var timeZone = TimeZoneInfo.FindSystemTimeZoneById(timeZoneId);
var dateTimeOffset = DateTimeOffset.UtcNow;

var localTime = TimeZoneInfo.ConvertTimeFromUtc(dateTimeOffset.DateTime, timeZone);

I would expect the function TimeZoneInfo.ConvertTimeFromUtc would correctly apply DST when a timezone with DST is selected both locally and in the Azure App Service. Instead, it seems to work properly in Windows 10 but randomly in Azure App Service.

Glezalex
  • 33
  • 5

2 Answers2

1

On Azure, add WEBSITE_TIME_ZONE to Pacific SA Standard Time and use methods of TimeZoneInfo structure as below:

DateTime timeUtc = DateTime.UtcNow;
TimeZoneInfo timeZone = TimeZoneInfo.FindSystemTimeZoneById("Pacific SA Standard Time"); 
DateTime kstTime = TimeZoneInfo.ConvertTimeFromUtc(timeUtc, timeZone );
Joey Cai
  • 18,968
  • 1
  • 20
  • 30
  • This isn't much different than what was put in the question. It's not wrong, just it doesn't help much. The only real difference is that `timeUtc.Kind` will be `DateTimeKind.Utc` instead of `DateTimeKind.Unspecified`, but the `TimeZoneInfo.ConvertTimeFromUtc` will behave the same way with either. – Matt Johnson-Pint Apr 18 '19 at 20:46
1

Update

It would appear that the time zone update in KB4486459 that covered changes for Chile's DST schedule in 2019 had not yet been applied to Azure App Service. Thus explaining why you got different results locally for certain dates than when you deployed to Azure.

4486459 is included in the Azure March 2019 Guest OS patches, which are still being deployed to Azure App Service. Thus, this issue will resolve itself as individual instances receive the updates.


Original Answer

A few things:

  • WEBSITE_TIME_ZONE should only be used if you have code that you cannot change that works with local time. For example, if you have lots of calls to DateTime.Now, that will reflect the local time zone. Changing WEBSITE_TIME_ZONE will change the time zone used to determine that. If you have control of your own code, then simply never write DateTime.Now, or use any other function that depends on the local time zone. Then you will never need to use this setting. Consider it a last resort - not a recommended way of doing things.

  • In general, you should try to not write server-side code that will change its behavior depending on system time zone settings, whether that's the ones in your control panel on your local machine, or the WEBSITE_TIME_ZONE setting mentioned above.

  • Not that it should matter, but the "Adjust for daylight saving time automatically" setting should almost always be left on. Disabling it (or by passing _dstoff to TZUtil.exe) is mostly a legacy setting. (There is a rare edge case, but not worth talking about here.)

  • Yes, "Pacific SA Standard Time" is the correct Windows time zone ID for mainland Chile (Santiago). The others that apply to Chile are for Punta Arenas ("Magallanes Standard Time") and Easter Island ("Easter Island Standard Time").

  • Be aware that Chile had a change in dates for its daylight saving time schedule in 2019. Read about it here. This was released in an update by Microsoft in February 2019, described here. This update should already be installed on your Azure web site, but you may want to verify your own local machine.

  • You said you originally used TimeZoneInfo.ConvertTimeBySystemTimeZoneId. If you used the overload that accepts a DateTime, then be aware that if .Kind is DateTimeKind.Unspecified then it will be treated as local time. If you didn't change the WEBSITE_TIME_ZONE, then the default local time is UTC. But if you did, then that would affect the behavior.

  • Also be aware that when you ask for the .DateTime property of a DateTimeOffset, the kind will always be DateTimeKind.Unspecified. Though that doesn't affect your current code because TimeZoneInfo.ConvertTimeFromUtc treats unspecified kind as if it were UTC (hence the "FromUTC" in the name).

  • If you are working with DateTimeOffset types, you would be better off using TimeZoneInfo.ConvertTimeBySystemTimeZoneId or just TimeZoneInfo.ConvertTime, with the overloads that accept and return a DateTimeOffset. Then DateTimeKind won't get in your way.

Lastly, I'll point out that your question isn't very clear with regard to what isn't working exactly. The code you showed will ultimately do the right thing, even if it isn't ideal. There's nothing about it that would produce intermittent results, regardless of if you changed the system settings or WEBSITE_TIME_ZONE. Is it possible you're just feeding in different dates and times and seeing that some have DST and some do not? If so, that may be entirely normal. I'd check them against the Chile DST schedule to see if they align or not. Remember, it's not about whether DST applies at the time you execute your code or not, but rather whether it applies for the value given.

If you still are seeing problems, please comment with an example of input and output along with what you expected. Thanks.

Matt Johnson-Pint
  • 230,703
  • 74
  • 448
  • 575
  • Thanks @matt-johnson in short my issue is that when we catch the current DateTime with DateTimeOffset.UtcNow that returns the right UTC time (so for example '4/19/2019 9:28:20 AM +00:00') but when I convert it to Chile local time with the aforementioned function it returns an hour later in Azure (so '4/19/2019 6:28:20 AM' when I would expect it to be '4/19/2019 5:28:20 AM'). Anyway you've some good points that I would like to check! – Glezalex Apr 19 '19 at 09:31
  • It's possible that the Azure website doesn't have that update installed. That would explain your findings. Does it work correctly for a date past May 5th? That would have been the DST end date on the old schedule. – Matt Johnson-Pint Apr 19 '19 at 14:51
  • If you do find that Azure is missing the update (It's [KB4486459](https://support.microsoft.com/en-us/help/4486459/dst-changes-in-windows-for-chile)), then please open a support request through the portal. Thanks. – Matt Johnson-Pint Apr 19 '19 at 18:11
  • Thanks @matt-johnson, it seems to be working already as expected. I assume the update has already been deployed -wich was super fast :)- – Glezalex Apr 24 '19 at 13:48
  • @Glezalex - see my updated answer at the top. Your instance likely has received the update while we were discussing. :) – Matt Johnson-Pint Apr 24 '19 at 23:13