Если вы ранее разрабатывали кроссплатформенное приложение, вы могли столкнуться с ситуацией, когда разные платформы по-прежнему имеют разную производительность, несмотря на использование кроссплатформенного решения. И в этом посте будет обсуждаться ситуация, когда результат получения данных о часовом поясе различается на разных платформах в .NET Core.
Получение данных о часовых поясах на платформе Windows
Во-первых, давайте создадим новое консольное приложение .NET Core на платформе Windows. В этом случае я возьму в качестве примера новозеландское время.
using System; namespace DotNETTips { class Program { static void Main(string[] args) { var dateTime = DateTime.UtcNow; Console.WriteLine($"dateTime in UTC : {dateTime}"); var nzTzInfo = TimeZoneInfo.FindSystemTimeZoneById("New Zealand Standard Time"); dateTime = TimeZoneInfo.ConvertTimeFromUtc(dateTime, nzTzInfo); Console.WriteLine($"dateTime in NZ Time Zone : {dateTime}"); Console.ReadKey(); } } }
В приведенном выше коде идентификатором часового пояса Новой Зеландии на платформе Windows является «Стандартное время Новой Зеландии», как вы можете видеть на снимке экрана ниже.
И если вас интересует тема данных о часовых поясах на платформе Windows, вы можете найти список часовых поясов по умолчанию в Windows по следующей ссылке.
Следовательно, мы можем получить данные TimeZoneInfo Новой Зеландии, вызвав метод FindSystemTimeZoneById.
TimeZoneInfo.FindSystemTimeZoneById("New Zealand Standard Time");
Затем мы можем преобразовать данные даты и времени в формате UTC в NZDT.
TimeZoneInfo.ConvertTimeFromUtc(dateTime, nzTzInfo);
Приведенный выше код на самом деле очень хорошо работает на платформе Windows, и вы можете обнаружить, что дата и время печатаются в терминале, как и ожидалось.
Получить данные о часовом поясе в macOS / Linux
Однако, если вы хотите запустить тот же код на своем ноутбуке Mac Pro или компьютере с Linux, он будет распечатывать не дату и время в часовом поясе Новой Зеландии, а TimeZoneNotFoundException.
Это не потому, что на вашем Mac Pro не установлены данные о часовых поясах, но в macOS используется другой поставщик данных о часовых поясах - База данных часовых поясов IANA.
В отличие от идентификатора часового пояса на платформе Windows, идентификатор часового пояса IANA для Новой Зеландии - «Pacific / Auckland». И для вас также есть список часовых поясов, вы можете щелкнуть следующую ссылку, чтобы проверить список часовых поясов в базе данных часовых поясов.
Следовательно, если вы хотите, чтобы ваш код работал должным образом, вам необходимо изменить аргумент метода FindSystemTimeZoneById с «Стандартное время Новой Зеландии» на « Pacific / Auckland » в macOS / Linux.
И правильная дата-время будет напечатана в консоли. Поэтому, если ваше приложение будет работать на разных платформах, вам нужно будет учесть различия.
Решение
Однако, если вы не хотите самостоятельно разбираться с различиями, поскольку их сложно поддерживать, на GitHub есть доступный пакет с открытым исходным кодом, который может помочь вам решить эту проблему.
TimeZoneConverter - это легкая библиотека для быстрого преобразования между именами часовых поясов IANA, Windows и Rails.
Мы можем очень легко установить пакет через NuGet.
Я использовал VS Code в macOS для установки этого пакета NuGet, затем изменил FindSystemTimeZoneById на GetTimeZoneInfo и передал методу тот же идентификатор / идентификатор часового пояса, что и в Windows, «Стандартное время Новой Зеландии». И код напечатал правильный результат в консоли.
Таким образом, мы можем работать с разными поставщиками часовых поясов единообразно, а наш код легче поддерживать.
Спасибо за чтение и надеюсь, что это полезно.
Поболтать в