michael@0: /* This Source Code Form is subject to the terms of the Mozilla Public michael@0: * License, v. 2.0. If a copy of the MPL was not distributed with this michael@0: * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ michael@0: michael@0: const xpcom = require("sdk/platform/xpcom"); michael@0: const { Cc, Ci, Cm, Cr } = require("chrome"); michael@0: const { isCIDRegistered } = Cm.QueryInterface(Ci.nsIComponentRegistrar); michael@0: const { Class } = require("sdk/core/heritage"); michael@0: const { Loader } = require("sdk/test/loader"); michael@0: michael@0: exports['test Unknown implements nsISupports'] = function(assert) { michael@0: let actual = xpcom.Unknown(); michael@0: assert.equal(actual.QueryInterface(Ci.nsISupports), michael@0: actual, michael@0: 'component implements nsISupports'); michael@0: }; michael@0: michael@0: exports['test implement xpcom interfaces'] = function(assert) { michael@0: let WeakReference = Class({ michael@0: extends: xpcom.Unknown, michael@0: interfaces: [ 'nsIWeakReference' ], michael@0: QueryReferent: function() {} michael@0: }); michael@0: let weakReference = WeakReference() michael@0: michael@0: assert.equal(weakReference.QueryInterface(Ci.nsISupports), michael@0: weakReference, michael@0: 'component implements nsISupports'); michael@0: assert.equal(weakReference.QueryInterface(Ci.nsIWeakReference), michael@0: weakReference, michael@0: 'component implements specified interface'); michael@0: michael@0: assert.throws(function() { michael@0: component.QueryInterface(Ci.nsIObserver); michael@0: }, "component does not implements interface"); michael@0: michael@0: let Observer = Class({ michael@0: extends: WeakReference, michael@0: interfaces: [ 'nsIObserver', 'nsIRequestObserver' ], michael@0: observe: function() {}, michael@0: onStartRequest: function() {}, michael@0: onStopRequest: function() {} michael@0: }); michael@0: let observer = Observer() michael@0: michael@0: assert.equal(observer.QueryInterface(Ci.nsISupports), michael@0: observer, michael@0: 'derived component implements nsISupports'); michael@0: assert.equal(observer.QueryInterface(Ci.nsIWeakReference), michael@0: observer, michael@0: 'derived component implements supers interface'); michael@0: assert.equal(observer.QueryInterface(Ci.nsIObserver), michael@0: observer.QueryInterface(Ci.nsIRequestObserver), michael@0: 'derived component implements specified interfaces'); michael@0: }; michael@0: michael@0: exports['test implement factory without contract'] = function(assert) { michael@0: let actual = xpcom.Factory({ michael@0: get wrappedJSObject() this, michael@0: }); michael@0: michael@0: assert.ok(isCIDRegistered(actual.id), 'factory is regiseterd'); michael@0: xpcom.unregister(actual); michael@0: assert.ok(!isCIDRegistered(actual.id), 'factory is unregistered'); michael@0: }; michael@0: michael@0: exports['test implement xpcom factory'] = function(assert) { michael@0: let Component = Class({ michael@0: extends: xpcom.Unknown, michael@0: interfaces: [ 'nsIObserver' ], michael@0: get wrappedJSObject() this, michael@0: observe: function() {} michael@0: }); michael@0: michael@0: let factory = xpcom.Factory({ michael@0: register: false, michael@0: contract: '@jetpack/test/factory;1', michael@0: Component: Component michael@0: }); michael@0: michael@0: assert.ok(!isCIDRegistered(factory.id), 'factory is not registered'); michael@0: xpcom.register(factory); michael@0: assert.ok(isCIDRegistered(factory.id), 'factory is registered'); michael@0: michael@0: let actual = Cc[factory.contract].createInstance(Ci.nsIObserver); michael@0: michael@0: assert.ok(actual.wrappedJSObject instanceof Component, michael@0: "createInstance returnes wrapped factory instances"); michael@0: michael@0: assert.notEqual(Cc[factory.contract].createInstance(Ci.nsIObserver), michael@0: Cc[factory.contract].createInstance(Ci.nsIObserver), michael@0: "createInstance returns new instance each time"); michael@0: }; michael@0: michael@0: exports['test implement xpcom service'] = function(assert) { michael@0: let actual = xpcom.Service({ michael@0: contract: '@jetpack/test/service;1', michael@0: register: false, michael@0: Component: Class({ michael@0: extends: xpcom.Unknown, michael@0: interfaces: [ 'nsIObserver'], michael@0: get wrappedJSObject() this, michael@0: observe: function() {}, michael@0: name: 'my-service' michael@0: }) michael@0: }); michael@0: michael@0: assert.ok(!isCIDRegistered(actual.id), 'component is not registered'); michael@0: xpcom.register(actual); michael@0: assert.ok(isCIDRegistered(actual.id), 'service is regiseterd'); michael@0: assert.ok(Cc[actual.contract].getService(Ci.nsIObserver).observe, michael@0: 'service can be accessed via get service'); michael@0: assert.equal(Cc[actual.contract].getService(Ci.nsIObserver).wrappedJSObject, michael@0: actual.component, michael@0: 'wrappedJSObject is an actual component'); michael@0: xpcom.unregister(actual); michael@0: assert.ok(!isCIDRegistered(actual.id), 'service is unregistered'); michael@0: }; michael@0: michael@0: michael@0: function testRegister(assert, text) { michael@0: michael@0: const service = xpcom.Service({ michael@0: description: 'test about:boop page', michael@0: contract: '@mozilla.org/network/protocol/about;1?what=boop', michael@0: register: false, michael@0: Component: Class({ michael@0: extends: xpcom.Unknown, michael@0: get wrappedJSObject() this, michael@0: interfaces: [ 'nsIAboutModule' ], michael@0: newChannel : function(aURI) { michael@0: var ios = Cc["@mozilla.org/network/io-service;1"]. michael@0: getService(Ci.nsIIOService); michael@0: michael@0: var channel = ios.newChannel( michael@0: "data:text/plain;charset=utf-8," + text, michael@0: null, michael@0: null michael@0: ); michael@0: michael@0: channel.originalURI = aURI; michael@0: return channel; michael@0: }, michael@0: getURIFlags: function(aURI) { michael@0: return Ci.nsIAboutModule.ALLOW_SCRIPT; michael@0: } michael@0: }) michael@0: }); michael@0: michael@0: xpcom.register(service); michael@0: michael@0: assert.equal(isCIDRegistered(service.id), true); michael@0: michael@0: var aboutFactory = xpcom.factoryByContract(service.contract); michael@0: var about = aboutFactory.createInstance(Ci.nsIAboutModule); michael@0: michael@0: var ios = Cc["@mozilla.org/network/io-service;1"]. michael@0: getService(Ci.nsIIOService); michael@0: assert.equal( michael@0: about.getURIFlags(ios.newURI("http://foo.com", null, null)), michael@0: Ci.nsIAboutModule.ALLOW_SCRIPT michael@0: ); michael@0: michael@0: var aboutURI = ios.newURI("about:boop", null, null); michael@0: var channel = ios.newChannelFromURI(aboutURI); michael@0: var iStream = channel.open(); michael@0: var siStream = Cc['@mozilla.org/scriptableinputstream;1'] michael@0: .createInstance(Ci.nsIScriptableInputStream); michael@0: siStream.init(iStream); michael@0: var data = new String(); michael@0: data += siStream.read(-1); michael@0: siStream.close(); michael@0: iStream.close(); michael@0: assert.equal(data, text); michael@0: michael@0: xpcom.unregister(service); michael@0: assert.equal(isCIDRegistered(service.id), false); michael@0: } michael@0: michael@0: exports["test register"] = function(assert) { michael@0: testRegister(assert, "hai2u"); michael@0: }; michael@0: michael@0: exports["test re-register"] = function(assert) { michael@0: testRegister(assert, "hai2u again"); michael@0: }; michael@0: michael@0: exports["test unload"] = function(assert) { michael@0: let loader = Loader(module); michael@0: let sbxpcom = loader.require("sdk/platform/xpcom"); michael@0: michael@0: let auto = sbxpcom.Factory({ michael@0: contract: "@mozilla.org/test/auto-unload;1", michael@0: description: "test auto", michael@0: name: "auto" michael@0: }); michael@0: michael@0: let manual = sbxpcom.Factory({ michael@0: contract: "@mozilla.org/test/manual-unload;1", michael@0: description: "test manual", michael@0: register: false, michael@0: unregister: false, michael@0: name: "manual" michael@0: }); michael@0: michael@0: assert.equal(isCIDRegistered(auto.id), true, 'component registered'); michael@0: assert.equal(isCIDRegistered(manual.id), false, 'component not registered'); michael@0: michael@0: sbxpcom.register(manual) michael@0: assert.equal(isCIDRegistered(manual.id), true, michael@0: 'component was automatically registered on first instance'); michael@0: loader.unload(); michael@0: michael@0: assert.equal(isCIDRegistered(auto.id), false, michael@0: 'component was atumatically unregistered on unload'); michael@0: assert.equal(isCIDRegistered(manual.id), true, michael@0: 'component was not automatically unregistered on unload'); michael@0: sbxpcom.unregister(manual); michael@0: assert.equal(isCIDRegistered(manual.id), false, michael@0: 'component was manually unregistered on unload'); michael@0: }; michael@0: michael@0: require("test").run(exports);