-
Notifications
You must be signed in to change notification settings - Fork 1.3k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Normative: Specify Date string conversion functions #848
Conversation
spec.html
Outdated
<!-- es6num="20.3.4.41.1" --> | ||
<emu-clause id="sec-todatestring" aoid="ToDateString"> | ||
<h1>Runtime Semantics: ToDateString( _tv_ )</h1> | ||
<p>The following steps are performed:</p> | ||
<emu-alg> | ||
1. Assert: Type(_tv_) is Number. | ||
1. If _tv_ is *NaN*, return `"Invalid Date"`. | ||
1. Return an implementation-dependent String value that represents _tv_ as a date and time in the current time zone using a convenient, human-readable form. | ||
1. Let _t_ be LocalTime(_tv_). | ||
1. Return the String value formed by concatenating DateString(_t_), `" "`, and TimeString(_t_), TimeZoneString(_tv_). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
... `" "`, TimeString(_t_), and TimeZoneString(_tv_).
(the word and is misplaced)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed, thanks
@domenic Do you have good suggestions for how to write tests here? I'm not sure how to do it in a way that will work in all time zones. (test262 has repeatedly had issues where tests were broken in certain timezones.) |
spec.html
Outdated
<emu-alg> | ||
1. Assert: Type(_tv_) is Number. | ||
1. Assert: _tv_ is not *NaN*. | ||
1. Return String value formed by concatenating _result_, ToString(HourFromTime(_tv_)), `":"`, ToString(MinFromTime(_tv_)), `":"`, ToString(SecFromTime(_tv_)) and `" GMT"` |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
delete extraneous result variable
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed
spec.html
Outdated
1. Let _offset_ be (LocalTZA + DaylightSavingTA(_tv_)) / msPerSecond. | ||
1. Assert: _offset_ is an integer, and -100000 < _offset_ < 100000. | ||
1. If _offset_ ≥ 0, let _offsetSign_ be `"+"`; otherwise, let _offsetSign_ be `"-"`. | ||
1. Let _offsetString_ be abs(_offset_) formatted as a four-digit number, padded to the left with zeros if necessary. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The offset needs to be formatted as HHMM
, not as SSSS
. The four preceding steps (starting with Let _offset_
) should be replaced with:
- Let offset be LocalTZA + DaylightSavingTA(tv) /* (NB: value in milliseconds) */
- If offset ≥ 0, let offsetSign be
"+"
; otherwise, let offsetSign be"-"
. - Let offsetMin be the String representation of MinFromTime(abs(offset)), formatted as a two-digit number, padded to the left with a zero if necessary.
- Let offsetHour be the String representation of HourFromTime(abs(offset)), formatted as a two-digit number, padded to the left with a zero if necessary.
And the last step of the algorithm, below:
- Let offsetString be the concatenation of offsetSign, offsetHour, offsetMin, and tzName.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thanks, of course! Uploaded a new version to use your text.
Well, you can certainly test the Invalid Date cases. You should be able to run regexps to make sure the patterns are met for all methods, including the time zone format restriction. You should be able to test .toUTCString() exactly on its entire range of inputs, including extreme ones like 0, +/- Infinity, Number.(MIN/MAX)_SAFE_INTEGER, and Number.(MIN/MAX)_VALUE. You should be able to pick times in the middle of a given month so that timezone changes can't change the month string, thus allowing you to test the month name mapping even for toString(). You might be able to pick times such that in every timezone they fall on the same day of the week, thus allowing testing the week day mapping for toString(), but I am not sure. |
spec.html
Outdated
1. Let _O_ be this Date object. | ||
1. Let _tv_ be ? thisTimeValue(_O_). | ||
1. If _tv_ is *NaN*, return `"Invalid Date"`. | ||
1. Return the String value formed by concatenating DateString(_tv_), `" "`, and TimeString(_tv_). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
also here
<!-- es6num="20.3.4.41.1" --> | ||
<emu-clause id="sec-todatestring" aoid="ToDateString"> | ||
<h1>Runtime Semantics: ToDateString( _tv_ )</h1> | ||
<p>The following steps are performed:</p> | ||
<emu-alg> | ||
1. Assert: Type(_tv_) is Number. | ||
1. If _tv_ is *NaN*, return `"Invalid Date"`. | ||
1. Return an implementation-dependent String value that represents _tv_ as a date and time in the current time zone using a convenient, human-readable form. | ||
1. Let _t_ be LocalTime(_tv_). | ||
1. Return the String value formed by concatenating DateString(_t_), `" "`, TimeString(_t_), and TimeZoneString(_tv_). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
for the space, the convention i've seen (and followed in padStart/padEnd) to avoid whitespace ambiguity is " " (a String consisting of 0x0020 SPACE)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@bterlson, thoughts on this?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@ljharb I was going to clean this up myself (working on it soon). Planning on replacing all spaces with "the code unit 0x0020 (SPACE)"
spec.html
Outdated
1. Assert: _offset_ is an integer, and -100000 < _offset_ < 100000. | ||
1. If _offset_ ≥ 0, let _offsetSign_ be `"+"`; otherwise, let _offsetSign_ be `"-"`. | ||
1. Let _offsetString_ be abs(_offset_) formatted as a four-digit number, padded to the left with zeros if necessary. | ||
1. Let _tzName_ be an implementation-defined string, either `""` or a string of the form `" ("` _name_ `")"` where _name_ is an implementation-defined timezone name. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
similarly (and throughout this PR where strings appear), this might want to specify the code units for the space and parens, to avoid ambiguity.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What ambiguity would there be? There are many other places in the spec that use characters with multiple Unicode code points that render similarly or the same (e.g., every a character).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
¯\_(ツ)_/¯ there are many characters for whitespace. Being precise about the code point ensures no confusion, even with a non-english-centric implementation.
Implementations seem to agree on semantics here for the most part, modulo timezone strings, which are left implementation-defined. Addresses part of tc39#845
Also fix up the text of DateString().
21923ce
to
873e0d2
Compare
This actually gets into an area of apparent disagreement between implementations. For years less than 1000, JSC and SpiderMonkey implement the specification here, whereas V8 pads to four digits with spaces, and ChakraCore does not pad the number.
Following the proposed specification in tc39/ecma262#848
There's a small part of this which actually differs between browsers: When printing the year, if the number is below 1000, JSC and SpiderMonkey pad 0s to the left, V8 pads with spaces, and ChakraCore doesn't pad. This patch goes with the SpiderMonkey/JSC behavior. Before merging it, we should make sure that those engines are OK with the potential compatibility impact of this change. |
We should definitely pad with 0s, so that years between 0 and 99 look unambiguous, and we will be able to correct the following glitch of var d = new Date;
d.setFullYear(97);
d.toString(); // variation on: Sat Mar 23 0097 16:04:11 GMT+0100 (CET)
var d2 = new Date(Date.parse(d.toString()));
d2.toString(); // variation on: Sun Mar 23 1997 16:04:11 GMT+0100 (CET) //oops, wrong year |
spec.html
Outdated
<emu-alg> | ||
1. Assert: Type(_tv_) is Number. | ||
1. Assert: _tv_ is not *NaN*. | ||
1. Let _offset_ be (LocalTZA + DaylightSavingTA(_tv_)) / msPerSecond. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This will be in conflict with #778 that drops DaylightSavingTA(tv) and change LocalTZA to take two params. We have to sort that out somehow.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You're right; this is written against the current spec, but needs to be updated against the other one (based on whichever lands second). I guess rather than LocalTZA, we'd use LocalTimeZoneAdjustment(tz, true), right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok. this one was landed first. Then, the other one (#778) has to revise this part as well.
spec.html
Outdated
1. Assert: _offset_ is an integer, and -100000 < _offset_ < 100000. | ||
1. If _offset_ ≥ 0, let _offsetSign_ be `"+"`; otherwise, let _offsetSign_ be `"-"`. | ||
1. Let _offsetString_ be abs(_offset_) formatted as a four-digit number, padded to the left with zeros if necessary. | ||
1. Let _tzName_ be an implementation-defined string, either `""` or a string of the form `" ("` _name_ `")"` where _name_ is an implementation-defined timezone name. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Would it make sense to give a recommendation while leaving it still up to an implementation about tzName?
If it does, it can be recommended to use the canonicalized timezone in Ecma402. Perhaps, cross-referencing is not a good idea?
Just my 2 cents.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I meant for this first patch to be purely 100% descriptive. Maybe a change like this could be in a follow-on patch?
As for making that recommendation: I don't know whether we can make it in good faith in the spec yet, as we don't know whether it's web-compatible yet. Maybe the right thing to do would be to try it out in one browser and see if it works. A good thing to know from the committee beforehand would be--would everyone be up for specifying this behavior, assuming it's web-compatible?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you for the PR ! A couple of comments.
Sorry for the label noise. |
I previously removed the needs tests label because tests are at tc39/test262#930 (though they need a small fix). |
@littledan I did a follow up from @leobalter's initial review and merged the test262 PR |
Implementations seem to agree on semantics here for the most
part, modulo timezone strings, which are left implementation-defined.
Addresses part of #845