Skip to content

Instantly share code, notes, and snippets.

@creachadair
Last active February 15, 2024 16:55
Show Gist options
  • Save creachadair/ff3d273e9b81ae1b24eb309eccc786f2 to your computer and use it in GitHub Desktop.
Save creachadair/ff3d273e9b81ae1b24eb309eccc786f2 to your computer and use it in GitHub Desktop.
A script to start and stop an AWS VM for development and testing
#!/bin/sh
#
# ws.sh: start and stop an EC2 VM
#
# Requires:
# - https://github.com/99designs/aws-vault
# - https://aws.amazon.com/cli/
#
# Usage:
# ws.sh start [--wait]
# ws.sh status
# ws.sh stop
#
# Environment:
# WS_INSTANCE : instance ID (i-xxxxx)
# WS_REGION : EC2 region where instance runs
# WS_PROFILE : aws-vault config profile to use
#
set -euo pipefail
: ${WS_REGION:=us-west-2}
: ${WS_INSTANCE:?missing instance id}
: ${WS_PROFILE:=workstations}
size_small='t3.small'
size_medium='t3.medium'
size_large='t3.large'
size_xlarge='t3.xlarge'
size_buff='m5a.xlarge'
describe() {
awscli describe-instances --instance-ids "$WS_INSTANCE" --region "$WS_REGION" |
jq '.Reservations[0].Instances[0]'
}
awscli() { aws-vault exec "$WS_PROFILE" -- aws ec2 "$@" ; }
status() { describe | jq -r '.State.Name' ; }
set_instance_type() {
local size="${1:?missing instance type}"
awscli modify-instance-attribute --instance-id="$WS_INSTANCE" --region "$WS_REGION" \
--instance-type '{"Value":"'"$size"'"}'
}
size_type() { eval "echo \$size_${1}" ; }
case "${1:-}" in
(start)
awscli start-instances --instance-ids "$WS_INSTANCE" --region "$WS_REGION"
if [[ "${2:-}" =~ -?-wait ]] ; then
while [[ "$(status)" = stopped ]] ; do
printf "?"
sleep 2
done
"$0" wait
fi
;;
(stop)
awscli stop-instances --instance-ids "$WS_INSTANCE" --region "$WS_REGION"
if [[ "${2:-}" =~ -?-wait ]] ; then
"$0" wait
fi
;;
(status)
status
;;
(info)
describe
;;
(ip)
describe | jq -r '.PublicIpAddress'
;;
('wait')
while true ; do
s="$(status)"
case "$s" in
(stopped)
echo "$s"
exit 1
;;
(pending|initializing|stopping)
printf "."
sleep 4
;;
(running)
echo "$s"
exit 0
;;
(*)
echo "Unknown status" 1>&2
exit 2
;;
esac
done
;;
(resize)
case "${2:?missing size (try 'help')}" in
(small|medium|large|xlarge|buff)
msize=`size_type $2`
set_instance_type $msize
echo "Set instance size to '$msize'" 1>&2
;;
(*)
echo "Usage: $(basename $0) resize [small|medium|large|xlarge|buff]" 1>&2
exit 1
;;
esac
;;
(connect)
if [[ "$(status)" != ok ]] ; then
"$0" start --wait
fi
tssh fromberger-workstation
;;
(help|'')
echo "Usage: $(basename $0) [start|stop|status|connect|info|ip|wait|resize <size>]" 1>&2
exit 2
;;
(*)
echo "Error: unknown command '${1:-}' (try 'help')" 1>&2
exit 2
;;
esac
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment