Skip to content

Conversation

chirizxc
Copy link
Contributor

@chirizxc chirizxc commented Jul 23, 2025

Summary

Part of #2331

Test Plan

cargo nextest run flake8_use_pathlib

@chirizxc
Copy link
Contributor Author

@ntBre It's part of #19213 (check_os_pathlib_single_arg_calls)

Copy link
Contributor

github-actions bot commented Jul 23, 2025

ruff-ecosystem results

Linter (stable)

✅ ecosystem check detected no linter changes.

Linter (preview)

ℹ️ ecosystem check detected linter changes. (+0 -0 violations, +212 -0 fixes in 5 projects; 50 projects unchanged)

apache/airflow (+0 -0 violations, +50 -0 fixes)

ruff check --no-cache --exit-zero --ignore RUF9 --no-fix --output-format concise --preview --select ALL

+ airflow-core/tests/unit/utils/log/test_file_processor_handler.py:105:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- airflow-core/tests/unit/utils/log/test_file_processor_handler.py:105:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ airflow-core/tests/unit/utils/log/test_log_reader.py:96:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- airflow-core/tests/unit/utils/log/test_log_reader.py:96:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ airflow-core/tests/unit/utils/test_file.py:106:9: PTH102 [*] `os.mkdir()` should be replaced by `Path.mkdir()`
- airflow-core/tests/unit/utils/test_file.py:106:9: PTH102 `os.mkdir()` should be replaced by `Path.mkdir()`
+ airflow-core/tests/unit/utils/test_file.py:164:9: PTH102 [*] `os.mkdir()` should be replaced by `Path.mkdir()`
- airflow-core/tests/unit/utils/test_file.py:164:9: PTH102 `os.mkdir()` should be replaced by `Path.mkdir()`
+ airflow-ctl/src/airflowctl/api/client.py:133:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- airflow-ctl/src/airflowctl/api/client.py:133:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
... 41 additional changes omitted for rule PTH103
... 40 additional changes omitted for project

apache/superset (+0 -0 violations, +6 -0 fixes)

ruff check --no-cache --exit-zero --ignore RUF9 --no-fix --output-format concise --preview --select ALL

