win32com.client.Dispatch returns CLSID different than makepy

Stefano Masini stefano at stefanomasini.com
Mon Mar 8 09:05:09 EST 2004


Hi Markus, thanks for your help.

I dug deeper into the makepy/gencache stuff and I found a way
to solve my problem. I think it may apply to yours as well.
I'm gonna describe the details of what I learned, hoping to be helpful
and not too much boring.

Basically I compared my application (Adobe InDesign) with one that is
working, Microsoft Word. For the former, Dispatch only returns dumb
objects, while for the latter, it correctly returns instances of the
makepy generated code.

I found the ultimate responsible for this behaviour is makepy itself.

When __WrapDispatch is called, the gencache module checks into a 
dictionary called clsidToTypelib (defined as global) to find the
required CLSID. Of course in the case of Adobe InDesign, the required
CLSID is not there, so gencache returns None, and __WrapDispatch falls
back to returning dynamic dumb objects.

clsidToTypelib is stored as a pickled file called 'dicts.dat' in the
directory 'gen_py', together with the makepy generated files. And it
is updated/managed by makepy itself.

makepy fills up this dictionary whenever a new module is compiled and
it does so by looking into a few dictionaries that are defined inside
the module itself. More specifically these are: CLSIDToClassMap,
CLSIDToPackageMap, VTablesToPackageMap and VTablesToClassMap.

The first one is broken in the case of Adobe InDesign. It only
contains one CLSID, when it should instead contain one CLSID for each
class defined in the InDesign API.

I checked the code responsible for the creation of this dictionary, and
it is the module genpy.py around line 850 (for python 2.3), pasted
here:

print 'CLSIDToClassMap = {'
for item in oleItems.values():
  if item is not None and item.bWritten and item.bIsDispatch:
    print "\t'%s' : %s," % (str(item.clsid), item.python_name)
print '}'

The for loop goes through the keys of the dictionary oleItems, and
only those that satisfy some conditions are printed in the dictionary
(the generated code is captured on stdout here).
Through some convenience prints, I found out that the CLSIDs needed by
my application are indeed present in oleItems, but for some reason the
boolean value item.bIsDispatch is set to False, and the if condition
fails.

I did not investigate further. I don't know how the oleItems
dictionary is built, nor what the bIsDispatch flag means exactly.
But I tried hacking the code and placing a crude 
item.bIsDispatch = True
just before the if statement, and it WORKS!

Just by adding this line genpy was able to produce a full blown
dictionary and now all the required CLSID's get registered. When I
call Dispatch now I do obtain the static code, and not the dumb object
anymore.

Only problem is: I don't fully understand why this works, and most
importantly, why that flag was not set to begin with. Is it a problem
in the implementation of the COM api by the Adobe guys, or is it a bug
in the python com implementation?

Btw, I don't think this hack is required on every machine that my
application is gonna be working on. I think it should be possible to
rename the generated code to something more decent and include it in
the source code of my application. This way I should be able to work
with a clean python installation.

Well, I hope this helps, and thank you again for the advice.

If anybody else knows this stuff, I would appreciate any insight.

- stefano


Markus Wankus <markus_wankusGETRIDOFALLCAPS at hotmail.com> wrote in message news:<Gen2c.16985$JZ6.592577 at news20.bellglobal.com>...
> This sounds like a problem I ran into that I was never able to figure
> out either.  Mark Hammond says there is nothing that can be done about
> it, but if you jump through some manual hoops you may be able to get it
> to work.
> 
> For more info, Google for "solidworks python win32com" in the Google
> "groups", and click the first hit you get.  Or, if you don't mind long 
> URL's:
> 
> http://groups.google.com/groups?hl=en&lr=&ie=UTF-8&oe=UTF-8&q=solidworks+python+win32com&sa=N&tab=wg
> 
> HTH.
> Markus
>



More information about the Python-list mailing list