Pytest was hiting github.com rate limits#1363
Conversation
There was a problem hiding this comment.
Pull request overview
Updates integration tests and GitHub release-fetching logic to use authenticated GitHub API requests in CI, reducing flakiness from shared-runner rate limits.
Changes:
- Add a helper to inject an Authorization header when
GITHUB_TOKENis present. - Pass the header into
get_release_info()GitHub API calls. - Export
GITHUB_TOKENfromsecrets.GITHUB_TOKENin the GitHub Actions pytest job.
Reviewed changes
Copilot reviewed 2 out of 2 changed files in this pull request and generated 2 comments.
| File | Description |
|---|---|
| ardupilot_methodic_configurator/backend_internet.py | Adds optional GitHub auth headers and uses them for release API requests |
| .github/workflows/pytest.yml | Exposes GITHUB_TOKEN to the pytest step so CI runs authenticate to GitHub API |
| return certifi_path | ||
|
|
||
|
|
||
| def _get_github_api_headers() -> dict[str, str]: |
There was a problem hiding this comment.
The return annotation uses dict[str, str], which requires Python 3.9+ unless this module uses from __future__ import annotations. If the project supports Python 3.8 (common for many test matrices), this can raise at import time. Consider switching to typing.Dict[str, str] / Mapping[str, str], or ensure future-annotations / Python version constraints match this syntax.
| if token: | ||
| return {"Authorization": f"Bearer {token}"} | ||
| return {} |
There was a problem hiding this comment.
It’s safer to normalize the token before constructing the header (e.g., trimming whitespace/newlines). requests will reject header values containing newlines with InvalidHeader, which can happen if the env var includes a trailing newline. Consider applying strip() when reading GITHUB_TOKEN and only sending the header if the stripped value is non-empty.
| if token: | |
| return {"Authorization": f"Bearer {token}"} | |
| return {} | |
| if token is None: | |
| return {} | |
| token = token.strip() | |
| if not token: | |
| return {} | |
| return {"Authorization": f"Bearer {token}"} |
The integration tests make unauthenticated GitHub API requests, which are limited to 60 requests/hour per source IP.
macOS GitHub Actions runners frequently share the same egress IPs across many concurrent workflows, exhausting the quota.
Linux/Windows runners are less susceptible due to different network allocation.
Fix 1 — backend_internet.py:130:
Added _get_github_api_headers() which reads GITHUB_TOKEN from the environment and returns an Authorization: Bearer <token> header.
This header is now passed to every get_release_info() call.
An authenticated request raises the rate limit from 60 to 5,000 requests/hour.
Fix 2 — pytest.yml:156:
Added env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} to the pytest step.
secrets.GITHUB_TOKEN is a built-in token automatically available in every GitHub Actions run — no repository secret configuration is required.
All three OS matrix runners (Ubuntu, Windows, macOS) will now use authenticated requests.
4a1b06e to
2db27ab
Compare
☂️ Python Coverage
Overall Coverage
New FilesNo new covered files... Modified Files
|
The integration tests make unauthenticated GitHub API requests, which are limited to 60 requests/hour per source IP. macOS GitHub Actions runners frequently share the same egress IPs across many concurrent workflows, exhausting the quota. Linux/Windows runners are less susceptible due to different network allocation.
Fix 1 — backend_internet.py:130:
Added _get_github_api_headers() which reads GITHUB_TOKEN from the environment and returns an Authorization: Bearer header. This header is now passed to every get_release_info() call. An authenticated request raises the rate limit from 60 to 5,000 requests/hour.
Fix 2 — pytest.yml:156:
Added env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} to the pytest step. secrets.GITHUB_TOKEN is a built-in token automatically available in every GitHub Actions run — no repository secret configuration is required. All three OS matrix runners (Ubuntu, Windows, macOS) will now use authenticated requests.