[email protected] schrieb:
> Hi,
>
> there is a bug in comtypes.client.GetBestInterface, as this:
>
> ----
> ## the following code works fine
> from comtypes.client import CreateObject
> wscriptObj = CreateObject("Wscript.Shell",dynamic=True)
> print(wscriptObj.CurrentDirectory)
> wscriptObj.run("cmd.exe /c notepad.exe",0)
>
> # But, when drop the "dynamic=True", it will fail
> from comtypes.client import CreateObject
> wscriptObj = CreateObject("Wscript.Shell")
> print(wscriptObj.CurrentDirectory) # Failed, AttributeError:
> CurrentDirectory
> wscriptObj.run("cmd.exe /c notepad.exe",0)
> ----
>
> Turns out that when progid="Wscript.Shell", in
> comtypes.client.GetBestInterface, the pci.GetClassInfo() returned
> TypeInfo of the default interface IWshShell3, not of the supposed
> CoClass WshShell. GetBestInterface searched IWshShell3, find what it
> implemented - IWshShell2, which has no property CurrentDirectory.
Yes, I see the problem.
>
> So I think here need an if stmt, such as "if (str(ta.guid) == punk.clsid): go
> best interface",
> or, try IDispatch.GetTypeInfo first.
I do not really understand what you mean.
But I have attached a patch for comtypes\client\__init__.py which should fix
the problem.
Index: __init__.py
===================================================================
--- __init__.py (revision 564)
+++ __init__.py (working copy)
@@ -70,18 +70,28 @@
tinfo = pci.GetClassInfo() # TypeInfo for the CoClass
# find the interface marked as default
ta = tinfo.GetTypeAttr()
- for index in range(ta.cImplTypes):
- if tinfo.GetImplTypeFlags(index) == 1:
- break
- else:
- if ta.cImplTypes != 1:
- # Hm, should we use dynamic now?
- raise TypeError("No default interface found")
- # Only one interface implemented, use that (even if
- # not marked as default).
- index = 0
- href = tinfo.GetRefTypeOfImplType(index)
- tinfo = tinfo.GetRefTypeInfo(href)
+ if ta.typekind in (3, 4): # TKIND_INTERFACE, TKIND_DISPATCH
+ # The tinfo that we got is an interface, we use this as
+ # the 'best interface'
+ pass
+ elif ta.typekind == 5: # TKIND_COCLASS
+ # The tinfo describes the coclass. We have to find out
+ # which interfaces this coclass implements and use the
+ # 'best' one.
+ for index in range(ta.cImplTypes):
+ if tinfo.GetImplTypeFlags(index) == 1: # IMPLTYPEFLAG_FDEFAULT
+ # This is the default interface
+ href = tinfo.GetRefTypeOfImplType(index)
+ tinfo = tinfo.GetRefTypeInfo(href)
+ break
+ else:
+ if ta.cImplTypes != 1:
+ # Hm, should we use dynamic now?
+ raise TypeError("No default interface found")
+ # Only one interface implemented, use that (even if
+ # not marked as default).
+ href = tinfo.GetRefTypeOfImplType(0)
+ tinfo = tinfo.GetRefTypeInfo(href)
except comtypes.COMError:
logger.debug("Does NOT implement IProvideClassInfo/IProvideClassInfo2")
try:
------------------------------------------------------------------------------
Download Intel® Parallel Studio Eval
Try the new software tools for yourself. Speed compiling, find bugs
proactively, and fine-tune applications for parallel performance.
See why Intel Parallel Studio got high marks during beta.
http://p.sf.net/sfu/intel-sw-dev
_______________________________________________
comtypes-users mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/comtypes-users