[python-win32] Accessing other interfaces of a Dispatch created COM object

Alec Munro alecmunro at gmail.com
Wed Sep 17 21:10:51 CEST 2008


I'm back.

I've taken a crack at rewriting the DLL to export the methods I need
through IDispatch. Unfortunately, what I discovered (and I'm probably
describing this in the wrong way), is that the class is declared
ATL_NO_VTABLE, and as far as I can tell, the third-party app relies on
the interfaces being exported through IDispatch. This means that the
methods suggested here won't work:

http://www.sellsbrothers.com/tools/multidisp/

Or at least the first two.

So I'm back to trying to figure out what might be going wrong in my
attempts to access the current implementation through Python.

I wonder, is there any way to log IDispatch operations? If so, that
might tell me what the third-party operation was doing differently.

I would be happy to hear any other suggestions.

Thanks,

Alec

On Fri, Sep 12, 2008 at 2:28 PM, Alec Munro <alecmunro at gmail.com> wrote:
> (I just noticed my last two responses only went to Mark. They were
> intended for the Mailing List and Tim as well. Sorry for the
> oversight.)
>
> So I just ran some tests, fruitlessly. Here is what I did:
>
>  - Removed all gen_py stuff
>  - Set registry entries for both interfaces to point to the BASICUHI typelib.
>  - Restarted
>  - Use Make_py on BASICUHI typelib
>
>  X: Same error
>
>  - Use Make_py for other typelib
>
>  X: Same error
>
>  - Removed all gen_py stuff
>  - Set registry entries for both interfaces to point to other typelib.
>  - Restarted
>  - Use Make_py for other typelib
>
>  X: Same error
>
>  - Use Make_py for BASICUHI typelib
>
>  X: Same error
>
> What I'm wondering at this point is how I determine what Library it is
> that isn't registered. That might yield some clues, but right now I'm
> pretty much out of ideas, and toying seriously with the idea of
> rewriting the dll to allow it to export the interfaces I need through
> IDispatch.
>
> Thanks again for your time,
>
> Alec
>
>
> On Fri, Sep 12, 2008 at 1:49 PM, Alec Munro <alecmunro at gmail.com> wrote:
>> Hi Mark,
>>
>> Ok, with my first object, everything works as you demonstrated. With
>> my second object (the first one CastTo(,I2)), I get the "Library not
>> Registered" message when I call GetTypeInfo(), which I guess is what
>> you were expecting.
>>
>> As far as Tim's question goes, I looked up the ID for the BasicUHI
>> typelib in the registry, and the path there does indeed point to the
>> BasicUHI file.
>>
>> I've got some ideas for things I can test, for the moment, but if you
>> have any ideas or additional information, I would love to hear it.
>>
>> Thanks again!
>>
>> Alec
>>
>>
>> On Wed, Sep 10, 2008 at 10:35 PM, Alec Munro <alecmunro at gmail.com> wrote:
>>> Thanks Mark, Tim!
>>>
>>> Lots of excellent information there for someone as COM-confused as I am. :)
>>>
>>> I'll try out your suggestions tomorrow, to see what I find, but for
>>> now, here's a little more information on our situation.
>>>
>>> We use a third-party solution for testing our products. This solution
>>> requires us to create a COM dll with a class implementing specific
>>> interfaces (at least I1, any others are optional). The third party
>>> defines the interfaces, we just provide implementations for them. The
>>> third party provides us with their testing solution itself, as well as
>>> an SDK for developing the dll.
>>>
>>> In order to use the dll, we do register it manually using regsvr32.
>>> Any other registrations I would assume are performed by the installers
>>> from the third party.
>>>
>>> We've been using this for several years now (I only took over
>>> maintenance on the project 6 months ago), but this is the first time
>>> we are trying to access the dll ourselves, so it's fairly new
>>> territory.
>>>
>>> Hopefully that makes sense, thanks again,
>>>
>>> Alec
>>>
>>> On Wed, Sep 10, 2008 at 8:59 PM, Mark Hammond <mhammond at skippinet.com.au> wrote:
>>>> I'm still a little lost too, but:
>>>>
>>>>>  * I maintain a dll that defines a class that implements I1 and I2. I
>>>>> use regsvr to register this dll.
>>>>>  * I1 and I2 come from a third party, and in order for my dll to work
>>>>> properly, it has to implement them (actually I2 is optional).
>>>>>  * I don't know how I1 and I2 are registered.
>>>>
>>>> I don't understand the above.  If you maintain the class that implements I1
>>>> and I2 how can:
>>>>
>>>> * they come from a 3rd party - either you maintain them, or they do?
>>>> * Surely you know how they are registered?
>>>>
>>>>
>>>>> I do know that if I use
>>>>> the COM browser, I can go to Registered Type Libraries, find one with
>>>>> the typelibname that is associated with my CastTo created objects,
>>>>> which has "Type Library" underneath it, and underneath that are
>>>>> entries for I1, I2, several related interfaces, and a variety of
>>>>> coclasses. Like this:
>>>>>  - TypeLibName 1.0 TypeLibrary
>>>>>  -- IID: {00..00}
>>>>>  -- Type Library
>>>>>  --- I1 - Dispatch
>>>>>  --- I2 - Dispatch
>>>>>  --- IX - Dispatch
>>>>>  --- CX - CoClass
>>>>>
>>>>> I've just spent some time hunting through the registry to determine
>>>>> the differences between I1 and I2.
>>>>
>>>> What I'm guessing is that the GetTypeInfo() and GetTypeLib() calls for the
>>>> other dispatch object are failing.  Below is how we expect things to work,
>>>> demonstratrated using for Internet Explorer:
>>>>
>>>>>>> from win32com.client import Dispatch
>>>>>>> d=Dispatch("InternetExplorer.Application")
>>>>>>> d=d._oleobj_
>>>>>>> d.GetTypeInfoCount()
>>>> 1
>>>>>>> d.GetTypeInfo(0)
>>>> <PyITypeInfo at 0x00D1B038 with obj at 0x0025285C>
>>>>>>> i=d.GetTypeInfo(0)
>>>>>>> tlb, index=i.GetContainingTypeLib()
>>>>>>> tlb.GetLibAttr()
>>>> (IID('{EAB22AC0-30C1-11CF-A7EB-0000C05BAE0B}'), 0, 1, 1, 1, 8)
>>>>>>>
>>>>
>>>> Which is the GUID, version, locale etc information (a TLIBATTR structure)
>>>> for the typelib, and you will find this in the registry.  It sounds like
>>>> this works for one of your objects and fails for the other (well - "fails"
>>>> might mean that the call works, but returns a GID and version info for a
>>>> typelib that isn't registered - ie, attempting to load that typelib would
>>>> fail.)  ie, you would also need the following to work:
>>>>
>>>>>>> guid, lcid, syskind, majver, minver, flags = tlb.GetLibAttr()
>>>>>>> import pythoncom
>>>>>>> pythoncom.LoadRegTypeLib(guid, majver, minver, lcid)
>>>> <PyITypeLib at 0x00D1B038 with obj at 0x00254530>
>>>>>>> _.GetDocumentation(1)
>>>> (u'DWebBrowserEvents', u'Web Browser Control Events (old)', 0, None)
>>>>>>>
>>>>
>>>> Hope this helps,
>>>>
>>>> Mark
>>>>
>>>>
>>>
>>
>


More information about the python-win32 mailing list