Skip to content

Instantly share code, notes, and snippets.

@maxim
Last active November 11, 2024 09:33
Show Gist options
  • Save maxim/6e15aa45ba010ab030c4 to your computer and use it in GitHub Desktop.
Save maxim/6e15aa45ba010ab030c4 to your computer and use it in GitHub Desktop.
Download assets from private Github releases
#!/usr/bin/env bash
#
# gh-dl-release! It works!
#
# This script downloads an asset from latest or specific Github release of a
# private repo. Feel free to extract more of the variables into command line
# parameters.
#
# PREREQUISITES
#
# curl, wget, jq
#
# USAGE
#
# Set all the variables inside the script, make sure you chmod +x it, then
# to download specific version to my_app.tar.gz:
#
# gh-dl-release 2.1.1 my_app.tar.gz
#
# to download latest version:
#
# gh-dl-release latest latest.tar.gz
#
# If your version/tag doesn't match, the script will exit with error.
TOKEN="<github_access_token>"
REPO="<user_or_org>/<repo_name>"
FILE="<name_of_asset_file>" # the name of your release asset file, e.g. build.tar.gz
VERSION=$1 # tag name or the word "latest"
GITHUB="https://api.github.com"
alias errcho='>&2 echo'
function gh_curl() {
curl -H "Authorization: token $TOKEN" \
-H "Accept: application/vnd.github.v3.raw" \
$@
}
if [ "$VERSION" = "latest" ]; then
# Github should return the latest release first.
parser=".[0].assets | map(select(.name == \"$FILE\"))[0].id"
else
parser=". | map(select(.tag_name == \"$VERSION\"))[0].assets | map(select(.name == \"$FILE\"))[0].id"
fi;
asset_id=`gh_curl -s $GITHUB/repos/$REPO/releases | jq "$parser"`
if [ "$asset_id" = "null" ]; then
errcho "ERROR: version not found $VERSION"
exit 1
fi;
wget -q --auth-no-challenge --header='Accept:application/octet-stream' \
https://$TOKEN:@api.github.com/repos/$REPO/releases/assets/$asset_id \
-O $2
@GElkayam
Copy link

As we needed some releases that were in the 5th page (so per_page=100 didn't help), I rewrote the query to query latest (it gives latest released) and tag. also needed some more information in the error reporting:

#!/usr/bin/env bash
#
# gh-dl-release! It works!
# 
# This script downloads an asset from latest or specific Github release of a
# private repo. Feel free to extract more of the variables into command line
# parameters.
#
# PREREQUISITES
#
# curl, wget, jq
#
# USAGE
#
# Set all the variables inside the script, make sure you chmod +x it, then
# to download specific version to my_app.tar.gz:
#
#     gh-dl-release 2.1.1 my_app.tar.gz
#
# to download latest version:
#
#     gh-dl-release latest latest.tar.gz
#
# If your version/tag doesn't match, the script will exit with error.

TOKEN="$3"
REPO="$4"
FILE="$2"      # the name of your release asset file, e.g. build.tar.gz
VERSION="$1"                       # tag name or the word "latest"
GITHUB="https://api.github.com"

alias errcho='>&2 echo'

function gh_curl() {
  curl -H "Authorization: token $TOKEN" \
       -H "Accept: application/vnd.github.v3.raw" \
       $@
}

parser=".assets | map(select(.name == \"$FILE\"))[0].id"
if [ "$VERSION" = "latest" ]; then
  # Github should return the latest release first.
  asset_id=`gh_curl -s $GITHUB/repos/$REPO/releases/latest | jq "$parser"`
else
  asset_id=`gh_curl -s $GITHUB/repos/$REPO/releases/tags/$VERSION | jq "$parser"`
fi;

if [ -z "$asset_id" ]; then
  errcho "ERROR: version not found $VERSION"
  exit 1
fi;
if [ "$asset_id" = "null" ]; then
  errcho "ERROR: file $FILE not found in version $VERSION"
  exit 2
fi;

wget -q --auth-no-challenge --header='Accept:application/octet-stream' \
  https://$TOKEN:@api.github.com/repos/$REPO/releases/assets/$asset_id \
  -O $2

@sonibla
Copy link

sonibla commented Nov 29, 2021

For Windows users, I made a PowerShell equivalent
https://gist.github.com/sonibla/a60fc31b244ceba3220b9bb33316798c

@AchalaDias
Copy link

AchalaDias commented Jan 8, 2022

I have updated the code for the latest github api and changed it to supporting for multiple files download. User can set only necessary file names in the array.

TOKEN="<PAT>"
REPO="<REPO>"
VERSION="<RELEASED-VERSION>" 
GITHUB="https://api.github.com"

function gh_curl() {
  curl -H "Authorization: token $TOKEN" \
       -H "Accept: application/vnd.github.v3+json" \
       $@
}

# assets list you want to download
AseertsList=( 
 asset1.zip asset2.zip
)

assets=$(gh_curl -s $GITHUB/repos/$REPO/releases/tags/$VERSION)

for row in $(echo "${assets}" | jq -c '.assets[]'); do
name=$( jq -r  '.name' <<< "${row}" ) 
echo ${name}
    if [[ ${AseertsList[*]} =~ ${name} ]] ; then

        id=$( jq -r  '.id' <<< "${row}" ) 

        wget -q --auth-no-challenge --header='Accept:application/octet-stream' \
        https://$TOKEN:@api.github.com/repos/$REPO/releases/assets/$asset_id \
        -O test/${name}
    fi
done

@shuantsu
Copy link

shuantsu commented Jan 12, 2022

using application/octet-stream as Accept header did the trick for me to download from a private repo

@gpaOliveira
Copy link

Using wget didn't fit my vanilla GH-Hosted-Runners, so I'm dropping here a curl version of that download that worked for me:

curl -L -s -H "Authorization: token $TOKEN" -H 'Accept:application/octet-stream' \
"https://api.github.com/repos/$REPO/releases/assets/$asset_id" \
-o $asset_name

@ringerc
Copy link

ringerc commented Oct 18, 2022

For releases, uses gh release download instead.

gh release download -R MyOrg/MyRepo --pattern 'myproject-*.tar.gz'

for example.

@jamesETsmith
Copy link

Here are the official docs for anyone else who stumbles on this thread which say to do (note octet-stream here bc I was downloading a binary):

curl -L \
  -H "Accept:  application/octet-stream" \ 
  -H "Authorization: Bearer <YOUR-TOKEN>"\
  -H "X-GitHub-Api-Version: 2022-11-28" \
  https://api.github.com/repos/OWNER/REPO/releases/assets/ASSET_ID

If (like me) you're confused about the best way to find out ASSET_ID I'd suggest looking at the json output for the latest release, see the docs here and the code here:

curl -L \
  -H "Accept: application/vnd.github+json" \
  -H "Authorization: Bearer <YOUR-TOKEN>"\
  -H "X-GitHub-Api-Version: 2022-11-28" \
  https://api.github.com/repos/OWNER/REPO/releases/latest

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment