Python предоставляя OSError: [Errno 27] Файл слишком большой для очень маленьких файлов с достаточным объемом дискового пространства / доступной памяти - PullRequest
0 голосов
/ 06 апреля 2020

У меня есть приложение, которое создает несколько очень маленьких временных файлов в рамках модульных тестов или определенных c функций. Я стал чаще сталкиваться с «случайными» ошибками OSError: [Errno 27] File too large. Под случайностью я подразумеваю, что проблема иногда исчезает при перезагрузке или если я повторно запускаю тесты через некоторое время. Я вручную проверил, что временная папка на Ma c очищена и имеет достаточно памяти / места для создания таких маленьких файлов. (доступно несколько ГБ) Небольшие файлы в этом контексте, например, имеют размер 16384, 58330, 26502 (в байтах) или даже меньше. Shutil.copyfile используется для создания этих файлов, но он также выдает ту же ошибку при выполнении os.link, которая должна занимать минимум места на диске. Я заменил shutil.copfile (где это возможно) на os.link, чтобы проверить, решает ли он проблему, но эффект тот же. В ОС Ma c эта ошибка часто выдается после некоторого случайного времени интенсивного запуска большого количества тестов, когда я занимаюсь разработкой. Однако ошибка постоянно сохраняется при работе внутри образа docker.

Фрагменты ошибок:

    @pytest.fixture(scope="module")
    def simulate_mirror(fixtures):
        """
        Thjs fixture creates a file/directory structure that simulates an offline PyPI mirror
        Used to test the `mirror://` bandersnatch integration for scanning the whole PyPI repository
        """
        from aura import mirror as amirror

        with tempfile.TemporaryDirectory(prefix="aura_test_mirror_") as mirror:
            pmirror = Path(mirror)
            assert pmirror.is_dir()
            os.mkdir(pmirror / "json")

            for pkg, pkg_files in MIRROR_FILES.items():
                # copy the package JSON metadata
                os.link(
                    fixtures.path(f"mirror/{pkg}.json"),
                    pmirror / "json" / pkg
                )

                for p in pkg_files:
                    os.makedirs(pmirror / p["path"])
                    os.link(
                        fixtures.path(f"mirror/{p['name']}"),
>                       os.fspath(pmirror / p["path"] / p["name"])
                    )
E                   OSError: [Errno 27] File too large: '/analyzer/tests/files/mirror/wheel-0.34.2-py2.py3-none-any.whl' -> '/tmp/aura_test_mirror_a6o5p8fn/packages/8c/23/848298cccf8e40f5bbb59009b32848a4c38f4e7f3364297ab3c3e2e2cd14/wheel-0.34.2-py2.py3-none-any.whl'

tests/conftest.py:204: OSError
    def test_apip():
        # Test package taken from pip tests
        # https://github.com/pypa/pip/tree/master/tests/data/packages
        whl = Path(__file__).parent /'files' / 'simplewheel-1.0-py2.py3-none-any.whl'

        venv_dir = tempfile.mkdtemp(suffix="_pytest_aura_apip")
        # print(f'Virtualenv created in {venv_dir}')
        try:
            # Create virtualenv
            venv.create(
                env_dir=venv_dir,
>               with_pip=True,
                # symlinks=True
            )

tests/test_apip.py:56:
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
/usr/local/lib/python3.7/venv/__init__.py:390: in create
    builder.create(env_dir)
/usr/local/lib/python3.7/venv/__init__.py:66: in create
    self.setup_python(context)
/usr/local/lib/python3.7/venv/__init__.py:233: in setup_python
    copier(context.executable, path)
/usr/local/lib/python3.7/venv/__init__.py:176: in symlink_or_copy
    shutil.copyfile(src, dst)
/usr/local/lib/python3.7/shutil.py:122: in copyfile
    copyfileobj(fsrc, fdst)
_ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _

fsrc = <_io.BufferedReader name='/usr/local/bin/python'>, fdst = <_io.BufferedWriter name='/tmp/tmpw5gbckwv_pytest_aura_apip/bin/python'>, length = 16384

    def copyfileobj(fsrc, fdst, length=16*1024):
        """copy data from file-like object fsrc to file-like object fdst"""
        while 1:
            buf = fsrc.read(length)
            if not buf:
                break
>           fdst.write(buf)
E           OSError: [Errno 27] File too large

/usr/local/lib/python3.7/shutil.py:82: OSError

Эти ошибки также иногда возникают при создании virtualenv с использованием venv.create. Я также всегда получаю sqlite3.OperationalError: ошибка ввода-вывода диска внутри docker образа, которая может быть связана с той же проблемой. Дополнительная техническая информация: Ma c ОС Catalina, полностью обновленная, переустановленная python с помощью brew до последней версии 3.7.7 +, воссоздала все virtualenv и переустановила все зависимости. Основываясь на других вопросах SO ( File too Large python), я уже проверил, что файловая система поддерживает размер файла в определенных пределах, а также максимальное количество файлов, допустимое в каталоге. Последний коммит, содержащий проблему (включает dockerfile, который завершается с ошибкой):

https://github.com/RootLUG/aura/commit/b4c730693e8f7fd36ab2acc78997694002c4e345

Местоположения кода, вызывающие ошибку:

https://github.com/RootLUG/aura/blob/dev/tests/conftest.py#L181

https://github.com/RootLUG/aura/blob/dev/tests/test_apip.py#L54

Travis log из модульных тестов:

https://travis-ci.org/github/RootLUG/aura/builds/671722230

1 Ответ

0 голосов
/ 06 апреля 2020

Работает ли он за пределами Docker? Я не знаком с тем, как они это делают на Mac, но, по крайней мере, на Windows, я считаю, что Docker работает на виртуальной машине с собственными ограничениями дискового пространства, поэтому, возможно, Docker не хватает места, и это проблема, которую вы подбегаете. Может быть стоит посмотреть на это.

...