Web Inspector: ES6: Improved Console Support for Symbol Objects
authorjoepeck@webkit.org <joepeck@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 5 Feb 2015 03:11:29 +0000 (03:11 +0000)
committerjoepeck@webkit.org <joepeck@webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Thu, 5 Feb 2015 03:11:29 +0000 (03:11 +0000)
https://bugs.webkit.org/show_bug.cgi?id=141173

Reviewed by Timothy Hatcher.

Source/JavaScriptCore:

* inspector/protocol/Runtime.json:
New type, "symbol".

* inspector/InjectedScriptSource.js:
Handle Symbol objects in a few places. They don't have properties
and they cannot be implicitly converted to strings.

Source/WebInspectorUI:

* UserInterface/Protocol/RemoteObject.js:
(WebInspector.RemoteObject):
(WebInspector.RemoteObject.prototype._isSymbol):
Symbols have an objectId because it is a non-primitive that cannot be passed
by value, however it cannot have properties, so handle some cases.

* UserInterface/Views/LogContentView.css:
(.console-formatted-symbol):
Give Symbol's their own color.

LayoutTests:

* inspector/model/remote-object-expected.txt:
* inspector/model/remote-object.html:
Update the RemoteObject test to include Symbols.

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

LayoutTests/ChangeLog
LayoutTests/inspector/model/remote-object-expected.txt
LayoutTests/inspector/model/remote-object.html
Source/JavaScriptCore/ChangeLog
Source/JavaScriptCore/inspector/InjectedScriptSource.js
Source/JavaScriptCore/inspector/protocol/Runtime.json
Source/WebInspectorUI/ChangeLog
Source/WebInspectorUI/UserInterface/Protocol/RemoteObject.js
Source/WebInspectorUI/UserInterface/Views/LogContentView.css

index a09334990c3dc23e4d864550c39ab1aa8cfe81cb..5afe59ccb84a0c03d55b3843cd6d207af5075d61 100644 (file)
@@ -1,3 +1,14 @@
+2015-02-04  Joseph Pecoraro  <pecoraro@apple.com>
+
+        Web Inspector: ES6: Improved Console Support for Symbol Objects
+        https://bugs.webkit.org/show_bug.cgi?id=141173
+
+        Reviewed by Timothy Hatcher.
+
+        * inspector/model/remote-object-expected.txt:
+        * inspector/model/remote-object.html:
+        Update the RemoteObject test to include Symbols.
+
 2015-02-04  Alexey Proskuryakov  <ap@apple.com>
 
         http/tests/misc/detached-frame-console.html is flaky
index 307bce7fbcba96f66ebf85225332c9520ebf03d7..1b3f919ec24258e44ef8b62e3464c793b3d80c6b 100644 (file)
@@ -15,6 +15,24 @@ EXPRESSION: undefined
   "_description": "undefined"
 }
 
+-----------------------------------------------------
+EXPRESSION: Symbol()
+{
+  "_type": "symbol",
+  "_subtype": "symbol",
+  "_objectId": "<filtered>",
+  "_description": "Symbol()"
+}
+
+-----------------------------------------------------
+EXPRESSION: Symbol('test')
+{
+  "_type": "symbol",
+  "_subtype": "symbol",
+  "_objectId": "<filtered>",
+  "_description": "Symbol(test)"
+}
+
 -----------------------------------------------------
 EXPRESSION: true
 {
@@ -1396,7 +1414,7 @@ EXPRESSION: ({a: 1})
 }
 
 -----------------------------------------------------
-EXPRESSION: ({a: 1, b: "string", c :/regex/})
+EXPRESSION: ({a: 1, b: "string", c: /regex/, d: Symbol('sym')})
 {
   "_type": "object",
   "_objectId": "<filtered>",
@@ -1421,6 +1439,11 @@ EXPRESSION: ({a: 1, b: "string", c :/regex/})
         "type": "object",
         "subtype": "regexp",
         "value": "/regex/"
+      },
+      {
+        "name": "d",
+        "type": "symbol",
+        "value": "Symbol(sym)"
       }
     ]
   }
index ea18ff3f52396178cd0142deeb8a6ad39d0e63a9..2ae061a4d09cd86f7295854455b2cf82d7fa93a5 100644 (file)
@@ -14,6 +14,10 @@ function test()
         {expression: "null"},
         {expression: "undefined"},
 
+        // Symbol
+        {expression: "Symbol()"},
+        {expression: "Symbol('test')"},
+
     // Primatives:
 
         // Boolean
@@ -83,7 +87,7 @@ function test()
         // Object
         {expression: "({})"},
         {expression: "({a: 1})"},
