Issue4438
Created on 2008-11-26 11:58 by mrts, last changed 2009-04-01 18:46 by georg.brandl.
|
msg76460 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-26 11:58 |
|
The need to dynamically import module foo given a module name string
'bar.baz.foo' is quite common.
Quite often, the hack described in http://bugs.python.org/issue2090 is
used (see e.g. the Google code results linked from the issue).
Quoting Brett Cannon from the issue:
"I plan to add a much simpler API to the imp module for people to use
directly so that these abuses don't continue."
Although there are reasonable workarounds, let the current ticket be a
remainder for Brett that his plan is indeed needed.
Perhaps the easiest thing to do would be to add yet another argument,
e.g. 'toplevel', to __import__, such that:
>>> __import__('imprt.foo.foo') # toplevel=True by default
<module 'imprt' from 'imprt/__init__.pyc'>
>>> __import__('imprt.foo.foo', toplevel=False)
<module 'imprt.foo.foo' from 'imprt/foo/foo.pyc'>
The latter can currently be achieved by
>>> __import__('imprt.foo.foo', {}, {}, ['foo'])
<module 'imprt.foo.foo' from 'imprt/foo/foo.pyc'>
which is cumbersome if the module name is given in a string, resulting
in unnecessarily complex code:
modname = "imprt.foo.foo"
>>> __import__(modname, {}, {}, [modname.rsplit(".", 1)[-1]])
<module 'imprt.foo.foo' from 'imprt/foo/foo.pyc'>
|
|
msg76466 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-26 14:23 |
|
Attached is a naive proof-of-concept implementation (that breaks things,
i.e. the real implementation should strive for better
general compatibility), but works as expected:
>>> __import__('imprt.foo.foo', submodule=True)
<module 'imprt.foo.foo' from 'imprt/foo/foo.py'>
>>> __import__('imprt.foo.foo', submodule=False)
<module 'imprt' from 'imprt/__init__.py'>
>>> __import__('imprt.foo.foo')
<module 'imprt' from 'imprt/__init__.py'>
# Die on unexpected arguments like strings, lists etc to
# avoid confusion
>>> __import__('imprt.foo.foo', submodule='z')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: an integer is required
|
|
msg76468 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-26 15:15 |
|
Just a note that `make test` passes:
322 tests OK.
38 tests skipped:
test_aepack test_al test_applesingle test_bsddb test_bsddb185
test_bsddb3 test_cd test_cl test_codecmaps_cn test_codecmaps_hk
test_codecmaps_jp test_codecmaps_kr test_codecmaps_tw test_curses
test_dbm test_dl test_gl test_imageop test_imgfile test_kqueue
test_linuxaudiodev test_macos test_macostools test_normalization
test_ossaudiodev test_pep277 test_py3kwarn test_scriptpackages
test_socketserver test_startfile test_sunaudiodev test_tcl
test_timeout test_urllib2net test_urllibnet test_winreg
test_winsound test_zipfile64
3 skips unexpected on linux2:
test_tcl test_dbm test_bsddb
|
|
msg76497 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-27 12:53 |
|
Corrections and clarifications:
* I'd say labeling the patch naive and "breaking things" was misleading
(there was a breakage that resulted from stale files with incorrect
permissions from my previous build of Python 2.6; after a make distclean
all tests passed as described above). The patch is correct and
backwards-compatible in Python level, but it introduces a change in the
C API:
PyAPI_FUNC(PyObject *) PyImport_ImportModuleLevel(char *name,
- PyObject *globals, PyObject *locals, PyObject *fromlist, int level);
+ PyObject *globals, PyObject *locals, PyObject *fromlist,
+ int level, char submodule);
* The patch was made against Python 2.6 release source.
* The argument is named 'submodule' instead of 'toplevel' to avoid
confusion with 'level'.
|
|
msg76515 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-27 20:49 |
|
See also
http://mail.python.org/pipermail/python-dev/2008-November/083727.html
|
|
msg76549 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-28 18:59 |
|
Implement imp.import_module() instead. See
http://mail.python.org/pipermail/python-dev/2008-November/083758.html
|
|
msg76550 - (view) |
Author: Mart Sõmermaa (mrts) |
Date: 2008-11-28 19:05 |
|
Note that the hack described in http://bugs.python.org/issue2090 should
be disabled once this gets integrated.
|
|
msg85071 - (view) |
Author: Georg Brandl (georg.brandl) |
Date: 2009-04-01 18:46 |
|
This feature is implemented as importlib.import_modules() in 2.7 and
3.1; for earlier versions there is also a backport on PyPI.
|
|
| Date |
User |
Action |
Args |
| 2009-04-01 18:46:48 | georg.brandl | set | status: open -> closed
nosy:
+ georg.brandl messages:
+ msg85071
resolution: out of date |
| 2008-11-28 19:09:09 | mrts | set | components:
- Interpreter Core title: Add an easy way to __import___ submodules -> Given a module hierarchy string 'a.b.c', add an easy way to import tail module 'c' |
| 2008-11-28 19:05:43 | mrts | set | messages:
+ msg76550 |
| 2008-11-28 19:02:09 | mrts | set | files:
+ imp_import_module.diff messages:
+ msg76549 |
| 2008-11-27 20:49:07 | mrts | set | messages:
+ msg76515 |
| 2008-11-27 12:53:31 | mrts | set | messages:
+ msg76497 |
| 2008-11-26 15:15:53 | mrts | set | messages:
+ msg76468 |
| 2008-11-26 14:23:58 | mrts | set | files:
+ issue4438.diff keywords:
+ patch messages:
+ msg76466 |
| 2008-11-26 11:58:38 | mrts | create | |
|