#!/usr/bin/env bash # TA-Proxmenu - Proxmox Setup Scripts for TA Use [ "${2:-}" != "q" ] && source /opt/idssys/defaults/colors.inc source /opt/idssys/defaults/default.inc source /opt/idssys/ta-proxmenu/defaults.inc ACTION_REQUESTED=0 [[ -n "${action:-}" ]] && ACTION_REQUESTED=1 FINISH_ACTION() { (( ACTION_REQUESTED == 1 )) && exit 0 ENTER2CONTINUE } INSTALL_PULSE() { echo bash <(curl -fsSL https://github.com/rcourtman/Pulse/releases/latest/download/install.sh) echo echo -e "\n${idsCL[Green]}Pulse has been installed${idsCL[Default]}" FINISH_ACTION } INSTALL_ACRONIS() { read -n 1 -p "Are you sure you wish to install Acronis (Y/n)?" choice case "$choice" in [Nn]) echo;; * ) echo cd /tmp || return 1 wget "https://us5-cloud.acronis.com/bc/api/ams/links/agents/redirect?language=multi&channel=CURRENT&system=linux&architecture=64&productType=enterprise&login=010180ae-63c4-4495-bed0-4ec934c25af9&white_labeled=0" -O ./acronisinstall chmod +x ./acronisinstall ./acronisinstall rm -f ./acronisinstall echo echo -e "\n${idsCL[Green]}Acronis has been installed${idsCL[Default]}" FINISH_ACTION ;; esac } INSTALL_PROXMENUX() { # read -n 1 -p "Are you sure you wish to install ProxMenux (Y/n)?" choice # case "$choice" in # [Nn]) MAIN_MENU;; # * ) # echo bash -c "$(wget -qLO - https://raw.githubusercontent.com/MacRimi/ProxMenux/main/install_proxmenux.sh)" # systemctl disable --now proxmenux-monitor menu # echo -e "\n${idsCL[Green]}ProxMenux has been installed${idsCL[Default]}" # esac } PROXMENUX_POST_INSTALL() { PMFLDR='/usr/local/share/proxmenux/scripts/post_install' [ ! -f "${PMFLDR}/customizable_post_install.sh" ] && INSTALL_PROXMENUX bash "${PMFLDR}/customizable_post_install.sh" touch /opt/.PROXMENUX_POST_INSTALL [ -s /etc/apt/sources.list ] && cat /dev/null > /etc/apt/sources.list } INSTALL_GLANCES() { read -n 1 -p "Are you sure you wish to install Glances (Y/n)?" choice case "$choice" in [Nn]) echo;; * ) echo apt install glances -y echo -e "\n${idsCL[Green]}Glances has been installed${idsCL[Default]}" FINISH_ACTION esac } INSTALL_SCREENCONNECT() { read -n 1 -p "Are you sure you wish to install ScreenConnect (Y/n)?" choice case "$choice" in [Nn]) echo;; * ) echo echo -en "\n${idsCL[LightYellow]}Paste the URL provided from the Build Installer: ${idsCL[Default]}" read -r -e SCURL [[ -n "$SCURL" ]] || { echo "No URL supplied."; FINISH_ACTION; return; } wget "${SCURL}" -O /tmp/scinstall dpkg -i /tmp/scinstall apt install --fix-broken -y apt remove "connectwis*" -y > /dev/null 2>&1 dpkg -i /tmp/scinstall rm -f /tmp/scinstall systemctl disable --now proxmenux-monitor echo -e "\n${idsCL[Green]}ScreenConnect has been installed${idsCL[Default]}" FINISH_ACTION esac } INSTALL_RMM() { read -n 1 -p "Are you sure you wish to install RMM (Y/n)?" choice case "$choice" in [Nn]) echo;; * ) echo echo -en "\n${idsCL[LightYellow]}Paste the Linux Server URL provided from the Download Agent screen: ${idsCL[Default]}" read -r -e RMMURL [[ -n "$RMMURL" ]] || { echo "No URL supplied."; FINISH_ACTION; return; } wget "${RMMURL}" -O /tmp/rmminstall if [[ "$RMMURL" != *TKN* || "$RMMURL" != */RUN* ]]; then echo "Unable to extract the RMM token from the URL." FINISH_ACTION return fi TOKEN="${RMMURL#*TKN}" TOKEN="${TOKEN%%/RUN*}" [[ -n "$TOKEN" ]] || { echo "The RMM token is empty."; FINISH_ACTION; return; } TOKEN="$TOKEN" bash /tmp/rmminstall systemctl restart ITSPlatform # rm -f /tmp/rmminstall echo -e "\n${idsCL[Green]}RMM has been installed${idsCL[Default]}" FINISH_ACTION esac } INSTALL_S1() { echo echo -en "${idsCL[LightYellow]}Paste the customers SentinelOne Site Token: ${idsCL[Default]}" read -r -e s1token [[ -n "$s1token" ]] || { echo "No SentinelOne site token supplied."; FINISH_ACTION; return; } cd /tmp || return 1 rm -f "/tmp/${S1_PACKAGE}" wget "$S1_DOWNLOAD_URL" -O "/tmp/${S1_PACKAGE}" dpkg -i "/tmp/${S1_PACKAGE}" /opt/sentinelone/bin/sentinelctl management token set "$s1token" /opt/sentinelone/bin/sentinelctl control start rm -f "/tmp/${S1_PACKAGE}" echo -e "\n${idsCL[Green]}SentinelOne Agent has been installed. Make sure its added to a \"DETECT ONLY\" policy${idsCL[Default]}" FINISH_ACTION } INSTALL_OMSA() { read -n 1 -p "Are you sure you wish to install Dell OpenManage Administrator (Y/n)?" choice case "$choice" in [Nn]) echo;; * ) echo mkdir -p /tmp/omsa cd /tmp/omsa || return 1 apt install -y gnupg libcurl4t64 libncurses6 libxslt1.1 libgpm2 libtinfo6 mkdir -p /etc/apt/keyrings wget -qO - https://linux.dell.com/repo/pgp_pubkeys/0x1285491434D8786F.asc | gpg --dearmor -o /etc/apt/keyrings/linux.dell.com.gpg chmod +r /etc/apt/keyrings/linux.dell.com.gpg echo "deb [signed-by=/etc/apt/keyrings/linux.dell.com.gpg] http://linux.dell.com/repo/community/openmanage/11000/jammy jammy main" > /etc/apt/sources.list.d/linux.dell.com.list apt update wget -c http://archive.ubuntu.com/ubuntu/pool/universe/o/openwsman/libwsman-curl-client-transport1_2.6.5-0ubuntu16_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/o/openwsman/libwsman-client4t64_2.6.5-0ubuntu16_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/o/openwsman/libwsman1t64_2.6.5-0ubuntu16_amd64.deb # wget -c http://http.us.debian.org/debian/pool/main/libx/libxml2/libxml2-16_2.15.1+dfsg-2+b1_amd64.deb wget -c http://http.us.debian.org/debian/pool/main/libx/libxml2/libxml2-16_2.15.2+dfsg-0.1_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/o/openwsman/libwsman-server1t64_2.6.5-0ubuntu16_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/s/sblim-sfcc/libcimcclient0_2.2.8-0ubuntu2_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/o/openwsman/openwsman_2.6.5-0ubuntu16_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/multiverse/c/cim-schema/cim-schema_2.48.0-0ubuntu1_all.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/s/sblim-sfc-common/libsfcutil0_1.0.1-0ubuntu4_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/multiverse/s/sblim-sfcb/sfcb_1.4.9-0ubuntu7_amd64.deb wget -c http://archive.ubuntu.com/ubuntu/pool/universe/s/sblim-cmpi-devel/libcmpicppimpl0_2.0.3-0ubuntu2_amd64.deb wget -c http://ftp.us.debian.org/debian/pool/main/o/openssl/libssl1.1_1.1.1w-0+deb11u1_amd64.deb dpkg -i libwsman-curl-client-transport1_2.6.5-0ubuntu16_amd64.deb dpkg -i libwsman-client4t64_2.6.5-0ubuntu16_amd64.deb dpkg -i libxml2-16_2.15.2+dfsg-0.1_amd64.deb dpkg -i libwsman1t64_2.6.5-0ubuntu16_amd64.deb dpkg -i libwsman-server1t64_2.6.5-0ubuntu16_amd64.deb dpkg -i libcimcclient0_2.2.8-0ubuntu2_amd64.deb dpkg -i openwsman_2.6.5-0ubuntu16_amd64.deb dpkg -i cim-schema_2.48.0-0ubuntu1_all.deb dpkg -i libsfcutil0_1.0.1-0ubuntu4_amd64.deb dpkg -i sfcb_1.4.9-0ubuntu7_amd64.deb dpkg -i libcmpicppimpl0_2.0.3-0ubuntu2_amd64.deb dpkg -i libssl1.1_1.1.1w-0+deb11u1_amd64.deb apt install -y srvadmin-all /opt/dell/srvadmin/sbin/srvadmin-services.sh start rm -rf -- /tmp/omsa echo -e "\n${idsCL[Green]}Dell OMSA has been installed${idsCL[Default]}" echo -e "\n${idsCL[LightCyan]}Available at: ${idsCL[LightGreen]}https://${RNIP}:1311${idsCL[Default]}" FINISH_ACTION esac } DOWNLOAD_VIRTIO() { echo -e "\n${idsCL[LightCyan]}Current \"Stable\" version available for download: ${idsCL[White]}${VIRTIO_FILE}${idsCL[Default]}" if [ -f "${DLDIR}/${VIRTIO_FILE}" ]; then echo -en "\n${idsCL[LightRed]}Removing existing download ... " rm -f "${DLDIR}/${VIRTIO_FILE}" echo -e "${idsCL[Red]}Done${idsCL[Default]}" fi wget -q -P "$DLDIR" "$VIRTIO_DOWNLOAD_URL" & echo -e "\n${idsCL[LightCyan]}Downloading will continue in the background\n" FINISH_ACTION } DETECT_CPU(){ # if [ ! -f /etc/apt/sources.list.d/proxlb.list ]; then # echo "deb https://repo.gyptazy.com/stable /" > /etc/apt/sources.list.d/proxlb.list # wget -O /etc/apt/trusted.gpg.d/proxlb.asc https://repo.gyptazy.com/repository.gpg # apt-get update # fi if [ ! -f /etc/apt/sources.list.d/gyptazy.list ]; then curl https://git.gyptazy.com/api/packages/gyptazy/debian/repository.key -o /etc/apt/keyrings/gyptazy.asc echo "deb [signed-by=/etc/apt/keyrings/gyptazy.asc] https://packages.gyptazy.com/api/packages/gyptazy/debian trixie main" | sudo tee -a /etc/apt/sources.list.d/gyptazy.list apt update fi if [ "$(dpkg -l | awk '/proxclmc/ {print }'|wc -l)" -eq 0 ]; then apt -y install proxclmc fi echo proxclmc echo echo -en "${idsCL[LightCyan]}Would you like to set '${idsCL[LightGreen]}cpu: $(proxclmc --list-only)${idsCL[LightCyan]}' on all VMs (y/N)?${idsCL[Default]} " read -n 1 choice case "$choice" in [Yy]) sed -i "/cpu:/c cpu: $(proxclmc --list-only)" /etc/pve/nodes/*/qemu-server/*.conf echo echo -e "\n${idsCL[Green]}All VM's have been reconfigured\n${idsCL[LightCyan]}This will require the VM's to be powered off and then turned back on in order to take effect${idsCL[Default]}" FINISH_ACTION ;; *) echo;; esac } RESTART_PVE_SERVICES(){ if [ "${1}" == "" ]; then echo -en "${idsCL[LightCyan]}Would you like to restart all Proxmox services on the local host (Y/n)?${idsCL[Default]} " read -n 1 choice else choice=${1} fi case "${choice}" in [Nn]) echo;; *) echo echo -en "\n${idsCL[Yellow]}Restarting services ... " #systemctl restart pve-cluster pvedaemon pvestatd pveproxy pve-ha-lrm pve-ha-crm systemctl restart pve-cluster pvedaemon pvestatd pveproxy echo -e "${idsCL[Green]}Done${idsCL[Default]}" echo -e "\n${idsCL[Green]}This hosts Proxmox services have been restarted${idsCL[Default]}\n" FINISH_ACTION ;; esac } MAINTENANCE_MODE(){ local local_node local_node="$(hostname -s)" if ha-manager status | grep -F "$local_node" | grep -q "maintenance mode"; then echo -en "${idsCL[LightCyan]}Take the local host out of maintenance mode (Y/n)?${idsCL[Default]} " else echo -en "${idsCL[LightCyan]}Put the local host into maintenance mode (Y/n)?${idsCL[Default]} " fi read -n 1 choice case "$choice" in [Nn]) echo;; *) echo if ha-manager status | grep -F "$local_node" | grep -q "maintenance mode"; then ha-manager crm-command node-maintenance disable "$local_node" echo -e "\n${idsCL[Green]}This host will be taken out of maintenance mode${idsCL[Default]}\n" else ha-manager crm-command node-maintenance enable "$local_node" echo -e "\n${idsCL[Green]}This host will be entered into maintenance mode${idsCL[Default]}\n" bash /opt/idssys/ta-proxmenu/inc/evacuate-proxmox-node.sh fi FINISH_ACTION ;; esac } INSTALL_KEEPALIVE() { read -n 1 -p "Are you sure you wish to install Keepalive on all Hosts (Y/n)?" choice case "$choice" in [Nn]) echo;; * ) echo bash /opt/idssys/ta-proxmenu/inc/deploy-proxmox-keepalived.sh echo -e "\n${idsCL[Green]}Keepalive has been installed${idsCL[Default]}" FINISH_ACTION esac } MENU_HEADER() { clear echo echo -e " ${idsCL[Green]}TA-ProxMenu - Proxmox Setup Scripts${idsCL[Default]} ${VERS}" echo -e "${idsCL[Green]}---------------------------------------------------------------------------${idsCL[Default]}" echo -e " Hostname: ${idsCL[Cyan]}$(hostname -s)${idsCL[Default]}" echo -e " IP Address: ${idsCL[Cyan]}${RNIP:-Unavailable}${idsCL[Default]}" echo -e "${idsCL[Green]}---------------------------------------------------------------------------${idsCL[Default]}" } SELECT_MENU() { local title="$1" local labels_name="$2" local values_name="$3" local allow_back="${4:-1}" local -n labels_ref="$labels_name" local -n values_ref="$values_name" local selected=0 local key local sequence local index while true; do MENU_HEADER echo echo -e " ${idsCL[LightCyan]}${title}${idsCL[Default]}" echo for index in "${!labels_ref[@]}"; do if (( index == selected )); then printf '\e[7m %d %-64s\e[0m\n' "$((index + 1))" "${labels_ref[$index]}" else printf ' %d %s\n' "$((index + 1))" "${labels_ref[$index]}" fi done echo if (( allow_back == 1 )); then echo " ↑/↓ Navigate Enter Select Number Quick Select ←/Esc/B Back Q Quit" else echo " ↑/↓ Navigate Enter Select Number Quick Select Q Quit" fi IFS= read -rsn1 key case "$key" in "") MENU_SELECTION="${values_ref[$selected]}" return 0 ;; [1-9]) index=$((10#$key - 1)) if (( index < ${#values_ref[@]} )); then MENU_SELECTION="${values_ref[$index]}" return 0 fi ;; [Qq]) MENU_SELECTION="quit" return 0 ;; [Bb]) if (( allow_back == 1 )); then MENU_SELECTION="back" return 0 fi ;; $'\e') sequence="" IFS= read -rsn2 -t 0.1 sequence || true case "$sequence" in "[A"|"OA") (( selected = (selected - 1 + ${#labels_ref[@]}) % ${#labels_ref[@]} )) ;; "[B"|"OB") (( selected = (selected + 1) % ${#labels_ref[@]} )) ;; "[C"|"OC") MENU_SELECTION="${values_ref[$selected]}" return 0 ;; "[D"|"OD"|"") if (( allow_back == 1 )); then MENU_SELECTION="back" return 0 fi ;; "[H") selected=0 ;; "[F") selected=$((${#labels_ref[@]} - 1)) ;; esac ;; esac done } SHOW_ABOUT() { MENU_HEADER echo echo -e " ${idsCL[LightCyan]}About TA-ProxMenu${idsCL[Default]}" echo echo " Version: ${VERS}" echo " Install: /opt/idssys/ta-proxmenu" echo " Branch: $(git -C /opt/idssys/ta-proxmenu branch --show-current 2>/dev/null || echo unknown)" echo read -r -p " Press ENTER to return..." _ } HOST_SETUP_MENU() { local -a labels local -a values=( "post_install" "cpu" "virtio" "glances" "omsa" ) while true; do labels=("Run ProxMenux post-install configuration") [ -f /opt/.PROXMENUX_POST_INSTALL ] && labels[0]="Run ProxMenux post-install configuration (previously run)" labels+=("Detect CPU model for live migrations") if [ -f "${DLDIR}/${VIRTIO_FILE}" ]; then labels+=("VirtIO drivers (${VIRTIO_FILE} already downloaded)") elif compgen -G "${DLDIR}/virtio*.iso" >/dev/null; then labels+=("Download updated VirtIO drivers") else labels+=("Download current VirtIO drivers") fi command -v glances >/dev/null 2>&1 && labels+=("Glances CLI monitor (installed)") || labels+=("Install Glances CLI monitor") dpkg-query -W -f='${Status}' srvadmin-all 2>/dev/null | grep -q "install ok installed" && labels+=("Dell OpenManage Server Administrator (installed)") || labels+=("Install Dell OpenManage Server Administrator") SELECT_MENU "Host Setup" labels values case "$MENU_SELECTION" in post_install) PROXMENUX_POST_INSTALL;; cpu) DETECT_CPU;; virtio) DOWNLOAD_VIRTIO;; glances) INSTALL_GLANCES;; omsa) INSTALL_OMSA;; back) return;; quit) EXIT1; exit 0;; esac done } MONITORING_MENU() { local -a labels local -a values=("pulse" "rmm" "acronis" "sentinelone" "screenconnect") local cluster_resources while true; do cluster_resources="$(pvesh get /cluster/resources 2>/dev/null)" grep -qi pulse <<< "$cluster_resources" && labels=("Pulse monitoring (installed)") || labels=("Install Pulse monitoring") systemctl is-active --quiet ITSPlatform && labels+=("ConnectWise RMM agent (installed)") || labels+=("Install ConnectWise RMM agent") dpkg-query -W -f='${Status}' cyberprotect 2>/dev/null | grep -q "install ok installed" && labels+=("Acronis backup agent (installed)") || labels+=("Install Acronis backup agent") dpkg-query -W -f='${Status}' sentinelagent 2>/dev/null | grep -q "install ok installed" && labels+=("SentinelOne agent (installed)") || labels+=("Install SentinelOne agent v${S1_VERSION//_/.}") systemctl is-active --quiet 'connectwise*' && labels+=("ScreenConnect agent (installed)") || labels+=("Install ScreenConnect agent") SELECT_MENU "Monitoring & Agents" labels values case "$MENU_SELECTION" in pulse) INSTALL_PULSE;; rmm) INSTALL_RMM;; acronis) INSTALL_ACRONIS;; sentinelone) INSTALL_S1;; screenconnect) INSTALL_SCREENCONNECT;; back) return;; quit) EXIT1; exit 0;; esac done } CLUSTER_MENU() { local -a labels local -a values=("maintenance" "restart" "keepalived") while true; do if ha-manager status | grep -F "$(hostname -s)" | grep -q "maintenance mode"; then labels=("Take this host out of maintenance mode") else labels=("Put this host into maintenance mode and evacuate guests") fi labels+=("Restart local Proxmox services") dpkg-query -W -f='${Status}' keepalived 2>/dev/null | grep -q "install ok installed" && labels+=("Deploy/reconfigure Keepalived (installed locally)") || labels+=("Deploy Keepalived on all cluster hosts") SELECT_MENU "Cluster & Maintenance" labels values case "$MENU_SELECTION" in maintenance) MAINTENANCE_MODE;; restart) RESTART_PVE_SERVICES;; keepalived) INSTALL_KEEPALIVE;; back) return;; quit) EXIT1; exit 0;; esac done } UTILITIES_MENU() { local -a labels=("Check for script updates" "Version and installation information") local -a values=("update" "about") while true; do SELECT_MENU "Utilities" labels values case "$MENU_SELECTION" in update) /opt/idssys/ta-proxmenu/run.sh update read -r -p " Press ENTER to return..." _ ;; about) SHOW_ABOUT;; back) return;; quit) EXIT1; exit 0;; esac done } MAIN_MENU() { local -a labels=( "Host Setup" "Monitoring & Agents" "Cluster & Maintenance" "Utilities" "Quit" ) local -a values=("host" "monitoring" "cluster" "utilities" "quit") while true; do SELECT_MENU "Main Menu" labels values 0 case "$MENU_SELECTION" in host) HOST_SETUP_MENU;; monitoring) MONITORING_MENU;; cluster) CLUSTER_MENU;; utilities) UTILITIES_MENU;; quit) EXIT1; exit 0;; esac done } if (( ACTION_REQUESTED == 1 )); then case "$action" in pulse) INSTALL_PULSE;; rmm) INSTALL_RMM;; omsa) INSTALL_OMSA;; glances) INSTALL_GLANCES;; acronis) INSTALL_ACRONIS;; post-install|post_install) PROXMENUX_POST_INSTALL;; proxmenux) [ ! -f /usr/local/bin/menu ] && INSTALL_PROXMENUX || /usr/local/bin/menu;; virtio) DOWNLOAD_VIRTIO;; sentinelone|s1) INSTALL_S1;; screenconnect) INSTALL_SCREENCONNECT;; restart) RESTART_PVE_SERVICES "${2:-}";; cpu) DETECT_CPU;; maintenance|mm) MAINTENANCE_MODE;; keepalived) INSTALL_KEEPALIVE;; *) MAIN_MENU;; esac else MAIN_MENU fi exit 0