+ superset/initialization/__init__.py:121:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- superset/initialization/__init__.py:121:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ superset/initialization/__init__.py:814:17: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- superset/initialization/__init__.py:814:17: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ superset/utils/core.py:1211:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- superset/utils/core.py:1211:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`

bokeh/bokeh (+0 -0 violations, +14 -0 fixes)

ruff check --no-cache --exit-zero --ignore RUF9 --no-fix --output-format concise --preview --select ALL

+ tests/support/defaults.py:114:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tests/support/defaults.py:114:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tests/support/plugins/jupyter_notebook.py:89:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tests/support/plugins/jupyter_notebook.py:89:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tests/support/util/examples.py:243:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tests/support/util/examples.py:243:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tests/support/util/filesystem.py:178:1: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tests/support/util/filesystem.py:178:1: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tests/support/util/filesystem.py:87:17: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tests/support/util/filesystem.py:87:17: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
... 4 additional changes omitted for project

milvus-io/pymilvus (+0 -0 violations, +18 -0 fixes)

ruff check --no-cache --exit-zero --ignore RUF9 --no-fix --output-format concise --preview

+ examples/bulk_import/example_bulkinsert_csv.py:122:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- examples/bulk_import/example_bulkinsert_csv.py:122:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ examples/bulk_import/example_bulkinsert_csv.py:127:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- examples/bulk_import/example_bulkinsert_csv.py:127:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ examples/bulk_import/example_bulkinsert_json.py:166:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- examples/bulk_import/example_bulkinsert_json.py:166:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ examples/bulk_import/example_bulkinsert_json.py:171:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- examples/bulk_import/example_bulkinsert_json.py:171:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ examples/bulk_import/example_bulkinsert_numpy.py:124:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- examples/bulk_import/example_bulkinsert_numpy.py:124:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
... 8 additional changes omitted for project

zulip/zulip (+0 -0 violations, +124 -0 fixes)

ruff check --no-cache --exit-zero --ignore RUF9 --no-fix --output-format concise --preview --select ALL

+ scripts/lib/puppet_cache.py:55:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- scripts/lib/puppet_cache.py:55:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ scripts/lib/zulip_tools.py:213:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- scripts/lib/zulip_tools.py:213:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ scripts/lib/zulip_tools.py:222:13: PTH102 [*] `os.mkdir()` should be replaced by `Path.mkdir()`
- scripts/lib/zulip_tools.py:222:13: PTH102 `os.mkdir()` should be replaced by `Path.mkdir()`
+ scripts/lib/zulip_tools.py:284:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- scripts/lib/zulip_tools.py:284:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ scripts/lib/zulip_tools.py:646:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- scripts/lib/zulip_tools.py:646:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tools/lib/provision.py:56:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tools/lib/provision.py:56:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tools/lib/provision_inner.py:62:9: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tools/lib/provision_inner.py:62:9: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tools/lib/test_script.py:126:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
- tools/lib/test_script.py:126:5: PTH103 `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
+ tools/setup/generate_bots_integrations_static_files.py:23:5: PTH103 [*] `os.makedirs()` should be replaced by `Path.mkdir(parents=True)`
... 102 additional changes omitted for rule PTH103
+ tools/setup/generate_landing_page_images.py:26:9: PTH102 [*] `os.mkdir()` should be replaced by `Path.mkdir()`
- tools/setup/generate_landing_page_images.py:26:9: PTH102 `os.mkdir()` should be replaced by `Path.mkdir()`
+ zerver/management/commands/backup.py:41:13: PTH102 [*] `os.mkdir()` should be replaced by `Path.mkdir()`
- zerver/management/commands/backup.py:41:13: PTH102 `os.mkdir()` should be replaced by `Path.mkdir()`
+ zerver/worker/base.py:275:13: PTH102 [*] `os.mkdir()` should be replaced by `Path.mkdir()`
- zerver/worker/base.py:275:13: PTH102 `os.mkdir()` should be replaced by `Path.mkdir()`
... 101 additional changes omitted for project

Changes by rule (2 rules affected)

code total + violation - violation + fix - fix
PTH103 200 0 0 200 0
PTH102 12 0 0 12 0

@ntBre ntBre self-requested a review July 23, 2025 17:55
@chirizxc
Copy link
Contributor Author

I see I made a mistake somewhere

@chirizxc
Copy link
Contributor Author

chirizxc commented Jul 23, 2025

Yes, it's because of a condition in check_os_pathlib_single_arg_calls

@chirizxc
Copy link
Contributor Author

now autofixes will be for all possible cases except dir_fd

@chirizxc
Copy link
Contributor Author

I think this PR can also include PTH211, there will be similar autofix

@ntBre ntBre added fixes Related to suggested fixes for violations preview Related to preview mode features labels Jul 24, 2025
Copy link
Contributor

@ntBre ntBre left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! I have a few suggestions here, but most of them are pretty minor, and this looks good overall. The main question is around adding the parents=True argument.

Copy link
Contributor

@ntBre ntBre left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks! This looks good except for some more concerns about argument handling, sorry for not catching this earlier.

@chirizxc
Copy link
Contributor Author

in this variant only for the case when all arguments are positional fix will make them named to avoid the problem with TypeError: Path.mkdir() got multiple values for argument ‘parents’

@chirizxc
Copy link
Contributor Author

Maybe there are more cases that I didn't see, I'll try to see more

@chirizxc chirizxc requested a review from ntBre August 1, 2025 15:38
@chirizxc
Copy link
Contributor Author

chirizxc commented Aug 1, 2025

We have only two autofix outputs, when all args positional:

  1. already used in the code
os.makedirs("name", 0o777, False) # => 
pathlib.Path("name").mkdir(mode=0o777, exist_ok=False, parents=True)
os.makedirs("name", 0o777, False) # =>
pathlib.Path("name").mkdir(0o777, True, False)

…inal call uses exactly 3 positional arguments and no keywords
@chirizxc
Copy link
Contributor Author

