1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/addon-sdk/source/test/test-xpcom.js Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,223 @@ 1.4 +/* This Source Code Form is subject to the terms of the Mozilla Public 1.5 + * License, v. 2.0. If a copy of the MPL was not distributed with this 1.6 + * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 1.7 + 1.8 +const xpcom = require("sdk/platform/xpcom"); 1.9 +const { Cc, Ci, Cm, Cr } = require("chrome"); 1.10 +const { isCIDRegistered } = Cm.QueryInterface(Ci.nsIComponentRegistrar); 1.11 +const { Class } = require("sdk/core/heritage"); 1.12 +const { Loader } = require("sdk/test/loader"); 1.13 + 1.14 +exports['test Unknown implements nsISupports'] = function(assert) { 1.15 + let actual = xpcom.Unknown(); 1.16 + assert.equal(actual.QueryInterface(Ci.nsISupports), 1.17 + actual, 1.18 + 'component implements nsISupports'); 1.19 +}; 1.20 + 1.21 +exports['test implement xpcom interfaces'] = function(assert) { 1.22 + let WeakReference = Class({ 1.23 + extends: xpcom.Unknown, 1.24 + interfaces: [ 'nsIWeakReference' ], 1.25 + QueryReferent: function() {} 1.26 + }); 1.27 + let weakReference = WeakReference() 1.28 + 1.29 + assert.equal(weakReference.QueryInterface(Ci.nsISupports), 1.30 + weakReference, 1.31 + 'component implements nsISupports'); 1.32 + assert.equal(weakReference.QueryInterface(Ci.nsIWeakReference), 1.33 + weakReference, 1.34 + 'component implements specified interface'); 1.35 + 1.36 + assert.throws(function() { 1.37 + component.QueryInterface(Ci.nsIObserver); 1.38 + }, "component does not implements interface"); 1.39 + 1.40 + let Observer = Class({ 1.41 + extends: WeakReference, 1.42 + interfaces: [ 'nsIObserver', 'nsIRequestObserver' ], 1.43 + observe: function() {}, 1.44 + onStartRequest: function() {}, 1.45 + onStopRequest: function() {} 1.46 + }); 1.47 + let observer = Observer() 1.48 + 1.49 + assert.equal(observer.QueryInterface(Ci.nsISupports), 1.50 + observer, 1.51 + 'derived component implements nsISupports'); 1.52 + assert.equal(observer.QueryInterface(Ci.nsIWeakReference), 1.53 + observer, 1.54 + 'derived component implements supers interface'); 1.55 + assert.equal(observer.QueryInterface(Ci.nsIObserver), 1.56 + observer.QueryInterface(Ci.nsIRequestObserver), 1.57 + 'derived component implements specified interfaces'); 1.58 +}; 1.59 + 1.60 +exports['test implement factory without contract'] = function(assert) { 1.61 + let actual = xpcom.Factory({ 1.62 + get wrappedJSObject() this, 1.63 + }); 1.64 + 1.65 + assert.ok(isCIDRegistered(actual.id), 'factory is regiseterd'); 1.66 + xpcom.unregister(actual); 1.67 + assert.ok(!isCIDRegistered(actual.id), 'factory is unregistered'); 1.68 +}; 1.69 + 1.70 +exports['test implement xpcom factory'] = function(assert) { 1.71 + let Component = Class({ 1.72 + extends: xpcom.Unknown, 1.73 + interfaces: [ 'nsIObserver' ], 1.74 + get wrappedJSObject() this, 1.75 + observe: function() {} 1.76 + }); 1.77 + 1.78 + let factory = xpcom.Factory({ 1.79 + register: false, 1.80 + contract: '@jetpack/test/factory;1', 1.81 + Component: Component 1.82 + }); 1.83 + 1.84 + assert.ok(!isCIDRegistered(factory.id), 'factory is not registered'); 1.85 + xpcom.register(factory); 1.86 + assert.ok(isCIDRegistered(factory.id), 'factory is registered'); 1.87 + 1.88 + let actual = Cc[factory.contract].createInstance(Ci.nsIObserver); 1.89 + 1.90 + assert.ok(actual.wrappedJSObject instanceof Component, 1.91 + "createInstance returnes wrapped factory instances"); 1.92 + 1.93 + assert.notEqual(Cc[factory.contract].createInstance(Ci.nsIObserver), 1.94 + Cc[factory.contract].createInstance(Ci.nsIObserver), 1.95 + "createInstance returns new instance each time"); 1.96 +}; 1.97 + 1.98 +exports['test implement xpcom service'] = function(assert) { 1.99 + let actual = xpcom.Service({ 1.100 + contract: '@jetpack/test/service;1', 1.101 + register: false, 1.102 + Component: Class({ 1.103 + extends: xpcom.Unknown, 1.104 + interfaces: [ 'nsIObserver'], 1.105 + get wrappedJSObject() this, 1.106 + observe: function() {}, 1.107 + name: 'my-service' 1.108 + }) 1.109 + }); 1.110 + 1.111 + assert.ok(!isCIDRegistered(actual.id), 'component is not registered'); 1.112 + xpcom.register(actual); 1.113 + assert.ok(isCIDRegistered(actual.id), 'service is regiseterd'); 1.114 + assert.ok(Cc[actual.contract].getService(Ci.nsIObserver).observe, 1.115 + 'service can be accessed via get service'); 1.116 + assert.equal(Cc[actual.contract].getService(Ci.nsIObserver).wrappedJSObject, 1.117 + actual.component, 1.118 + 'wrappedJSObject is an actual component'); 1.119 + xpcom.unregister(actual); 1.120 + assert.ok(!isCIDRegistered(actual.id), 'service is unregistered'); 1.121 +}; 1.122 + 1.123 + 1.124 +function testRegister(assert, text) { 1.125 + 1.126 + const service = xpcom.Service({ 1.127 + description: 'test about:boop page', 1.128 + contract: '@mozilla.org/network/protocol/about;1?what=boop', 1.129 + register: false, 1.130 + Component: Class({ 1.131 + extends: xpcom.Unknown, 1.132 + get wrappedJSObject() this, 1.133 + interfaces: [ 'nsIAboutModule' ], 1.134 + newChannel : function(aURI) { 1.135 + var ios = Cc["@mozilla.org/network/io-service;1"]. 1.136 + getService(Ci.nsIIOService); 1.137 + 1.138 + var channel = ios.newChannel( 1.139 + "data:text/plain;charset=utf-8," + text, 1.140 + null, 1.141 + null 1.142 + ); 1.143 + 1.144 + channel.originalURI = aURI; 1.145 + return channel; 1.146 + }, 1.147 + getURIFlags: function(aURI) { 1.148 + return Ci.nsIAboutModule.ALLOW_SCRIPT; 1.149 + } 1.150 + }) 1.151 + }); 1.152 + 1.153 + xpcom.register(service); 1.154 + 1.155 + assert.equal(isCIDRegistered(service.id), true); 1.156 + 1.157 + var aboutFactory = xpcom.factoryByContract(service.contract); 1.158 + var about = aboutFactory.createInstance(Ci.nsIAboutModule); 1.159 + 1.160 + var ios = Cc["@mozilla.org/network/io-service;1"]. 1.161 + getService(Ci.nsIIOService); 1.162 + assert.equal( 1.163 + about.getURIFlags(ios.newURI("http://foo.com", null, null)), 1.164 + Ci.nsIAboutModule.ALLOW_SCRIPT 1.165 + ); 1.166 + 1.167 + var aboutURI = ios.newURI("about:boop", null, null); 1.168 + var channel = ios.newChannelFromURI(aboutURI); 1.169 + var iStream = channel.open(); 1.170 + var siStream = Cc['@mozilla.org/scriptableinputstream;1'] 1.171 + .createInstance(Ci.nsIScriptableInputStream); 1.172 + siStream.init(iStream); 1.173 + var data = new String(); 1.174 + data += siStream.read(-1); 1.175 + siStream.close(); 1.176 + iStream.close(); 1.177 + assert.equal(data, text); 1.178 + 1.179 + xpcom.unregister(service); 1.180 + assert.equal(isCIDRegistered(service.id), false); 1.181 +} 1.182 + 1.183 +exports["test register"] = function(assert) { 1.184 + testRegister(assert, "hai2u"); 1.185 +}; 1.186 + 1.187 +exports["test re-register"] = function(assert) { 1.188 + testRegister(assert, "hai2u again"); 1.189 +}; 1.190 + 1.191 +exports["test unload"] = function(assert) { 1.192 + let loader = Loader(module); 1.193 + let sbxpcom = loader.require("sdk/platform/xpcom"); 1.194 + 1.195 + let auto = sbxpcom.Factory({ 1.196 + contract: "@mozilla.org/test/auto-unload;1", 1.197 + description: "test auto", 1.198 + name: "auto" 1.199 + }); 1.200 + 1.201 + let manual = sbxpcom.Factory({ 1.202 + contract: "@mozilla.org/test/manual-unload;1", 1.203 + description: "test manual", 1.204 + register: false, 1.205 + unregister: false, 1.206 + name: "manual" 1.207 + }); 1.208 + 1.209 + assert.equal(isCIDRegistered(auto.id), true, 'component registered'); 1.210 + assert.equal(isCIDRegistered(manual.id), false, 'component not registered'); 1.211 + 1.212 + sbxpcom.register(manual) 1.213 + assert.equal(isCIDRegistered(manual.id), true, 1.214 + 'component was automatically registered on first instance'); 1.215 + loader.unload(); 1.216 + 1.217 + assert.equal(isCIDRegistered(auto.id), false, 1.218 + 'component was atumatically unregistered on unload'); 1.219 + assert.equal(isCIDRegistered(manual.id), true, 1.220 + 'component was not automatically unregistered on unload'); 1.221 + sbxpcom.unregister(manual); 1.222 + assert.equal(isCIDRegistered(manual.id), false, 1.223 + 'component was manually unregistered on unload'); 1.224 +}; 1.225 + 1.226 +require("test").run(exports);