Importing in Python - python

In Python 2.5, I import modules by changing environment variables. It works, but using site-packages does not. Is there another way to import modules in directories other than C:\Python25 ?

On way is with PYTHONPATH environment variable. Other one is to add path to sys.path either directly by sys.path.append(path) or by defining .pth files and add them to with site.addsitedir(dirWithPths). Path files (.pth) are simple text files with a path in each line. Every .pth file in dirWithPths will be read.

Append the location to the module to sys.path.
Edit: (to counter the post below ;-) )
os.path does something completely different. You need to use sys.path.
sys.path.append("/home/me/local/modules")

Directories added to the PYTHONPATH environment variable are searched after site-packages, so if you have a module in site-packages with the same name as the module you want from your PYTHONPATH, the site-packages version will win. Also, you may need to restart your interpreter and the shell that launched it for the change to the environment variable to take effect.
If you want to add a directory to the search path at run time, without restarting your program, add the directory to sys.path. For example:
import sys
sys.path.append(newpath)
If you want your new directory to be searched before site-packages, put the directory at the front of the list, like this:
import sys
sys.path.insert(0, newpath)

sys.path is a list to which you can append custom paths to search like this:
sys.path.append("/home/foo")

Related

Why sys.path doesn't contain cwd()?

I use python3 with emacs (editor and shell) under Linux OS. Why the cwd is not in the sys.path ?? How can we put it, for all sessions !!
I Thank you.
You do not want to add cwd() to the sys.path. Always adding cwd() would be a terrible idea as you can no longer control what files are available for import.
Python adds the directory of the script being executed instead.
E.g. when you run:
python.exe path/to/script.py
then path/to is automatically added to the sys.path.
Only if you run a script from the current directory is '' added to the start of the path, meaning the current working directory is searched for imports. E.g. when you run python.exe localfile.py then Python does add the current working directory, in the assumption you wont't change the current working directory while importing.
See Interface options in the Command line and environment documentation:
If the script name refers directly to a Python file, the directory containing that file is added to the start of sys.path, and the file is executed as the __main__ module.
and the sys.path documentation:
As initialized upon program startup, the first item of this list, path[0], is the directory containing the script that was used to invoke the Python interpreter. If the script directory is not available (e.g. if the interpreter is invoked interactively or if the script is read from standard input), path[0] is the empty string, which directs Python to search modules in the current directory first. Notice that the script directory is inserted before the entries inserted as a result of PYTHONPATH.
You can always add the current working directory to sys.path explicitly:
import sys
if sys.path[0] != '':
sys.path.insert(0, '')
Be careful, any python file or package in that working directory with a name matching a module you are already using in your code will mask that module, easily leading to breakage.
sys.path isn't the System Path, it's the path that python checks when looking for modules (when you execute import statements, for example).
To change it permanently, change the environment variable PYTHONPATH.
You can change your PYTHONPATH environmental variable.
This prepends locations to the default module search path.
The docs say that, when running a script from the command line,
the first item in sys.path will be the path to the script.
The docs say that sys.path is then
“initialized from the environment variable PYTHONPATH, plus an installation-dependent default.”
For example, if PYTHONPATH is empty (PowerShell: $env:PYTHONPATH = ""),
only the installation-dependent default is added.
However, if PYTHONPATH starts with an empty string,
then the current working directory (that the script is run from) is added to PYTHONPATH.
(Even just an initial separator will add this—for example a semicolon in PowerShell: $env:PYTHONPATH = ";".)
This is not always the desired behavior,
so you may wish to hesitate before making permanent changes in your PYTHONPATH.

Using .pth files

I am trying to make a module discoverable on a system where I don't have write access to the global site-packages directory, and without changing the environment (PYTHONPATH). I have tried to place a .pth file in the same directory as a script I'm executing, but it seems to be ignored. E.g., I created a file extras.pth with the following content:
N:\PythonExtras\lib\site-packages
But the following script, placed and run in the same directory, prints False.
import sys
print r"N:\PythonExtras\lib\site-packages" in sys.paths
The only directory in sys.path to which I have write access is the directory containing the script. Is there another (currently non-existent) directory where I could place extras.pth and have it be seen? Is there a better way to go about this?
I'm using python 2.7 on Windows. All .pth questions I could find here use the system module directories.
Edit: I've tracked down the Windows per-user installation directory, at %APPDATA%\Python\Python27\site-packages. I can place a module there and it will be imported, but if I put a .pth file there, it has no effect. Is this really not supposed to work, or am I doing something wrong?
As described in the documentation, PTH files are only processed if they are in the site-packages directory. (More precisely, they are processed if they are in a "site directory", but "site directory" itself is a setting global to the Python installation and does not depend on the current directory or the directory where the script resides.)
If the directory containing your script is on sys.path, you could create a sitecustomize.py in that directory. This will be loaded when Python starts up. Inside sitecustomize.py, you can do:
import site
site.addsitedir('/some/dir/you/want/on/the/path')
This will not only add that directory, but will add it as a "site directory", causing PTH files there to be processed. This is handy if you want to create your own personal site-packages-like-directory.
If you only need to add one or two directories to the path, you could do so more simply. Just create a tiny Python library that manipulates sys.path, and then import that library from your script. Something like:
# makepath.py
import sys
sys.path.append('/whatever/dir/you/want')
# script.py
import makepath
Edit: Again, according to the documentation, there is the possibility of a site-specific directory in %APPDATA%\Python\PythonXY\site-packages (on Windows). You could try that, if in fact you have write access to that (and not just to your script directory).
You can make a .pth (path) file in a directory already in sys.path so it can be included/