chirizxc commented Aug 6, 2025

# ruff: noqa: FBT003
import os

os.makedirs("name", True)
os.makedirs("name", 0o777)
os.makedirs("name", 0o777, True)
os.makedirs("name", 0o777, exist_ok=True)
os.makedirs("name", mode=0o777, exist_ok=True)
os.makedirs(name="name", mode=0o777, exist_ok=True)
os.makedirs("name", exist_ok=True, mode=0o777)

os.makedirs("name", idk="123")
os.makedirs("name", mode=0o777, exist_ok=False, x=True)

after fix:

# ruff: noqa: FBT003
import os
from pathlib import Path

Path("name").mkdir(True, parents=True)
Path("name").mkdir(0o777, parents=True)
Path("name").mkdir(0o777, True, True)
Path("name").mkdir(0o777, exist_ok=True, parents=True)
Path("name").mkdir(mode=0o777, exist_ok=True, parents=True)
Path("name").mkdir(mode=0o777, exist_ok=True, parents=True)
Path("name").mkdir(exist_ok=True, mode=0o777, parents=True)

os.makedirs("name", idk="123")
os.makedirs("name", mode=0o777, exist_ok=False, x=True)

@chirizxc
Copy link
Contributor Author

@ntBre can you check this realization please?

@ntBre
Copy link
Contributor

ntBre commented Aug 12, 2025

Yes, sorry, this has been on my todo list. Do you have a question about the implementation or is this just ready for review again?

And sorry for all the snapshot conflicts, we just updated our diagnostic rendering. I think you should just need to accept the new versions of the snapshots after re-running the tests.

@chirizxc
Copy link
Contributor Author

Yes, sorry, this has been on my todo list. Do you have a question about the implementation or is this just ready for review again?

And sorry for all the snapshot conflicts, we just updated our diagnostic rendering. I think you should just need to accept the new versions of the snapshots after re-running the tests.

it's ready

Copy link
Contributor

@ntBre ntBre left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you, this is looking good. I had a couple more, smaller argument validation suggestions and a potential simplification for the parents argument addition. Thanks for handling all of my pedantic feedback here, these are going to be great fixes :)

Copy link
Contributor

@ntBre ntBre left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thank you!

@ntBre ntBre changed the title [flake8-use-pathlib] Add autofix for PTH102, PTH103 [flake8-use-pathlib] Add fixes for PTH102 and PTH103 Aug 20, 2025
@ntBre ntBre merged commit d04dcd9 into astral-sh:main Aug 20, 2025
35 checks passed
dcreager added a commit that referenced this pull request Aug 21, 2025
* main: (29 commits)
  [ty] add docstrings to completions based on type (#20008)
  [`pyupgrade`] Avoid reporting `__future__` features as unnecessary when they are used (`UP010`) (#19769)
  [`flake8-use-pathlib`] Add fixes for `PTH102` and `PTH103` (#19514)
  [ty] correctly ignore field specifiers when not specified (#20002)
  `Option::unwrap` is now const (#20007)
  [ty] Re-arrange "list modules" implementation for Salsa caching
  [ty] Test "list modules" versus "resolve module" in every mdtest
  [ty] Wire up "list modules" API to make module completions work
  [ty] Tweak some completion tests
  [ty] Add "list modules" implementation
  [ty] Lightly expose `FileModule` and `NamespacePackage` fields
  [ty] Add some more helper routines to `ModulePath`
  [ty] Fix a bug when converting `ModulePath` to `ModuleName`
  [ty] Split out another constructor for `ModuleName`
  [ty] Add stub-file tests to existing module resolver
  [ty] Expose some routines in the module resolver
  [ty] Add more path helper functions
  [`flake8-annotations`] Remove unused import in example (`ANN401`) (#20000)
  [ty] distinguish base conda from child conda (#19990)
  [ty] Fix server hang (#19991)
  ...
@chirizxc chirizxc deleted the feat/pth-autofixes branch September 18, 2025 14:39
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
fixes Related to suggested fixes for violations preview Related to preview mode features
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants