Skip to content

Commit

Permalink
fix: cache github release data per bench (backport #26382) (#26387)
Browse files Browse the repository at this point in the history
* fix: cache github release data per bench (#26382)

Reduce API calls to github as public calls are limited.

(cherry picked from commit c2d5ef1)

# Conflicts:
#	frappe/utils/caching.py

* chore: conflicts

---------

Co-authored-by: Ankush Menat <ankush@frappe.io>
  • Loading branch information
mergify[bot] and ankush committed May 9, 2024
1 parent 52c335c commit 6e8ef85
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 18 deletions.
13 changes: 6 additions & 7 deletions frappe/utils/caching.py
Original file line number Diff line number Diff line change
Expand Up @@ -130,7 +130,7 @@ def site_cache_wrapper(*args, **kwargs):
return time_cache_wrapper


def redis_cache(ttl: int | None = 3600, user: str | bool | None = None) -> Callable:
def redis_cache(ttl: int | None = 3600, user: str | bool | None = None, shared: bool = False) -> Callable:
"""Decorator to cache method calls and its return values in Redis
args:
Expand All @@ -151,12 +151,11 @@ def clear_cache():
def redis_cache_wrapper(*args, **kwargs):
func_call_key = func_key + "::" + str(__generate_request_cache_key(args, kwargs))
if frappe.cache.exists(func_call_key):
return frappe.cache.get_value(func_call_key, user=user)
else:
val = func(*args, **kwargs)
ttl = getattr(func, "ttl", 3600)
frappe.cache.set_value(func_call_key, val, expires_in_sec=ttl, user=user)
return val
return frappe.cache.get_value(func_call_key, user=user, shared=shared)
val = func(*args, **kwargs)
ttl = getattr(func, "ttl", 3600)
frappe.cache.set_value(func_call_key, val, expires_in_sec=ttl, user=user, shared=shared)
return val

return redis_cache_wrapper

Expand Down
39 changes: 28 additions & 11 deletions frappe/utils/change_log.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
import frappe
from frappe import _, safe_decode
from frappe.utils import cstr
from frappe.utils.caching import redis_cache
from frappe.utils.frappecloud import on_frappecloud


Expand Down Expand Up @@ -250,22 +251,16 @@ def check_release_on_github(
raise ValueError("Repo cannot be empty")

# Get latest version from GitHub
r = requests.get(f"https://api.github.com/repos/{owner}/{repo}/releases")
if r.ok:
latest_non_beta_release = parse_latest_non_beta_release(r.json(), current_version)
if latest_non_beta_release:
return Version(latest_non_beta_release), owner
releases = _get_latest_releases(owner, repo)
latest_non_beta_release = parse_latest_non_beta_release(releases, current_version)
if latest_non_beta_release:
return Version(latest_non_beta_release), owner

return None, None


def security_issues_count(owner: str, repo: str, current_version: Version, target_version: Version) -> int:
import requests

r = requests.get(f"https://api.github.com/repos/{owner}/{repo}/security-advisories")
if not r.ok:
return 0
advisories = r.json()
advisories = _get_security_issues(owner, repo)

def applicable(advisory) -> bool:
# Current version is in vulnerable range
Expand All @@ -285,6 +280,28 @@ def applicable(advisory) -> bool:
return len([sa for sa in advisories if applicable(sa)])


@redis_cache(ttl=6 * 24 * 60 * 60, shared=True)
def _get_latest_releases(owner, repo):
import requests

r = requests.get(f"https://api.github.com/repos/{owner}/{repo}/releases")
if not r.ok:
return []

return r.json()


@redis_cache(ttl=6 * 24 * 60 * 60, shared=True)
def _get_security_issues(owner, repo):
import requests

r = requests.get(f"https://api.github.com/repos/{owner}/{repo}/security-advisories")
if not r.ok:
return []

return r.json()


def parse_github_url(remote_url: str) -> tuple[str, str] | tuple[None, None]:
"""Parse the remote URL to get the owner and repo name."""
import re
Expand Down

0 comments on commit 6e8ef85

Please sign in to comment.