[INTL] Implement Array.prototype.toLocaleString in ECMA-402
authorcommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 22 Jan 2016 02:05:28 +0000 (02:05 +0000)
committercommit-queue@webkit.org <commit-queue@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Fri, 22 Jan 2016 02:05:28 +0000 (02:05 +0000)
https://bugs.webkit.org/show_bug.cgi?id=147614

Patch by Andy VanWagoner <andy@instructure.com> on 2016-01-21
Reviewed by Benjamin Poulain.

Source/JavaScriptCore:

The primary changes in the ECMA-402 version, and the existing implementation
are passing the arguments on to each element's toLocaleString call, and
missing/undefined/null elements become empty string instead of being skipped.

* runtime/ArrayPrototype.cpp:
(JSC::arrayProtoFuncToLocaleString):

LayoutTests:

* js/array-toLocaleString-expected.txt: Added.
* js/array-toLocaleString.html: Added.
* js/script-tests/array-toLocaleString.js: Added.

git-svn-id: https://svn.webkit.org/repository/webkit/trunk@195431 268f45cc-cd09-0410-ab3c-d52691b4dbfc

LayoutTests/ChangeLog
LayoutTests/js/array-toLocaleString-expected.txt [new file with mode: 0644]
LayoutTests/js/array-toLocaleString.html [new file with mode: 0644]
LayoutTests/js/script-tests/array-toLocaleString.js [new file with mode: 0644]
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/runtime/ArrayPrototype.cpp

index 0ba8e2e..423b1a5 100644 (file)
@@ -1,3 +1,14 @@
+2016-01-21  Andy VanWagoner  <andy@instructure.com>
+
+        [INTL] Implement Array.prototype.toLocaleString in ECMA-402
+        https://bugs.webkit.org/show_bug.cgi?id=147614
+
+        Reviewed by Benjamin Poulain.
+
+        * js/array-toLocaleString-expected.txt: Added.
+        * js/array-toLocaleString.html: Added.
+        * js/script-tests/array-toLocaleString.js: Added.
+
 2016-01-21  Ryan Haddad  <ryanhaddad@apple.com>
 
         Rebaseline fast/block/float/overhanging-tall-block.html for ios-simulator-wk2
