PYTHONPATH vs. sys.path
python-import (5)
Otro desarrollador y yo no estamos de acuerdo sobre si PYTHONPATH o sys.path deberían usarse para permitir que Python encuentre un paquete de Python en un directorio de usuario (por ejemplo, desarrollo).
Tenemos un proyecto de Python con una estructura de directorio típica:
Project
setup.py
package
__init__.py
lib.py
script.py
En script.py, tenemos que import package.lib
. Cuando el paquete se instala en site-packages, script.py puede encontrar package.lib
.
Sin embargo, cuando se trabaja desde un directorio de usuarios, se necesita hacer algo más. Mi solución es configurar mi PYTHONPATH para que incluya "~ / Proyecto". Otro desarrollador quiere poner esta línea de código al comienzo de script.py:
sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
Para que Python pueda encontrar la copia local de package.lib
.
Creo que esta es una mala idea, ya que esta línea solo es útil para desarrolladores o personas que ejecutan una copia local, pero no puedo dar una buena razón por la cual es una mala idea.
¿Deberíamos usar PYTOHNPATH, sys.path, o está bien?
Creo que, en este caso, usar PYTHONPATH es algo mejor, sobre todo porque no introduce un código innecesario (cuestionable).
Después de todo, si lo piensa, su usuario no necesita esa sys.path
, porque su paquete se instalará en paquetes de sitio, porque usará un sistema de empaquetamiento.
Si el usuario elige ejecutar desde una "copia local", como lo llama, he observado que la práctica habitual es indicar que el paquete debe agregarse a PYTHONPATH manualmente, si se usa fuera de los paquetes del sitio. .
En general, consideraría la creación de una variable de entorno (como PYTHONPATH) como una mala práctica. Si bien esto podría estar bien para una depuración única, pero usando esto como
una práctica regular puede no ser una buena idea.
El uso de la variable de entorno conduce a situaciones como "me funciona" cuando alguien
else informa problemas en la base de código. También uno podría llevar la misma práctica con el entorno de prueba, lo que lleva a situaciones como las pruebas que funcionan bien para un desarrollador en particular, pero que probablemente fallan cuando alguien inicia las pruebas.
Junto con las muchas otras razones ya mencionadas, también podría señalar que la codificación dura
sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
es frágil porque supone la ubicación de script.py - solo funcionará si script.py está ubicado en Proyecto / paquete. Se romperá si un usuario decide mover / copiar / enlace simbólico script.py (casi) en cualquier otro lugar.
Odio PYTHONPATH. Me resulta frágil y molesto establecerlo por usuario (especialmente para usuarios daemon) y hacer un seguimiento de las carpetas de proyectos que se mueven. Preferiría establecer sys.path
en las secuencias de comandos de invocación para proyectos independientes.
Sin embargo, sys.path.append
no es la forma de hacerlo. Puede obtener duplicados fácilmente y no .pth
archivos .pth
. Mejor (y más legible): site.addsitedir
.
Y script.py
normalmente no sería el lugar más apropiado para hacerlo, ya que está dentro del paquete que desea que esté disponible en la ruta. Los módulos de la biblioteca no deberían tocar a sys.path
. En cambio, normalmente tendrías un script hashbanged fuera del paquete que usas para crear y ejecutar la aplicación, y es en este script de envoltura trivial sys.path
pondrías detalles de implementación como sys.path
-frobbing.
Si la única razón para modificar la ruta es que los desarrolladores trabajen desde su árbol de trabajo, entonces debe usar una herramienta de instalación para configurar su entorno. virtualenv es muy popular, y si está utilizando setuptools, simplemente puede ejecutar setup.py develop
para semi-instalar el árbol de trabajo en su instalación actual de Python.