JavaScript: отримуємо інформацію про тимчасову зону.

Іноді дуже красиво зберігати час на сервері UTC і перетворювати його на локальний час користувача при видачі сторінки. Принаймні таке завдання постало в проекті, в якому я беру участь. Переклад з utc в локальний час завдання непросте, але по ньому досить багато інформації і опублікованих алгоритмів. Все що для них потрібно це дані про тимчасову зону клієнта, але як виявилося інформації про це якраз не так вже й багато.


Все опубліковане нижче результати власних напрацювань

var now = new Date();
function СheckDLT(sm, em)
  {
   return ((new Date(em)).getTimezoneOffset() - (new Date(sm)).getTimezoneOffset());
  }
function getTZLowerBound( start, end, cmp )
  {
   var nstart, count, count2;
count = end - start;
while(count>0)
     {
      end = start + count;
nstart = start + ( count2 = Math.floor(count / 2) );
if ( cmp(СheckDLT(nstart,end)) )
        {
         start = nstart + 1;
count -= count2 + 1;
        }
      else
        count = count2;
     }
   return [start, -(new Date(start)).getTimezoneOffset()];
  }
var dlt = Date.UTC(now.getFullYear(), 0, 1, 0, 0, 0, 0),
std = Date.UTC(now.getFullYear(), 6, 1, 0, 0, 0, 0);
if(СheckDLT(dlt,std))
  {
   dlt = getTZLowerBound(dlt,std, function (b) {return (b<0)});
std = getTZLowerBound(Date.UTC(now.getFullYear(), 6, 1, 0, 0, 0, 0),
                        Date.UTC(now.getFullYear(), 11, 1, 0, 0, 0, 0),
                        function (b) {return (b>0)});
dlt[0] = dlt[0] + std[1]*60000;
std[0] = std[0] + dlt[1]*60000;
  }
else
  std = dlt = [0,-now.getTimezoneOffset()];

Ось що ми маємо в результаті виконання цього коду. На виході у нас виходить два масиви dlt і std. Перший містить дані про точку переходу на літній час, другий на стандартний. Першим елементом кожного масиву йде timestamp точки переходу в локальному часі, другий зміщення відносно GMT після переходу. Якщо в часовій зоні клієнта немає переходу на літній час, то перші елементи обох масивів будуть рівні нулю, а другі зміщенню часової зони по GMT

Звичайно за цими даними не можна однозначно визначити часову зону клієнта, так як серед них багато перетинів в даний час, але є розбіжність в минулому. Проте якщо використовувати їх для автоматичної конвертації часу, то цього цілком достатньо.