1 // Copyright 2014 the V8 project authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 // Flags: --harmony-tostring 6 7 var global = this; 8 9 var funs = { 10 Object: [ Object ], 11 Function: [ Function ], 12 String: [ String ], 13 Boolean: [ Boolean ], 14 Number: [ Number ], 15 Date: [ Date ], 16 RegExp: [ RegExp ], 17 Error: [ Error, TypeError, RangeError, SyntaxError, ReferenceError, 18 EvalError, URIError ] 19 } 20 for (f in funs) { 21 for (i in funs[f]) { 22 assertEquals("[object " + f + "]", 23 Array.prototype.toString.call(new funs[f][i]), 24 funs[f][i]); 25 assertEquals("[object Function]", 26 Array.prototype.toString.call(funs[f][i]), 27 funs[f][i]); 28 } 29 } 30 31 32 function testToStringTag(className) { 33 // Using builtin toStringTags 34 var obj = {}; 35 obj[Symbol.toStringTag] = className; 36 assertEquals("[object " + className + "]", 37 Array.prototype.toString.call(obj)); 38 39 // Getter throws 40 obj = {}; 41 Object.defineProperty(obj, Symbol.toStringTag, { 42 get: function() { throw className; } 43 }); 44 assertThrowsEquals(function() { 45 Array.prototype.toString.call(obj); 46 }, className); 47 48 // Getter does not throw 49 obj = {}; 50 Object.defineProperty(obj, Symbol.toStringTag, { 51 get: function() { return className; } 52 }); 53 assertEquals("[object " + className + "]", 54 Array.prototype.toString.call(obj)); 55 56 // Custom, non-builtin toStringTags 57 obj = {}; 58 obj[Symbol.toStringTag] = "X" + className; 59 assertEquals("[object X" + className + "]", 60 Array.prototype.toString.call(obj)); 61 62 // With getter 63 obj = {}; 64 Object.defineProperty(obj, Symbol.toStringTag, { 65 get: function() { return "X" + className; } 66 }); 67 assertEquals("[object X" + className + "]", 68 Array.prototype.toString.call(obj)); 69 70 // Undefined toStringTag should return [object className] 71 var obj = className === "Arguments" ? 72 (function() { return arguments; })() : new global[className]; 73 obj[Symbol.toStringTag] = undefined; 74 assertEquals("[object " + className + "]", 75 Array.prototype.toString.call(obj)); 76 77 // With getter 78 var obj = className === "Arguments" ? 79 (function() { return arguments; })() : new global[className]; 80 Object.defineProperty(obj, Symbol.toStringTag, { 81 get: function() { return undefined; } 82 }); 83 assertEquals("[object " + className + "]", 84 Array.prototype.toString.call(obj)); 85 } 86 87 88 [ 89 "Arguments", 90 "Boolean", 91 "Date", 92 "Error", 93 "Function", 94 "Number", 95 "RegExp", 96 "String" 97 ].forEach(testToStringTag); 98 99 100 function testToStringTagNonString(value) { 101 var obj = {}; 102 obj[Symbol.toStringTag] = value; 103 assertEquals("[object Object]", Array.prototype.toString.call(obj)); 104 105 // With getter 106 obj = {}; 107 Object.defineProperty(obj, Symbol.toStringTag, { 108 get: function() { return value; } 109 }); 110 assertEquals("[object Object]", Array.prototype.toString.call(obj)); 111 } 112 113 114 [ 115 null, 116 function() {}, 117 [], 118 {}, 119 /regexp/, 120 42, 121 Symbol("sym"), 122 new Date(), 123 (function() { return arguments; })(), 124 true, 125 new Error("oops"), 126 new String("str") 127 ].forEach(testToStringTagNonString); 128 129 130 function testArrayToStringPropertyDesc() { 131 var desc = Object.getOwnPropertyDescriptor(Object.prototype, "toString"); 132 assertTrue(desc.writable); 133 assertFalse(desc.enumerable); 134 assertTrue(desc.configurable); 135 } 136 testArrayToStringPropertyDesc(); 137 138 139 function testArrayToStringOwnNonStringValue() { 140 var obj = Object.defineProperty({}, Symbol.toStringTag, { value: 1 }); 141 assertEquals("[object Object]", ([]).toString.call(obj)); 142 } 143 testArrayToStringOwnNonStringValue(); 144 145 146 function testArrayToStringBasic() { 147 assertEquals("1,2,3", [1,2,3].toString()); 148 assertEquals(",,3", [,,3].toString()); 149 } 150 testArrayToStringBasic(); 151 152 153 function testArrayToStringObjectWithCallableJoin() { 154 var obj = { join: function() { return "CallableJoin"; } }; 155 assertEquals("CallableJoin", Array.prototype.toString.call(obj)); 156 } 157 testArrayToStringObjectWithCallableJoin(); 158