snoottube-ops/azure-upload-vm-image.sh

165 lines
4.8 KiB
Bash
Executable File

#!/usr/bin/env -S nix develop --command bash
# Based on https://github.com/society-for-the-blind/nixos-azure-deploy/blob/main/nixos/maintainers/scripts/azure-new/upload-image.sh
# but only the part i need, namely, uploading an image.
####################################################
# AZ LOGIN CHECK #
####################################################
# Making sure that one is logged in (to avoid
# surprises down the line).
if [ $(az account list | jq -r 'length') -eq 0 ]
then
echo '********************************************************'
echo 'Please log into Azure now, and run the script again.'
echo '********************************************************'
az login
exit 1
fi
####################################################
# HELPERS #
####################################################
show_id() {
az $1 show \
--resource-group "${resource_group}" \
--name "${img_name}" \
--query "[id]" \
--output tsv
}
usage() {
echo ''
echo 'USAGE: (Every switch requires an argument)'
echo ''
echo '-g --resource-group REQUIRED Created if does not exist. Will'
echo ' house a new disk and the created'
echo ' image.'
echo ''
echo '-n --image-name REQUIRED The name of the image created'
echo ' (and also of the new disk).'
echo ''
echo '-i --image-path Path to the image to upload.'
echo ' Generate using nixos-generators.'
echo ' Defaults to ./result/disk.vhd'
echo ''
echo '-l --location Values from `az account list-locations`.'
echo ' Default value: "westus2".'
}
####################################################
# SWITCHES #
####################################################
# https://unix.stackexchange.com/a/204927/85131
while [ $# -gt 0 ]; do
case "$1" in
-i|--image-path)
img_path="$2"
;;
-l|--location)
location="$2"
;;
-g|--resource-group)
resource_group="$2"
;;
-n|--image-name)
img_name="$2"
;;
-h|--help)
usage
exit 1
;;
*)
printf "***************************\n"
printf "* Error: Invalid argument *\n"
printf "***************************\n"
usage
exit 1
esac
shift
shift
done
if [ -z "${img_name}" ] || [ -z "${resource_group}" ]
then
printf "************************************\n"
printf "* Error: Missing required argument *\n"
printf "************************************\n"
usage
exit 1
fi
####################################################
# DEFAULTS #
####################################################
img_path_d="${img_path:-"./result/disk.vhd"}"
location_d="${location:-"westus2"}"
####################################################
# PUT IMAGE INTO AZURE CLOUD #
####################################################
# https://vaneyckt.io/posts/safer_bash_scripts_with_set_euxo_pipefail/
set -euxo pipefail
# Make resource group exists
if ! az group show --resource-group "${resource_group}" &>/dev/null
then
az group create \
--name "${resource_group}" \
--location "${location_d}"
fi
# NOTE: The disk access token song/dance is
# tedious but allows us to upload direct
# to a disk image thereby avoid storage
# accounts (and naming them) entirely!
if ! show_id "disk" &>/dev/null
then
img_file="$(readlink -f ${img_path_d})"
bytes="$(stat -c %s ${img_path_d})"
az disk create \
--resource-group "${resource_group}" \
--name "${img_name}" \
--for-upload true \
--upload-size-bytes "${bytes}"
timeout=$(( 60 * 60 )) # disk access token timeout
sasurl="$(\
az disk grant-access \
--access-level Write \
--resource-group "${resource_group}" \
--name "${img_name}" \
--duration-in-seconds ${timeout} \
--query "[accessSas]" \
--output tsv
)"
azcopy copy "${img_file}" "${sasurl}" \
--blob-type PageBlob
# https://docs.microsoft.com/en-us/cli/azure/disk?view=azure-cli-latest#az-disk-revoke-access
# > Revoking the SAS will change the state of
# > the managed disk and allow you to attach
# > the disk to a VM.
az disk revoke-access \
--resource-group "${resource_group}" \
--name "${img_name}"
fi
if ! show_id "image" &>/dev/null
then
az image create \
--resource-group "${resource_group}" \
--name "${img_name}" \
--source "$(show_id "disk")" \
--os-type "linux" >/dev/null
fi