> > After doing some searching on the web, I had (naively?) thought perhaps
> > the answer might be creating a type library that defines the interface.
> > ...
> > Am I going down the wrong path with this or would it actually help?
>
> I don't honestly know.  I'm dubious that it will help, because no matter
> how you describe it, a Python COM server must ALWAYS be called with late
> binding.
 
Creating a type library for my COM server seems to have fixed the problem.
After setting up VBA to use the type library (Tools->References...), I can
now use either variables or constants for the input-only parameters and the
input/output parameters are still set correctly.
 
However, there are some side effects:
 
1) When using the COM server without the type library, I was returning a
tuple with the return value of the function (in my case, an error code) as
the first element.  With the type library, this value must be the last
element (because the [out, retval] parameter in the IDL file must be last to
prevent a compile error?).  Not a big deal but it does mean going through
the existing code and making sure I have the returned values in the right
order.
 
2) VBA was giving me an error like "Expecting 3 return values, got: 2"
whenever a function contained an [in, out] parameter.  It looks like the
extra parameter it is looking for is the HRESULT signifying the success of
the call itself, because if I insert a 0 at the beginning of my returned
tuple the problem goes away but any other value causes an error saying the
method call failed.  I'm guessing this is an error in my code, because I
don't think I'm supposed to be setting this value myself.  Any hints as to
why I would be getting this error?
 
I've appended the code I am using for my tests.  To register the type
library and COM server, I use the same code found in the pippo_server.py
example that is distributed with Python-win32.
 

--------- IDL File Begin ---------
// TestLib.idl : IDL source for a COM object testing the type library
//
 
import "oaidl.idl";
import "ocidl.idl";
    [
        object,
        uuid(51B3EE2D-8759-4117-BF94-ACD1AAAD8553)
    ]
    interface ITestLib : IUnknown
    {
        HRESULT Method1([in] long in1, [in, out] long *inout1, [in] long in2,
                [in, out] long *inout2, [out, retval] long *val);
        HRESULT Method2([out, retval] long *val);
        HRESULT Method3([in] long in1, [out, retval] long *val);
        HRESULT Method4([in] long in1, [in, out] long *inout1,
                [out, retval] long *val);
        [propget]HRESULT MyProp1([out, retval] long *pVal);
        [propput]HRESULT MyProp1([in] long pVal);
        [propget]HRESULT TESTLIB_CONSTANT([out, retval] long *pVal);
    };
 
[
    uuid(AA8220B6-69FE-4e3d-827F-06A6A63B5887),
    version(1.0),
    helpstring("TestLibServer 1.0 Type Library")
]
library LibTest
{
    importlib("stdole32.tlb");
    importlib("stdole2.tlb");
 
    [
        uuid(5A1B4C64-4C93-434c-8DC4-432667EB58FA),
        helpstring("TestLib Class")
    ]
    coclass Server
    {
        [default] interface ITestLib;
    };
};
--------- IDL File End ---------
 
--------- Python Code Begin ---------
 
class CTestLib:
    #
    # COM declarations   
    #
    _reg_clsid_ = "{05AC1CCE-3F9B-4d9a-B0B5-DFE8BE45AFA8}"
    _reg_desc_ = "Type Library Test Server"
    _reg_progid_ = "LibTest.Server"
 
    ### Link to typelib
    _typelib_guid_ = '{AA8220B6-69FE-4e3d-827F-06A6A63B5887}'
    _typelib_version_ = 1, 0
    _com_interfaces_ = ['ITestLib']
 
    TESTLIB_CONSTANT = 13
 
    def __init__(self):
        self.MyProp1 = 10
 
    def Method1(self, in1, inout1, in2, inout2 ):
        retVal = 0
        if( in1 != 0 ):
            new_inout1 = in1 * 10
            new_inout2 = in2 * 10
        else:
            retVal = -1
            new_inout1 = inout1
            new_inout2 = inout2
        return( 0, new_inout1, new_inout2, retVal )
 
    def Method2(self):
        retVal = -11
        return( retVal )
 
    def Method3(self, in1):
        retVal = -21
        return( retVal )
 
    def Method4(self, in1, inout1):
        new_inout1 = -31
        retVal = -41
        return( 0, new_inout1, retVal )
 
--------- Python Code End ---------



CONFIDENTIAL AND PRIVILEGED INFORMATION NOTICE

This e-mail, and any attachments, may contain information that
is confidential, subject to copyright, or exempt from disclosure.
Any unauthorized review, disclosure, retransmission, 
dissemination or other use of or reliance on this information 
may be unlawful and is strictly prohibited.  

AVIS D'INFORMATION CONFIDENTIELLE ET PRIVILÉGIÉE

Le présent courriel, et toute pièce jointe, peut contenir de 
l'information qui est confidentielle, régie par les droits 
d'auteur, ou interdite de divulgation. Tout examen, 
divulgation, retransmission, diffusion ou autres utilisations 
non autorisées de l'information ou dépendance non autorisée 
envers celle-ci peut être illégale et est strictement interdite.
_______________________________________________
Python-win32 mailing list
Python-win32@python.org
http://mail.python.org/mailman/listinfo/python-win32

Reply via email to