Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

running pytest as a pre-commit hook // no such file or directory issue

in my Python project I use pytest as a pre-commit hook. Some tests create and delete temporary files, everything works fine when I run pytest <test directory>. However, when I run git commit and pre-commit hook triggers pytest, some tests fail because of FileNotFoundError: [Errno 2] No such file or directory: '<file name>'. I have an impression this happens when many files have been changed and are in the staging area (with 1-2 files I do not observe this issue). Here is my pytest section from .pre-commit-config.yaml:

  - repo: local
    hooks:
      - id: pytest-check
        name: pytest-check
        entry: bash -c 'pytest'
        language: system

the output looks as follows:

pytest-check.............................................................Failed
- hook id: pytest-check
- exit code: 1

tests/utils/test_application.py F                                        [ 91%]
tests/utils/test_image_io.py .FFF.........                               [100%]

==================================== ERRORS ====================================
_ ERROR at teardown of test_calling_with_nonexisting_parameter[--non_existing 1337-hm] _

    def teardown_module() -> None:
>       os.remove(OUTPUT_FILE)
E       FileNotFoundError: [Errno 2] No such file or directory: 'output.png'

tests/bdd/step_defs/test_runner_steps.py:98: FileNotFoundError

this does not happen when I run pytest from the console.

with pass_filenames: false and always_run: true the error does not show up any more:

  - repo: local
    hooks:
      - id: pytest-check
        name: pytest-check
        entry: pytest
        language: system
        pass_filenames: false
        always_run: true

with respect to wrapping things in bash, I'm still doing this for pylint:

  - repo: local
    hooks:
      - id: pylint-check
        name: pylint-check
        entry: bash -c 'find . -name "*.py" | xargs pylint'
        language: system
        types: [python]
        pass_filenames: false
        always_run: true

is there any better solution for this? pylint does not support recursion of an unlimited depth, thus I need a bash command there.

Thanks!

Best, Alexey

like image 363
Alexey Abramov Avatar asked Nov 27 '22 05:11

Alexey Abramov


1 Answers

show your output, we can only guess at the problem otherwise

that said, you probably want to use always_run: true and pass_filenames: false -- also your entry is bogus, no need to wrap things in bash, just call the executable directly. Putting all that together:

  - repo: local
    hooks:
      - id: pytest-check
        name: pytest-check
        entry: pytest
        language: system
        pass_filenames: false
        always_run: true

disclaimer: I am the author of pre-commit

like image 97
Anthony Sottile Avatar answered Nov 29 '22 17:11

Anthony Sottile