#!/bin/bash
#(Semi)GUI updater for antiX Linux, using yad and gksudo to provide interfaces and perform updates and upgrades always selecting the default options
#Version 3.3 by PPC. 19/January/2023, GPL license, please keep this atribution, but use and adapt the code freely

TEXTDOMAINDIR=/usr/share/locale
TEXTDOMAIN=yad-updater

windowicon="--window-icon=software-sources"
touch /tmp/loggy
log="/tmp/$(date +%s)"

#Strings used in the script, grouped here for easy changes/ easier localization
title=$"antiX - Updater"
internet_detected_message=$"Internet connection detected"
apt_error_message=$"\n <b><big><big>  It seems that apt is already in use.  </big></big></b> \n \n Close any application using it (like Package Installer or Synaptic) and try to run $title again. \n \n (Please note that you can only run one instance of $title at a time) \n"
apt_error_message2=$"antiX Updater will now try to force close any  already running instance of apt, in order to be able to perform the update."
no_internet_message=$"No Internet connection detected"
root_message=$"You are Root or running the script in sudo mode"
not_root_message=$"You entered the wrong password or you cancelled"
wait_for_network_message=$"Waiting for a Network connection..."
already_updated_message=$"\n No updates were found \n Your system is up to date \n"
finished_updating_message=$"\n Your system is now updated \n" 
error_upgrading_message=$"\n <b><big><big>  There was an error while updating your system! </big></big></b> \n \n Please read the output in the Terminal window below this one. \n After closing this window, you can try to fix the problem by running <b> sudo apt -f install  </b> \n in a new Terminal window and then try to update your system again. \n \n If the problem still remains, copy any error messages that appear in the Terminal and \n ask for help at antixforum.com \n"
error_upgrading_messagefixed=$(echo "$error_upgrading_message" | tr "'" \`)  ### cut '
title_terminal=$"antiX - Updater: DO NOT CLOSE THIS WINDOW"
automatic_upgrade_button=$"'Automatic' Update"
manual_upgrade_button=$"'Manual' Update"
available_updates_message_part1=$"<b><big><big> There's, at least, "
available_updates_message_part2=$" available update(s) </big></big></b> \n \n <b> 'Automatic' Update </b> - usually it's completely unattended. and normally safe, since it always makes the default choices for you  \n (Pressing the Enter key now will select the Automatic mode) \n <b> 'Manual' Update </b> - gives you full control of the update process, but may require you to make some choices \n"

###allow only one instance of the script:
if wmctrl -l | grep -q "$title"; then
    echo $"$title is already running."
    exit 1
fi

#Start of "Update reminder" Function
REMINDER() {
# script to remind users to update regulary, meant to be run regulary, by PPC, full GPL license
days_to_wait_before_warning=2

#check if a network connection is available, if no network is detected, exit
#if ! nc -zw1 google.com 443; then   exit;  fi 
if ! ip route | grep -q default; then  exit; fi

##Only run script if it was not already ran before on current day (check if file  /tmp/ft10-update-reminder-ran exits with today's date)
last_check=$(cat $HOME/.config/antiX-update-lastest-run)
today=$(date +%x)
if [[ $today == $last_check ]]; then echo $"Already warned user to check for updates OR already checked for updates today"; exit;

	else
		echo CHECKING FOR UPDATES
  
		##Main part of update reminder:
		date_of_last_update=$(stat -c %y /var/lib/apt/periodic/update-success-stamp| cut -d" " -f1)
		today=$(date +%Y-%m-%d)
		let DIFF=(`date +%s -d $today`-`date +%s -d $date_of_last_update`)/86400
		test_for_available_updates=$(apt list --upgradable | wc |  awk '{print $1;}')
		available_updates=$(expr $test_for_available_updates - 1)

		##Create temp file that stores the info that the script already ran today
		touch $HOME/.config/antiX-update-lastest-run
		echo $(date +%x) > $HOME/.config/antiX-update-lastest-run

		###testing if it's time to remind the user to check for updates:
		echo Days since last update or check for updates: $DIFF
		if [ $DIFF -ge $days_to_wait_before_warning ]; then
				#Warning user to check for updates
				yad --borders=10 --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-important.png" --undecorated --geometry=280x50-40-50  --window-icon="software-sources" --title=$"antix Updater Reminder" --text=$"It's been $DIFF days since you last checked for updates.You should check for updates now." --button="x":1 --button=$"Check for Updates":2
				### wait for a button to be pressed then perform the selected function, if user selected to exit, then leave, if not keep running the script and check for updates
				  foo=$?
				  [[ $foo -eq 1 ]] && exit 0
			else
			   #Wait for another day to remind user to check for updates: leave this function
			   #return
			   exit 
		fi

fi 
} # end of "Update reminder" Function

# Parse command-line options
while getopts ":r" opt; do
 case ${opt} in
    r )
      REMINDER
      ;;
    ? )
      echo $"Invalid Option: -$OPTARG" 1>&2
      exit 1
      ;;
 esac
done
shift $((OPTIND -1))

##MAIN SCRIPT
### These lines of code check for internet connectivity 
# adapted from https://unix.stackexchange.com/questions/190513/shell-scripting-proper-way-to-check-for-internet-connectivity
#if ! nc -zw1 google.com 443; then
if ! ip route | grep -q default; then
		yad $windowicon --center --width=250 --text-align=center  --text="$no_internet_message" --title="$title" --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-obstructed.png" --button=' x ':1  --borders=5 --fixed
		exit
	else
		echo $internet_detected_message
fi

### Check if user is Root, if not, pop up window asking for password, to run updater. If Cancelled, exit.
# adapted from  https://stackoverflow.com/questions/42875809/checking-sudo-in-bash-script-with-if-statements 
if [[ "$EUID" = 0 ]]; then
    echo $root_message
else
    gksudo "$title"
    if sudo true; then
        echo $root_message
    else
        echo $not_root_message
        yad $windowicon --center --width=250 --text-align=center  --text="$not_root_message" --title="$title" --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-obstructed.png" --button=' x '  --borders=5 --fixed
        exit 1
    fi
fi

###check if apt is being used, if so, warn the user!- adapted from this example: https://askubuntu.com/questions/132059/how-to-make-a-package-manager-wait-if-another-instance-of-apt-is-running
while sudo fuser /var/{lib/{dpkg,apt/lists},cache/apt/archives}/lock >/dev/null 2>&1; do
   yad $windowicon --center --width=250 --text-align=left  --text="$apt_error_message" --title="$title" --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-obstructed.png" --button='OK':1  --borders=5 --fixed
   sleep 1
done

#Perform "sudo apt update" and output it's result to a yad window with a progress bar
sudo apt update 2> "${log}" |
while read -r line; do echo "# ${line}"; echo " ${line}" > /tmp/loggy; done |
    yad --borders=5 $windowicon --progress --pulsate --center --no-buttons --auto-close --progress-text="$wait_for_network_message" --width=595 --height=100 --title="$title" --fixed --borders=5

#Check if there are updates, if there are none, display yad window informing the user of that fact and exit the script   
string=$(cat /tmp/loggy)
 for reqsubstr in 'up to date';do
	apt list --upgradable > /tmp/list_of_upgradable_packages.txt
	wc -l /tmp/list_of_upgradable_packages.txt
	upgradables=$(cat /tmp/list_of_upgradable_packages.txt | wc -l)
if [ $upgradables -eq 1 ]; then
  yad $windowicon --center --width=250 --text-align=center --text="$already_updated_message" --title="$title" --button=" x ":1  --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-normal.png" --fixed --borders=5 ; 
  ##Create temp file that stores the info that the script already ran today and exit
  echo Saving date of last update...
  touch $HOME/.config/antiX-update-lastest-run
  echo $(date +%x) > $HOME/.config/antiX-update-lastest-run
  exit 0
fi	
  
#Procedure to follow if updates are available to be installed
# Inform the user of how many updates are available and ask the user if the upgrade should be done in automatic or manual mode
 test_for_available_updates=$(apt list --upgradable | wc |  awk '{print $1;}')
 number_of_available_updates=$(expr $test_for_available_updates - 1)
 yad --borders=5 --center  --window-icon="software-sources" --title="$title" --text="$available_updates_message_part1 $number_of_available_updates $available_updates_message_part2" --button="$automatic_upgrade_button":1 --button="$manual_upgrade_button":2 --fixed
  
#Check for user's selection  
  foo=$?
  
#if user selected automatic (option 1)  
 if [[ $foo -eq 1 ]]; then
	x-terminal-emulator --colour-scheme=GTK --hide-menubar -T "$title_terminal" -e /bin/bash -c "tput civis  && sudo apt -q -y -o Dpkg::Options::=--force-confdef -o Dpkg::Options::=--force-confold dist-upgrade --fix-missing && sleep 0.1 && yad --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-normal.png" --center --borders=5 --width=250 --text-align=center  --text='$finished_updating_message' --window-icon=software-sources --button='OK' --title='$title' --fixed || yad --borders=5 --center --window-icon='software-sources' --title='$title' --text='$error_upgrading_messagefixed' --button=' x ' --fixed --image='/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-obstructed.png'"
 fi

#if user selected manual (option 2)  
 if [[ $foo -eq 2 ]]; then
      x-terminal-emulator -T "$title_terminal" -e /bin/bash -c "sudo apt dist-upgrade && sleep 0.1 && yad --image="/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-normal.png" --center --borders=5 --width=250 --text-align=center  --text='$finished_updating_message' --window-icon=software-sources --button='OK' --title=$'antiX - Updater' --fixed|| yad --borders=5 --center --window-icon='software-sources' --title='$title' --text='$error_upgrading_messagefixed' --button=' x ' --fixed --image='/usr/share/icons/papirus-antix/48x48/emblems/emblem-rabbitvcs-obstructed.png'"
 fi
 
 ##Create temp file that stores the info that the script already ran today and exit
 echo Saving date of last update...
 touch $HOME/.config/antiX-update-lastest-run
 echo $(date +%x) > $HOME/.config/antiX-update-lastest-run
 
    done #close the do-done loop opened when checking for updates
