Skip to content

Commit 2543d59

Browse files
committed
Merge branch 'main' into pep-735
2 parents 456eaf2 + 9574b40 commit 2543d59

File tree

28 files changed

+146
-182
lines changed

28 files changed

+146
-182
lines changed

.github/workflows/python-checks.yml

Lines changed: 78 additions & 93 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,20 @@ on:
1212

1313
permissions: read-all
1414

15+
env:
16+
CACHE_GLOBS: |
17+
**/pyproject.toml
18+
**/requirements*.txt
19+
**/setup.py
20+
**/uv.lock
21+
ENDPOINT_WHITELIST: >-
22+
pypi.org:443
23+
github.com:443
24+
releases.astral.sh
25+
files.pythonhosted.org:443
26+
*.github.com:443
27+
*.githubusercontent.com:443
28+
1529
jobs:
1630
pytest:
1731
runs-on: ${{ matrix.os }}
@@ -24,7 +38,6 @@ jobs:
2438
- '3.11'
2539
- '3.12'
2640
- '3.13'
27-
- '3.14'
2841
os:
2942
- ubuntu-latest
3043
- windows-latest
@@ -41,19 +54,28 @@ jobs:
4154
- uses: step-security/harden-runner@a90bcbc6539c36a85cdfeb73f7e2f433735f215b
4255
with:
4356
disable-sudo: true
44-
egress-policy: audit
57+
egress-policy: block
58+
allowed-endpoints: auth.docker.io:443 ${{ env.ENDPOINT_WHITELIST}}
59+
60+
- id: pytest-run-key
61+
run: |
62+
echo "\
63+
RUN_KEY=\
64+
${{ hashFiles('pyproject.toml') }}\
65+
-${{ matrix.os }}\
66+
-${{ matrix.python-version }}\
67+
-${{ matrix.resolution }}\
68+
" >> $GITHUB_ENV
4569
4670
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
4771

48-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
72+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
4973
with:
5074
python-version: ${{ matrix.python-version }}
51-
cache: pip
52-
53-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
75+
activate-environment: true
76+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
5477

5578
- if: matrix.resolution != 'limited-dependencies'
56-
continue-on-error: ${{ contains(matrix.python-version, '3.14') }}
5779
run: >-
5880
uv sync
5981
--upgrade
@@ -62,10 +84,9 @@ jobs:
6284
--all-extras
6385
--resolution ${{ matrix.resolution }}
6486
65-
- if: matrix.resolution == 'limited-dependencies'
66-
continue-on-error: ${{ contains(matrix.python-version, '3.14') }}
67-
env:
68-
PARSONS_LIMITED_DEPENDENCIES: 'TRUE'
87+
- env:
88+
UV_RESOLUTION: ${{ matrix.resolution == 'limited-dependencies' && 'highest' || matrix.resolution }}
89+
PARSONS_LIMITED_DEPENDENCIES: ${{ matrix.resolution == 'limited-dependencies' && 'TRUE' || 'FALSE' }}
6990
run: >-
7091
uv sync
7192
--upgrade
@@ -77,23 +98,16 @@ jobs:
7798
uses: actions/cache@cdf6c1fa76f9f475f3d7449005a359c84ca0f306
7899
with:
79100
path: .pytest_cache
80-
key: >-
81-
pytest
82-
-${{ matrix.python-version }}
83-
-${{ matrix.os }}
84-
-${{ matrix.resolution }}
85-
-${{ hashFiles('pyproject.toml') }}
101+
key: pytest-${{ env.RUN_KEY }}
86102

87103
- env:
88-
COVERAGE_FILE: ".coverage.${{ matrix.os }}.${{ matrix.python-version }}.${{ matrix.resolution }}"
89-
continue-on-error: ${{ contains(matrix.python-version, '3.14') }}
90-
run: uv run pytest
104+
COVERAGE_FILE: .coverage.${{ env.RUN_KEY }}
105+
run: uv run pytest --failed-first
91106

92107
- uses: actions/upload-artifact@bbbca2ddaa5d8feaa63e36b76fdaad77386f024f
93-
if: ${{ !contains(matrix.python-version, '3.14') }}
94108
with:
95-
name: coverage-${{ matrix.os }}-${{ matrix.python-version }}-${{ matrix.resolution }}
96-
path: .coverage.${{ matrix.os }}.${{ matrix.python-version }}.${{ matrix.resolution }}
109+
name: coverage-${{ env.RUN_KEY }}
110+
path: .coverage.${{ env.RUN_KEY }}
97111
include-hidden-files: true
98112

99113
pytest-extras-config:
@@ -107,19 +121,15 @@ jobs:
107121
with:
108122
disable-sudo: true
109123
egress-policy: block
110-
allowed-endpoints: >
111-
files.pythonhosted.org:443
112-
github.com:443
113-
pypi.org:443
124+
allowed-endpoints: ${{ env.ENDPOINT_WHITELIST}}
114125

115126
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
116127

117-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
128+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
118129
with:
119130
python-version: '3.13'
120-
cache: pip
121-
122-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
131+
activate-environment: true
132+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
123133

124134
- run: >-
125135
uv sync
@@ -159,53 +169,50 @@ jobs:
159169
fail-fast: false
160170
matrix:
161171
extra: ${{ fromJson(needs.pytest-extras-config.outputs.extras) }}
162-
python-version:
163-
- '3.13'
164-
os:
165-
- ubuntu-latest
166-
resolution:
167-
- highest
172+
python-version: ['3.13']
173+
os: ['ubuntu-latest']
174+
resolution: ['highest']
168175

169176
steps:
170177
- uses: step-security/harden-runner@a90bcbc6539c36a85cdfeb73f7e2f433735f215b
171178
with:
172179
disable-sudo: true
173180
egress-policy: block
174-
allowed-endpoints: >
175-
files.pythonhosted.org:443
176-
github.com:443
177-
pypi.org:443
181+
allowed-endpoints: ${{ env.ENDPOINT_WHITELIST}}
182+
183+
- id: pytest-run-key
184+
run: |
185+
echo "\
186+
RUN_KEY=\
187+
${{ hashFiles('pyproject.toml') }}\
188+
-${{ matrix.os }}\
189+
-${{ matrix.python-version }}\
190+
-${{ matrix.resolution }}\
191+
" >> $GITHUB_ENV
178192
179193
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
180194

181-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
195+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
182196
with:
183197
python-version: ${{ matrix.python-version }}
184-
cache: pip
185-
186-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
198+
activate-environment: true
199+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
187200

188201
- env:
189-
PARSONS_LIMITED_DEPENDENCIES: 'TRUE'
202+
UV_RESOLUTION: ${{ matrix.resolution }}
203+
PARSONS_LIMITED_DEPENDENCIES: 'TRUE'
190204
run: >-
191205
uv sync
192206
--upgrade
193207
--no-default-groups
194208
--group test
195209
--extra ${{ matrix.extra }}
196-
--resolution ${{ matrix.resolution }}
197210
198211
- id: cache-pytest
199212
uses: actions/cache@cdf6c1fa76f9f475f3d7449005a359c84ca0f306
200213
with:
201214
path: .pytest_cache
202-
key: >-
203-
pytest
204-
-${{ hashFiles('pyproject.toml') }}
205-
-${{ matrix.os }}
206-
-${{ matrix.python-version }}
207-
-${{ matrix.resolution }}
208-
-${{ matrix.extra }}
215+
key: pytest-${{ env.RUN_KEY }}
209216

210217
- run: uv run pytest test/test_${{ matrix.extra }}
211218

@@ -217,19 +224,15 @@ jobs:
217224
with:
218225
disable-sudo: true
219226
egress-policy: block
220-
allowed-endpoints: >
221-
files.pythonhosted.org:443
222-
github.com:443
223-
pypi.org:443
227+
allowed-endpoints: ${{ env.ENDPOINT_WHITELIST}}
224228

225229
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
226230

227-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
231+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
228232
with:
229233
python-version: '3.13'
230-
cache: pip
231-
232-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
234+
activate-environment: true
235+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
233236

234237
- run: >-
235238
uv sync
@@ -263,20 +266,15 @@ jobs:
263266
with:
264267
disable-sudo: true
265268
egress-policy: block
266-
allowed-endpoints: >
267-
api.github.com:443
268-
files.pythonhosted.org:443
269-
github.com:443
270-
pypi.org:443
269+
allowed-endpoints: ${{ env.ENDPOINT_WHITELIST}}
271270

272271
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
273272

274-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
273+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
275274
with:
276275
python-version: '3.13'
277-
cache: pip
278-
279-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
276+
activate-environment: true
277+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
280278

281279
- run: >-
282280
uv sync
@@ -324,20 +322,15 @@ jobs:
324322
with:
325323
disable-sudo: true
326324
egress-policy: block
327-
allowed-endpoints: >
328-
api.github.com:443
329-
files.pythonhosted.org:443
330-
github.com:443
331-
pypi.org:443
325+
allowed-endpoints: ${{ env.ENDPOINT_WHITELIST}}
332326

333327
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
334328

335-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
329+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
336330
with:
337331
python-version: '3.13'
338-
cache: pip
339-
340-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
332+
activate-environment: true
333+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
341334

342335
- run: >-
343336
uv sync
@@ -384,10 +377,7 @@ jobs:
384377
with:
385378
disable-sudo: true
386379
egress-policy: block
387-
allowed-endpoints: >
388-
api.github.com:443
389-
github.com:443
390-
img.shields.io:443
380+
allowed-endpoints: img.shields.io:443 ${{ env.ENDPOINT_WHITELIST}}
391381

392382
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
393383