How does python find a module file if the import statement only contains the filename?

Everywhere I see Python code importing modules using import sys or import mymodule
How does the interpreter find the correct file if no directory or path is provided?
http://docs.python.org/3/tutorial/modules.html#the-module-search-path
6.1.2. The Module Search Path
When a module named spam is imported, the interpreter first searches for a built-in module with that name. If not found, it then searches for a file named spam.py in a list of directories given by the variable sys.path. sys.path is initialized from these locations:
The directory containing the input script (or the current directory when no file is specified).
PYTHONPATH (a list of directory names, with the same syntax as the shell variable PATH).
The installation-dependent default.
Note: On file systems which support symlinks, the directory containing the input script is calculated after the symlink is followed. In other words the directory containing the symlink is not added to the module search path.
After initialization, Python programs can modify sys.path. The directory containing the script being run is placed at the beginning of the search path, ahead of the standard library path. This means that scripts in that directory will be loaded instead of modules of the same name in the library directory. This is an error unless the replacement is intended. See section Standard Modules for more information.
For information on the "installation-specific default", see documentation on the site module.
Also, you can see what the current path is by using the sys module
import sys
print(sys.path)
It uses the PYTHONPATH, set as an environment variable, to find packages (folders containing __init__.py files) and modules (or, if already loaded once, retrieves the module object from sys.modules).
Python has a path variable just like the one you have inside your terminal. Python looks for modules in folders inside that path, or in the folder where your program is located.

Python packages and imports

I wanted to know if you can use the import statement in python from a directory that is not your local directory if that directory is not a package? Also, do all the directories on your system path have to be packages? If you add a relative path to your system path, what is it relative to?
you can alter sys.path in order to achieve all the results you are asking for.
Yes you can. To add a directory that is not your local directory:
import sys
sys.path += '/your_path/your_subpath/' # absolute paths
import your_package
If you need to load the module from an arbitrary path in the filesystem without adding it to sys.path you can use also imp.load_module
do all the directories on your system path have to be packages? No, they do not
If you add a relative path to your system path, what is it relative to?
to the directory containing the script that was used to invoke the Python interpreter.
I suggest, however, to set it in this way:
import sys,os
sys.path.append(os.path.realpath('..'))
or from the path of the script:
import sys,os
sys.path.append(os.path.realpath(os.path.join(os.path.dirname(sys.argv[0]), '..')))
both the examples work also from interactive shells. Both examples ensure the relative path is what you meant, regardless of the OS
see also this post for more details on relative paths in python
That's really 3 different questions:
I wanted to know if you can use the import statement in python from a directory that is not your local directory if that directory is not a package
Yes, you can.
Also, do all the directories on your system path have to be packages?
No, they don't.
If you add a relative path to your system path, what is it relative to?
Relative to the current working directory.

how to set up environment variables for python

On WinXP sp2 I'd like to have a directory of modules that other python scripts will be using called "SharedPython" in the same directory as my python scripts. so, basically:
/pythonScripts
/pythonScripts/SharedPython
as well as other python scripts on the same level as the SharedPython directory.
when I run
print sys.path
I get the following output:
C:\WINDOWS\system32\python25.zip
C:\Python25\DLLs
C:\Python25\lib
C:\Python25\lib\plat-win
C:\Python25\lib\lib-tk
C:\Python25
C:\Python25\lib\site-packages
I don't know what environment variable controls this and, in fact, I don't see one that contains all these directories.
So,
a.)how do I determine which environment variable contains this list of dirs?
and
b.)can I just add the aforementioned SharedPython dir to that list?
I've tried setting PYTHONPATH to the following: %PYTHONPATH%C:\PythonScripts\SharedPython
You need the PYTHONPATH env var. The dirs listed in it are prepended to sys.path.
The correct way to setup PYTHONPATH in your case is:
set PYTHONPATH=%PYTHONPATH%;C:\PythonScripts\SharedPython
Note the semicolon between the second % and the C:\
Those paths are added by the site module; do not change this module, but rather create a batch file that adds your paths in %PYTHONPATH% and then runs the script.

Categories