get.configserver.dev ¶
The subdomain get.configserver.dev provides a simple online service for downloading the latest version of CSF using a Bash script.
By default, running the script downloads the latest CSF release to the current directory. Optional arguments allow you to extend its functionality, including automatically extracting the archive and installing CSF immediately after download.
.zip
vs .tgz
format
Our documentation frequently mentions both .zip
and .tgz
releases of CSF.
When we initially developed addons for CSF, we pushed all of our releases in a .zip
archive.
However, after taking over full development of CSF, we opted to migrate back to the .tgz
format to keep conformity with how the original developer packaged releases. This is why our scripts mention both extensions, and why our scripts look for both.
Usage¶
This section explains how the get.sh script can be utilized when obtaining the latest version of CSF from our servers.
Examples¶
Command | Description |
---|---|
bash <(wget -qO - https://get.configserver.dev) |
Download CSF w/ filename csf.zip or csf.tgz |
bash <(wget -qO - https://get.configserver.dev) --preserve-name |
Download CSF w/ filename csf-firewall-vXX.XX.zip or csf-firewall-vXX.XX.tgz |
bash <(wget -qO - https://get.configserver.dev) --extract |
Download CSF w/ filename csf.zip or csf.tgz , extract to csf |
bash <(wget -qO - https://get.configserver.dev) --extract --folder csftest |
Download CSF w/ filename csf.zip or csf.tgz , extract to csftest |
bash <(wget -qO - https://get.configserver.dev) --install |
Download CSF w/ filename csf.zip or csf.tgz , extract to csf , install CSF |
bash <(wget -qO - https://get.configserver.dev) --install --folder csftest |
Download CSF w/ filename csf.zip or csf.tgz , extract to csftest , install CSF |
bash <(wget -qO - https://get.configserver.dev) --install --dryrun |
Download CSF w/ filename csf.zip or csf.tgz , extract to csf , simulate install CSF |
bash <(wget -qO - https://get.configserver.dev) --install --folder csftest --dryrun |
Download CSF w/ filename csf.zip or csf.tgz , extract to csftest , simulate install CSF |
bash <(wget -qO - https://get.configserver.dev) --install-only |
No download, install existing local folder csf |
bash <(wget -qO - https://get.configserver.dev) --install-only --folder csftest |
No download, install existing local folder csftest |
bash <(wget -qO - https://get.configserver.dev) --install-only --dryrun |
No download, simulate install existing local folder csf |
bash <(wget -qO - https://get.configserver.dev) --install-only --folder csftest --dryrun |
No download, simulate install existing local folder csftest |
bash <(wget -qO - https://get.configserver.dev) --clean |
Delete existing csf.zip or csf.tgz , remove folder csf |
bash <(wget -qO - https://get.configserver.dev) --clean --folder csftest |
Delete existing csf.zip or csf.tgz , remove folder csftest |
Standard¶
The command below will download the latest version of CSF and place the archive file on your machine in the folder where you ran the command. The archive file will either be csf.zip
or csf.tgz
, depending on which release is available.
Advanced¶
The get.sh script has additional arguments that you can pass which expands on its functionality.
Download Only¶
To download the latest version of CSF and do nothing else; pass no arguments.
Download + Extract¶
Downloads the latest version of CSF to your local machine as the file csf.zip
or csf.tgz
and extracts to csf
Out of box, this script extracts CSF to the folder csf
; you can change the default extraction folder with:
Download + Extract + Install¶
Downloads the latest version of CSF to your local machine as the file csf.zip
or csf.tgz
, extracts to csf
, and installs by running csf/install.sh
Out of box, this script extracts CSF to the folder csf
, and then installs by running the file csf/install.sh
. You can change the default folder with:
Download + Extract + Install (Dryrun)¶
Downloads the latest version of CSF to your local machine as the file csf.zip
or csf.tgz
, extracts to csf
, and does a dry-run install without actually installing anything
Out of box, this script extracts CSF to the folder csf
, and then installs by running the file csf/install.sh
. You can change the default folder with:
Install Local Folder¶
Does not download or extract CSF. Installs an existing local copy of CSF contained within the folder csf
. This will error if you attempt to pass this argument and the file csf/install.sh
does not exist.
Out of box, this script looks for the install file csf/install.sh
; you can change the folder with the command below. You must have the file csf-folder/install.sh
:
Install Local Folder (Dryrun)¶
Does a dry-run installs on an existing local copy of CSF contained within the folder csf
, but does not actually install CSF. This will error if you attempt to pass this argument and the file csf/install.sh
does not exist.
Out of box, this script looks for the install file csf/install.sh
; you can change the folder with the command below. You must have the path csf-folder/install.sh
:
Clean¶
Removes any existing .zip
and .tgz
files, removes local csf
folders.
Preserve Preserve Filename¶
Out of box, the get.sh script finds the latest version of CSF. When it downloads the archive .zip
or .tgz
to your machine, it automatically re-names the archive file csf.xxx
.
You can skip the re-name to csf.zip/tgz
and preseve the original release's archive name, which is typically csf-firewall-vXX.XX.zip
or csf-firewall-vXX.XX.tgz
.
We have provided examples of what each command does:
Running this command will download the latest CSF release, and name the archive file csf.zip
or csf.tgz
.
Arguments¶
The get.sh script includes numerous arguments that can be passed to expand the functionality. The available arguments are listed below.
Extract¶
15.10 .sh
get.sh -e, --extract
Downloads the latest version of CSF, saves it to your machine as csf.zip
or csf.tgz
, extracts it to a local folder.
Install¶
15.10 .sh
get.sh -i, --install
Downloads the latest version of CSF, saves it to your machine as csf.zip
or csf.tgz
, extracts it to a local folder., and then run the CSF install.sh
installation wizard.
Install Only¶
15.10 .sh
get.sh -I, --install-only
Requires an existing local extracted version of CSF which resides in a folder (defaults to csf
). Default folder can be changed with -f
, --folder
Folder¶
Allows you to override the default extraction and installation folder csf
. Can be used in combination with:
Preserve Original Filename¶
15.10 .sh
get.sh -p, --preserve-name
When downloading the latest version of CSF, the script automatically re-names the latest release archive file from csf-firewall-vXX.XX.zip
to csf.zip
. Passing this parameter skips the re-name, and downloads the file to your system as csf-firewall-vXX.XX.zip
.
Dryrun¶
When --install
or --install-only
are passed, this arguments simulations installation, but does not actually install CSF to your system.
Clean¶
Removes any csf.zip
or csf.tgz
files lintering within the folder. Also removes any extracted csf files and folders.
Help¶
Shows the help menu for the get.sh script. Performs no other actions.
Version¶
15.10 .sh
get.sh -v, --version
Shows the current version of the get.sh script being used.
Source Code¶
The source code for get.configserver.dev can be found within the official CSF repository below:
#!/bin/sh
# #
# @app ConfigServer Firewall & Security (CSF)
# Login Failure Daemon (LFD)
# @service get.configserver.dev
# @script Bash › Script › Installation
# @desc installation script for csf
# @website https://configserver.dev
# @docs https://docs.configserver.dev
# @download https://download.configserver.dev
# @repo https://github.com/Aetherinox/csf-firewall
# @copyright Copyright (C) 2025-2026 Aetherinox
# @license GPLv3
# @updated 09.28.2025
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 3 of the License, or (at
# your option) any later version.
#
# This program is distributed in the hope that it will be useful, but
# WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
# General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, see <https://www.gnu.org/licenses>.
# #
# #
# @usage Download Only sh get.sh
# Download Only (Maintain original filename) sh get.sh --preserve-name
# Download + Extract sh get.sh --extract
# Download + Extract Custom Dir sh get.sh --extract --folder csftemp
# Download + Extract + Install sh get.sh --install
# Download + Extract + Install Custom Dir sh get.sh --install --folder csftemp
# Download + Install (Dryrun) sh get.sh --install --dryrun
# Install Only Existing Archive sh get.sh --install-only
# Install Only Existing Archive (Dryrun) sh get.sh --install-only --dryrun
# Clean existing archive + folder sh get.sh --clean
# Help menu sh get.sh --help
# Version information sh get.sh --version
#
# @notes --install automatically extracts
# --dryrun passed to csf install.sh script when used
# --install-only requires existing .tar/.zip;
# will not download new from github.
# --clean removes .tar/.zip and csf folder
# #
# #
# define › colors
# #
esc=$(printf '\033')
end="${esc}[0m"
bold="${esc}[1m"
dim="${esc}[2m"
underline="${esc}[4m"
blink="${esc}[5m"
white="${esc}[97m"
black="${esc}[0;30m"
redl="${esc}[0;91m"
redd="${esc}[38;5;196m"
magental="${esc}[0;95m"
magentad="${esc}[0;35m"
fuchsial="${esc}[38;5;205m"
fuchsiad="${esc}[38;5;198m"
bluel="${esc}[38;5;75m"
blued="${esc}[38;5;33m"
greenl="${esc}[38;5;76m"
greend="${esc}[38;5;2m"
orangel="${esc}[0;93m"
oranged="${esc}[38;5;202m"
yellowl="${esc}[38;5;190m"
yellowd="${esc}[38;5;184m"
greyl="${esc}[38;5;250m"
greym="${esc}[38;5;244m"
greyd="${esc}[0;90m"
navy="${esc}[38;5;62m"
olive="${esc}[38;5;144m"
peach="${esc}[38;5;210m"
# #
# define › general
# #
app_title="ConfigServer Firewall & Security"
app_about="Bash utility to download the latest version of ConfigServer Firewall from the official github repository."
app_repo_branch="main"
app_ver=1.0.0
app_repo="Aetherinox/csf-firewall"
github_url="https://github.com/$app_repo"
api_url="https://api.github.com/repos/$app_repo/releases/latest"
file_release="csf-firewall-v"
file_installer="install.sh"
folder_extract="csf"
# #
# define › args
# #
argExtract="false"
argInstall="false"
argInstallOnly="false"
argDryrun="false"
argInstaller=""
argDev="false"
argStatus="downloaded"
argOriginalName="false"
argFolder="$folder_extract"
# #
# define › files
# #
app_file_this=$(basename "$0") # get.sh (with ext)
app_file_bin="${app_file_this%.*}" # get (without ext)
# #
# define › folders
# #
app_dir=$(dirname -- "$0")
app_dir=$(cd "$app_dir" && pwd)
app_dir_this_dir=$PWD
# #
# https://man7.org/linux/man-pages/man1/date.1.html
#
# Thu, 01 May 2025 14:33:00 +0200
#
# %a locale's abbreviated weekday name (e.g., Sun)
# %d day of month (e.g., 01)
# %b locale's abbreviated month name (e.g., Jan)
# %Y year
# %H hour (00..23)
# %M minute (00..59)
# %S second (00..60)
# #
date_now=$(date -u '+%a, %d %b %Y %H:%M:%S')
date_stamp=$(date -u '+%m/%d/%Y %H:%M')
# #
# func › usage menu
# #
opt_usage()
{
echo
printf " ${bluel}${app_title}${end}\n" 1>&2
printf " ${greym}${app_about}${end}\n" 1>&2
printf " ${greyd}version:${end} ${greyd}$app_ver${end}\n" 1>&2
printf " ${fuchsiad}$app_file_this${end} ${greyd}[${greym}--help${greyd}]${greyd} | ${greyd}[${greym}--version${greyd}]${greyd} | ${greyd}[${greym}--clean${greyd}]${greyd} | ${greyd}[${greym}--extract${greyd}${end} ${greyd}[${greym}--install${greyd}] ${end}${greyd}[${greym}--dryrun${greyd}]]${greyd} | ${greyd}[${greym}--install-only${greyd} ${greyd}[${greym}--dryrun${greyd}]]${greyd} | ${greyd}[${greym}--install${greyd} ${greyd}[${greym}--dryrun${greyd}]]${end}" 1>&2
echo
echo
printf ' %-5s %-40s\n' "${greyd}Syntax:${end}" "" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}Command${end} " "${fuchsiad}$app_file_this${greyd} [ ${greym}-option ${greyd}[ ${yellowd}arg${greyd} ]${greyd} ]${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}Options${end} " "${fuchsiad}$app_file_this${greyd} [ ${greym}-h${greyd} | ${greym}--help${greyd} ]${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " " ${greym}-A${end} " " ${white}required" 1>&2
printf ' %-5s %-30s %-40s\n' " " " ${greym}-A...${end} " " ${white}required; multiple can be specified" 1>&2
printf ' %-5s %-30s %-40s\n' " " " ${greym}[ -A ]${end} " " ${white}optional" 1>&2
printf ' %-5s %-30s %-40s\n' " " " ${greym}[ -A... ]${end} " " ${white}optional; multiple can be specified" 1>&2
printf ' %-5s %-30s %-40s\n' " " " ${greym}{ -A | -B }${end} " " ${white}one or the other; do not use both" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}Arguments${end} " "${fuchsiad}$app_file_this${end} ${greyd}[ ${greym}-d${yellowd} arg${greyd} | ${greym}--name ${yellowd}arg${greyd} ]${end}${yellowd} arg${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}Examples${end} " "${fuchsiad}$app_file_this${end} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greym}--install${yellowd} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greym}--extract${yellowd} ${greym}--install${yellowd} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greym}--extract${yellowd} ${greym}--install${yellowd} ${greym}--dryrun${yellowd} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greym}--install${yellowd} ${greym}--dryrun${yellowd} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greym}--install-only${yellowd} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greym}--install-only${yellowd} ${greym}--dryrun${yellowd} ${end}" 1>&2
printf ' %-5s %-30s %-40s\n' " " "${greyd}${end} " "${fuchsiad}$app_file_this${end} ${greyd}[ ${greym}--help${greyd} | ${greym}-h${greyd} | ${greym}/?${greyd} ]${end}" 1>&2
echo
printf ' %-5s %-40s\n' "${greyd}Options:${end}" "" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-e${greyd},${blued} --extract ${yellowd}${end} " "download, extract latest version of csf ${navy}<default> ${peach}$argExtract ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-i${greyd},${blued} --install ${yellowd}${end} " "download, extract, and install latest version of csf ${end} ${navy}<default> ${peach}$argInstall ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-I${greyd},${blued} --install-only ${yellowd}${end} " "no download, no extract, installs csf from existing folder ${navy}<default> ${peach}$argInstallOnly ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-p${greyd},${blued} --preserve-name ${yellowd}${end} " "preserves original filename, skips rename to csf.zip ${navy}<default> ${peach}$argOriginalName ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-f${greyd},${blued} --folder ${yellowd}<string>${end} " "override default folder where csf is extracted ${navy}<default> ${peach}$argFolder ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-c${greyd},${blued} --clean ${yellowd}${end} " "cleans up lingering archive and tmp folders and exits ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-D${greyd},${blued} --dryrun ${yellowd}${end} " "pass dryrun to csf installer script, does not install csf ${end} ${navy}<default> ${peach}$argDryrun ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-V${greyd},${blued} --version ${yellowd}${end} " "current version of this utilty ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-d${greyd},${blued} --dev ${yellowd}${end} " "developer mode; verbose logging ${end}" 1>&2
printf ' %-5s %-81s %-40s\n' " " "${blued}-h${greyd},${blued} --help ${yellowd}${end} " "show this help menu ${end}" 1>&2
echo
echo
}
# #
# args › handle
# #
while [ "$#" -gt 0 ]; do
case "$1" in
-d|--dev)
argDev="true"
;;
-e|--extract)
argExtract="true"
argStatus="extracted"
;;
-i|--install)
argExtract="true"
argInstall="true"
argStatus="installed"
;;
-f|--folder|--install-folder)
case "$1" in
*=*) argFolder="${1#*=}" ;;
*) shift; argFolder="$1" ;;
esac
;;
-I|--installOnly|--install-only|--install-local)
argInstallOnly="true"
argStatus="installed local"
;;
-c|--clean)
printf '%-31s %-65s\n' " ${bluel} STATUS ${end}" \
"${greym} cleaning existing files and folders ${end}"
rm -rf "./$argFolder" "./$file_release"*.zip "./$file_release"*-tgz
# #
# Verify cleanup / deletion
# #
if [ ! -d "./$argFolder" ] && [ ! -e "./$file_release"*.zip ] && [ ! -e "./$file_release"*-tgz ]; then
printf '%-31s %-65s\n' " ${greenl} SUCCESS ${end}" \
"${greym} all files and folders removed ${end}"
else
printf '%-31s %-65s\n' " ${redd} ERROR ${end}" \
"${greym} some files or folders could not be removed ${end}"
fi
exit 0
;;
-D|--dryrun)
if [ -n "$argInstaller" ]; then
argInstaller="$argInstaller --dryrun"
else
argInstaller="--dryrun"
fi
;;
-o|-p|--original-name|--preserve-name|--preserve-filename)
argOriginalName="true"
;;
-v|--version|/v)
echo
printf " ${bluel}${app_title} (v$app_ver) ${end}\n" 1>&2
printf " ${end}${app_about} ${end}\n" 1>&2
printf " ${greyd}${github_url} ${end}\n" 1>&2
echo
exit 1
;;
-h|--help|/?)
opt_usage
return
;;
*)
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} Unknown parameter:${redl} $1 ${greym}. Aborting ${end}"
exit 1
;;
esac
shift
done
# #
# output › header
# #
echo
echo " ${greyd}―――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――― ${end}"
printf '%-32s %-65s\n' " ${greym} App${end}" "${fuchsial} $app_title › Downloader ${end}"
printf '%-32s %-65s\n' " ${greym} Repository${end}" "${fuchsial} ${app_repo} ${end}"
printf '%-32s %-65s\n' " ${greym} Api${end}" "${fuchsial} ${api_url} ${end}"
printf '%-32s %-65s\n' " ${greym} Version${end}" "${fuchsial} v${app_ver} ${end}"
echo " ${greyd}―――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――――― ${end}"
echo
# #
# api url › missing
# #
if [ -z "$api_url" ]; then
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} api_url empty, cannot retrieve from api.github.com. Aborting ${end}"
exit 1
fi
# #
# get json information from latest releases
# #
printf '%-31s %-65s\n' " ${bluel} STATUS ${end}" "${greym} fetching latest release info from${bluel} $api_url ${end}"
release_json=$(curl -sL "$api_url")
# #
# extract latest tag
# #
tag_latest=$(echo "$release_json" | grep -m1 '"tag_name"' | awk -F'"' '{print $4}')
if [ -z "$tag_latest" ]; then
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} could not find latest release tag. Aborting ${end}"
exit 1
else
printf '%-31s %-65s\n' " ${greenl} OK ${end}" "${greym} found latest release tag${greenl} $tag_latest ${end}"
fi
# #
# extract download URL for latest release, detect zip or tgz
# #
DOWNLOAD_URL=$(echo "$release_json" \
| grep '"browser_download_url"' \
| awk -F'"' '{print $4}' \
| grep "$file_release$tag_latest" \
| grep -E '\.zip$|\.tgz$|\.tar\.gz$|-tgz$' \
| grep -vE 'helpers|theme' \
| head -n1)
if [ -z "$DOWNLOAD_URL" ]; then
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} could not find download url for latest release tag (zip or tgz). Aborting ${end}"
exit 1
fi
# #
# get latest release filename from URL
# #
file_name_orig=$(basename "$DOWNLOAD_URL")
file_name_out="$file_name_orig"
# #
# normalize filename to csf.zip / csf.tgz unless --original-name provided
# #
if [ "$argOriginalName" = "false" ]; then
case "$file_name_orig" in
*.zip)
file_name_out="csf.zip"
;;
*.tar.gz|*.tgz|*-tgz)
file_name_out="csf.tgz"
;;
*)
file_name_out="$file_name_orig"
;;
esac
else
file_name_out="$file_name_orig"
fi
# #
# download latest release unless --install-only
# #
if [ "$argInstallOnly" = "false" ]; then
printf '%-31s %-65s\n' " ${bluel} STATUS ${end}" "${greym} downloading file${bluel} $file_name_out ${greym}from${bluel} $DOWNLOAD_URL ${end}"
echo
curl -L -o "$file_name_out" "$DOWNLOAD_URL"
echo
fi
# #
# check if new release file downloaded / exists
# #
if [ -f "$file_name_out" ]; then
printf '%-31s %-65s\n' " ${greenl} OK ${end}" "${greym} file${bluel} $file_name_out ${greym}downloaded successfully. ${end}"
else
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} archive file${bluel} $file_name_out ${greym}missing or not downloaded. Please check the URL or your connection. Aborting ${end}"
exit 1
fi
# #
# extract archive if -e, --extract arg specified
# #
if [ "$argExtract" = "true" ] || [ "$argInstall" = "true" ]; then
printf '%-31s %-65s\n' " ${bluel} STATUS ${end}" "${greym} extracting file${bluel} $file_name_out ${end}"
[ ! -d $argFolder ] && mkdir $argFolder
case "$file_name_out" in
*.zip)
unzip -oq "$file_name_out" -d "$argFolder"
;;
*.tar.gz|*.tgz)
tar -xzf "$file_name_out" -C "$argFolder"
;;
*)
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} unknown archive format for file${redl} $file_name_out ${greym}. Aborting ${end}"
exit 1
;;
esac
printf '%-31s %-65s\n' " ${greenl} OK ${end}" "${greym} extracted to ${greenl}./$argFolder/ ${end}"
fi
# #
# install
# #
if [ "$argInstall" = "true" ] || [ "$argInstallOnly" = "true" ]; then
path_installer="./$argFolder/$file_installer"
if [ ! -f "$path_installer" ]; then
printf '%-28s %-65s\n' " ${redl} ERROR ${end}" "${greym} install script not found at${redl} $path_installer ${greym}. Aborting ${end}"
exit 1
fi
printf '%-31s %-65s\n' " ${bluel} STATUS ${end}" "${greym} running install script${bluel} $path_installer ${greym}with elevated permissions ${end}"
# sudo check
if command -v sudo >/dev/null 2>&1; then
sudo sh "$path_installer" $argInstaller
else
sh "$path_installer" $argInstaller
fi
printf '%-31s %-65s\n' " ${greenl} OK ${end}" "${greym} installation script ${greenl} $path_installer ${greym}finished with args${greenl} $argInstaller ${end}"
fi
# #
# output › footer
# #
printf '%-31s %-65s\n' " ${greenl} OK ${end}" "${greym} successfully $argStatus $app_title ${end}"