@@ -424,20 +414,15 @@ jobs:
424414
with:
425415
disable-sudo: true
426416
egress-policy: block
427-
allowed-endpoints: >
428-
files.pythonhosted.org:443
429-
github.com:443
430-
proxy.golang.org:443
431-
pypi.org:443
417+
allowed-endpoints: proxy.golang.org:443 ${{ env.ENDPOINT_WHITELIST}}
432418

433419
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd
434420

435-
- uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405
421+
- uses: astral-sh/setup-uv@5a095e7a2014a4212f075830d4f7277575a9d098
436422
with:
437423
python-version: '3.13'
438-
cache: pip
439-
440-
- uses: install-pinned/uv@4d66dd6355704140c330bc2a2e6291cbf3bcb67f
424+
activate-environment: true
425+
cache-dependency-glob: ${{ env.CACHE_GLOBS }}
441426

442427
- run: >-
443428
uv sync

docs/conf.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -197,7 +197,7 @@
197197
smv_branch_whitelist = r"^stable|latest$" # creates version for latest master/main branch
198198

199199
# Get tags to whitelist from DOCUMENTED_VERSIONS const
200-
smv_tag_whitelist = "|".join(["^" + version + "$" for version in DOCUMENTED_VERSIONS])
200+
smv_tag_whitelist = "|".join(f"^{version}$" for version in DOCUMENTED_VERSIONS)
201201

202202
# Adds Google Analytics tracking code to the HTML output
203203
googleanalytics_id = "G-L2YB7WHTRG"

parsons/braintree/braintree.py

Lines changed: 10 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import itertools
12
import logging
23

34
import braintree
@@ -327,7 +328,7 @@ def get_subscriptions(
327328
f"Braintree subscriptions search resulted in subscriptions count of {query_count}"
328329
)
329330
if just_ids:
330-
return Table([("id",)] + [[item_id] for item_id in collection.ids])
331+
return Table(list(itertools.chain([["id"]], ([i] for i in collection.ids))))
331332

332333
# Iterating on collection.items triggers web requests in batches of 50 records
333334
# This can be frustratingly slow :-(
@@ -407,15 +408,20 @@ def get_transactions(
407408
query_count = len(collection.ids)
408409
logger.info(f"Braintree transactions resulted in transaction count of {query_count}")
409410
if just_ids:
410-
return Table([("id",)] + [[item_id] for item_id in collection.ids])
411+
return Table(list(itertools.chain([["id"]], ([i] for i in collection.ids))))
411412

412413
# Iterating on collection.items triggers web requests in batches of 50 records
413414
# This can be frustratingly slow :-(
414415
# Also note: Braintree will push you to their new GraphQL API,
415-
# but it, too, paginates with a max of 50 records
416+
# but it, too, paginates with a max of 50 records
416417
logger.debug("Braintree transactions iterating to build transaction table")
417418
return Table(
418-
[self._transaction_header()] + [self._transaction_to_row(r) for r in collection.items]
419+
list(
420+
itertools.chain(
421+
[self._transaction_header()],
422+
(self._transaction_to_row(r) for r in collection.items),
423+
)
424+
)
419425
)
420426

421427
def _dispute_header(self):

parsons/databases/redshift/redshift.py

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1134,7 +1134,7 @@ def upsert(
11341134
logger.info(f"{target_table} vacuumed.")
11351135

11361136
def drop_dependencies_for_cols(self, schema, table, cols):
1137-
fmt_cols = ", ".join([f"'{c}'" for c in cols])
1137+
fmt_cols = ", ".join(f"'{c}'" for c in cols)
11381138
sql_depend = f"""
11391139
select
11401140
distinct dependent_ns.nspname||'.'||dependent_view.relname as table_name
@@ -1163,7 +1163,7 @@ def drop_dependencies_for_cols(self, schema, table, cols):
11631163
tbl = self.query_with_connection(sql_depend, connection)
11641164
dropped_views = [row["table_name"] for row in tbl]
11651165
if dropped_views:
1166-
sql_drop = "\n".join([f"drop view {view} CASCADE;" for view in dropped_views])
1166+
sql_drop = "\n".join(f"drop view {view} CASCADE;" for view in dropped_views)
11671167
tbl = self.query_with_connection(sql_drop, connection)
11681168
logger.info(f"Dropped the following views: {dropped_views}")
11691169

parsons/databases/redshift/rs_table_utilities.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -687,7 +687,7 @@ def get_table_definitions(self, schema=None, table=None):
687687
return None
688688

689689
def join_sql_parts(columns, rows):
690-
return [f"{columns[1]}.{columns[2]}", "\n".join([row[4] for row in rows])]
690+
return [f"{columns[1]}.{columns[2]}", "\n".join(row[4] for row in rows)]
691691

692692
# The query returns the sql over multiple rows
693693
# We need to join then into a single row

0 commit comments

Comments
 (0)