Skip to content

Commit

Permalink
fix(datepicker): force Intl.DateTimeFormat to use UTC time zone ... (#…
Browse files Browse the repository at this point in the history
…5747)

* fix(datepicker): force Intl.DateTimeFormat to use UTC time zone so it
doesn't display incorrect dates.

* fix lint and test

* don't use Object.assign
  • Loading branch information
mmalerba authored and andrewseguin committed Jul 25, 2017
1 parent f06fe11 commit 76cc6f0
Show file tree
Hide file tree
Showing 2 changed files with 23 additions and 0 deletions.
8 changes: 8 additions & 0 deletions src/lib/core/datetime/native-date-adapter.spec.ts
Expand Up @@ -296,6 +296,14 @@ describe('NativeDateAdapter', () => {
new Date(2018, FEB, 1), new Date(2018, JAN, 1), new Date(2019, JAN, 1)))
.toEqual(new Date(2018, FEB, 1));
});

it('should use UTC for formatting by default', () => {
if (SUPPORTS_INTL) {
expect(adapter.format(new Date(1800, 7, 14), {day: 'numeric'})).toBe('14');
} else {
expect(adapter.format(new Date(1800, 7, 14), {day: 'numeric'})).toBe('Thu Aug 14 1800');
}
});
});


Expand Down
15 changes: 15 additions & 0 deletions src/lib/core/datetime/native-date-adapter.ts
Expand Up @@ -8,6 +8,7 @@

import {Inject, Injectable, Optional, LOCALE_ID} from '@angular/core';
import {DateAdapter} from './date-adapter';
import {extendObject} from '../util/object-extend';


// TODO(mmalerba): Remove when we no longer support safari 9.
Expand Down Expand Up @@ -56,6 +57,14 @@ export class NativeDateAdapter extends DateAdapter<Date> {
super.setLocale(localeId);
}

/**
* Whether to use `timeZone: 'utc'` with `Intl.DateTimeFormat` when formatting dates.
* Without this `Intl.DateTimeFormat` sometimes chooses the wrong timeZone, which can throw off
* the result. (e.g. in the en-US locale `new Date(1800, 7, 14).toLocaleDateString()`
* will produce `'8/13/1800'`.
*/
useUtcForDisplay = true;

getYear(date: Date): number {
return date.getFullYear();
}
Expand Down Expand Up @@ -154,6 +163,12 @@ export class NativeDateAdapter extends DateAdapter<Date> {

format(date: Date, displayFormat: Object): string {
if (SUPPORTS_INTL_API) {
if (this.useUtcForDisplay) {
date = new Date(Date.UTC(
date.getFullYear(), date.getMonth(), date.getDate(), date.getHours(),
date.getMinutes(), date.getSeconds(), date.getMilliseconds()));
displayFormat = extendObject({}, displayFormat, {timeZone: 'utc'});
}
let dtf = new Intl.DateTimeFormat(this.locale, displayFormat);
return this._stripDirectionalityCharacters(dtf.format(date));
}
Expand Down

0 comments on commit 76cc6f0

Please sign in to comment.