| #!/usr/bin/env bash |
| # Licensed to the Apache Software Foundation (ASF) under one |
| # or more contributor license agreements. See the NOTICE file |
| # distributed with this work for additional information |
| # regarding copyright ownership. The ASF licenses this file |
| # to you under the Apache License, Version 2.0 (the |
| # "License"); you may not use this file except in compliance |
| # with the License. You may obtain a copy of the License at |
| # |
| # http://www.apache.org/licenses/LICENSE-2.0 |
| # |
| # Unless required by applicable law or agreed to in writing, |
| # software distributed under the License is distributed on an |
| # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
| # KIND, either express or implied. See the License for the |
| # specific language governing permissions and limitations |
| # under the License. |
| |
| # This was lovingly copied from Apache HBase |
| |
| set -e |
| function usage { |
| echo "Usage: ${0} [options] /path/to/download/file.tar.gz download/fragment/eg/project/subdir/some-artifact-version.tar.gz" |
| echo "" |
| echo " --force for a redownload even if /path/to/download/file.tar.gz exists." |
| echo " --working-dir /path/to/use Path for writing tempfiles. must exist." |
| echo " defaults to making a directory via mktemp that we clean." |
| echo " --keys url://to/project/KEYS where to get KEYS. needed to check signature on download." |
| echo "" |
| exit 1 |
| } |
| # if no args specified, show usage |
| if [ $# -lt 2 ]; then |
| usage |
| fi |
| |
| |
| # Get arguments |
| declare done_if_cached="true" |
| declare working_dir |
| declare cleanup="true" |
| declare keys |
| while [ $# -gt 0 ] |
| do |
| case "$1" in |
| --force) shift; done_if_cached="false";; |
| --working-dir) shift; working_dir=$1; cleanup="false"; shift;; |
| --keys) shift; keys=$1; shift;; |
| --) shift; break;; |
| -*) usage ;; |
| *) break;; # terminate while loop |
| esac |
| done |
| |
| # should still have required args |
| if [ $# -lt 2 ]; then |
| usage |
| fi |
| |
| target="$1" |
| artifact="$2" |
| |
| if [ -f "${target}" ] && [ "true" = "${done_if_cached}" ]; then |
| echo "Reusing existing download of '${artifact}'." |
| exit 0 |
| fi |
| |
| if [ -z "${working_dir}" ]; then |
| if ! working_dir="$(mktemp -d -t hbase-download-apache-artifact)" ; then |
| echo "Failed to create temporary working directory. Please specify via --working-dir" >&2 |
| exit 1 |
| fi |
| else |
| # absolutes please |
| working_dir="$(cd "$(dirname "${working_dir}")"; pwd)/$(basename "${working_dir}")" |
| if [ ! -d "${working_dir}" ]; then |
| echo "passed working directory '${working_dir}' must already exist." >&2 |
| exit 1 |
| fi |
| fi |
| |
| function cleanup { |
| if [ -n "${keys}" ]; then |
| echo "Stopping gpg agent daemon" |
| gpgconf --homedir "${working_dir}/.gpg" --kill gpg-agent |
| echo "Stopped gpg agent daemon" |
| fi |
| |
| if [ "true" = "${cleanup}" ]; then |
| echo "cleaning up temp space." |
| rm -rf "${working_dir}" |
| fi |
| } |
| trap cleanup EXIT SIGQUIT |
| |
| echo "New download of '${artifact}'" |
| |
| # N.B. this comes first so that if gpg falls over we skip the expensive download. |
| if [ -n "${keys}" ]; then |
| if [ ! -d "${working_dir}/.gpg" ]; then |
| rm -rf "${working_dir}/.gpg" |
| mkdir -p "${working_dir}/.gpg" |
| chmod -R 700 "${working_dir}/.gpg" |
| fi |
| |
| echo "installing project KEYS" |
| curl -L --fail -o "${working_dir}/KEYS" "${keys}" |
| if ! gpg --homedir "${working_dir}/.gpg" --import "${working_dir}/KEYS" ; then |
| echo "ERROR importing the keys via gpg failed. If the output above mentions this error:" >&2 |
| echo " gpg: can't connect to the agent: File name too long" >&2 |
| # we mean to give them the command to run, not to run it. |
| #shellcheck disable=SC2016 |
| echo 'then you prolly need to create /var/run/user/$(id -u)' >&2 |
| echo "see this thread on gnupg-users: https://s.apache.org/uI7x" >&2 |
| exit 2 |
| fi |
| |
| echo "downloading signature" |
| curl -L --fail -o "${working_dir}/artifact.asc" "https://archive.apache.org/dist/${artifact}.asc" |
| fi |
| |
| echo "downloading artifact" |
| if ! curl --dump-header "${working_dir}/artifact_download_headers.txt" -L --fail -o "${working_dir}/artifact" "https://www.apache.org/dyn/closer.lua?filename=${artifact}&action=download" ; then |
| echo "Artifact wasn't in mirror system. falling back to archive.a.o." |
| curl --dump-header "${working_dir}/artifact_fallback_headers.txt" -L --fail -o "${working_dir}/artifact" "http://archive.apache.org/dist/${artifact}" |
| fi |
| |
| if [ -n "${keys}" ]; then |
| echo "verifying artifact signature" |
| gpg --homedir "${working_dir}/.gpg" --verify "${working_dir}/artifact.asc" |
| echo "signature good." |
| fi |
| |
| echo "moving artifact into place at '${target}'" |
| # ensure we're on the same filesystem |
| mv "${working_dir}/artifact" "${target}.copying" |
| # attempt atomic move |
| mv "${target}.copying" "${target}" |
| echo "all done!" |