Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add: pagination support for issue requests #140

Merged
merged 1 commit into from
Mar 20, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
- Fix: Refactor all issue related GitHub methods to gh_client module (@lwasser, #125)
- Add: support for partners and emeritus_editor in contributor model (@lwasser, #133)
- Fix: Refactor all contributor GitHub related methods into gh_client module from contributors module (@lwasser, #125)
- Fix: Add support for pagination in github issue requests (@lwasser, #139)


## [v0.2.3] - 2024-02-29
Expand Down
54 changes: 48 additions & 6 deletions src/pyosmeta/github_api.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@

import logging
import os
import time

import requests
from dataclasses import dataclass
Expand Down Expand Up @@ -80,28 +81,69 @@
)
return url

def handle_rate_limit(self, response):
"""
Handle rate limiting by waiting until the rate limit resets.

Parameters
----------
response : requests.Response
The response object from the API request.

Notes
-----
This method checks the remaining rate limit in the response headers.
If the remaining requests are exhausted, it calculates the time
until the rate limit resets and sleeps accordingly.
"""

if "X-RateLimit-Remaining" in response.headers:
remaining_requests = int(response.headers["X-RateLimit-Remaining"])

Check warning on line 101 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L101

Added line #L101 was not covered by tests
if remaining_requests <= 0:
reset_time = int(response.headers["X-RateLimit-Reset"])
sleep_time = max(reset_time - time.time(), 0) + 1
time.sleep(sleep_time)

Check warning on line 105 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L103-L105

Added lines #L103 - L105 were not covered by tests

def return_response(self) -> list[dict[str, object]]:
"""
Make a GET request to the Github API endpoint
Deserialize json response to list of dicts.

Handles pagination as github has a REST api 100 request max.

Returns
-------
list
List of dict items each containing a review issue
"""

results = []

Check warning on line 120 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L120

Added line #L120 was not covered by tests
# This is computed as a property. Reassign here to support pagination
# and new urls for each page
api_endpoint_url = self.api_endpoint

Check warning on line 123 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L123

Added line #L123 was not covered by tests
try:
response = requests.get(
self.api_endpoint,
headers={"Authorization": f"token {self.get_token()}"},
)
response.raise_for_status()
while True:
response = requests.get(

Check warning on line 126 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L125-L126

Added lines #L125 - L126 were not covered by tests
api_endpoint_url,
headers={"Authorization": f"token {self.get_token()}"},
)
response.raise_for_status()
results.extend(response.json())

Check warning on line 131 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L130-L131

Added lines #L130 - L131 were not covered by tests

# Check if there are more pages to fetch
if "next" in response.links:
next_url = response.links["next"]["url"]
api_endpoint_url = next_url

Check warning on line 136 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L135-L136

Added lines #L135 - L136 were not covered by tests
else:
break

Check warning on line 138 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L138

Added line #L138 was not covered by tests

# Handle rate limiting
self.handle_rate_limit(response)

Check warning on line 141 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L141

Added line #L141 was not covered by tests

except requests.HTTPError as exception:
raise exception

return response.json()
return results

Check warning on line 146 in src/pyosmeta/github_api.py

View check run for this annotation

Codecov / codecov/patch

src/pyosmeta/github_api.py#L146

Added line #L146 was not covered by tests

def get_repo_meta(self, url: str) -> dict[str, Any] | None:
"""
Expand Down