Skip to content

black could more efficiently skip directories listed in .gitignore #4405

@rmcloughlin

Description

@rmcloughlin

Say I have this file structure:

my-project
├── large_ignored_dir
│   ├── a.py
│   ├── inner
│   │   └── b.py
│   ├── inner2
│   │   └── c.py
│   └── inner3
│       └── d.py
└── z.py

The only file I want black to pay attention to is z.py.

Then I run black --exclude='large_ignored_dir/' --check -v . which shows me:

Identified `/` as project root containing a file system root.
Found input source directory: "[...]/my-project"
[...]/my-project/large_ignored_dir ignored: matches the --exclude regular expression
would reformat [...]/my-project/z.py

Oh no! 💥 💔 💥
1 file would be reformatted.

That seems to be the correct behavior.

But black is supposed to automatically ignore directories listed in .gitignore (docs). So if I add a .gitignore file containing this line:

large_ignored_dir/

Then I should be able to run black --check -v . and see the same result as above. But instead I see:

Identified `/` as project root containing a file system root.
Found input source directory: "[...]/my-project"
[...]/my-project/large_ignored_dir/inner ignored: matches a .gitignore file content
[...]/my-project/large_ignored_dir/a.py ignored: matches a .gitignore file content
[...]/my-project/large_ignored_dir/inner2 ignored: matches a .gitignore file content
[...]/my-project/large_ignored_dir/inner3 ignored: matches a .gitignore file content
would reformat [...]/my-project/z.py

Oh no! 💥 💔 💥
1 file would be reformatted.

Even though the final result is the same (only z.py is reformatted), in this second case black is wasting time checking files that it could have skipped. Instead of ignoring all of large_ignored_dir it is descending one level inside it and then deciding to skip every file and subdirectory.

This has performance consequences with directories like node_modules and __pycache__.

Environment

  • Black's version: 24.4.2
  • OS and Python version: macOS Sonoma 14.5, M1 chip, Python 3.12

Metadata

Metadata

Assignees

No one assigned

    Labels

    T: bugSomething isn't working

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions