Expandir la ruta de búsqueda de Python a otra fuente

Acabo de unirme a un proyecto con una base de código existente bastante grande. Desarrollamos en linux y no utilizamos e IDE. Corremos a través de la línea de comando. Estoy tratando de averiguar cómo hacer que Python busque el camino correcto cuando ejecuto los módulos del proyecto. Por ejemplo, cuando corro algo como:

python someprojectfile.py 

yo obtengo

 ImportError: no module named core.'somemodule' 

Obtengo esto para todas mis importaciones y asumo que es un problema con la ruta.

TLDR:

¿Cómo puedo hacer que Python busque ~/codez/project/ y todos los archivos y carpetas para los archivos * .py durante las declaraciones de importación?

Hay algunas formas posibles de hacer esto:

  • Establezca la variable de entorno PYTHONPATH en una lista de directorios separados por dos puntos para buscar módulos importados.
  • En su progtwig, use sys.path.append('/path/to/search') para agregar los nombres de los directorios en los que desea que Python busque los módulos importados. sys.path es solo la lista de directorios que Python busca cada vez que se le pide que importe un módulo, y puede modificarlo según sea necesario (¡aunque no recomendaría eliminar ninguno de los directorios estándar!). Cualquier directorio que coloque en la variable de entorno PYTHONPATH se insertará en sys.path cuando Python se inicie.
  • Utilice site.addsitedir para agregar un directorio a sys.path . La diferencia entre esto y simplemente agregar es que cuando se usa addsitedir , también busca archivos .pth dentro de ese directorio y los usa para agregar directorios adicionales a sys.path según el contenido de los archivos. Consulte la documentación para más detalles.

Cuál de estos desea utilizar depende de su situación. Recuerde que cuando distribuye su proyecto a otros usuarios, generalmente lo instalan de tal manera que el importador de Python detectará automáticamente los archivos de código de Python (es decir, los paquetes generalmente se instalan en el directorio site-packages ), por lo que si se meten con sys.path en su código, eso puede ser innecesario e incluso puede tener efectos adversos cuando ese código se ejecuta en otra computadora. Para el desarrollo, me atrevería a suponer que el ajuste de PYTHONPATH suele ser la mejor opción.

Sin embargo, cuando estás usando algo que solo se ejecuta en tu propia computadora (o cuando tienes configuraciones no estándar, por ejemplo, a veces en marcos de aplicaciones web), no es del todo raro hacer algo como

 from os.path import dirname sys.path.append(dirname(__file__)) 

También debe leer sobre los paquetes de python aquí: http://docs.python.org/tutorial/modules.html .

Por su ejemplo, creo que realmente tiene un paquete en ~/codez/project . El archivo __init__.py en un directorio de python asigna un directorio a un espacio de nombres. Si todos sus subdirectorios tienen un archivo __init__.py , entonces solo necesita agregar el directorio base a su PYTHONPATH . Por ejemplo:

PYTHONPATH = $ PYTHONPATH: $ HOME / adaifotis / project

Además de probar su variable de entorno PYTHONPATH, como explica David, puede probarla en python así:

 $ python >>> import project # should work if PYTHONPATH set >>> import sys >>> for line in sys.path: print line # print current python path 

Sé que este hilo es un poco viejo, pero me tomó algo de tiempo llegar al corazón de esto, así que quería compartirlo.

En mi proyecto, tenía el script principal en un directorio principal y, para diferenciar los módulos, coloqué todos los módulos de soporte en una subcarpeta llamada “módulos”. En mi script principal, importo estos módulos como este (para un módulo llamado report.py):

 from modules.report import report, reportError 

Si llamo a mi script principal, esto funciona. SIN EMBARGO, quería probar cada módulo incluyendo un main() en cada uno, y llamando a cada uno directamente, como:

 python modules/report.py 

Ahora Python se queja de que no puede encontrar “un módulo llamado módulos”. La clave aquí es que, de forma predeterminada, Python incluye la carpeta del script en su ruta de búsqueda, PERO NO LA CWD. Entonces, lo que realmente dice este error es “No puedo encontrar una subcarpeta de módulos”. Esto se debe a que no hay un subdirectorio de “módulos” del directorio donde reside el módulo report.py.

Me parece que la mejor solución para esto es agregar el CWD en la ruta de búsqueda de Python al incluir esto en la parte superior:

 import sys sys.path.append(".") 

Ahora Python busca el CWD (directorio actual), encuentra la subcarpeta “módulos” y todo está bien.

Leí esta pregunta buscando una respuesta y no me gustó ninguna de ellas.

Así que escribí una solución rápida y sucia. Simplemente coloque esto en algún lugar de su sys.path, y agregará cualquier directorio en la folder (del directorio de trabajo actual), o en abspath :

 #using.py import sys, os.path def all_from(folder='', abspath=None): """add all dirs under `folder` to sys.path if any .py files are found. Use an abspath if you'd rather do it that way. Uses the current working directory as the location of using.py. Keep in mind that os.walk goes *all the way* down the directory tree. With that, try not to use this on something too close to '/' """ add = set(sys.path) if abspath is None: cwd = os.path.abspath(os.path.curdir) abspath = os.path.join(cwd, folder) for root, dirs, files in os.walk(abspath): for f in files: if f[-3:] in '.py': add.add(root) break for i in add: sys.path.append(i) >>> import using, sys, pprint >>> using.all_from('py') #if in ~, /home/user/py/ >>> pprint.pprint(sys.path) [ #that was easy ] 

Y me gusta porque puedo tener una carpeta para algunas herramientas aleatorias y no tenerlas como parte de paquetes ni nada, y aún así tener acceso a algunas (o todas) de ellas en un par de líneas de código.

La forma más fácil de encontrar es crear un archivo “any_name.pth” y ponerlo en su carpeta “\ Lib \ site-packages”. Debes encontrar esa carpeta donde sea que esté instalado Python.

En ese archivo, coloque una lista de directorios donde desea guardar los módulos para importar. Por ejemplo, haz una línea en ese archivo como este:

C: \ Users \ example … \ example

Podrás decir que funciona ejecutando esto en python:

 import sys for line in sys: print line 

Verá su directorio impreso, entre otros, desde donde también puede importar. Ahora puede importar un archivo “mymodule.py” que se encuentra en ese directorio tan fácilmente como:

 import mymodule 

Esto no importará subcarpetas. Para eso podría imaginar crear un script en Python para crear un archivo .pth que contenga todas las subcarpetas de una carpeta que usted defina. Haz que se ejecute al inicio tal vez.