diff --git a/LayoutTests/js/array-toLocaleString-expected.txt b/LayoutTests/js/array-toLocaleString-expected.txt
new file mode 100644 (file)
index 0000000..f48c042
--- /dev/null
@@ -0,0 +1,23 @@
+This test checks the behavior of Array.prototype.toLocaleString as described in the ECMAScript Internationalization API Specification (ECMA-402 2.0).
+
+On success, you will see a series of "PASS" messages, followed by "TEST COMPLETE".
+
+
+PASS Array.prototype.toLocaleString.length is 0
+PASS Object.getOwnPropertyDescriptor(Array.prototype, 'toLocaleString').enumerable is false
+PASS Object.getOwnPropertyDescriptor(Array.prototype, 'toLocaleString').configurable is true
+PASS Object.getOwnPropertyDescriptor(Array.prototype, 'toLocaleString').writable is true
+PASS Array.prototype.toLocaleString.call() threw exception TypeError: undefined is not an object (evaluating 'Array.prototype.toLocaleString.call()').
+PASS Array.prototype.toLocaleString.call(undefined) threw exception TypeError: undefined is not an object (evaluating 'Array.prototype.toLocaleString.call(undefined)').
+PASS Array.prototype.toLocaleString.call(null) threw exception TypeError: null is not an object (evaluating 'Array.prototype.toLocaleString.call(null)').
+PASS Array.prototype.toLocaleString.call({ length: 5, 0: 'zero', 1: 1, 3: 'three', 5: 'five' }) is "zero,1,,three,"
+PASS [].toLocaleString() is ""
+PASS Array(5).toLocaleString() is ",,,,"
+PASS [ null, null ].toLocaleString() is ","
+PASS [ undefined, undefined ].toLocaleString() is ","
+PASS [ new Date ].toLocaleString('i') threw exception RangeError: invalid language tag: i.
+PASS [ new Date(NaN), new Date(0) ].toLocaleString('zh-Hans-CN-u-nu-hanidec', { timeZone: 'UTC' }) is "Invalid Date,一九七〇/一/一 上午一二:〇〇:〇〇"
+PASS successfullyParsed is true
+
+TEST COMPLETE
+
diff --git a/LayoutTests/js/array-toLocaleString.html b/LayoutTests/js/array-toLocaleString.html
new file mode 100644 (file)
index 0000000..2a05a5e
--- /dev/null
@@ -0,0 +1,11 @@
+<!DOCTYPE HTML PUBLIC "-//IETF//DTD HTML//EN">
+<html>
+<head>
+<meta charset="utf-8">
+<script src="../resources/js-test-pre.js"></script>
+</head>
+<body>
+<script src="script-tests/array-toLocaleString.js"></script>
+<script src="../resources/js-test-post.js"></script>
+</body>
+</html>
diff --git a/LayoutTests/js/script-tests/array-toLocaleString.js b/LayoutTests/js/script-tests/array-toLocaleString.js
new file mode 100644 (file)
index 0000000..117d944
--- /dev/null
@@ -0,0 +1,26 @@
+description("This test checks the behavior of Array.prototype.toLocaleString as described in the ECMAScript Internationalization API Specification (ECMA-402 2.0).");
+
+shouldBe("Array.prototype.toLocaleString.length", "0");
+shouldBeFalse("Object.getOwnPropertyDescriptor(Array.prototype, 'toLocaleString').enumerable");
+shouldBeTrue("Object.getOwnPropertyDescriptor(Array.prototype, 'toLocaleString').configurable");
+shouldBeTrue("Object.getOwnPropertyDescriptor(Array.prototype, 'toLocaleString').writable");
+
+// Test toObject abrupt completion.
+shouldThrow("Array.prototype.toLocaleString.call()", "'TypeError: undefined is not an object (evaluating \\'Array.prototype.toLocaleString.call()\\')'");
+shouldThrow("Array.prototype.toLocaleString.call(undefined)", "'TypeError: undefined is not an object (evaluating \\'Array.prototype.toLocaleString.call(undefined)\\')'");
+shouldThrow("Array.prototype.toLocaleString.call(null)", "'TypeError: null is not an object (evaluating \\'Array.prototype.toLocaleString.call(null)\\')'");
+
+// Test Generic invocation.
+shouldBeEqualToString("Array.prototype.toLocaleString.call({ length: 5, 0: 'zero', 1: 1, 3: 'three', 5: 'five' })", "zero,1,,three,")
+
+// Empty array is always an empty string.
+shouldBeEqualToString("[].toLocaleString()", "");
+
+// Missing still get a separator.
+shouldBeEqualToString("Array(5).toLocaleString()", ",,,,");
+shouldBeEqualToString("[ null, null ].toLocaleString()", ",");
+shouldBeEqualToString("[ undefined, undefined ].toLocaleString()", ",");
+
+// Test that parameters are passed through properly.
+shouldThrow("[ new Date ].toLocaleString('i')");
+shouldBeEqualToString("[ new Date(NaN), new Date(0) ].toLocaleString('zh-Hans-CN-u-nu-hanidec', { timeZone: 'UTC' })", "Invalid Date,一九七〇/一/一 上午一二:〇〇:〇〇");
index 877ce81..f3f4a78 100644 (file)
@@ -1,3 +1,17 @@
+2016-01-21  Andy VanWagoner  <andy@instructure.com>
+
+        [INTL] Implement Array.prototype.toLocaleString in ECMA-402
+        https://bugs.webkit.org/show_bug.cgi?id=147614
+
+        Reviewed by Benjamin Poulain.
+
+        The primary changes in the ECMA-402 version, and the existing implementation
+        are passing the arguments on to each element's toLocaleString call, and
+        missing/undefined/null elements become empty string instead of being skipped.
+
+        * runtime/ArrayPrototype.cpp:
+        (JSC::arrayProtoFuncToLocaleString):
+
 2016-01-21  Per Arne Vollan  <peavo@outlook.com>
 
         [B3][Win64] Compile fixes.
index fcec28a..04f86ba 100644 (file)
@@ -336,6 +336,31 @@ EncodedJSValue JSC_HOST_CALL arrayProtoFuncToLocaleString(ExecState* exec)
     if (exec->hadException())
         return JSValue::encode(jsUndefined());
 
+#if ENABLE(INTL)
+    ArgList arguments(exec);
+    for (unsigned i = 0; i < length; ++i) {
+        JSValue element = thisObject->getIndex(exec, i);
+        if (exec->hadException())
+            return JSValue::encode(jsUndefined());
+        if (element.isUndefinedOrNull())
+            element = jsEmptyString(exec);
+        else {
+            JSValue conversionFunction = element.get(exec, exec->propertyNames().toLocaleString);
+            if (exec->hadException())
+                return JSValue::encode(jsUndefined());
+            CallData callData;
+            CallType callType = getCallData(conversionFunction, callData);
+            if (callType != CallTypeNone) {
+                element = call(exec, conversionFunction, callType, callData, element, arguments);
+                if (exec->hadException())
+                return JSValue::encode(jsUndefined());
+            }
+        }
+        stringJoiner.append(*exec, element);
+        if (exec->hadException())
+            return JSValue::encode(jsUndefined());
+    }
+#else // !ENABLE(INTL)
     for (unsigned i = 0; i < length; ++i) {
         JSValue element = thisObject->getIndex(exec, i);
         if (exec->hadException())
@@ -356,6 +381,7 @@ EncodedJSValue JSC_HOST_CALL arrayProtoFuncToLocaleString(ExecState* exec)
         if (exec->hadException())
             return JSValue::encode(jsUndefined());
     }
+#endif // !ENABLE(INTL)
 
     return JSValue::encode(stringJoiner.join(*exec));
 }