Skip to content

Instantly share code, notes, and snippets.

@realslacker
Last active March 25, 2020 07:02
Show Gist options
  • Save realslacker/6dce254e16003fbec5451689c9ba1e49 to your computer and use it in GitHub Desktop.
Save realslacker/6dce254e16003fbec5451689c9ba1e49 to your computer and use it in GitHub Desktop.
Ubuntu Auto-Update Script
#!/bin/bash
# to install directly from the Gist
# curl https://gist.githubusercontent.com/realslacker/6dce254e16003fbec5451689c9ba1e49/raw/ | bash -s -- -i
# test getopt
getopt --test > /dev/null
if [[ $? -ne 4 ]]; then
echo "Error: `getopt --test` failed in this environment, please update to a newer 'getopt' package"
exit 1
fi
# test realpath
command -v realpath >/dev/null 2>&1 || {
echo >&2 "I require realpath but it's not installed."
exit 1
}
OPTIONS=iurhn
LONGOPTIONS=install,update,remove,help,norestart
auto_restart=true
function _help() {
echo "this is the help"
# screen -d -m -t updates ./do_updates.sh
exit 0
}
function _install() {
# download and install
wget --output-document="autoupdate.sh" https://gist.githubusercontent.com/realslacker/6dce254e16003fbec5451689c9ba1e49/raw/
chmod +x "autoupdate.sh"
# make log dir
if [ ! -d /var/log/autoupdate ]; then
mkdir -p /var/log/autoupdate
fi
# create the logrotate file
if [ ! -f /etc/logrotate.d/autoupdate ]; then
cat > /etc/logrotate.d/autoupdate <<LOGROTATE
/var/log/autoupdate/lastrun.log {
rotate 14
daily
missingok
}
LOGROTATE
fi
if [ "$0" == "bash" ]; then
script=`realpath autoupdate.sh`
else
script=`realpath $0`
fi
# add script to crontab
crontab -l | grep -v "$script" | crontab -
crontab -l | { cat; echo "0 3 * * 0 $script"; } | crontab -
echo "Installation Finished"
}
function _update() {
script=`realpath $0`
wget --output-document="$script.tmp" https://gist.githubusercontent.com/realslacker/6dce254e16003fbec5451689c9ba1e49/raw/
chmod +x "$script.tmp"
mv "$script.tmp" "$script"
echo "Upgrade Finished"
}
function _remove() {
script=`realpath $0`
if [ -f /etc/logrotate.d/autoupdate ]; then
rm /etc/logrotate.d/autoupdate
fi
if [ -d /var/log/autoupdate ]; then
rm -rf /var/log/autoupdate
fi
crontab -l | grep -v "$script" | crontab -
echo "Remove Finished"
}
# -temporarily store output to be able to check for errors
# -e.g. use <93>--options<94> parameter by name to activate quoting/enhanced mode
# -pass arguments only via -- "$@" to separate them correctly
PARSED=$(getopt --options=$OPTIONS --longoptions=$LONGOPTIONS --name "$0" -- "$@")
if [[ $? -ne 0 ]]; then
# e.g. $? == 1
# then getopt has complained about wrong arguments to stdout
exit 2
fi
# read getopt<92>s output this way to handle the quoting right:
eval set -- "$PARSED"
# now enjoy the options in order and nicely split until we see --
while true; do
case "$1" in
-i|--install)
_install
exit 0
;;
-u|--update)
_update
exit 0
;;
-r|--remove)
_remove
exit 0
;;
-h|--help)
_help
exit 0
;;
-n|--norestart)
auto_restart=false
shift
break
;;
--)
shift
break
;;
*)
echo "Programming error"
exit 3
;;
esac
done
echo "Running..."
# check for log director, if it doesn't exist turn off logging
if [ ! -d /var/log/autoupdate ]; then
logfile=/dev/null
else
logfile=/var/log/autoupdate/lastrun.log
fi
echo "Automatic Update Script Run" > $logfile
date >> $logfile
DEBIAN_FRONTEND=noninteractive
apt-get update --yes | tee --append $logfile
apt-get upgrade -o Dpkg::Options::="--force-confnew" --yes | tee --append $logfile
apt-get dist-upgrade -o Dpkg::Options::="--force-confnew" --yes | tee --append $logfile
apt-mark auto ^linux-image- | tee --append $logfile
apt-get autoremove --yes | tee --append $logfile
if [ $logfile != '/dev/null' ]; then
if [ $( grep -Po '\d+(?= (upgraded|newly installed|to remove))' /var/log/autoupdate/lastrun.log | awk '{ SUM += $1 } END { print SUM }' ) -gt 0 ]; then
if [ $auto_restart = false ]; then
echo "Skipping required reboot, please restart this server"
else
echo "Rebooting server..."
reboot
fi
else
echo "No reboot required."
fi
fi
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment