Почему мой текущий каталог не отображается в пути с помощью pytest в Windows?

У меня есть следующая структура папок;

myapp\
  myapp\
     __init__.py
  tests\
     test_ecprime.py

и мой pwd

C:\Users\wwerner\programming\myapp\

У меня есть следующая тестовая установка:

import pytest
import sys
import pprint

def test_cool():
    pprint.pprint(sys.path)
    assert False

Это создает следующие пути:

['C:\\Users\\wwerner\\programming\\myapp\\tests',
 'C:\\Users\\wwerner\\programming\\envs\\myapp\\Scripts',
 'C:\\Windows\\system32\\python34.zip',
 'C:\\Python34\\DLLs',
 'C:\\Python34\\lib',
 'C:\\Python34',
 'C:\\Users\\wwerner\\programming\\envs\\myapp',
 'C:\\Users\\wwerner\\programming\\envs\\myapp\\lib\\site-packages']

И когда я пытаюсь import myapp, я получаю следующую ошибку:

ImportError: No module named 'ecprime'

Так что похоже, что текущий каталог не добавляется к моему пути.

Изменив мою строку импорта, чтобы она выглядела так:

import sys
sys.path.insert(0, '.')
import myapp

Затем я могу импортировать myapp без проблем.

Почему мой текущий каталог не отображается в пути при запуске pytest? Является ли мой единственный обходной путь для вставки . в sys.path? (Я использую Python 3.4, если это имеет значение)


person Wayne Werner    schedule 21.01.2014    source источник
comment
Вы пытались импортировать myapp перед импортом pytest (чтобы убедиться, что проблема в pytest)? Попробуйте import myapp в качестве самой первой строки в скрипте.   -  person Sunny Nanda    schedule 21.01.2014
comment
@SunnyNanda тоже пробовал. Все еще не работает.   -  person Wayne Werner    schedule 22.01.2014


Ответы (3)


Ах ах!

После сравнения макета моего репозитория cookiecutter. оказывается намного проще (и лучше).

tests/
    __init__.py
    test_myapp.py

Простое добавление файла __init__.py в мой тестовый каталог позволяет мне запускать py.test из моего основного каталога.

person Wayne Werner    schedule 21.01.2014
comment
Делать это явно не рекомендуется в разделе передовой практики документации pytest. Это делает ваш пакет импортируемым только случайно. Если вы делаете это таким образом, вы в некоторой степени обязаны использовать макет проекта на основе src. См. github.com/pytest-dev/pytest/pull/2297. все подробности почему. - person wim; 04.04.2019
comment
На днях я должен вернуться и выяснить, зачем мне это нужно :) Я подозреваю, что есть гораздо лучший способ сделать то, что мне нужно (например, установить мой пакет в виртуальную среду с python -m pip install -e . или что-то в этом роде) - person Wayne Werner; 04.04.2019
comment
Да, установка пакета является обычным/рекомендуемым способом. Если вы не хотите его устанавливать (например, у вас нет установщика), то использование python -m pytest вместо простого pytest — это задокументированный способ получить cwd, присутствующий в sys.path. Должен ли я добавить ответ? Здесь еще никто не упомянул.. - person wim; 04.04.2019

sys.path автоматически содержит каталог сценария, а не текущий рабочий каталог.

Я предполагаю, что ваш скрипт находится в каталоге tests. Исходя из этого предположения, ваш код должен выглядеть так:

import sys
import os

ROOT_DIR = os.path.dirname(os.path.dirname(__file__))
sys.path.append(ROOT_DIR)

import myapp # Should work now
person Sunny Nanda    schedule 21.01.2014

Используйте переменную среды PYTHONPATH.

В Windows:

set PYTHONPATH=.
py.test

В Юникс:

PYTHONPATH=. py.test
person falsetru    schedule 21.01.2014
comment
В этом нет необходимости, потому что по умолчанию текущий каталог должен быть вставлен в sys.path. См. docs.python.org/3/library/sys.html#sys .путь - person Sunny Nanda; 21.01.2014
comment
@SunnyNanda, вставляется не текущий рабочий каталог, а каталог, содержащий скрипт. - person falsetru; 21.01.2014
comment
Спасибо за исправление. Ранее я предполагал, что скрипт присутствует в самом основном каталоге. Я добавил ответ с предположением, что вызываемый скрипт находится в дочернем каталоге. - person Sunny Nanda; 21.01.2014