-        {expression: "({a: 1, b: \"string\", c :/regex/})"},
+        {expression: "({a: 1, b: \"string\", c: /regex/, d: Symbol('sym')})"},
         {expression: "({a:function a(){}, b:function b(){}, get getter(){}, set setter(v){}})"},
         {expression: "function Foo() {}; new Foo"},
         {expression: "function Bar() { this._x = 5 }; Bar.prototype = {constructor: Bar, get x() {return this._x;}}; new Bar"},
index fb364d9b2561262ea02eff420e5803f7e6260f8b..9cdb38442c8217cf95c38a8a61584adec081bcdc 100644 (file)
@@ -1,3 +1,17 @@
+2015-02-04  Joseph Pecoraro  <pecoraro@apple.com>
+
+        Web Inspector: ES6: Improved Console Support for Symbol Objects
+        https://bugs.webkit.org/show_bug.cgi?id=141173
+
+        Reviewed by Timothy Hatcher.
+
+        * inspector/protocol/Runtime.json:
+        New type, "symbol".
+
+        * inspector/InjectedScriptSource.js:
+        Handle Symbol objects in a few places. They don't have properties
+        and they cannot be implicitly converted to strings.
+
 2015-02-04  Mark Lam  <mark.lam@apple.com>
 
         Undo gardening: Restoring the expected ERROR message since that is not the cause of the bot unhappiness.
index 3e652eceb28b2905adf6d5d974a972d13387f003..147dc8459e66ea6e7b7a0dde236b6125f971143c 100644 (file)
@@ -36,7 +36,7 @@ var Object = {}.constructor;
 
 function toString(obj)
 {
-    return "" + obj;
+    return String(obj);
 }
 
 function isUInt32(obj)
@@ -46,6 +46,11 @@ function isUInt32(obj)
     return "" + (obj >>> 0) === obj;
 }
 
