advanced.html revision 16a8d09569a2ebd598cef72fa605be6fb4563607
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<html>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<!-- ***** BEGIN LICENSE BLOCK *****
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - Version: MPL 1.1/GPL 2.0/LGPL 2.1
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith -
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - The contents of this file are subject to the Mozilla Public License Version
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - 1.1 (the "License"); you may not use this file except in compliance with
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - the License. You may obtain a copy of the License at
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - http://www.mozilla.org/MPL/
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith -
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - Software distributed under the License is distributed on an "AS IS" basis,
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - for the specific language governing rights and limitations under the
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - License.
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly -
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - The Original Code is PyXPCOM.
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly -
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - The Initial Developer of the Original Code is
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - ActiveState Tool Corporation.
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - Portions created by the Initial Developer are Copyright (C) 2000-2001
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - the Initial Developer. All Rights Reserved.
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith -
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - Contributor(s):
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith -
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - Alternatively, the contents of this file may be used under the terms of
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - either the GNU General Public License Version 2 or later (the "GPL"), or
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - in which case the provisions of the GPL or the LGPL are applicable instead
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith - of those above. If you wish to allow use of your version of this file only
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - under the terms of either the GPL or the LGPL, and not to allow others to
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - use your version of this file under the terms of the MPL, indicate your
819e90d415ed17d59af3a247b2ad9d6feb0c21b5Luke Smith - decision by deleting the provisions above and replace them with the notice
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - and other provisions required by the LGPL or the GPL. If you do not delete
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - the provisions above, a recipient may use your version of this file under
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - the terms of any one of the MPL, the GPL or the LGPL.
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly -
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly - ***** END LICENSE BLOCK ***** -->
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<head>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<meta http-equiv="Content-Type" content="text/html; charset=windows-1252">
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<meta name="GENERATOR" content="Microsoft FrontPage 4.0">
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<meta name="ProgId" content="FrontPage.Editor.Document">
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<title>Python XPCOM Advanced Topics</title>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly</head>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<body>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<h1>Python XPCOM Advanced Topics</h1>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<p>This document contains a series of tidbits that don't fit
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithanywhere else. As the Python XPCOM Package documentation matures, most of
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smiththese topics will have another home.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<h2>XPCOM Services</h2>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>An XPCOM service is simply a singleton registered by name.&nbsp; Python has
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithfull support for both using and implementing XPCOM services.&nbsp; To use a
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyservice, use <i>xpcom.components.services</i> just like the JavaScript
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellycounterpart.&nbsp; There is nothing special about implementing a service in
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny DonnellyPython; see the standard XPCOM documentation on services for more information.</p>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<h2>nsIVariant</h2>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<p>There is (almost) full support for <i>nsIVariant</i>.&nbsp; Any <i>nsIVariant</i>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyparameters will automatically be translated to and from regular Python objects
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellygiving, in effect, a multi-type parameter.&nbsp; This should be automatic, so
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellythere is not much else to say!&nbsp; Note that if you really want, you can
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellycreate and pass your own <i>nsIVariant</i> object instead of a regular Python
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyobject, thereby allowing explicit control over the type of variant created.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<h2>nsISupports Primitives.</h2>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>There is a set of interfaces described in <i>nsISupportsPrimitives.idl</i>, which I
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyterm collectively the <i>nsISupports Primitives Interfaces</i>.&nbsp; These
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithare a set of interfaces a component can support to allow automatic conversion to
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithand from many basic types.&nbsp; For example, an interface can define that it
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithsupports the <i>nsISupportsCString</i> interface, and this could be used by any
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithprogram that wishes to get a string representation of the object.&nbsp; If an
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithinterface wishes to expose itself as a &quot;boolean value&quot;, it may choose
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithto support the <i>nsISupportsPRBool</i> interface.</p>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<p>When you call an XPCOM object (i.e., you have an XPCOM interface you are
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellycalling), you can use
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellythe builtin functions <i>str()</i>, <i>int()</i>, <i>long()</i> etc., on the
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyobject<i>.</i>&nbsp; In the
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellycase of <i>str()</i>, if the object does not support the <i>nsISupportsCString</i>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyor <i>nsISupportsString</i> interfaces, the default string <i>str()</i> for the
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyobject will be returned (i.e., what is normally returned for most XPCOM objects -
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellysupport for these interface is not very common!).&nbsp; In the case of the numeric functions, a <i>ValueError</i>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyexception will be raised if the objects do not support any interface that can be
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithused for the conversion.&nbsp;<i>ValueError</i> is used instead of <i>TypeError</i>,
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithas the type itself (i.e., an XPCOM object) can sometimes be used in this context -
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithhence it is the specific <i>value</i> of the object that is the problem.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>The use of <i>repr()</i> on an XPCOM interface object prevents support
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithattempts for these interfaces, and allows you to see the
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith&quot;real&quot; object, rather than what the object wants you to see!</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>When you implement an XPCOM object, you have two choices for implementation
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithof these interfaces:</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<ul>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith <li>You can explicitly handle these interfaces like any other interface.&nbsp;
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith In this case, you have full control.&nbsp; However, if you
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith implement only one of these standard interfaces, then you are only
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith overriding the default behavior for that specific interface - all other
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith interfaces not explicitly listed in your class will still get the behavior
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith described below.<br>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith </li>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith <li>If your class does not define support for these interfaces, the framework
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith will use standard Python class semantics to implement them - i.e., if your
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith class provides a <i>__str__</i> method, it will be used to implement <i>nsISupportsCString</i>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith and <i>nsISupportsString</i>, if you provide <i>__int__</i>, <i>__long__</i>,
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith <i>__float__</i> etc., methods, they will be used to implement the numeric
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith interfaces.&nbsp; If your class defines no such special methods, then the <i>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith QueryInterface()</i> for those interfaces fails (rather than the QI succeeding
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith and the operation to fetch the data failing).</li>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith</ul>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<blockquote>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>This allows for an interesting feature that would not normally be
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithpossible.&nbsp; Consider Python code that does a <i>str()</i> on an&nbsp; XPCOM
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithinterface, and where the XPCOM interface itself is implemented in Python and
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithprovides a <i>__str__</i> method.&nbsp; The <i>str()</i> on the original
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithinterface queries for the <i>nsISupportsCString</i> interface.&nbsp; The
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke SmithPython implemented object responds to this interface and delegates to the <i>__str__</i>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithmethod. At the end of all this, <i>str()</i> returns the same result
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithas if the objects were native Python objects with no XPCOM layer in between.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith</blockquote>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<h2>Enumerators</h2>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>The primary enumerator used by XPCOM is <i>nsISimpleEnumerator</i>.
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke SmithAlthough the Python XPCOM package has full support for <i>nsIEnumerator</i>,
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithsince this interface is not &quot;scriptable&quot;, you should avoided using it in interfaces
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithyou design.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>When you use <i>nsISimpleEnumerator</i> from Python, the following enhancements
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithare available:</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<ul>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith <li>The <i>GetNext()</i> method takes an optional IID as a parameter. If
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith this is specified, the returned object will be of this interface.&nbsp; This
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith prevents the manual <i>QueryInterface()</i> generally required from other
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith languages.</li>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith <li>There is a <i>FetchBlock(num, [iid])</i> method, which fetches the
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith specified number of elements in one operation and returns a Python
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith list. This can be useful for large enumerator sets, so the loop
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith iterating the elements runs at full C++ speed.</li>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith</ul>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p><i>nsIEnumerator</i> has similar enhancements.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>When implementing a Python XPCOM object, the Python class <i>xpcom.server.enumerator.SimpleEnumerator()</i>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithcan be used.&nbsp; You can pass a standard Python sequence (list, etc), and it
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithwill be correctly wrapped in an <i>nsISimpleEnumerator</i> interface.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<h2>Files</h2>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>The Python XPCOM package provides an <i> xpcom.file</i> module.&nbsp; This implements
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smitha Python-like file object on top of the XPCOM/Mozilla stream interfaces.&nbsp;
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke SmithWhen run from within the Mozilla environment, this allows you to open almost any
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke SmithURL supported by Mozilla (including &quot;chrome://&quot; etc.,).</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>See this module for more information, including test code.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<h2>XPCOM Object Identity</h2>
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnelly<p>XPCOM has defined rules for object identity and for how objects must behave
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyin their <i> QueryInterface()</i> implementations.&nbsp; The Python XPCOM framework
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellymanages this for you; your code can return new Python instances etc., when
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellyresponding to new interfaces, and the framework itself will ensure the XPCOM
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellysemantics are followed.&nbsp; Critically, the framework provides no mechanism
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithfor breaking these rules.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<h2>Policies</h2>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>The Python XPCOM framework has the concept of &quot;policies&quot; that
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithdefine how XPCOM semantics are mapped to Python objects.&nbsp; It is the policy
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smiththat implements delegation of <i> QueryInterface()</i>, translates property
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithreferences into direct property references, and failing that, &quot;get_name&quot;
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithand &quot;set_name&quot; calls, decides how to handle exceptions in the
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithcomponent, and so on.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith<p>The default policy is very flexible and suitable for most purposes.
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny DonnellyIndeed, the Komodo project has never had to implement a custom policy.
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny DonnellyHowever, you should be aware the feature exists should you wish to do some
cf6c1ae1ed15095f8dc269bb9d7a373a1b87990eJenny Donnellybizarre things, such as using Python as a bridge between XPCOM and some other
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smithcomponent technology.</p>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith</body>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith</html>
68dfd2985f43ea9d8de9e52fa68ab5274917c045Luke Smith