You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
ORPA-pyOpenRPA/Resources/WPy64-3720/python-3.7.2.amd64/Lib/site-packages/comtypes/client/_generate.py

192 lines
6.9 KiB

import types
import os
import sys
import comtypes.client
import comtypes.tools.codegenerator
import logging
logger = logging.getLogger(__name__)
if os.name == "ce":
# Windows CE has a hard coded PATH
# XXX Additionally there's an OEM path, plus registry settings.
# We don't currently use the latter.
PATH = ["\\Windows", "\\"]
else:
PATH = os.environ["PATH"].split(os.pathsep)
def _my_import(fullname):
# helper function to import dotted modules
import comtypes.gen
if comtypes.client.gen_dir \
and comtypes.client.gen_dir not in comtypes.gen.__path__:
comtypes.gen.__path__.append(comtypes.client.gen_dir)
return __import__(fullname, globals(), locals(), ['DUMMY'])
def _name_module(tlib):
# Determine the name of a typelib wrapper module.
libattr = tlib.GetLibAttr()
modname = "_%s_%s_%s_%s" % \
(str(libattr.guid)[1:-1].replace("-", "_"),
libattr.lcid,
libattr.wMajorVerNum,
libattr.wMinorVerNum)
return "comtypes.gen." + modname
def GetModule(tlib):
"""Create a module wrapping a COM typelibrary on demand.
'tlib' must be an ITypeLib COM pointer instance, the pathname of a
type library, or a tuple/list specifying the arguments to a
comtypes.typeinfo.LoadRegTypeLib call:
(libid, wMajorVerNum, wMinorVerNum, lcid=0)
Or it can be an object with _reg_libid_ and _reg_version_
attributes.
A relative pathname is interpreted as relative to the callers
__file__, if this exists.
This function determines the module name from the typelib
attributes, then tries to import it. If that fails because the
module doesn't exist, the module is generated into the
comtypes.gen package.
It is possible to delete the whole comtypes\gen directory to
remove all generated modules, the directory and the __init__.py
file in it will be recreated when needed.
If comtypes.gen __path__ is not a directory (in a frozen
executable it lives in a zip archive), generated modules are only
created in memory without writing them to the file system.
Example:
GetModule("shdocvw.dll")
would create modules named
comtypes.gen._EAB22AC0_30C1_11CF_A7EB_0000C05BAE0B_0_1_1
comtypes.gen.SHDocVw
containing the Python wrapper code for the type library used by
Internet Explorer. The former module contains all the code, the
latter is a short stub loading the former.
"""
pathname = None
if isinstance(tlib, str):
# pathname of type library
if not os.path.isabs(tlib):
# If a relative pathname is used, we try to interpret
# this pathname as relative to the callers __file__.
frame = sys._getframe(1)
_file_ = frame.f_globals.get("__file__", None)
if _file_ is not None:
directory = os.path.dirname(os.path.abspath(_file_))
abspath = os.path.normpath(os.path.join(directory, tlib))
# If the file does exist, we use it. Otherwise it may
# still be that the file is on Windows search path for
# typelibs, and we leave the pathname alone.
if os.path.isfile(abspath):
tlib = abspath
logger.debug("GetModule(%s)", tlib)
pathname = tlib
tlib = comtypes.typeinfo.LoadTypeLibEx(tlib)
elif isinstance(tlib, (tuple, list)):
# sequence containing libid and version numbers
logger.debug("GetModule(%s)", (tlib,))
tlib = comtypes.typeinfo.LoadRegTypeLib(comtypes.GUID(tlib[0]), *tlib[1:])
elif hasattr(tlib, "_reg_libid_"):
# a COMObject implementation
logger.debug("GetModule(%s)", tlib)
tlib = comtypes.typeinfo.LoadRegTypeLib(comtypes.GUID(tlib._reg_libid_),
*tlib._reg_version_)
else:
# an ITypeLib pointer
logger.debug("GetModule(%s)", tlib.GetLibAttr())
# create and import the module
mod = _CreateWrapper(tlib, pathname)
try:
modulename = tlib.GetDocumentation(-1)[0]
except comtypes.COMError:
return mod
if modulename is None:
return mod
if sys.version_info < (3, 0):
modulename = modulename.encode("mbcs")
# create and import the friendly-named module
try:
mod = _my_import("comtypes.gen." + modulename)
except Exception as details:
logger.info("Could not import comtypes.gen.%s: %s", modulename, details)
else:
return mod
# the module is always regenerated if the import fails
logger.info("# Generating comtypes.gen.%s", modulename)
# determine the Python module name
fullname = _name_module(tlib)
modname = fullname.split(".")[-1]
code = "from comtypes.gen import %s\nglobals().update(%s.__dict__)\n" % (modname, modname)
code += "__name__ = 'comtypes.gen.%s'" % modulename
if comtypes.client.gen_dir is None:
mod = types.ModuleType("comtypes.gen." + modulename)
mod.__file__ = os.path.join(os.path.abspath(comtypes.gen.__path__[0]),
"<memory>")
exec(code, mod.__dict__)
sys.modules["comtypes.gen." + modulename] = mod
setattr(comtypes.gen, modulename, mod)
return mod
# create in file system, and import it
ofi = open(os.path.join(comtypes.client.gen_dir, modulename + ".py"), "w")
ofi.write(code)
ofi.close()
return _my_import("comtypes.gen." + modulename)
def _CreateWrapper(tlib, pathname=None):
# helper which creates and imports the real typelib wrapper module.
fullname = _name_module(tlib)
try:
return sys.modules[fullname]
except KeyError:
pass
modname = fullname.split(".")[-1]
try:
return _my_import(fullname)
except Exception as details:
logger.info("Could not import %s: %s", fullname, details)
# generate the module since it doesn't exist or is out of date
from comtypes.tools.tlbparser import generate_module
if comtypes.client.gen_dir is None:
import io
ofi = io.StringIO()
else:
ofi = open(os.path.join(comtypes.client.gen_dir, modname + ".py"), "w")
# XXX use logging!
logger.info("# Generating comtypes.gen.%s", modname)
generate_module(tlib, ofi, pathname)
if comtypes.client.gen_dir is None:
code = ofi.getvalue()
mod = types.ModuleType(fullname)
mod.__file__ = os.path.join(os.path.abspath(comtypes.gen.__path__[0]),
"<memory>")
exec(code, mod.__dict__)
sys.modules[fullname] = mod
setattr(comtypes.gen, modname, mod)
else:
ofi.close()
mod = _my_import(fullname)
return mod
################################################################
if __name__ == "__main__":
# When started as script, generate typelib wrapper from .tlb file.
GetModule(sys.argv[1])