1- [build-system ]
2- requires = [" pdm-backend" ]
3- build-backend = " pdm.backend"
4-
51[project ]
62name = " stack-pr"
73authors = [
@@ -20,20 +16,40 @@ classifiers = [
2016 " Intended Audience :: Developers" ,
2117 " Topic :: Software Development :: Version Control :: Git" ,
2218 " License :: OSI Approved :: Apache Software License" ,
19+ " Operating System :: OS Independent" ,
20+ " Environment :: Console" ,
21+ " Topic :: Utilities" ,
2322 " Programming Language :: Python" ,
23+ " Programming Language :: Python :: 3.9" ,
24+ " Programming Language :: Python :: 3.10" ,
25+ " Programming Language :: Python :: 3.11" ,
26+ " Programming Language :: Python :: 3.12" ,
27+ " Programming Language :: Python :: 3.13" ,
2428]
2529# Version is dynamically set by pdm by the SCM version
2630dynamic = [" version" ]
27- dependencies = []
31+ dependencies = [" typing_extensions; python_version<\" 3.13\" " ]
32+
33+ [project .optional-dependencies ]
34+ dev = [
35+ " pytest" ,
36+ " pytest-mock" ,
37+ " mypy" ,
38+ " ruff" ,
39+ ]
2840
2941[project .urls ]
30- Homepage = " https://github.com/modularml /stack-pr"
31- Repository = " https://github.com/modularml /stack-pr"
32- "Bug Tracker" = " https://github.com/modularml /stack-pr/issues"
42+ Homepage = " https://github.com/modular /stack-pr"
43+ Repository = " https://github.com/modular /stack-pr"
44+ "Bug Tracker" = " https://github.com/modular /stack-pr/issues"
3345
3446[project .scripts ]
3547stack-pr = " stack_pr.cli:main"
3648
49+ [build-system ]
50+ requires = [" pdm-backend" ]
51+ build-backend = " pdm.backend"
52+
3753[tool .pdm ]
3854distribution = true
3955
@@ -52,4 +68,134 @@ pdm = ">=2.17.1,<2.18"
5268[tool .pixi .tasks ]
5369
5470[tool .pixi .dependencies ]
55- python = " >=3.8"
71+ python = " 3.9.*"
72+
73+ [tool .ruff ]
74+
75+ # Same as Black.
76+ line-length = 88
77+
78+ # Assume Python 3.9
79+ target-version = " py39"
80+
81+ [tool .ruff .lint ]
82+ # Enable pycodestyle (`E`), Pyflakes (`F`), and isort (`I`) codes
83+ select = [
84+ " E" , # pycodestyle errors
85+ " F" , # pyflakes
86+ " I" , # isort
87+ " B" , # flake8-bugbear
88+ " C4" , # flake8-comprehensions
89+ " UP" , # pyupgrade
90+ " N" , # pep8-naming
91+ " SIM" , # flake8-simplify
92+ " RUF" , # ruff-specific rules
93+ " W" , # pycodestyle warnings
94+ " YTT" , # flake8-2020
95+ " ANN" , # flake8-annotations
96+ " S" , # flake8-bandit
97+ " BLE" , # flake8-blind-except
98+ " FBT" , # flake8-boolean-trap
99+ " A" , # flake8-builtins
100+ " C" , # flake8-comprehensions
101+ " DTZ" , # flake8-datetimez
102+ " T10" , # flake8-debugger
103+ " ISC" , # flake8-implicit-str-concat
104+ " G" , # flake8-logging-format
105+ " INP" , # flake8-no-pep420
106+ " PIE" , # flake8-pie
107+ " T20" , # flake8-print
108+ " PT" , # flake8-pytest-style
109+ " Q" , # flake8-quotes
110+ " RSE" , # flake8-raise
111+ " RET" , # flake8-return
112+ " SLF" , # flake8-self
113+ " TID" , # flake8-tidy-imports
114+ " ARG" , # flake8-unused-arguments
115+ " PTH" , # flake8-use-pathlib
116+ " ERA" , # eradicate
117+ " PD" , # pandas-vet
118+ " PGH" , # pygrep-hooks
119+ " PL" , # pylint
120+ " TRY" , # tryceratops
121+ " FA100" , # future-rewritable-type-annotation
122+ " PYI036" , # bad-exit-annotation
123+ # "COM812", # trailing-comma (this one makes ruff formater mad)
124+ ]
125+
126+ # Ignore specific rules
127+ ignore = [
128+ # This is just too complex to do anything about when invoking gh suprocess.
129+ " S603" , # subprocess call with untrusted input
130+
131+ # We use some of the strings for output in the CLI and want specific formatting.
132+ " TRY003" , # Avoid specifying long messages outside exception class
133+
134+ # We forward kwargs a lot and ruff doesn't like it. (more than 5)
135+ " PLR0913" , # Too many arguments
136+
137+ # FIXME: We use print statements in the CLI instead of stderr/stdout (this may change)
138+ " T201" , # allow print statements
139+
140+ # FIXME: Some of our strings are long for CLI output. We should refactor them.
141+ " E501" , # Line too long
142+ ]
143+
144+ # Borrowing a rustism and allow unused variables when underscore-prefixed.
145+ dummy-variable-rgx = " ^(_+|(_+[a-zA-Z0-9_]*[a-zA-Z0-9]+?))$"
146+
147+ [tool .ruff .lint .isort ]
148+ known-first-party = [" stack_pr" ]
149+
150+ [tool .ruff .lint .mccabe ]
151+ # Unlike Flake8, default to a complexity level of 16.
152+ max-complexity = 16
153+
154+ [tool .ruff .lint .per-file-ignores ]
155+ # Ignore unused imports in __init__.py files
156+ "__init__.py" = [" F401" ]
157+
158+ [tool .ruff .lint .pydocstyle ]
159+ convention = " google"
160+
161+ [tool .ruff .lint .pycodestyle ]
162+ max-doc-length = 88
163+
164+ [tool .ruff .lint .flake8-quotes ]
165+ docstring-quotes = " double"
166+ inline-quotes = " double"
167+ multiline-quotes = " double"
168+
169+ [tool .ruff .lint .extend-per-file-ignores ]
170+ # Allow certain useful patterns in tests
171+ "tests/**/*.py" = [
172+ " S101" , # allow assert statements within if statements
173+ " ARG" , # allow unused arguments
174+ " FBT" , # allow boolean traps
175+ " ANN401" , # allow Any in tests
176+ " T201" , # allow print statements in tests
177+ " PLR2004" , # allow magic value comparisons in tests
178+ ]
179+
180+ [tool .pytest .ini_options ]
181+ asyncio_mode = " auto"
182+ asyncio_default_fixture_loop_scope = " function"
183+ testpaths = [" tests" ]
184+ python_files = [" test_*.py" ]
185+ addopts = " -v"
186+
187+ [tool .mypy ]
188+ # Let's be strict.
189+ python_version = " 3.9"
190+ warn_return_any = true
191+ warn_unused_configs = true
192+ disallow_untyped_defs = true
193+ disallow_incomplete_defs = true
194+ check_untyped_defs = true
195+ disallow_untyped_decorators = true
196+ no_implicit_optional = true
197+ warn_redundant_casts = true
198+ warn_unused_ignores = true
199+ warn_no_return = true
200+ warn_unreachable = true
201+ strict_optional = true
0 commit comments