common/src/validation/file1.py
In the common/src/validation/ and common/src/ folder "_init_" is defined.
common/test/validation/file2.py
common/test/validation/case/file3.py
In file2.py and file3.py, I want to import class from file1.py.
Im giving the following line in file2.py and file3.py.:
from file1 import class1
I currently get error:
#ImportError: No module named file1
what should be the sys.path.append ?
If you want to import a file from a folder you should have a file named
__init__.py
in that folder (it could also be a blank file).
You can basically just change PYTHONPATH to common and run from there. Then reference all import paths in relation to that.
like so: (assuming you are in common and your main is in file3.py)
PYTHONPATH=. python test/validation/case/file3.py
Make sure to have __init__.py files in any directory you import (the content of this file doesn't matter)
I usually like putting in the root of every project a run.sh file with some version of this line (pointing to wherever my main func is) in it.
It will usually contain a simple something like that:
#!/bin/bash
source some_env/bin/activate # start the relevant environment if you have one
PYTHONPATH=. python src/main.py # set PYTHONPATH and run
deactivate # exit the relevant environment if started one
Another option is to do this but is't not as elegant.
Related
I defined a directory named common in the root directory of my project. Basically, there isn't a main file, but rather lots of scripts which I want to directly run.
What I want to do is something like that:
from ../../common/ import <python_file>
Is it possible without too much of a hustle?
Would I need to put __init__.py to make it work?
The use of .. for imports is really a bad practice. What you should do is that. Create a virtualenv using virtualenvwrapper and then use add2virtualenv common
OR
Add the path of the root directory of your project into your PYTHONPATH env variable
export PYTHONPATH=$PYTHONPATH:/path/of/my/project
An __init__.py file must be placed in every folder containing python code
I met a very strange problem:
My file structure is like: (core and test are directories)
core
----file1.py
----__init__.py
test
----file2.py
in file2, i wrote:
from core import file1
result is:
ImportError: cannot import name file1
Have to create __init__.py file inside the test dir:
Because The __init__.py files are required to make Python treat the directories as containing packages.
parent/
child1/
__init__.py
file1.py
child2/
__init__.py
file2.py
From the error:
If run the child2/file2.py file directly. You are not able to access child1/file1.py from the child2/file2.py
Because only from the parent directory can access the child.
If have a folder structure like:
parent/
child1/
__init__.py
file1.py
child2/
__init__.py
file2.py
file3.py
If we run the file3.py file. Can able to access both child1/file1.py, child2/file2.py in file3.py
Because It is running from the parent directory.
If we need to access child1/file1 from child2/file2.py, We need to set the parent directory:
By running this below command we can achieve it...
PYTHONPATH=. python child2/file2.py
PYTHONPATH=. It refers the parent path. Then runs child2/file2.py file from the shell
It's not a strange problem, imports simply don't work like that.
From the official documentation: https://docs.python.org/3/tutorial/modules.html
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.
You could look into relative imports, here's a good source: https://stackoverflow.com/a/16985066/4886716
The relevant info from that post is that there's no good way to do it unless you add core to PYTHONPATH like Shawn. L says.
When I tried your case, I got
Traceback (most recent call last):
File "file2.py", line 3, in <module>
from core import file1
ImportError: No module named core
The reason is that Python does not find core. In this case, you need to add core to the system path, as shown below (add them at the very beginning of file2.py):
import sys,os
sys.path.append(path_to_core.py)
Or, if you would run it using command line, you could simply put the following at the beginning of file2.py
import sys,os
sys.path.append(os.path.join(os.path.dirname(__file__),'../'))
Here, os.path.join(os.path.dirname(__file__),'../') is to state the path to file2.py.
I have a module I have installed called lts_fits, and this is its path:
~/Enthought/Canopy_64bit/User/lib/python2.7/site-packages/lts_fits
So it is clearly in the site packages folder. Within this folder, there is a python script:
lts_linefit.py
Yet when I have this line of code in my script:
from lts_fits import lts_linefit
I get this error:
ImportError: No module named lts_fits
How? It's clearly in there, and I have tried this same syntax with other random scripts and they import just fine. For instance, a file abc.py located in the folder ~/Enthought/Canopy_64bit/User/lib/python2.7/site-packages/sympy imports just fine when I have the line from sympy import abc. What could be going wrong?
You need an __init__.py file in that directory (you do not have to put anything into the file, all you need to do is create it).
The easiest way to create said file is by using:
touch __init__.py
from within your lts_fits directory in your command line/terminal/console.
See this SO article: What is __init__.py for?
And the Python Documentation for packages.
I have the following directory structure:
application
tests
main.py
main.py
application/main.py contains some functions.
tests/main.py will contain my tests for these functions but I can't import the top level main.py. I get the following error:
ImportError: Import by filename is not supported.
I am attempting to import using the following syntax:
import main
What am I doing wrong?
If you'd like your script to be more portable, consider finding the parent directory automatically:
import os, sys
sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
# import ../db.py
import db
You must add the application dir to your path:
import sys
sys.path.append("/path/to/dir")
from app import object
Or from shell:
setenv PATH $PATH:"path/to/dir"
In case you use windows:
Adding variable to path in windows.
Or from the command line:
set PATH=%PATH%;C:\path\to\dir
Please mind the diff between PYTHONPATH, PATH, sys.path.
Late to the party - most other answers here are not correct unfortunately - apart LennartRegebro's (and BrenBarn's) which is incomplete. For the benefit of future readers - the OP should, first of all, add the __init__.py files as in
root
application
__init__.py
main.py
tests
__init__.py
main.py
then:
$ cd root
$ python -m application.tests.main
or
$ cd application
$ python -m tests.main
Running a script directly from inside its package is an antipattern - the correct way is running with the -m switch from the parent directory of the root package - this way all packages are detected and relative/absolute imports work as expected.
First of all you need to make your directories into packages, by adding __init__.py files:
application
tests
__init__.py
main.py
__init__.py
main.py
Then you should make sure that the directory above application is on sys.path. There are many ways to do that, like making the application infto a package and installing it, or just executing things in the right folder etc.
Then your imports will work.
You cannot import things from parent/sibling directories as such. You can only import things from directories on the system path, or the current directory, or subdirectories within a package. Since you have no __init__.py files, your files do not form a package, and you can only import them by placing them on the system path.
To import a file in a different subdirectory of the parent directory, try something like this:
sys.path.append(os.path.abspath('../other_sub_dir'))
import filename_without_py_extension
Edit: Missing closing bracket.
in python . exists for same directory, .. for parent directory
to import a file from parent directory you can use ..
from .. import filename (without .py extension)
I know this is a dumb question but i'm stumped. My directory structure used to look like this:
-src
|
-module.py
-program.py
when this what my directory structure, I referenced module from program and all was well.
I've since changed my directory structure to this:
-src
|
-__init.py
-module.py
|
-programDir
|
-__init.py
-program.py
now, of course, I can't reach the module from program. How can I reference src as a package. I tried to create an
__init__.py
file in the src directory, but no luck.
Moar deets:
import statements i've tried in program.py:
import module
and
from src import module
the first one worked when the other module and program were in the same directory.
error i'm getting:
ImportError: No module named module
and just for the record: No, my module and program are not called module OR program
update: I've tried this in my program.py file:
from ...src import module
and
from ..src import module
both are giving me:
ValueError: Attempted relative import in non-package
For starters, I recommend reading the entry Modifying Python's Search Path in the docs.
It might be frowned upon by some, but if you wish to modify the PYTHONPATH from within your program, according to the documentation's standard modules entry you can use the sys.path.append method:
import sys
sys.path.append('..')
import module
Couldn't you use PEP 328 to solve this?
If you run program.py directly, with python program.py or with #!, then module.py's directory should be in the PYTHONPATH for import module to work. This can be achieved using a helper shell script that's kept in programDir, for instance, and looks something like:
#!/bin/bash
script_dir=`dirname $0`
# Add the script's parent directory to the PYTHONPATH
export PYTHONPATH=$PYTHONPATH:$script_dir/..
python $script_dir/program.py
Another, probably better, way would be to have program.py export a "main()" function, and create a helper python script at src/program that looks like:
#!/usr/bin/env python
from programDir.program import main
main()
In this case, you can use relative imports in src/programDir/program.py, so this should work:
from .. import module
The first one worked because Python's sys.path's first entry is '' which means it will look for module names in the current working directory from which you've executed the Python interpreter.
The issue you seem to have is that the directory located at src is not set on your PYTHONPATH. So, you can do is set the PYTHONPATH environment variable explicitly.
Here's an example using bash:
export PYTHONPATH=PATH_TO_SRC:${PYTHONPATH}
then run your program as normal
Another approach is that you can explicitly set sys.path by appending to it upon execution of your program.
So, in your program.py, you would have:
if __name__ == '__main__':
import os
import sys
sys.path.append(os.path.dirname(os.path.dirname(__file__)))
your_main_function()
Lastly, for serious python development, you should consider virtualenv and virtualenvwrapper as it will take care of most of these things for you.
You need to add __init__.py to /programDir to interpret the directory as a package. Once a package, you can import the package's contents.
So, in your case, if /src is on the PYTHONPATH, from module.py you can import program.py with from programDir import program.
If you use program as part of a package, in another python module, such as
import src.programDir.program as p
p.some_method()
you can use relative import in program.py, assuming you are creating a package with src (__init__.py in both src and programDir)
from .. import module
If not, for example you are calling program.py from the command line, you must add the directory containing src to your search path either by modifying sys.path or the PYTHONPATH env var, before importing.