+function isSymbol(obj)
+{
+    return typeof obj === "symbol";
+}
+
 var InjectedScript = function()
 {
     this._lastBoundObjectId = 1;
@@ -59,7 +64,7 @@ InjectedScript.primitiveTypes = {
     undefined: true,
     boolean: true,
     number: true,
-    string: true
+    string: true,
 }
 
 InjectedScript.CollectionMode = {
@@ -200,6 +205,9 @@ InjectedScript.prototype = {
         if (!this._isDefined(object))
             return false;
 
+        if (isSymbol(object))
+            return false;
+
         var collectionMode = InjectedScript.CollectionMode.AllProperties;
         if (ownProperties)
             collectionMode = InjectedScript.CollectionMode.OwnProperties;
@@ -231,9 +239,13 @@ InjectedScript.prototype = {
         var parsedObjectId = this._parseObjectId(objectId);
         var object = this._objectForId(parsedObjectId);
         var objectGroupName = this._idToObjectGroupName[parsedObjectId.id];
+
         if (!this._isDefined(object))
             return false;
 
+        if (isSymbol(object))
+            return false;
+
         var descriptors = [];
         var internalProperties = InjectedScriptHost.getInternalProperties(object);
         if (internalProperties) {
@@ -669,6 +681,9 @@ InjectedScript.prototype = {
         if (this.isPrimitiveValue(obj))
             return null;
 
+        if (isSymbol(obj))
+            return toString(obj);
+
         var subtype = this._subtype(obj);
 
         if (subtype === "regexp")
@@ -940,6 +955,17 @@ InjectedScript.RemoteObject.prototype = {
                 continue;
             }
 
+            // Symbol.
+            if (isSymbol(value)) {
+                var symbolString = toString(value);
+                if (symbolString.length > maxLength) {
+                    symbolString = this._abbreviateString(symbolString, maxLength, true);
+                    preview.lossless = false;
+                }
+                this._appendPropertyPreview(preview, {name: name, type: type, value: symbolString}, propertiesThreshold);
+                return;
+            }
+
             // Object.
             var property = {name: name, type: type};
             var subtype = injectedScript._subtype(value);
index 7ffdb786fc9b0c1d20365cd461e50ae4f34100e4..7e09636f8ce5146802d37601e2358dd23416e673 100644 (file)
@@ -12,7 +12,7 @@
             "type": "object",
             "description": "Mirror object referencing original JavaScript object.",
             "properties": [
-                { "name": "type", "type": "string", "enum": ["object", "function", "undefined", "string", "number", "boolean"], "description": "Object type." },
+                { "name": "type", "type": "string", "enum": ["object", "function", "undefined", "string", "number", "boolean", "symbol"], "description": "Object type." },
                 { "name": "subtype", "type": "string", "optional": true, "enum": ["array", "null", "node", "regexp", "date", "error", "map", "set", "weakmap"], "description": "Object subtype hint. Specified for <code>object</code> type values only." },
                 { "name": "className", "type": "string", "optional": true, "description": "Object class (constructor) name. Specified for <code>object</code> type values only." },
                 { "name": "value", "type": "any", "optional": true, "description": "Remote object value (in case of primitive values or JSON values if it was requested)." },
@@ -26,7 +26,7 @@
             "type": "object",
             "description": "Object containing abbreviated remote object value.",
             "properties": [
-                { "name": "type", "type": "string", "enum": ["object", "function", "undefined", "string", "number", "boolean"], "description": "Object type." },
+                { "name": "type", "type": "string", "enum": ["object", "function", "undefined", "string", "number", "boolean", "symbol"], "description": "Object type." },
                 { "name": "subtype", "type": "string", "optional": true, "enum": ["array", "null", "node", "regexp", "date", "error", "map", "set", "weakmap"], "description": "Object subtype hint. Specified for <code>object</code> type values only." },
                 { "name": "description", "type": "string", "optional": true, "description": "String representation of the object." },
                 { "name": "lossless", "type": "boolean", "description": "Determines whether preview is lossless (contains all information of the original object)." },
@@ -40,7 +40,7 @@
             "type": "object",
             "properties": [
                 { "name": "name", "type": "string", "description": "Property name." },
-                { "name": "type", "type": "string", "enum": ["object", "function", "undefined", "string", "number", "boolean", "accessor"], "description": "Object type." },
+                { "name": "type", "type": "string", "enum": ["object", "function", "undefined", "string", "number", "boolean", "symbol", "accessor"], "description": "Object type." },
                 { "name": "subtype", "type": "string", "optional": true, "enum": ["array", "null", "node", "regexp", "date", "error", "map", "set", "weakmap"], "description": "Object subtype hint. Specified for <code>object</code> type values only." },
                 { "name": "value", "type": "string", "optional": true, "description": "User-friendly property value string." },
                 { "name": "valuePreview", "$ref": "ObjectPreview", "optional": true, "description": "Nested value preview." }
index 301dfb464d42f1cb6f4ef44f0a0bc8e4143d9be5..647a30ffa0e39e5d46a10e4e70f74b6eacc0ec8a 100644 (file)
@@ -1,3 +1,20 @@
+2015-02-04  Joseph Pecoraro  <pecoraro@apple.com>
+
+        Web Inspector: ES6: Improved Console Support for Symbol Objects
+        https://bugs.webkit.org/show_bug.cgi?id=141173
+
+        Reviewed by Timothy Hatcher.
+
+        * UserInterface/Protocol/RemoteObject.js:
+        (WebInspector.RemoteObject):
+        (WebInspector.RemoteObject.prototype._isSymbol):
+        Symbols have an objectId because it is a non-primitive that cannot be passed
+        by value, however it cannot have properties, so handle some cases.
+
+        * UserInterface/Views/LogContentView.css:
+        (.console-formatted-symbol):
+        Give Symbol's their own color.
+
 2015-02-04  Nikita Vasilyev  <nvasilyev@apple.com>
 
         Web Inspector: Insertion bar (caret) is hidden behind the placeholder text in the style editor
index 439aa1ed9e39f7de0382649bc791639d13b94d1c..cad32a6a82e957b80d866c499c70ad46b4332545 100644 (file)
@@ -36,7 +36,7 @@ WebInspector.RemoteObject = function(objectId, type, subtype, value, description
         // handle
         this._objectId = objectId;
         this._description = description;
-        this._hasChildren = true;
+        this._hasChildren = type !== "symbol";
         this._preview = preview;
     } else {
         // Primitive or null object.
@@ -134,7 +134,7 @@ WebInspector.RemoteObject.prototype = {
 
     _getProperties: function(ownProperties, ownAndGetterProperties, callback)
     {
-        if (!this._objectId) {
+        if (!this._objectId || this._isSymbol()) {
             callback([]);
             return;
         }
@@ -188,7 +188,7 @@ WebInspector.RemoteObject.prototype = {
 
     setPropertyValue: function(name, value, callback)
     {
-        if (!this._objectId) {
+        if (!this._objectId || this._isSymbol()) {
             callback("Can't set a property of non-object.");
             return;
         }
@@ -223,6 +223,11 @@ WebInspector.RemoteObject.prototype = {
         }
     },
 
+    _isSymbol: function()
+    {
+        return this.type === "symbol";
+    },
+
     isCollectionType: function()
     {
         return this.subtype === "map" || this.subtype === "set" || this.subtype === "weakmap";
index f0519e54e1684b6578044c249f50598c840bc5df..1e9fbe8fe58dfe65c18bf37851bef8a1e89f0d45 100644 (file)
     color: rgb(255, 88, 0);
 }
 
+.console-formatted-symbol {
+    color: rgb(63, 169, 156);
+}
+
 .console-formatted-null, .console-formatted-undefined {
     color: rgb(128, 128, 128);
 }