2015-03-25 2 views
-1

Я ищу лучший способ написать запрос, который берет существующее поле DateTime/значение в базе данных (более 50K строк) и обновляет DateTime в другой часовой пояс. То, что я хочу сделать, - изменить существующее значение даты/времени с GMT (текущее время сервера) на PST (будет меньше 7 часов). Я хочу изменить значения в базе данных, тогда я изменю время сервера на сервере на PST, чтобы отразить часовой пояс, чтобы все новые записи отображали часовой пояс PST.SQL Query для обновления существующего поля DateTime и значений в DB для PST из GMT

Любая помощь по этому вопросу будет оценена, спасибо заранее за ваше время.

ответ

-1

Вы можете изменить часовой пояс базы данных, используя предложение SET TIME_ZONE оператора ALTER DATABASE. Например:

ALTER DATABASE SET TIME_ZONE='Europe/London';ALTER DATABASE SET TIME_ZONE='-05:00'; 

Для получения более подробной информации, пожалуйста, перейдите по следующей ссылке. http://docs.oracle.com/cd/E11882_01/server.112/e10729/ch4datetime.htm#NLSPG263

+0

Я думаю, что решение является скорее решением часового пояса базы данных, но оно не изменяет существующие значения базы данных даты и времени в часовой пояс PST из GMT. – thenextmogul

+0

@thenextmogul В дополнение к тому, что вы сделали о том, что это параметр уровня DB, а не сами данные, это также опция Oracle, опция _not_ SQL Server. –

0

К сожалению, SQL Server не имеет встроенной функции преобразования часового пояса. Однако это может быть выполнено с помощью SQLCLR. Вы можете создать скалярные пользовательские функции, используя метод DateTime.ToLocalTime().

Да, технически вы можете использовать TimeZoneInfo класс, который имеет такие методы, как ConvertTime(DateTime, TimeZoneInfo, TimeZoneInfo) и ConvertTimeFromUtc(DateTime, TimeZoneInfo), но TimeZoneInfo класс требует, чтобы сборка имеет PERMISSION_SET из UNSAFE тогда DateTime может работать в качестве SAFE. Единственным недостатком придерживаться методов DateTime является то, что они могут конвертировать только между UTC и локальным временем сервера, в отличие от TimeZoneInfo, который может конвертировать между любыми двумя заданными часовыми поясами.

Поскольку ваши данные уже в GMT/UTC, было бы довольно легко преобразовать в Тихий океан * время использования DateTime.ToLocalTime, но только если изменить часовой пояс вашего сервера перед тем обновления данных, а не после того, как (как упоминается в вопросе). В этот момент вы могли бы сделать что-то вроде следующего:

ALTER TABLE [SchemaName].[TableName] 
    ADD [IsConverted] BIT NULL; -- make sure we don't convert multiple times 

WHILE (1 = 1) 
BEGIN 
    UPDATE TOP (2000) tab 
    SET tab.DateField = dbo.ConvertTimeToLocalTime(tab.DateField), 
     tab.IsConverted = 1 
    FROM [SchemaName].[TableName] tab 
    WHERE tab.IsConverted IS NULL; 

    IF (@@ROWCOUNT = 0) 
    BEGIN 
    BREAK; 
    END; 
END; 

-- Remove the temporary tracking field, but not until all rows are converted 
IF (NOT EXISTS(
       SELECT * 
       FROM [SchemaName].[TableName] tab 
       WHERE tab.IsConverted IS NULL 
      ) 
    ) 
BEGIN 
    ALTER TABLE [SchemaName].[TableName] 
    DROP COLUMN [IsConverted]; 
END; 

* Обратите внимание, что я использовал «Pacific» время вместо PST, потому что тихоокеанскому времени может быть или PST или PDT в зависимости от Daylight Savings. Следовательно, попытка преобразования путем простого выполнения DATEADD(HOUR, -7, [DateField]) будет верна для некоторых строк, но не для всех строк.

Кроме того, для тех, кто интересуется данной функцией преобразования, он доступен (хотя и не бесплатно) в полной версии библиотеки SQL# (которой я являюсь автором). Есть несколько сообщений в блогах, которые показывают, как это сделать, хотя я не видел того, что следует за лучшими практиками, так что он будет работать оптимально. Конечно, если это разовое преобразование, то оптимальная производительность по цене, по общему признанию, менее важна, чем менее эффективная, но бесплатная :-).

1

Вы, вероятно, не должны этого делать вообще. Храните свои данные в GMT (действительно, UTC) в базе данных и конвертируйте их в мирное время в логике приложения по мере необходимости. Например, если вы подключаетесь к вам SQL Server из приложения .NET, запрашиваете время UTC из базы данных и конвертируете его с помощью TimeZoneInfo.ConvertTimeFromUtc

Самая большая причина этого в том, что для тихоокеанского времени используется daylight saving time. Так что в то время как часть года она соответствует PST (UTC-8), летом она следует за PDT (это UTC-7).Это означает, что время корректировки составляет переменная и зависит от самой даты.

Не только это, но и значение, которое происходит во время переходного периода, является неоднозначным по местному времени. Например, 2015-11-01 в 1:30 происходит дважды в тихоокеанское время. Если вы преобразуете все свои данные в тихоокеанское время, вы можете потерять некоторую информацию.

Если у вас действительно необходимо преобразовать между часовыми поясами непосредственно на SQL Server, рассмотрите возможность использования моего проекта SQL Server Time Zone Support. Например:

SELECT Tzdb.UtcToLocal('2015-07-01 00:00:00', 'America/Los_Angeles') 

 Смежные вопросы

  • Нет связанных вопросов^_^