ARCH=$(uname -m)
BINARY_DOCKER=/usr/bin/docker

DOCKER_REPO="ghcr.io/home-assistant"

SERVICE_DOCKER="docker.service"
SERVICE_NM="NetworkManager.service"

PREFIX=${PREFIX:-/usr}
SYSCONFDIR=${SYSCONFDIR:-/usr/lib}
DATA_SHARE=${DATA_SHARE:-$PREFIX/share/hassio}
CONFIG="/etc/hassio.json"

# Read infos from web
URL_CHECK_ONLINE="8.8.8.8"
URL_VERSION="https://version.home-assistant.io/stable.json"
HASSIO_VERSION=$(curl -s ${URL_VERSION} | jq -e -r '.supervisor')
URL_APPARMOR_PROFILE="https://version.home-assistant.io/apparmor.txt"

check_arch() {
    case ${ARCH} in
        "i386" | "i686")
            MACHINE=${MACHINE:=qemux86}
            HASSIO_DOCKER="${DOCKER_REPO}/i386-hassio-supervisor"
        ;;
        "x86_64")
            MACHINE=${MACHINE:=qemux86-64}
            HASSIO_DOCKER="${DOCKER_REPO}/amd64-hassio-supervisor"
        ;;
        "arm" |"armv6l")
            HASSIO_DOCKER="${DOCKER_REPO}/armhf-hassio-supervisor"
        ;;
        "armv7l")
            HASSIO_DOCKER="${DOCKER_REPO}/armv7-hassio-supervisor"
        ;;
        "aarch64")
            HASSIO_DOCKER="${DOCKER_REPO}/aarch64-hassio-supervisor"
        ;;
        *)
            echo
            echo "${ARCH} is not supported!"
            exit 1
        ;;
    esac
}

check_machine() {
    if [ -z "${MACHINE}" ]; then
        echo
        echo "MACHINE environment variable unknown! Please choose one of the following options:"
        echo " - generic-x86-64"
        echo " - odroid-c2"
        echo " - odroid-c4"
        echo " - odroid-n2"
        echo " - odroid-xu"
        echo " - qemuarm"
        echo " - qemuarm-64"
        echo " - qemux86"
        echo " - qemux86-64"
        echo " - raspberrypi"
        echo " - raspberrypi2"
        echo " - raspberrypi3"
        echo " - raspberrypi4"
        echo " - raspberrypi3-64"
        echo " - raspberrypi4-64"
        echo " - raspberrypi5-64"
        echo " - tinker"
        echo " - khadas-vim3"
        echo
        exit 1
    fi
}

