[Tutor] COM Interfaces

Lloyd Kvam pythontutor@venix.com
Mon, 13 May 2002 19:41:06 -0400


I'm not going to be of much help to you.  I've only used Excel, Word,
and my own Python programs as COM objects.  Chapter 12 of "Python Programming
on Win32" discusses IID's.  It also discussesIUnknown and the QueryInterface()
method.  "The pythoncom module is primarily concerned with exposing raw COM
interfaces to Python."  "win32com.client is a set of source files that use the
pythoncom module ot provide additional services..."

Hopefully, someone else will pick up the ball, or you will find what you are
looking for in the win32 documentation.

dominic.fox wrote:

> Lloyd Kvam was kind enough to reply:
> 
> 
>>Python depends on the registry entries to find the COM object it is
>>
> running.
> 
>>The name passed to Dispatch MUST exactly match the name in the registry.
>>
> You
> 
>>can't make it up.
>>
> 
> Well, this is much like creating an object in, say, VBScript or JavaScript
> by passing the progid to CreateObject(). You can't do much with
> multiple-interface objects in JavaScript, to my knowledge; what I was
> wondering was whether PyWin & c. managed to improve on the situation.
> 
> 
>>I suspect that 'MSXML2.DOMDocument30' should be 'MSXML3.DOMDocument30'.
>>
> If you
> 
>>search your registry, you should be able to find the name.
>>
>>To run your VB COM object, you need to get it registered.  Then simply
>>
> pass
> 
>>the name you used to register it to dispatch, just like you did for MSXML.
>>
> 
> I can do this without difficulty for single-interface objects, but not at
> all for dual or multiple interface objects. Yesterday evening I coded up a
> small-ish .dll to try some of these things out with. Getting instances of
> the more conventional objects by progid was a doddle. There didn't seem to
> be any way at all of using the multiple-interface ones.
> 
> Just to clarify: in VB you can do the following:
> 
> Class MyInterface
> 
> Public Sub DoSomethingExciting()
> End Sub
> 
> ---
> 
> Class InheritorTheFirst
> 
> Implements MyInterface
> 
> Private Sub MyInterface_DoSomethingExciting()
> 
>     Msgbox "Wow!"
> 
> End Sub
> 
> ---
> 
> Class InheritorTheSecond
> 
> Implements MyInterface
> 
> Private Sub MyInterface_DoSomethingExciting()
> 
>     Msgbox "Whoopee!"
> 
> End Sub
> 
> ---
> 
> and then...
> 
> Dim MyInstance As MyInterface
> Set MyInstance = New InheritorTheSecond
> MyInstance.DoSomethingExciting
> Set MyInstance = New InheritorTheFirst
> MyInstance.DoSomethingExciting
> 
> ---
> 
> MyInterface is something like an abstract base class, which simply outlines
> in skeleton form the COM interface that the other two classes will use. Just
> to confuse matters, they are allowed to implement as many different
> interfaces as they like; they are also allowed their own 'native' COM
> interface as well. The specifics of how this is implemented escape me, but I
> think it has to do with the way IUnknown and IDispatch are mapped to method
> calls through whatever mechanism it is that VB uses. Whatever: it's ugly,
> and Python is beautiful, so I feel as if I ought to be apologising for
> bringing the matter up at all...
> 
> Now the question is, assuming I have created and registered a .dll
> containing the above, and want to create an object in Python which behaves
> like an instance of InheritorTheSecond, and want Python to know that I can
> call MyInterface's methods on it, can I? If I can, how can I? You only get
> to pass one progid to Dispatch. If it's the progid of MyInterface, you get
> an instance of the base class which doesn't do anything. If it's the progid
> of InheritorTheSecond, the "inherited" or "implemented" member functions are
> invisible and can't be used.
> 
> For my own purposes, it would be easy enough just to eschew this technique;
> or better still, write everything in Python to begin with. But there are
> other libraries out there that I didn't write, can't obtain the source code
> for, and might still want to use. Some of them (like MSHTML, which gives you
> access to the DOM in Internet Explorer HTML documents) use multiple
> interfaces fairly extensively. It would be useful to know whether I can use
> them directly in Python, or whether I'd need to come up with a set of
> simplified "wrapper" classes in VB for them first.
> 
> As an aside, the reason why VB *has* multiple interfaces is that it's a
> statically typed language, which means amongst other things that, as in Java
> and C++, the signatures of method function calls include the types of the
> parameters being supplied (this might come as a surprise to some VB
> programmers of my acquaintance, who use Variants for everything...). So if I
> have a variety of different persistence mechanisms, say, which can all store
> basic plain-text strings, I might want to have a method which writes a given
> string in uppercase to any one of them, without needing to know what the
> underlying mechanism is. If my method looks like this:
> 
> Public Sub writeUppercase( persistenceMechanism as IPersist, stringToWrite
> as String)
> 
>     IPersist.writeString strconv( stringToWrite, vbUpperCase )
> 
> End Sub
> 
> then I can pass it an instance of any class that "implements" IPersist, be
> it a wrapper for database access, textfile access, storing things in cells
> in an Excel worksheet or whatever. In Python, which is dynamically typed,
> all of this is pretty much redundant...although I did read somewhere an
> article by a diehard Smalltalk enthusiast who nevertheless admitted,
> vis-a-vis Java, that programming to interfaces sounded like quite a sensible
> idea...
> 
> Dominic
> 
> 
> 
> _______________________________________________
> Tutor maillist  -  Tutor@python.org
> http://mail.python.org/mailman/listinfo/tutor
> 
> 


-- 
Lloyd Kvam
Venix Corp.
1 Court Street, Suite 378
Lebanon, NH 03766-1358

voice: 
603-443-6155
fax: 
801-459-9582