Import mechanism to support multiple Python versions

N

Nicolas Fleury

Hi,
I'm trying to support two Python versions at the same time and I'm
trying to find effective mechanisms to support modules compiled in C++
transparently.

All my code in under a single package. Is it possible to override the
import mechanism only for modules under that package and sub-packages so
that?:

import cppmymodule

would be equivalent to:

if sys.version == "2.4":
import cppmymodule24 as cppmymodule
elif sys.version == "2.3":
import cppmymodule23 as cppmymodule

for all modules under the package and all modules with names beginning
with cpp (or another way to identify them).


I have also third party packages. Is it possible to make a package
point to another folder? For example:

psyco23/...
psyco24/...
psyco/__init__.py => points to psyco23 or psyco24 depending on Python
version used.

Note that I cannot use .pth files or symbolic links, since I would want
the exact same code hierarchy to work with both Python 2.3 and 2.4.

Any help appreciated.
Thx and regards,
Nicolas
 
T

Thomas Heller

Nicolas Fleury said:
I have also third party packages. Is it possible to make a package
point to another folder? For example:

psyco23/...
psyco24/...
psyco/__init__.py => points to psyco23 or psyco24 depending on Python
version used.

You may manipulate the package path in the __init__.py file.
pkgutil may also be useful.

Thomas
 
N

Nicolas Fleury

Nicolas said:
import cppmymodule

would be equivalent to:

if sys.version == "2.4":
import cppmymodule24 as cppmymodule
elif sys.version == "2.3":
import cppmymodule23 as cppmymodule

for all modules under the package and all modules with names beginning
with cpp (or another way to identify them).

Since all my imports are absolute, my code looks more like:

import root.subpackage.cppmymodule

So I guess, I can add this in root/__init__.py and everything would be fine:

def myimport(name, globals=None, locals=None, fromlist=None,
__import__=__import__):
names = name.split('.')
if names[0] == 'root' and names[-1][0:3] == 'cpp':
name += '%s%s' % sys.version_info[0:2]
return __import__(name, globals, locals, fromlist)

__builtins__['__import__'] = myimport

It seems to work, is that right?

Thx and regards,
Nicolas
 
S

Serge Orlov

Nicolas said:
Hi,
I'm trying to support two Python versions at the same time and I'm
trying to find effective mechanisms to support modules compiled in
C++ transparently.

All my code in under a single package. Is it possible to override
the import mechanism only for modules under that package and
sub-packages so that?:

import cppmymodule

would be equivalent to:

if sys.version == "2.4":
import cppmymodule24 as cppmymodule
elif sys.version == "2.3":
import cppmymodule23 as cppmymodule

for all modules under the package and all modules with names
beginning with cpp (or another way to identify them).

I used the following approach application-wide:
===== The very start of main file ===
resolve_package_dependencies()
import package

def main():
...

# boilerplate at the end of main file
def resolve_package_dependencies():
if sys.version_info[0:2] == (2,5):
import package1
sys.modules["package"] = sys.modules["package1"]
else:
import package2
sys.modules["package"] = sys.modules["package2"]

=====================================

I've never needed that for packages like you, but as far as I
remember package specific modules are stored like
"package.module" so aliasing "package45" with "package" in your
case will look like
sys.modules[__name__+".package"] = sys.modules[__name__+".package45"]

Serge.
 
G

Greg Ewing

Nicolas said:
All my code in under a single package. Is it possible to override the
import mechanism only for modules under that package and sub-packages so
that?:

Yes. A package module has a __path__ attribute to which
you can add additional directories to be searched for
submodules of that package. So in your package's
__init__.py you can do something like

if sys.version == "2.4":
subdir = "python24"
elif sys.version == "2.3":
subdir = "python23"

__path__.append(os.path.join(os.path.basename(__file__, subdir)))

The directory structure is then

yourpackage/
__init__.py
python23/
cppmymodule.pyd (2.3 version)
python24/
cppmymodule.pyd (2.4 version)

but at run time it will appear as though one version or
the other of cppmymodule is a direct submodule of
yourpackage.
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,767
Messages
2,569,570
Members
45,045
Latest member
DRCM

Latest Threads

Top