adjust_config() {
    systemctl daemon-reload

    # Restart NetworkManager
    echo "Enable NetworkManager"
    systemctl enable "${SERVICE_NM}"> /dev/null 2>&1;
    echo "Restarting NetworkManager"
    systemctl restart "${SERVICE_NM}"

    # Check and fix systemd-journal-gatewayd socket location
    if [ ! -S "/run/systemd-journal-gatewayd.sock" ]; then
        echo "Set up systemd-journal-gatewayd socket file"
        if [ "$(systemctl is-active systemd-journal-gatewayd.socket)" = 'active' ]; then
            systemctl stop systemd-journal-gatewayd.socket> /dev/null 2>&1;
        fi
        rm -rf "/run/systemd-journal-gatewayd.sock";
    fi

    # Enable and start systemd-journal-gatewayd
    if [ "$(systemctl is-active systemd-journal-gatewayd.socket)" = 'inactive' ]; then
        echo "Enable systemd-journal-gatewayd"
        systemctl enable systemd-journal-gatewayd.socket> /dev/null 2>&1;
        systemctl start systemd-journal-gatewayd.socket
    fi
    # Start nfs-utils.service for nfs mounts
    if [ "$(systemctl is-active nfs-utils.service)" = 'inactive' ]; then
        echo "Start nfs-utils.service"
        systemctl start nfs-utils.service
    fi

    # Revert default value
    if [ -f /usr/lib/systemd/system/systemd-journal-gatewayd.socket ]
    then
        if ! grep -q "ListenStream=/run/systemd-journal-gatewayd.sock" /usr/lib/systemd/system/systemd-journal-gatewayd.socket; then
            sed -i.bak 's/ListenStream=\/run\/systemd-journal-gatewayd.sock/ListenStream=/' /usr/lib/systemd/system/systemd-journal-gatewayd.socket
        fi
    fi

    # Set permissions of /etc/systemd/resolved.conf
    # check if file has correct permissions
    if [ "$(stat -c %a /etc/systemd/resolved.conf)" != "644" ]; then
        echo "Setting permissions of /etc/systemd/resolved.conf"
        chmod 644 /etc/systemd/resolved.conf
    fi

    # Enable and restart systemd-resolved
    echo "Enable systemd-resolved"
    systemctl enable systemd-resolved.service> /dev/null 2>&1;
    echo "Restarting systemd-resolved"
    systemctl restart systemd-resolved.service

    # Install Supervisor
    sed -i "s,%%HASSIO_CONFIG%%,${CONFIG},g" "${PREFIX}/bin/hassio-supervisor"
    sed -i -e "s,%%BINARY_DOCKER%%,${BINARY_DOCKER},g" \
        -e "s,%%SERVICE_DOCKER%%,${SERVICE_DOCKER},g" \
        -e "s,%%BINARY_HASSIO%%,${PREFIX}/bin/hassio-supervisor,g" \
        "${SYSCONFDIR}/systemd/system/hassio-supervisor.service"

    systemctl daemon-reload
    systemctl enable hassio-supervisor.service > /dev/null 2>&1;

    # Install AppArmor
    mkdir -p "${DATA_SHARE}/apparmor"
    curl -sL ${URL_APPARMOR_PROFILE} > "${DATA_SHARE}/apparmor/hassio-supervisor"
    sed -i "s,%%HASSIO_CONFIG%%,${CONFIG},g" "${PREFIX}/bin/hassio-apparmor"
    sed -i -e "s,%%SERVICE_DOCKER%%,${SERVICE_DOCKER},g" \
        -e "s,%%HASSIO_APPARMOR_BINARY%%,${PREFIX}/bin/hassio-apparmor,g" \
        "${SYSCONFDIR}/systemd/system/hassio-apparmor.service"

    # Restart Docker service
    systemctl restart "${SERVICE_DOCKER}"> /dev/null 2>&1;
}

## arg 1:  the new package version
pre_install() {

    # Check if we are running on a supported OS
    BYPASS_OS_CHECK=${BYPASS_OS_CHECK:-true}
    CURRENT_OS=$(lsb_release -d)
    if [[ $CURRENT_OS != *"Debian GNU/Linux 11 (bullseye)"* ]]; then
    # Strip first feild of string
        CURRENT_OS=$(echo $CURRENT_OS | cut -d' ' -f2-)
        if [[ $BYPASS_OS_CHECK != "true" ]]; then
            error "${CURRENT_OS} is not supported!"
        fi
        echo "Bypassing OS check..."
        echo "${CURRENT_OS} is not supported!"
        echo "Please DO NOT report issues regarding this OS!"
    fi

    check_arch
    check_machine

    # Check if Modem Manager is enabled
    if systemctl is-enabled ModemManager.service &> /dev/null; then
        echo
        echo "ModemManager service is enabled. This might cause issue when using serial devices."
        echo
    fi

    # Check dmesg access
    if [[ "$(sysctl --values kernel.dmesg_restrict)" != "0" ]]; then
        # Fix kernel dmesg restriction
        echo 0 > /proc/sys/kernel/dmesg_restrict
        echo "kernel.dmesg_restrict=0" >> /etc/sysctl.conf
    fi
}

