feat: support submissions from app.tinytapeout.com (#21)

* feat: copy_macros and copy_final_results commands

* feat: generate shuttle index JSON
includes information about all projects:
- repo
- commit
- mux index
- mux position (X/Y)

* feat: add --create-efabless-submission option
This commit is contained in:
Uri Shaked
2023-07-21 15:52:04 +03:00
committed by GitHub
parent bb58ee1fae
commit 26785bea0e
7 changed files with 254 additions and 554 deletions
-121
View File
@@ -3,21 +3,7 @@ from urllib.parse import urlparse
import logging
import requests
import os
import zipfile
import io
import errno
import sys
def unique(duplist):
unique_list = []
# traverse for all elements
for x in duplist:
# check if exists in unique_list or not
if x not in unique_list:
unique_list.append(x)
return unique_list
def fetch_file(url, filename):
logging.info("trying to download {}".format(url))
@@ -64,50 +50,6 @@ def headers_try_to_add_authorization_from_environment(headers: dict) -> bool:
print("WARNING: No github token found from environment, trying public API requests without, see docs/INFO.md#instructions-to-build-gds", file=sys.stderr)
return False
def fetch_file_from_git(git_url, path):
# get the basics
user_name, repo = split_git_url(git_url)
headers = {
"Accept" : "application/vnd.github+json",
}
# authenticate for rate limiting
headers_try_to_add_authorization_from_environment(headers)
api_url = 'https://api.github.com/repos/%s/%s/contents/%s' % (user_name, repo, path)
logging.debug(api_url)
r = requests.get(api_url, headers=headers)
check_status(r)
requests_remaining = int(r.headers['X-RateLimit-Remaining'])
if requests_remaining == 0:
logging.error("no API requests remaining")
exit(1)
logging.debug("API requests remaining %d" % requests_remaining)
data = r.json()
if 'content' not in data:
return None
file_content = data['content']
file_content_encoding = data.get('encoding')
if file_content_encoding == 'base64':
file_content = base64.b64decode(file_content)
return file_content
# the latest artifact isn't necessarily the one related to the latest commit, as github
# could have taken longer to process an older commit than a newer one.
# so iterate through commits and return the artifact that matches
def get_most_recent_action_url(commits, artifacts):
release_sha_to_download_url = {artifact['workflow_run']['head_sha']: artifact['archive_download_url'] for artifact in artifacts}
for commit in commits:
if commit['sha'] in release_sha_to_download_url:
return release_sha_to_download_url[commit['sha']]
def get_most_recent_action_page(commits, runs):
release_sha_to_page_url = {run['head_sha']: run['html_url'] for run in runs if run['name'] == 'gds'}
@@ -127,69 +69,6 @@ def split_git_url(url):
return user_name, repo
# download the artifact for each project to get the gds & lef
def install_artifacts(url, directory):
logging.debug(url)
user_name, repo = split_git_url(url)
headers = {
"Accept" : "application/vnd.github+json",
}
# authenticate for rate limiting
headers_try_to_add_authorization_from_environment(headers)
# first fetch the git commit history
api_url = f'https://api.github.com/repos/{user_name}/{repo}/commits'
r = requests.get(api_url, headers=headers)
check_status(r)
requests_remaining = int(r.headers['X-RateLimit-Remaining'])
if requests_remaining == 0:
logging.error("no API requests remaining")
exit(1)
commits = r.json()
# now get the artifacts
api_url = f'https://api.github.com/repos/{user_name}/{repo}/actions/artifacts'
r = requests.get(api_url, headers=headers, params={'per_page': 100})
check_status(r)
data = r.json()
# check there are some artifacts
if 'artifacts' not in data:
logging.error(f"no artifact found for {url}")
exit(1)
else:
# only get artifacts called GDS
artifacts = [a for a in data['artifacts'] if a['name'] == 'GDS']
logging.debug(f"found {len(artifacts)} artifacts")
if len(artifacts) == 0:
logging.error("no artifacts for this project")
exit(1)
download_url = get_most_recent_action_url(commits, artifacts)
# need actions access on the token to get the artifact
# won't work on a pull request because they won't have the token
attempts = 1
max_attempts = 3
while attempts < max_attempts:
try:
logging.debug(f"download url {download_url} attempt {attempts}")
r = requests.get(download_url, headers=headers)
check_status(r)
z = zipfile.ZipFile(io.BytesIO(r.content))
z.extractall(directory)
break
except zipfile.BadZipFile:
attempts += 1
logging.warning(f"problem with zipfile, retry {attempts}")
if attempts == max_attempts:
logging.error("gave up downloading zipfile")
exit(1)
def get_latest_action_url(url, directory):
logging.debug(url)