Skip to content

Commit

Permalink
fix: ignore redirects and use more specific urls
Browse files Browse the repository at this point in the history
  • Loading branch information
beckermr committed Nov 27, 2024
1 parent ca9acad commit 66e2786
Show file tree
Hide file tree
Showing 2 changed files with 55 additions and 6 deletions.
32 changes: 26 additions & 6 deletions conda_smithy/lint_recipe.py
Original file line number Diff line number Diff line change
Expand Up @@ -413,9 +413,18 @@ def _maintainer_exists(maintainer: str) -> bool:
gh = _cached_gh()
try:
gh.get_user(maintainer)
is_user = True
except github.UnknownObjectException:
return False
return True
is_user = False

# for w/e reason, the user endpoint returns an entry for orgs
# however the org endpoint does not return an entry for users
# so we have to check both
try:
gh.get_organization(maintainer)
is_org = True
except github.UnknownObjectException:
is_org = False
else:
# this API request has no token and so has a restrictive rate limit
# return (
Expand All @@ -425,12 +434,23 @@ def _maintainer_exists(maintainer: str) -> bool:
# == 200
# )
# so we check two public URLs instead.
# 1. github.com/<maintainer> - this URL works for all users and all orgs
# 1. github.com/<maintainer>?tab=repositories - this URL works for all users and all orgs
# 2. https://github.com/orgs/<maintainer>/teams - this URL only works for
# orgs so we make sure it fails
req_profile = requests.get(f"https://github.com/{maintainer}")
req_org = requests.get(f"https://github.com/orgs/{maintainer}/teams")
return req_profile.status_code == 200 and req_org.status_code != 200
# we do not allow redirects to ensure we get the correct status code
# for the specific URL we requested
req_profile = requests.get(
f"https://github.com/{maintainer}?tab=repositories",
allow_redirects=False,
)
is_user = req_profile.status_code == 200
req_org = requests.get(
f"https://github.com/orgs/{maintainer}/teams",
allow_redirects=False,
)
is_org = req_org.status_code == 200

return is_user and not is_org


@lru_cache(maxsize=1)
Expand Down
29 changes: 29 additions & 0 deletions tests/test_lint_recipe.py
Original file line number Diff line number Diff line change
Expand Up @@ -1878,6 +1878,35 @@ def test_maintainer_exists(self):
expected_message = 'Recipe maintainer "conda-forge" does not exist'
self.assertIn(expected_message, lints)

def test_maintainer_exists_no_token(self):
gh_token = os.environ.get("GH_TOKEN", None)
try:
if "GH_TOKEN" in os.environ:
del os.environ["GH_TOKEN"]

lints, _ = linter.lintify_meta_yaml(
{"extra": {"recipe-maintainers": ["support"]}},
conda_forge=True,
)
expected_message = 'Recipe maintainer "support" does not exist'
self.assertIn(expected_message, lints)

lints, _ = linter.lintify_meta_yaml(
{"extra": {"recipe-maintainers": ["isuruf"]}}, conda_forge=True
)
expected_message = 'Recipe maintainer "isuruf" does not exist'
self.assertNotIn(expected_message, lints)

lints, _ = linter.lintify_meta_yaml(
{"extra": {"recipe-maintainers": ["conda-forge"]}},
conda_forge=True,
)
expected_message = 'Recipe maintainer "conda-forge" does not exist'
self.assertIn(expected_message, lints)
finally:
if gh_token is not None:
os.environ["GH_TOKEN"] = gh_token

def test_maintainer_team_exists(self):
lints, _ = linter.lintify_meta_yaml(
{
Expand Down

0 comments on commit 66e2786

Please sign in to comment.