Absolute imports?

R

Roy Smith

If I have an absolute path to a file (i.e. '/home/roy/foo.py'), is there
a way to import that as a module WITHOUT modifying sys.path? I'm using
Python 2.6.

I've read PEP 328, and don't really understand how the absolute imports
it's talking about are supposed to work. Should I be using
imp.load_source()?
 
T

Terry Reedy

If I have an absolute path to a file (i.e. '/home/roy/foo.py'), is there
a way to import that as a module WITHOUT modifying sys.path? I'm using
Python 2.6.

Import from another file in /home/roy. (since '.' is part of sys.path).
Or put module or package of modules in Lib/site-packages.
But why the horror of modifying sys.path? It is normal proceedure.
I've read PEP 328, and don't really understand how the absolute imports
it's talking about are supposed to work.

Those are the normal imports that start from a directory in sys.path.
Relative imports (now) are ones that use '.'s to locate relative to the
importing module. I have never done that. Purpose is to make a
subpackage relocatable to another package without modification.
Should I be using imp.load_source()?

No idea, never done that. Try it if you want.
 
R

Roy Smith

Ben Finney said:
Importing a module with ‘import’ is done by using the module's name,
which is only *incidentally* related to its filesystem path.

What is the problem you're trying to solve? It is likely we can suggest
a better solution.

Well, the problem I'm trying to solve is that I have an absolute
pathname to a python source file that I want to import as a module :)

I'm working on a project where developers will typically have several
sandboxes, with different versions of the code. There's a config file
(which I have no control over) which defines a big multi-level dict
containing configuration options:

config = {
'memcache_servers' : ['localhost'],
'build_type' : 'development',
'thrift_configs' : {
'SearchService' : {'hosts' : ['localhost'],
'sendTimeout' : 300,
'port' : 9192,
'recvTimeout' : 3000
},
}
}

and so on. The file is auto-generated by some huge pile of perl scripts
which also generates the same information in a forms ingestible by perl,
PHP, Java, shell scripts, etc. Not how I would have designed it, but it
is what it is.

The best I can describe how to find the location of the config file is,
"Work your way up the directory tree from where you are now, (i.e.
following '..' links) until you get to the top level of the project,
then from there, it's ./code/configs/autogen/config.py."

It's reasonably straight-forward to figure out that absolute path,
starting from sys.argv[0] and using the tools in os.path. Now I need to
import the file, given that I know its absolute pathname. It looks like
imp.load_source() does what I want, I'm just wondering if there's a
cleaner way.
 
R

Roy Smith

Terry Reedy said:
Import from another file in /home/roy. (since '.' is part of sys.path).
Or put module or package of modules in Lib/site-packages.
But why the horror of modifying sys.path? It is normal proceedure.

Not quite horror, but since I already know the absolute path to the
file, it seems silly to change the search path just so import can use it
to search. Also, if I change the search path, I risk other things
finding my module by mistake (if there's a module name collision).
 
T

Terry Reedy

Not quite horror, but since I already know the absolute path to the
file, it seems silly to change the search path just so import can use it
to search. Also, if I change the search path, I risk other things
finding my module by mistake (if there's a module name collision).

Ben Finney asked you the right question. If config.py is the only .py
file in .../autogen/, which I infer from your responses, you could
..pop() .../autogen after the append and import. Or open config.py and
use imp.load_module, being careful to get all the args correct. In
either case, if I had a startup module or utility module that is
imported right away, I would do the import with extra code there, just
once. Then, either refer to util.config after importing util in other
modules, or just do 'import config'. The latter should work because
import first looks for already imported modules (in sys.modules). When
the module is already there, 'import x' reduces to "x = sys.modules['x']".
 
J

Jean-Michel Pichavant

Roy said:
[snip]
It's reasonably straight-forward to figure out that absolute path,
starting from sys.argv[0] and using the tools in os.path. Now I need to
import the file, given that I know its absolute pathname. It looks like
imp.load_source() does what I want, I'm just wondering if there's a
cleaner way.

What about

config = __import__(configPath.replace('.py', ''))


JM
 

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,965
Messages
2,570,148
Members
46,710
Latest member
FredricRen

Latest Threads

Top