js/xpconnect/tests/chrome/test_xrayToJS.xul

Wed, 31 Dec 2014 06:09:35 +0100

author
Michael Schloh von Bennewitz <michael@schloh.com>
date
Wed, 31 Dec 2014 06:09:35 +0100
changeset 0
6474c204b198
permissions
-rw-r--r--

Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.

michael@0 1 <?xml version="1.0"?>
michael@0 2 <?xml-stylesheet type="text/css" href="chrome://global/skin"?>
michael@0 3 <?xml-stylesheet type="text/css" href="chrome://mochikit/content/tests/SimpleTest/test.css"?>
michael@0 4 <!--
michael@0 5 https://bugzilla.mozilla.org/show_bug.cgi?id=933681
michael@0 6 -->
michael@0 7 <window title="Mozilla Bug 933681"
michael@0 8 xmlns="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
michael@0 9 <script type="application/javascript" src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"/>
michael@0 10
michael@0 11 <!-- test results are displayed in the html:body -->
michael@0 12 <body xmlns="http://www.w3.org/1999/xhtml">
michael@0 13 <a href="https://bugzilla.mozilla.org/show_bug.cgi?id=933681"
michael@0 14 target="_blank">Mozilla Bug 933681</a>
michael@0 15 </body>
michael@0 16
michael@0 17 <!-- test code goes here -->
michael@0 18 <script type="application/javascript">
michael@0 19 <![CDATA[
michael@0 20
michael@0 21 /** Test for ES constructors on Xrayed globals. **/
michael@0 22 SimpleTest.waitForExplicitFinish();
michael@0 23 const Cu = Components.utils;
michael@0 24 let global = Cu.getGlobalForObject.bind(Cu);
michael@0 25
michael@0 26 simpleConstructors = ['Object', 'Function', 'Array', 'Boolean', 'Date', 'Number',
michael@0 27 'String', 'RegExp', 'Error', 'InternalError', 'EvalError',
michael@0 28 'RangeError', 'ReferenceError', 'SyntaxError', 'TypeError',
michael@0 29 'URIError', 'ArrayBuffer', 'Int8Array', 'Uint8Array',
michael@0 30 'Int16Array', 'Uint16Array', 'Int32Array', 'Uint32Array',
michael@0 31 'Float32Array', 'Float64Array', 'Uint8ClampedArray',
michael@0 32 'WeakMap', 'Map', 'Set'];
michael@0 33
michael@0 34 function go() {
michael@0 35 window.iwin = document.getElementById('ifr').contentWindow;
michael@0 36
michael@0 37 // Test constructors that can be instantiated with zero arguments.
michael@0 38 for (var c of simpleConstructors) {
michael@0 39 ok(iwin[c], "Constructors appear: " + c);
michael@0 40 is(iwin[c], Cu.unwaiveXrays(iwin.wrappedJSObject[c]),
michael@0 41 "we end up with the appropriate constructor: " + c);
michael@0 42 is(Cu.unwaiveXrays(Cu.waiveXrays(new iwin[c]).constructor), iwin[c],
michael@0 43 "constructor property is set up right: " + c);
michael@0 44 is(Object.getPrototypeOf(new iwin[c]),
michael@0 45 Cu.unwaiveXrays(Cu.waiveXrays(iwin[c]).prototype),
michael@0 46 "prototype is correct: " + c);
michael@0 47 is(global(new iwin[c]), iwin, "Got the right global: " + c);
michael@0 48 }
michael@0 49
michael@0 50 // Test Object in more detail.
michael@0 51 var num = new iwin.Object(4);
michael@0 52 is(num.valueOf(), 4, "primitive object construction works");
michael@0 53 is(global(num), iwin, "correct global for num");
michael@0 54 var obj = new iwin.Object();
michael@0 55 obj.foo = 2;
michael@0 56 var withProto = iwin.Object.create(obj);
michael@0 57 is(global(withProto), iwin, "correct global for withProto");
michael@0 58 is(withProto.foo, 2, "Inherits properly");
michael@0 59
michael@0 60 // Test Function.
michael@0 61 var primitiveFun = new iwin.Function('return 2');
michael@0 62 is(global(primitiveFun), iwin, "function construction works");
michael@0 63 is(primitiveFun(), 2, "basic function works");
michael@0 64 var doSetFoo = new iwin.Function('arg', 'arg.foo = 2;');
michael@0 65 is(global(doSetFoo), iwin, "function with args works");
michael@0 66 try {
michael@0 67 doSetFoo(new Object());
michael@0 68 ok(false, "should have thrown while setting property on object");
michael@0 69 } catch (e) {
michael@0 70 ok(!!/denied/.test(e), "Threw correctly: " + e);
michael@0 71 }
michael@0 72 var factoryFun = new iwin.Function('return {foo: 32}');
michael@0 73 is(global(factoryFun), iwin, "proper global for factoryFun");
michael@0 74 is(factoryFun().foo, 32, "factoryFun invokable");
michael@0 75 is(global(factoryFun()), iwin, "minted objects live in the content scope");
michael@0 76
michael@0 77 // Test interface objects that don't actually construct things.
michael@0 78 is(iwin.Math.tan(4.5), Math.tan(4.5), "Math.tan works");
michael@0 79 is(iwin.Math.E, Math.E, "Math.E works");
michael@0 80 var json = JSON.stringify({a: 2, b: 'hi', c: {d: 'there'}});
michael@0 81 is(global(iwin.JSON.parse(json)), iwin, "JSON rehydrated into the right context");
michael@0 82 is(iwin.JSON.stringify(iwin.JSON.parse(json)), json, "JSON composition identity holds");
michael@0 83
michael@0 84 // Test proxies.
michael@0 85 var targetObject = new iwin.Object();
michael@0 86 targetObject.foo = 9;
michael@0 87 var forwardingProxy = new iwin.Proxy(targetObject, new iwin.Object());
michael@0 88 is(global(forwardingProxy), iwin, "proxy global correct");
michael@0 89 is(forwardingProxy.foo, 9, "forwards correctly");
michael@0 90 // NB: COW-implemented proxy handlers are super dangerous, and we should not
michael@0 91 // encourage them.
michael@0 92 var handler = {get: function(target, name) { return name * 2; }, __exposedProps__: {get: 'r'}};
michael@0 93 var doublingProxy = new iwin.Proxy(targetObject, handler);
michael@0 94 is(global(doublingProxy), iwin, "doubling proxy global correct");
michael@0 95 is(doublingProxy[3], 6, "Doubles correctly");
michael@0 96 is(doublingProxy[20], 40, "Doubles correctly");
michael@0 97
michael@0 98 // Test eval.
michael@0 99 var toEval = "({a: 2, b: {foo: 'bar'}, f: function() { return window; }})";
michael@0 100 is(global(iwin.eval(toEval)), iwin, "eval creates objects in the correct global");
michael@0 101 is(iwin.eval(toEval).b.foo, 'bar', "eval-ed object looks right");
michael@0 102 is(iwin.eval(toEval).f(), iwin, "evaled function works right");
michael@0 103
michael@0 104 testDate();
michael@0 105
michael@0 106 // We could also test DataView and Iterator here for completeness, but it's
michael@0 107 // more trouble than it's worth.
michael@0 108
michael@0 109
michael@0 110 SimpleTest.finish();
michael@0 111 }
michael@0 112
michael@0 113 function filterOut(array, props) {
michael@0 114 return array.filter(p => props.indexOf(p) == -1);
michael@0 115 }
michael@0 116
michael@0 117 function testXray(classname, xray, xray2, propsToSkip) {
michael@0 118 propsToSkip = propsToSkip || [];
michael@0 119 let xrayProto = Object.getPrototypeOf(xray);
michael@0 120 let localProto = window[classname].prototype;
michael@0 121 let protoProps = filterOut(Object.getOwnPropertyNames(localProto), propsToSkip).sort();
michael@0 122 let protoMethods = protoProps.filter(name => typeof localProto[name] == 'function' &&
michael@0 123 name != 'constructor');
michael@0 124 ok(protoMethods.length > 0, "Need something to test");
michael@0 125 is(xrayProto, iwin[classname].prototype, "Xray proto is correct");
michael@0 126 is(xrayProto, xray.__proto__, "Proto accessors agree");
michael@0 127 is(Object.getPrototypeOf(xrayProto), iwin.Object.prototype, "proto proto is correct");
michael@0 128 for (let name of protoMethods) {
michael@0 129 info("Running tests for property: " + name);
michael@0 130 ok(xrayProto.hasOwnProperty(name), "proto should have the property as own");
michael@0 131 ok(!xray.hasOwnProperty(name), "instance should not have the property as own");
michael@0 132 let method = xrayProto[name];
michael@0 133 is(typeof method, 'function', "Methods from Xrays are functions");
michael@0 134 is(global(method), window, "Methods from Xrays are local");
michael@0 135 ok(method instanceof Function, "instanceof works on methods from Xrays");
michael@0 136 is(xrayProto[name], method, "Holder caching works properly");
michael@0 137 is(xray[name], method, "Proto props resolve on the instance");
michael@0 138 let local = localProto[name];
michael@0 139 is(method.length, local.length, "Function.length identical");
michael@0 140 if (method.length == 0) {
michael@0 141 is(xray[name]() + "", local.call(xray) + "",
michael@0 142 "Xray and local method results stringify identically");
michael@0 143 is(xray[name]() + "", xray.wrappedJSObject[name]() + "",
michael@0 144 "Xray and waived method results stringify identically");
michael@0 145 }
michael@0 146 }
michael@0 147 is(Object.getOwnPropertyNames(xrayProto).sort().toSource(),
michael@0 148 protoProps.toSource(), "getOwnPropertyNames works");
michael@0 149
michael@0 150 is(xrayProto.constructor, iwin[classname], "constructor property works");
michael@0 151
michael@0 152 xrayProto.expando = 42;
michael@0 153 is(xray.expando, 42, "Xrayed instances see proto expandos");
michael@0 154 is(xray2.expando, 42, "Xrayed instances see proto expandos");
michael@0 155 }
michael@0 156
michael@0 157 function testDate() {
michael@0 158 // toGMTString is handled oddly in the engine. We don't bother to support
michael@0 159 // it over Xrays.
michael@0 160 //
michael@0 161 // We don't yet support self-hosted functions on Xrays. See bug 972987.
michael@0 162 let propsToSkip = ['toGMTString', 'toLocaleString',
michael@0 163 'toLocaleDateString', 'toLocaleTimeString'];
michael@0 164 testXray('Date', new iwin.Date(), new iwin.Date(), propsToSkip);
michael@0 165 }
michael@0 166
michael@0 167 ]]>
michael@0 168 </script>
michael@0 169 <iframe id="ifr" onload="go();" src="http://example.org/tests/js/xpconnect/tests/mochitest/file_empty.html" />
michael@0 170 </window>

mercurial