88//! [mdn]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date
99
1010use crate :: {
11- Context , JsArgs , JsData , JsError , JsResult , JsString ,
11+ Context , JsArgs , JsData , JsResult , JsString ,
1212 builtins:: {
1313 BuiltInBuilder , BuiltInConstructor , BuiltInObject , IntrinsicObject ,
1414 date:: utils:: {
@@ -1608,6 +1608,15 @@ impl Date {
16081608 func. call ( this, & [ ] , context)
16091609 }
16101610
1611+ /// Returns the `[[DateValue]]` internal slot (RequireInternalSlot(dateObject, `[[DateValue]]`)).
1612+ fn this_date_value ( this : & JsValue ) -> JsResult < f64 > {
1613+ this. as_object ( )
1614+ . and_then ( |obj| obj. downcast_ref :: < Date > ( ) . as_deref ( ) . copied ( ) )
1615+ . ok_or_else ( || JsNativeError :: typ ( ) . with_message ( "'this' is not a Date" ) )
1616+ . map ( |d| d. 0 )
1617+ . map_err ( Into :: into)
1618+ }
1619+
16111620 /// [`Date.prototype.toLocaleDateString()`][spec].
16121621 ///
16131622 /// The `toLocaleDateString()` method returns the date portion of the given Date instance according
@@ -1616,16 +1625,47 @@ impl Date {
16161625 /// More information:
16171626 /// - [MDN documentation][mdn]
16181627 ///
1619- /// [spec]: https://tc39.es/ecma262/#sec -date.prototype.tolocaledatestring
1628+ /// [spec]: https://tc39.es/ecma402/#sup -date.prototype.tolocaledatestring
16201629 /// [mdn]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/toLocaleDateString
1630+ #[ allow(
1631+ unused_variables,
1632+ reason = "`args` and `context` are used when the `intl` feature is enabled"
1633+ ) ]
16211634 pub ( crate ) fn to_locale_date_string (
1622- _this : & JsValue ,
1623- _args : & [ JsValue ] ,
1624- _context : & mut Context ,
1635+ this : & JsValue ,
1636+ args : & [ JsValue ] ,
1637+ context : & mut Context ,
16251638 ) -> JsResult < JsValue > {
1626- Err ( JsError :: from_opaque ( JsValue :: new ( js_string ! (
1627- "Function Unimplemented"
1628- ) ) ) )
1639+ // Let dateObject be the this value.
1640+ // Perform ? RequireInternalSlot(dateObject, [[DateValue]]).
1641+ // Let x be dateObject.[[DateValue]].
1642+ let t = Self :: this_date_value ( this) ?;
1643+ // If x is NaN, return "Invalid Date".
1644+ if t. is_nan ( ) {
1645+ return Ok ( JsValue :: new ( js_string ! ( "Invalid Date" ) ) ) ;
1646+ }
1647+ // Let dateFormat be ? CreateDateTimeFormat(%Intl.DateTimeFormat%, locales, options, date, date).
1648+ // Return ! FormatDateTime(dateFormat, x).
1649+ #[ cfg( feature = "intl" ) ]
1650+ {
1651+ use crate :: builtins:: intl:: date_time_format:: {
1652+ FormatDefaults , FormatType , format_date_time_locale,
1653+ } ;
1654+ let locales = args. get_or_undefined ( 0 ) ;
1655+ let options = args. get_or_undefined ( 1 ) ;
1656+ format_date_time_locale (
1657+ locales,
1658+ options,
1659+ FormatType :: Date ,
1660+ FormatDefaults :: Date ,
1661+ t,
1662+ context,
1663+ )
1664+ }
1665+ #[ cfg( not( feature = "intl" ) ) ]
1666+ {
1667+ Self :: to_string ( this, & [ ] , context)
1668+ }
16291669 }
16301670
16311671 /// [`Date.prototype.toLocaleString()`][spec].
@@ -1635,16 +1675,47 @@ impl Date {
16351675 /// More information:
16361676 /// - [MDN documentation][mdn]
16371677 ///
1638- /// [spec]: https://tc39.es/ecma262/#sec -date.prototype.tolocalestring
1678+ /// [spec]: https://tc39.es/ecma402/#sup -date.prototype.tolocalestring
16391679 /// [mdn]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/toLocaleString
1680+ #[ allow(
1681+ unused_variables,
1682+ reason = "`args` and `context` are used when the `intl` feature is enabled"
1683+ ) ]
16401684 pub ( crate ) fn to_locale_string (
1641- _this : & JsValue ,
1642- _ : & [ JsValue ] ,
1643- _context : & mut Context ,
1685+ this : & JsValue ,
1686+ args : & [ JsValue ] ,
1687+ context : & mut Context ,
16441688 ) -> JsResult < JsValue > {
1645- Err ( JsError :: from_opaque ( JsValue :: new ( js_string ! (
1646- "Function Unimplemented]"
1647- ) ) ) )
1689+ // Let dateObject be the this value.
1690+ // Perform ? RequireInternalSlot(dateObject, [[DateValue]]).
1691+ // Let x be dateObject.[[DateValue]].
1692+ let t = Self :: this_date_value ( this) ?;
1693+ // If x is NaN, return "Invalid Date".
1694+ if t. is_nan ( ) {
1695+ return Ok ( JsValue :: new ( js_string ! ( "Invalid Date" ) ) ) ;
1696+ }
1697+ // Let dateFormat be ? CreateDateTimeFormat(%Intl.DateTimeFormat%, locales, options, any, all).
1698+ // Return ! FormatDateTime(dateFormat, x).
1699+ #[ cfg( feature = "intl" ) ]
1700+ {
1701+ use crate :: builtins:: intl:: date_time_format:: {
1702+ FormatDefaults , FormatType , format_date_time_locale,
1703+ } ;
1704+ let locales = args. get_or_undefined ( 0 ) ;
1705+ let options = args. get_or_undefined ( 1 ) ;
1706+ format_date_time_locale (
1707+ locales,
1708+ options,
1709+ FormatType :: Any ,
1710+ FormatDefaults :: All ,
1711+ t,
1712+ context,
1713+ )
1714+ }
1715+ #[ cfg( not( feature = "intl" ) ) ]
1716+ {
1717+ Self :: to_string ( this, & [ ] , context)
1718+ }
16481719 }
16491720
16501721 /// [`Date.prototype.toLocaleTimeString()`][spec].
@@ -1655,16 +1726,47 @@ impl Date {
16551726 /// More information:
16561727 /// - [MDN documentation][mdn]
16571728 ///
1658- /// [spec]: https://tc39.es/ecma262/#sec -date.prototype.tolocaletimestring
1729+ /// [spec]: https://tc39.es/ecma402/#sup -date.prototype.tolocaletimestring
16591730 /// [mdn]: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Date/toLocaleTimeString
1731+ #[ allow(
1732+ unused_variables,
1733+ reason = "`args` and `context` are used when the `intl` feature is enabled"
1734+ ) ]
16601735 pub ( crate ) fn to_locale_time_string (
1661- _this : & JsValue ,
1662- _args : & [ JsValue ] ,
1663- _context : & mut Context ,
1736+ this : & JsValue ,
1737+ args : & [ JsValue ] ,
1738+ context : & mut Context ,
16641739 ) -> JsResult < JsValue > {
1665- Err ( JsError :: from_opaque ( JsValue :: new ( js_string ! (
1666- "Function Unimplemented]"
1667- ) ) ) )
1740+ // Let dateObject be the this value.
1741+ // Perform ? RequireInternalSlot(dateObject, [[DateValue]]).
1742+ // Let x be dateObject.[[DateValue]].
1743+ let t = Self :: this_date_value ( this) ?;
1744+ // If x is NaN, return "Invalid Date".
1745+ if t. is_nan ( ) {
1746+ return Ok ( JsValue :: new ( js_string ! ( "Invalid Date" ) ) ) ;
1747+ }
1748+ // Let timeFormat be ? CreateDateTimeFormat(%Intl.DateTimeFormat%, locales, options, time, time).
1749+ // Return ! FormatDateTime(timeFormat, x).
1750+ #[ cfg( feature = "intl" ) ]
1751+ {
1752+ use crate :: builtins:: intl:: date_time_format:: {
1753+ FormatDefaults , FormatType , format_date_time_locale,
1754+ } ;
1755+ let locales = args. get_or_undefined ( 0 ) ;
1756+ let options = args. get_or_undefined ( 1 ) ;
1757+ format_date_time_locale (
1758+ locales,
1759+ options,
1760+ FormatType :: Time ,
1761+ FormatDefaults :: Time ,
1762+ t,
1763+ context,
1764+ )
1765+ }
1766+ #[ cfg( not( feature = "intl" ) ) ]
1767+ {
1768+ Self :: to_string ( this, & [ ] , context)
1769+ }
16681770 }
16691771
16701772 /// [`Date.prototype.toString()`][spec].
0 commit comments