From 688f88b837f9a1e65d422a1658bde464b8bf830d Mon Sep 17 00:00:00 2001 From: ivanharvard <144486839+ivanharvard@users.noreply.github.com> Date: Tue, 5 Aug 2025 17:14:34 -0400 Subject: [PATCH 1/8] added support for auth_method in push() and authenticate() --- lib50/_api.py | 12 +++++++---- lib50/authentication.py | 47 ++++++++++++++++++++++++++++------------- 2 files changed, 40 insertions(+), 19 deletions(-) diff --git a/lib50/_api.py b/lib50/_api.py index b66578d..e78b3de 100644 --- a/lib50/_api.py +++ b/lib50/_api.py @@ -39,7 +39,7 @@ DEFAULT_FILE_LIMIT = 10000 -def push(tool, slug, config_loader, repo=None, data=None, prompt=lambda question, included, excluded: True, file_limit=DEFAULT_FILE_LIMIT): +def push(tool, slug, config_loader, repo=None, data=None, prompt=lambda question, included, excluded: True, file_limit=DEFAULT_FILE_LIMIT, auth_method=None): """ Pushes to Github in name of a tool. What should be pushed is configured by the tool and its configuration in the .cs50.yml file identified by the slug. @@ -61,6 +61,10 @@ def push(tool, slug, config_loader, repo=None, data=None, prompt=lambda question :type prompt: lambda str, list, list => bool, optional :param file_limit: maximum number of files to be matched by any globbing pattern. :type file_limit: int + :param auth_method: The authentication method to use. Accepts `"https"` or `"ssh"`. \ + If any other value is provided, attempts SSH \ + authentication first and fall back to HTTPS if SSH fails. + :type auth_method: str :return: GitHub username and the commit hash :type: tuple(str, str) @@ -89,7 +93,7 @@ def push(tool, slug, config_loader, repo=None, data=None, prompt=lambda question remote, (honesty, included, excluded) = connect(slug, config_loader, file_limit=DEFAULT_FILE_LIMIT) # Authenticate the user with GitHub, and prepare the submission - with authenticate(remote["org"], repo=repo) as user, prepare(tool, slug, user, included): + with authenticate(remote["org"], repo=repo, auth_method=auth_method) as user, prepare(tool, slug, user, included): # Show any prompt if specified if prompt(honesty, included, excluded): @@ -465,7 +469,7 @@ def batch_files(files, size=100): files_list = list(files) for i in range(0, len(files_list), size): yield files_list[i:i + size] - + for batch in batch_files(included): quoted_files = ' '.join(shlex.quote(f) for f in batch) run(git(f"add -f -- {quoted_files}")) @@ -962,7 +966,7 @@ def run(command, quiet=False, timeout=None): ProgressBar.stop_all() passphrase = _prompt_password("Enter passphrase for SSH key: ") child.sendline(passphrase) - + # Get the full output by reading until EOF full_output = child.before + child.after + child.read() command_output = full_output.strip().replace("\r\n", "\n") diff --git a/lib50/authentication.py b/lib50/authentication.py index 71d1e46..196fb79 100644 --- a/lib50/authentication.py +++ b/lib50/authentication.py @@ -32,14 +32,18 @@ class User: init=False) @contextlib.contextmanager -def authenticate(org, repo=None): +def authenticate(org, repo=None, auth_method=None): """ - A contextmanager that authenticates a user with GitHub via SSH if possible, otherwise via HTTPS. + A contextmanager that authenticates a user with GitHub. :param org: GitHub organisation to authenticate with :type org: str :param repo: GitHub repo (part of the org) to authenticate with. Default is the user's GitHub login. :type repo: str, optional + :param auth_method: The authentication method to use. Accepts `"https"` or `"ssh"`. \ + If any other value is provided, attempts SSH \ + authentication first and fall back to HTTPS if SSH fails. + :type auth_method: str, optional :return: an authenticated user :type: lib50.User @@ -51,21 +55,34 @@ def authenticate(org, repo=None): print(user.name) """ - with api.ProgressBar(_("Authenticating")) as progress_bar: - # Both authentication methods can require user input, best stop the bar - progress_bar.stop() + def try_https(org, repo): + with _authenticate_https(org, repo=repo) as user: + return user - # Try auth through SSH + def try_ssh(org, repo): user = _authenticate_ssh(org, repo=repo) - - # SSH auth failed, fallback to HTTPS if user is None: - with _authenticate_https(org, repo=repo) as user: - yield user - # yield SSH user - else: - yield user + raise ConnectionError + return user + + # Showcase the type of authentication based on input + method_label = f" ({auth_method.upper()})" if auth_method in ("https", "ssh") else "" + with api.ProgressBar(_("Authenticating{}").format(method_label)) as progress_bar: + # Both authentication methods can require user input, best stop the bar + progress_bar.stop() + match auth_method: + case "https": + yield try_https(org, repo) + case "ssh": + yield try_ssh(org, repo) + case _: + # Try auth through SSH + try: + yield try_ssh(org, repo) + except ConnectionError: + # SSH auth failed, fallback to HTTPS + yield try_https(org, repo) def logout(): """ @@ -104,7 +121,7 @@ def run_authenticated(user, command, quiet=False, timeout=None): # Try to extract the conflicting branch prefix from the error message # Pattern: 'refs/heads/cs50/problems/2025/x' exists branch_prefix_match = re.search(r"'refs/heads/([^']+)' exists", command_output) - + if branch_prefix_match: conflicting_prefix = branch_prefix_match.group(1) error_msg = _("Looks like you're trying to push to a branch that conflicts with an existing one in the repository.\n" @@ -195,7 +212,7 @@ class State(enum.Enum): else: if not os.environ.get("CODESPACES"): _show_gh_changes_warning() - + return None finally: child.close() From 39bb3a8b34accce0b8a0a9990bd38481eaa6fc4e Mon Sep 17 00:00:00 2001 From: Rongxin Liu Date: Wed, 6 Aug 2025 02:45:24 -0400 Subject: [PATCH 2/8] removed empty lines --- lib50/_api.py | 4 ++-- lib50/authentication.py | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/lib50/_api.py b/lib50/_api.py index e78b3de..31defb1 100644 --- a/lib50/_api.py +++ b/lib50/_api.py @@ -469,7 +469,7 @@ def batch_files(files, size=100): files_list = list(files) for i in range(0, len(files_list), size): yield files_list[i:i + size] - + for batch in batch_files(included): quoted_files = ' '.join(shlex.quote(f) for f in batch) run(git(f"add -f -- {quoted_files}")) @@ -966,7 +966,7 @@ def run(command, quiet=False, timeout=None): ProgressBar.stop_all() passphrase = _prompt_password("Enter passphrase for SSH key: ") child.sendline(passphrase) - + # Get the full output by reading until EOF full_output = child.before + child.after + child.read() command_output = full_output.strip().replace("\r\n", "\n") diff --git a/lib50/authentication.py b/lib50/authentication.py index 196fb79..cc98ab0 100644 --- a/lib50/authentication.py +++ b/lib50/authentication.py @@ -121,7 +121,7 @@ def run_authenticated(user, command, quiet=False, timeout=None): # Try to extract the conflicting branch prefix from the error message # Pattern: 'refs/heads/cs50/problems/2025/x' exists branch_prefix_match = re.search(r"'refs/heads/([^']+)' exists", command_output) - + if branch_prefix_match: conflicting_prefix = branch_prefix_match.group(1) error_msg = _("Looks like you're trying to push to a branch that conflicts with an existing one in the repository.\n" @@ -212,7 +212,7 @@ class State(enum.Enum): else: if not os.environ.get("CODESPACES"): _show_gh_changes_warning() - + return None finally: child.close() From da541a4a5a6c7176d005ca94730092a8cfa2c503 Mon Sep 17 00:00:00 2001 From: Rongxin Liu Date: Thu, 7 Aug 2025 00:05:40 -0400 Subject: [PATCH 3/8] bump version to 3.1.2 --- setup.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/setup.py b/setup.py index 0654ac0..a23c3b1 100644 --- a/setup.py +++ b/setup.py @@ -27,6 +27,6 @@ python_requires=">= 3.8", packages=["lib50"], url="https://github.com/cs50/lib50", - version="3.1.1", + version="3.1.2", include_package_data=True ) From c6144061ccb39212503ff9b3374287073a22f2a6 Mon Sep 17 00:00:00 2001 From: Brandon Nguyen <112731698+bxngyn@users.noreply.github.com> Date: Thu, 7 Aug 2025 09:56:02 -0400 Subject: [PATCH 4/8] vietnamese support --- lib50/locale/vi/LC_MESSAGES/lib50.po | 243 +++++++++++++++++++++++++++ 1 file changed, 243 insertions(+) create mode 100644 lib50/locale/vi/LC_MESSAGES/lib50.po diff --git a/lib50/locale/vi/LC_MESSAGES/lib50.po b/lib50/locale/vi/LC_MESSAGES/lib50.po new file mode 100644 index 0000000..cbc2632 --- /dev/null +++ b/lib50/locale/vi/LC_MESSAGES/lib50.po @@ -0,0 +1,243 @@ +# Vietnamese translations for lib50. +# Copyright (C) 2025 ORGANIZATION +# This file is distributed under the same license as the lib50 project. +# FIRST AUTHOR , 2025. +# +msgid "" +msgstr "" +"Project-Id-Version: lib50 3.1.1\n" +"Report-Msgid-Bugs-To: EMAIL@ADDRESS\n" +"POT-Creation-Date: 2025-08-05 15:21-0400\n" +"PO-Revision-Date: 2025-08-05 15:21-0400\n" +"Last-Translator: FULL NAME \n" +"Language: vi\n" +"Language-Team: vi \n" +"Plural-Forms: nplurals=1; plural=0;\n" +"MIME-Version: 1.0\n" +"Content-Type: text/plain; charset=utf-8\n" +"Content-Transfer-Encoding: 8bit\n" +"Generated-By: Babel 2.17.0\n" + +#: lib50/_api.py:101 +msgid "No files were submitted." +msgstr "Không có tập tin nào để nộp." + +#: lib50/_api.py:158 +#, python-brace-format +msgid "{} does not exist at {}/{}" +msgstr "{} không tồn tại tại {}/{}" + +#: lib50/_api.py:286 +#, python-brace-format +msgid "" +"Cannot include/exclude paths outside the current directory, but such a " +"path ({}) was specified." +msgstr "" +"Không thể bao gồm/loại trừ các đường dẫn bên ngoài thư mục này, nhưng +"đường dẫn ({}) đã được chỉ định." + +#: lib50/_api.py:355 +msgid "Connecting" +msgstr "Đang kết nối" + +#: lib50/_api.py:363 +#, python-brace-format +msgid "Invalid slug for {}. Did you mean something else?" +msgstr "Slug cho {} không hợp lệ." + +#: lib50/_api.py:372 +#, python-brace-format +msgid "Go to {results} to see your results." +msgstr "Vui lòng đến {results} để xem kết qủa của bạn." + +#: lib50/_api.py:385 +#, python-brace-format +msgid "No files in this directory are expected by {}." +msgstr "Thư mục này không có tập tin nào {} đang mong đợi." + +#: lib50/_api.py:424 +msgid "Verifying" +msgstr "Đang thảm tra" + +#: lib50/_api.py:436 +#, python-brace-format +msgid "" +"Make sure your username and/or personal access token are valid and {} is " +"enabled for your account. To enable {}, " +msgstr "" +"Hãy đảm bảo username và/hoặc mã truy cập cá nhân của bạn hợp lệ và {} đã +"được bật cho tài khoản của bạn. Để bật {}, " + +#: lib50/_api.py:438 +msgid "please contact your instructor." +msgstr "vui lòng liên hệ với giáo viên." + +#: lib50/_api.py:440 +#, python-brace-format +msgid "please go to {} in your web browser and try again." +msgstr "vui lòng đến {} và thử lại." + +#: lib50/_api.py:447 +msgid "Preparing" +msgstr "Đang chuẩn bị" + +#: lib50/_api.py:510 +msgid "Uploading" +msgstr "Đang tải lên" + +#: lib50/_api.py:511 +#, python-brace-format +msgid "automated commit by {}" +msgstr "commit tự động bởi {}" + +#: lib50/_api.py:564 +#, python-brace-format +msgid "Invalid slug: {}. Did you mean something else?" +msgstr "Slug này không hợp lệ: {}. " + +#: lib50/_api.py:568 +#, python-brace-format +msgid "Invalid slug: {}. Multiple configurations (both .yaml and .yml) found." +msgstr "Slug này không hợp lệ: {} Đã tìm thấy nhiều cấu hình (cả .yaml và .yml)." + +#: lib50/_api.py:668 +msgid "You don't have git. Install git, then re-run!" +msgstr "Bạn không có git. Vui lòng cài đặt git và thử lại." + +#: lib50/_api.py:674 +msgid "You have an old version of git. Install version 2.7 or later, then re-run!" +msgstr "Bạn đang sử dụng phiên bản git cũ. Hãy cài đặt phiên bản 2.7 trở lên, sau đó thử lại." + +#: lib50/_api.py:758 lib50/_api.py:828 +msgid "Invalid slug" +msgstr "Slug này không hợp lệ." + +#: lib50/_api.py:786 +#, python-brace-format +msgid "Invalid slug: {}" +msgstr "Slug này không hợp lệ: {}" + +#: lib50/_api.py:792 +#, python-brace-format +msgid "Invalid slug. Did you mean {}, without the leading and trailing slashes?" +msgstr "Slug này không hợp lệ. Ý bạn là {}, không có dấu gạch chéo ở đầu và cuối phải không?" + +#: lib50/_api.py:795 +#, python-brace-format +msgid "Invalid slug. Did you mean {}, without the leading slash?" +msgstr "Slug này không hợp lệ. Ý bạn là {}, không có dấu gạch chéo ở đầu phải không?" + +#: lib50/_api.py:798 +#, python-brace-format +msgid "Invalid slug. Did you mean {}, without the trailing slash?" +msgstr "Slug này không hợp lệ. Ý bạn là {}, không có dấu gạch chéo ở cuối phải không?" + +#: lib50/_api.py:1028 +msgid "Invalid slug. Did you mean to submit something else?" +msgstr "Slug này không hợp lệ. Bạn có ý định nộp bài khác không?" + +#: lib50/_api.py:1034 lib50/_api.py:1056 +msgid "" +"Could not connect to GitHub. Do make sure you are connected to the " +"internet." +msgstr "" +"Không kết nối với GitHub được. Hãy đảm bảo bạn đã kết nối với " +"internet." + +#: lib50/_api.py:1066 +#, python-brace-format +msgid "" +"Could not connect to GitHub. It looks like GitHub is having some issues " +"with {}. Do check on https://www.githubstatus.com and try again later." +msgstr "" +"Không kết nối với GitHub được. GitHub có vẻ bị vấn đề về {}." +"Vui lòng kiểm tra tại https://www.githubstatus.com và thử lại sau." + +#: lib50/_api.py:1089 +#, python-brace-format +msgid "" +"These files are too large to be submitted:\n" +"{}\n" +"Remove these files from your directory and then re-run!" +msgstr "" +"Những tập tin này quá lớn để nộp:\n" +"{}\n" +"Hãy xóa những tập tin này khỏi thư mục, rồi thử lại." + +#: lib50/_api.py:1097 +#, python-brace-format +msgid "" +"These files are too large to be submitted:\n" +"{}\n" +"Install git-lfs (or remove these files from your directory) and then re-" +"run!" +msgstr "" +"Những tập tin này quá lớn để nộp:\n" +"{}\n" +"Vui lòng cài đặt git-lfs (hay xoá những tập tin này khỏi thư mục), rồi thử lại." + +#: lib50/_errors.py:54 +msgid "You seem to be missing these required files:" +msgstr "Bạn thiếu những tập tin bắt buộc này:" + +#: lib50/_errors.py:56 lib50/_errors.py:76 +#, python-brace-format +msgid "You are currently in: {}, did you perhaps intend another directory?" +msgstr "Bạn đang ở: {}, có lẽ bạn muốn chuyển đến thư mục khác phải không?" + +#: lib50/_errors.py:75 +#, python-brace-format +msgid "Looks like you are in a directory with too many (> {}) files." +msgstr "Bạn đang ở trong một thư mục có quá nhiều tập tin (> {})." + +#: lib50/authentication.py:54 +msgid "Authenticating" +msgstr "Đang xác nhận" + +#: lib50/authentication.py:110 +msgid "" +"Looks like you're trying to push to a branch that conflicts with an " +"existing one in the repository.\n" +msgstr "" + +#: lib50/authentication.py:115 +msgid "You are trying to push to a branch that is not allowed.\n" +msgstr "" + +#: lib50/authentication.py:265 +msgid "Enter username for GitHub: " +msgstr "Nhập username cho GitHub: " + +#: lib50/authentication.py:272 +msgid "Enter personal access token for GitHub: " +msgstr "Nhập mã truy cập cá nhân cho GitHub: " + +#: lib50/authentication.py:291 +msgid "" +"You might be using your GitHub password to log in, but that's no longer " +"possible. But you can still use check50 and submit50! See " +"https://cs50.readthedocs.io/github for instructions." +msgstr "" +"Bạn có thể đang sử dụng mật khẩu GitHub để đăng nhập, nhưng phương pháp này không còn khả thi nữa." +"Tuy nhiên, bạn vẫn có thể sử dụng check50 và submit50. Xem " +"https://cs50.readthedocs.io/github để biết hướng dẫn." + +#: lib50/config.py:50 +#, python-brace-format +msgid "Two config files (.cs50.yaml and .cs50.yml) found at {}" +msgstr "Hai tập tin cấu hình (.cs50.yaml và .cs50.yml) được tìm thấy tại {}" + +#: lib50/config.py:53 +#, python-brace-format +msgid "No config file (.cs50.yaml or .cs50.yml) found at {}" +msgstr "Không tìm thấy tập tin cấu hình (.cs50.yaml hoặc .cs50.yml) tại {}" + +#: lib50/config.py:192 +msgid "Config is not valid yaml." +msgstr "Cấu hình yaml không hợp lệ." + +#: lib50/config.py:274 +#, python-brace-format +msgid "{} is not a valid tag for {}" +msgstr "{} không phải là tag hợp lệ cho {}" + From 2d107dbf3a81c194ae64f2ab4d2f9d70e7cb9446 Mon Sep 17 00:00:00 2001 From: Brandon Nguyen <112731698+bxngyn@users.noreply.github.com> Date: Thu, 7 Aug 2025 10:01:26 -0400 Subject: [PATCH 5/8] add compiled file --- lib50/locale/vi/LC_MESSAGES/lib50.mo | Bin 0 -> 5975 bytes 1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 lib50/locale/vi/LC_MESSAGES/lib50.mo diff --git a/lib50/locale/vi/LC_MESSAGES/lib50.mo b/lib50/locale/vi/LC_MESSAGES/lib50.mo new file mode 100644 index 0000000000000000000000000000000000000000..4babb23e3e354c87f8f64725fe794a5b547977b0 GIT binary patch literal 5975 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 U<)q}E&L17Hn@@~Jc~K+(2MuA_j{pDw literal 0 HcmV?d00001 From 4dfe5382d43adbb9a579770cccbf2e20ce94e324 Mon Sep 17 00:00:00 2001 From: Brandon Nguyen <112731698+bxngyn@users.noreply.github.com> Date: Thu, 7 Aug 2025 10:05:56 -0400 Subject: [PATCH 6/8] Update lib50.po --- lib50/locale/vi/LC_MESSAGES/lib50.po | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib50/locale/vi/LC_MESSAGES/lib50.po b/lib50/locale/vi/LC_MESSAGES/lib50.po index cbc2632..995dd48 100644 --- a/lib50/locale/vi/LC_MESSAGES/lib50.po +++ b/lib50/locale/vi/LC_MESSAGES/lib50.po @@ -33,7 +33,7 @@ msgid "" "Cannot include/exclude paths outside the current directory, but such a " "path ({}) was specified." msgstr "" -"Không thể bao gồm/loại trừ các đường dẫn bên ngoài thư mục này, nhưng +"Không thể bao gồm/loại trừ các đường dẫn bên ngoài thư mục này, nhưng " "đường dẫn ({}) đã được chỉ định." #: lib50/_api.py:355 @@ -65,7 +65,7 @@ msgid "" "Make sure your username and/or personal access token are valid and {} is " "enabled for your account. To enable {}, " msgstr "" -"Hãy đảm bảo username và/hoặc mã truy cập cá nhân của bạn hợp lệ và {} đã +"Hãy đảm bảo username và/hoặc mã truy cập cá nhân của bạn hợp lệ và {} đã " "được bật cho tài khoản của bạn. Để bật {}, " #: lib50/_api.py:438 From 1d550d8b9c7e77b7d1ed770d57ad7fa961fe946c Mon Sep 17 00:00:00 2001 From: Brandon Nguyen <112731698+bxngyn@users.noreply.github.com> Date: Thu, 7 Aug 2025 10:06:33 -0400 Subject: [PATCH 7/8] add compiled file --- lib50/locale/vi/LC_MESSAGES/lib50.mo | Bin 5975 -> 5980 bytes 1 file changed, 0 insertions(+), 0 deletions(-) diff --git a/lib50/locale/vi/LC_MESSAGES/lib50.mo b/lib50/locale/vi/LC_MESSAGES/lib50.mo index 4babb23e3e354c87f8f64725fe794a5b547977b0..8a3918f98153db3f7a604991c13d9fb37b7da0bc 100644 GIT binary patch delta 333 zcmXZXJxfAi7{>9-w?VOdsdSM%QWQv>tRP$>mxj|4I3718ijb%#H=_?AO@%H(;Vv9% z6jCAFg9ck$`Tz}q(qE47aQ~j`9-jMtKFu$)TlLf%k}kv28cr~VnFXngd)USY+`|1u zDTNh0z}tE5;VOBI$M}a=codON@pW!0Dy7MHn8By0>MC&=(y-8A`fT6@o?s|09iojJ z*g}rpD3ADoHLNa4Mf^sdQhwRhLYr)30blSMe=+Eh&R4djT^ctD_h%j4B=>P0e{i;G cBq?Qa$7yz>% delta 326 zcmXZXF-yWx6vpA#$U)Ik%Y+C+30iR72TZF58&WXNFd}#5dMz3 zv?@4C;Lzd+a1#XSCkmJQoc9dp-m{3zBZHEu*_KqXNq*d*6R+)34rBO@9~j2_6X^=G z_<)T=9-)`~i!ZpwDke{*JPr?DI+#svp%42GHT6dEL*p5}yxzkirqJw?5}3vSej-OB zt}f27j)gPn75|V?x;x+dgc))gA8~*+T%pAzy}P4QoJRR#zgZuH Date: Fri, 8 Aug 2025 10:05:50 -0400 Subject: [PATCH 8/8] add fallback URL support for GitHub requests --- lib50/_api.py | 53 ++++++++++++++++++++++++++++++++++++--------------- 1 file changed, 38 insertions(+), 15 deletions(-) diff --git a/lib50/_api.py b/lib50/_api.py index 31defb1..f040b84 100644 --- a/lib50/_api.py +++ b/lib50/_api.py @@ -1024,23 +1024,46 @@ def _match_files(universe, pattern): def get_content(org, repo, branch, filepath): """Get all content from org/repo/branch/filepath at GitHub.""" - url = "https://github.com/{}/{}/raw/{}/{}".format(org, repo, branch, filepath) - try: - r = requests.get(url) - if not r.ok: - if r.status_code == 404: - raise InvalidSlugError(_("Invalid slug. Did you mean to submit something else?")) - else: - # Check if GitHub outage may be the source of the issue - check_github_status() - - # Otherwise raise a ConnectionError - raise ConnectionError(_("Could not connect to GitHub. Do make sure you are connected to the internet.")) - - except requests.exceptions.SSLError as e: + + def _handle_ssl_error(e): + """Handle SSL errors consistently.""" raise ConnectionError(_(f"Could not connect to GitHub due to a SSL error.\nPlease check GitHub's status at githubstatus.com.\nError: {e}")) + + def _handle_non_404_error(): + """Handle non-404 HTTP errors consistently.""" - return r.content + # Check if GitHub outage may be the source of the issue + check_github_status() + + # Otherwise raise a ConnectionError + raise ConnectionError(_("Could not connect to GitHub. Do make sure you are connected to the internet.")) + + def _make_request(url): + """Make a request and handle SSL errors.""" + try: + return requests.get(url) + except requests.exceptions.SSLError as e: + _handle_ssl_error(e) + + url = "https://github.com/{}/{}/raw/{}/{}".format(org, repo, branch, filepath) + r = _make_request(url) + + if r.ok: + return r.content + + if r.status_code == 404: + # Try fallback URL in case there were issues with github.com's redirect + fallback_url = "https://raw.githubusercontent.com/{}/{}/{}/{}".format(org, repo, branch, filepath) + r = _make_request(fallback_url) + + if r.ok: + return r.content + elif r.status_code == 404: + raise InvalidSlugError(_("Invalid slug. Did you mean to submit something else?")) + else: + _handle_non_404_error() + else: + _handle_non_404_error() def check_github_status():