## arg 1:  the new package version
post_install() {
    # Enable and start docker
    if [ "$(systemctl is-active ${SERVICE_DOCKER})" = 'inactive' ]; then
        systemctl enable "${SERVICE_DOCKER}"> /dev/null 2>&1;
        systemctl start "${SERVICE_DOCKER}"> /dev/null 2>&1;    
    fi

    # Enable and start haos-agent
    if [ "$(systemctl is-active haos-agent.service)" = 'inactive' ]; then
        systemctl enable haos-agent.service> /dev/null 2>&1;
        systemctl start haos-agent.service> /dev/null 2>&1;
    fi

    check_arch
    check_machine
    
    cat > "${CONFIG}" <<- EOF
{
"supervisor": "${HASSIO_DOCKER}",
"machine": "${MACHINE}",
"data": "${DATA_SHARE}"
}
EOF

    adjust_config
    
    # Check network connection
    while ! ping -c 1 -W 1 ${URL_CHECK_ONLINE}; do
        echo "Waiting for ${URL_CHECK_ONLINE} - network interface might be down..."
        sleep 2
    done

    # Get primary network interface
    PRIMARY_INTERFACE=$(ip route | awk '/^default/ { print $5; exit }')
    IP_ADDRESS=$(ip -4 addr show dev "${PRIMARY_INTERFACE}" | awk '/inet / { sub("/.*", "", $2); print $2 }')

    systemctl enable hassio-apparmor.service > /dev/null 2>&1;
    systemctl start hassio-apparmor.service

    # Start Supervisor 
    systemctl start hassio-supervisor.service

    # Switch to cgroup v1
    if [ -f /etc/default/grub ]
    then
        if ! grep -q "systemd.unified_cgroup_hierarchy=false" /etc/default/grub; then
            echo
            echo "You need to add systemd.unified_cgroup_hierarchy=false in your kernel parameters."
            echo "Read more at: https://wiki.archlinux.org/title/Kernel_parameters"
        fi
    elif [ -f /boot/firmware/cmdline.txt ]
    then
        if ! grep -q "systemd.unified_cgroup_hierarchy=false" /boot/firmware/cmdline.txt; then
            echo
            echo "You need to add systemd.unified_cgroup_hierarchy=false in your kernel parameters."
            echo "Read more at: https://wiki.archlinux.org/title/Kernel_parameters"
        fi
    else
        if ! grep -q "systemd.unified_cgroup_hierarchy=false" /proc/cmdline; then
            echo
            echo "You need to add systemd.unified_cgroup_hierarchy=false in your kernel parameters."
            echo "Read more at: https://wiki.archlinux.org/title/Kernel_parameters"
        fi
    fi
    echo
    echo "Within a few minutes you will be able to reach Home Assistant at:"
    echo "http://homeassistant.local:8123 or using the IP address of your"
    echo "machine: http://${IP_ADDRESS}:8123"
    echo
}

## arg 1:  the new package version
## arg 2:  the old package version
pre_upgrade() {
    # If the hassio_supervisor service is running or exists, stop it 
    if [[ "$(systemctl is-active hassio-supervisor.service)" == "active" ]]; then
        echo "Stopping hassio_supervisor service"
        systemctl stop hassio-supervisor.service
    fi

    # If the hassio_apparmor service is running or exists, stop it
    if [[ "$(systemctl is-active hassio-apparmor.service)" == "active" ]]; then
        echo "Stopping hassio_apparmor service"
        systemctl stop hassio-apparmor.service
    fi

    # Check for existing hassio_supervisor container and destroy it
    if [[ "$(docker ps -aq -f name=hassio_supervisor)" ]]; then
        # ensure the hassio_supervisor service is stopped
        echo "Removing existing hassio_supervisor container"
        docker container rm --force hassio_supervisor > /dev/null
    fi
}

## arg 1:  the new package version
## arg 2:  the old package version
post_upgrade() {
    adjust_config
    systemctl daemon-reload
    systemctl start hassio-apparmor.service
    systemctl start hassio-supervisor.service
}

## arg 1:  the old package version
pre_remove() {
	systemctl stop hassio-apparmor.service
    systemctl stop hassio-supervisor.service
	systemctl disable hassio-apparmor.service
	systemctl disable hassio-supervisor.service
    docker stop homeassistant hassio_multicast hassio_observer hassio_audio hassio_dns hassio_cli
}

## arg 1:  the old package version
post_remove() {
    docker rm homeassistant hassio_multicast hassio_observer hassio_audio hassio_dns hassio_cli
    # Check for existing hassio_supervisor container and destroy it
    if [[ "$(docker ps -aq -f name=hassio_supervisor)" ]]; then
        # ensure the hassio_supervisor service is stopped
        echo "Removing existing hassio_supervisor container"
        docker container rm --force hassio_supervisor > /dev/null
    fi
    echo "Removal complete, due to the complexity of this installation method,"
    echo "you will need to manually remove the containers created by the supervisor"
}