#!/bin/bash ## +----------------------------------------------------------------------+ ## | InterWorx Hosting Control Panel | ## +----------------------------------------------------------------------+ ## | Copyright (c) 2000-2013 INTERWORX L.L.C., All Rights Reserved. | ## +----------------------------------------------------------------------+ ## | Redistribution and use in source form, with or without modification | ## | is NOT permitted without consent from the copyright holder. | ## | | ## | THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS "AS IS" AND | ## | ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, | ## | THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A | ## | PARTICULAR PURPOSE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, | ## | EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, | ## | PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR | ## | PROFITS; OF BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY | ## | OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | ## | (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE | ## | USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH | ## | DAMAGE. | ## +----------------------------------------------------------------------+ ## | Authors: Paul Oehler | ## | Chris Wells | ## +----------------------------------------------------------------------+ # # Needs to match the content of the interworx.repo file(s) default_source_server=updates.interworx.com install_source_server=$default_source_server force_install=0 force_killconflict=0 debug=0 srpmdir='/usr/src/redhat/SRPMS' rpmdir='/usr/src/redhat/RPMS' opsys=$(uname -o) processor=$(uname -p) arch=$(uname -i) distro='unk' release='Unknown Distribution' target='unk' yumupdate=0 headless=0 iworxrepo="ga" testrepo="" iworxinstall=1 yumargs='' jailsetup=1 resolv=0 verbose=0 dorpmcheck=0 phpvers="" # This is set in phpdefinedefault() # repo is needed for C7 and before phprepo="" # module is needed for Alma9 phpmodule="" mariavers="" # This is set in mariadefinedefault() maria_user_vers="" mariadist="unk" iw_major_version="7" if [ -d /run/systemd/system ] ; then is_systemd=1 else is_systemd=0 fi # Major version of RH-derived OS rhel=0 LOG='iworx-install.log' LOG_REDIR='/dev/null' rhe7x_conflicts='bind redhat-config-bind caching-nameserver sendmail postfix exim mutt fetchmail spamassassin redhat-lsb evolution mod_python mod_auth_mysql mod_authz_ldap mod_auth_pgsql mod_auth_kerb mod_perl mdadm dovecot vsftpd httpd-tools' rhe8x_conflicts='bind redhat-config-bind caching-nameserver sendmail postfix exim mutt fetchmail spamassassin redhat-lsb evolution mod_python mod_auth_mysql mod_authz_ldap mod_auth_pgsql mod_auth_kerb mod_perl mdadm dovecot vsftpd httpd-tools httpd-filesystem' cos6x_conflicts='bind redhat-config-bind caching-nameserver sendmail postfix exim mutt fetchmail spamassassin redhat-lsb evolution mod_python mod_auth_mysql mod_authz_ldap mod_auth_pgsql mod_auth_kerb mod_perl mdadm dovecot vsftpd httpd-tools' ## # the main goiworx func ## function control_c { trap - SIGINT killall -2 -g yum python tee > /dev/null 2>&1 exit 1 } trap control_c SIGINT function goiworx { [ "$verbose" == "1" ] && LOG_REDIR='' [ "$debug" == "1" ] && LOG_REDIR='' distrocheck ifacecheck mariadefinedefault mariaverscheck phpdefinedefault phpverscheck banner if (( $rhel >= 7 )); then _rpms="iptables iptables-services" checkrpm $_rpms || runyum -y install $_rpms fi status_print "Installing wget (if needed)" _rpms="wget" checkrpm $_rpms || runyum -y install $_rpms status_print "Installing psmisc (if needed)" _rpms="psmisc" checkrpm $_rpms || runyum -y install $_rpms status_print "Installing yum-utils (if needed)" _rpms="yum-utils" checkrpm $_rpms || runyum -y install $_rpms gpgkeys basecheck [ -f "$LOG" ] && rm -f $LOG if [ $jailsetup -gt 0 ]; then setupjail fi yumconfig killconflicts distrofix mysqlinstall httpdinstall phpinstall iptablesinstall if [ $yumupdate -gt 0 ]; then updatesystem fi if [ $iworxinstall -gt 0 ]; then iworxinstall upstartconfig relocatedirs status_print "Installing any available hotfixes" ~iworx/bin/hotfix.pex --install fi installextras openvznotice2 killservices updatetime footer return 0 } function openvznotice1 { if [[ -e /proc/user_beancounters ]] || [[ -e /proc/vz/veinfo ]]; then echo header_print "ALERT: It appears this server is in a OpenVZ or Virtuzzo Environment." header_print "SECOND LEVEL QUOTAS MUST BE ENABLED for InterWorx to function properly!" header_print "If Second Level Quotas are not enabled, please hit Ctrl+C now, and enable" header_print "them, or ask your VPS provider to enable them for you, then re-run the" header_print "InterWorx install script." header_print "see: http://download.swsoft.com/virtuozzo/virtuozzo4.0/docs/en/lin/VzLinuxUG/293.htm" sleep 7 fi } function openvznotice2 { if [[ -e /proc/user_beancounters ]] || [[ -e /proc/vz/veinfo ]]; then if ! [[ -e /aquota.group ]]; then echo header_print "ALERT: It appears this server is in a OpenVZ or Virtuzzo Environment." header_print "It does NOT appear that second level quotas are enabled on this virtual machine" header_print "SECOND LEVEL QUOTAS MUST BE ENABLED for InterWorx to function properly!" header_print "Please hit Ctrl+C now, and enable them, or as your VPS provider to do so far you," header_print "then re-run the InterWorx install script." header_print "see: http://download.swsoft.com/virtuozzo/virtuozzo4.0/docs/en/lin/VzLinuxUG/293.htm" sleep 10 fi fi } ## # add our mysql lib dir to the ldconfig path ## function ldconfigfix { if [ `egrep -c interworx /etc/ld.so.conf` -eq 0 ]; then echo '/home/interworx/lib/mysql' >> /etc/ld.so.conf ldconfig fi } ## # install any extra packages iworx needs ## function installextras { debug_print "Installing misc extra tools" status_print "Installing misc extra tools (errors are ok here)" _rpms="mdadm emacs-nox quota netpbm netpbm-progs strace which ftp zip mailx vim-enhanced sysstat" checkrpm $_rpms || runyum $yumargs install $_rpms } ## # setup the jailing if possible. ## function setupjail { status_println "Setting up JAILED home/chroot dirs" if [ -L /home ]; then status_println "Looks like jailing is already setup" return 0 fi if [ ! -d /home ]; then error_print "/home doesn't exist, can't setup JAIL" return 1 fi # make sure /home isn't a mountable partition if [ `mount | egrep -c " \/home "` -eq 0 ]; then if [ ! -d /chroot ]; then status_println "Creating /chroot" mkdir /chroot fi if [[ -d /etc/systemd/system/multi-user.target.wants ]]; then for service in /etc/systemd/system/multi-user.target.wants/*.service; do grep -q ProtectHome $service && service $(basename $service) stop &>/dev/null if [[ $(basename $service) == "NetworkManager.service" ]]; then killall -9 dhclient 2> /dev/null fi done fi status_println "Moving /home to /chroot/home" mv /home /chroot status_println "Symlinking /home -> /chroot/home" ln -fs /chroot/home /home status_println "Fixing JAIL permissions" chown root:root /chroot chmod 711 /chroot chown root:root /chroot/home chmod 711 /chroot/home if [[ -d /etc/systemd/system/multi-user.target.wants ]]; then for service in /etc/systemd/system/multi-user.target.wants/*.service; do grep -q ProtectHome $service && service $(basename $service) start &>/dev/null done fi fi } ## # we need to configure svscanboot to start on boot # normally daemontools RPM would do this # but the "start" command fails inside the rpm scriptlet # for some reason ## function upstartconfig { if (( $rhel >= 8 )); then if [ -d /etc/init ]; then debug_print_read "About to configure svscanboot with upstart (/etc/init)" echo 'start on runlevel [12345] stop on runlevel [06] respawn exec /command/svscanboot ' > /etc/init/svscanboot.conf /sbin/start --quiet svscanboot > /dev/null 2>&1 fi if [ "${is_systemd}" == "1" ]; then debug_print_read "About to configure svscanboot with systemd" systemctl enable svscanboot service svscanboot restart fi fi } ## # we need to move vpopmail and interworx # from their /home locations for clustering ## function relocatedirs { debug_print_read "About to relocate InterWorx-CP and Vpopmail" if [ -d /home/interworx ] && [ ! -L /home/interworx ]; then status_println "moving InterWorx-CP to /usr/local/interworx" service iworx stop > /dev/null 2>&1 if [ -d /usr/local/interworx ]; then mv -f /home/interworx/* /usr/local/interworx/ mv -f /home/interworx/.[^.]* /usr/local/interworx/ rmdir /home/interworx/ else mv -f /home/interworx /usr/local fi ln -fs /usr/local/interworx /home/interworx service iworx start > /dev/null 2>&1 fi chown -h iworx:iworx /usr/local/interworx/html/siteworx/templates chown -h iworx:iworx /usr/local/interworx/html/nodeworx/templates if [ -d /home/vpopmail ] && [ ! -L /home/vpopmail ]; then status_println "moving Vpopmail to /var/vpopmail" mv -f /home/vpopmail /var ln -fs /var/vpopmail /home/vpopmail fi } ## # see wtf distro we're running on ## function distrocheck { status_println "Determining Linux distribution" ## # Figure out what platform we're on so we can build # RPMs accordingly. ## if [ -f /etc/redhat-release ]; then release=$(cat /etc/redhat-release) elif [ -f /etc/openna-release ]; then release=$(cat /etc/openna-release) elif [ -f /etc/system-release ]; then release=$(cat /etc/system-release) fi # # lowest common substring local cos7x="CentOS Linux release 7" local cloud7x="CloudLinux Server release 7" local rhe7x="Red Hat Enterprise Linux Server release 7" local cos8x="CentOS Stream release 8" local alma8x="AlmaLinux release 8" local rocky8x="Rocky Linux release 8" local rhe8x="Red Hat Enterprise Linux release 8" local rhe8xs="Red Hat Enterprise Linux Server release 8" if [ `echo "$release" | egrep -c "$cos7x"` -gt 0 ]; then distro='cos7x' mariadist='centos7' rhel=7 elif [ `echo "$release" | egrep -c "$cloud7x"` -gt 0 ]; then distro='cloud7x' rhel=7 elif [ `echo "$release" | egrep -c "$rhe7x"` -gt 0 ]; then distro='rhe7x' mariadist='rhel7' rhel=7 elif [ `echo "$release" | egrep -c "$alma8x"` -gt 0 ]; then distro='rhe8x' mariadist='rhel8' rhel=8 elif [ `echo "$release" | egrep -c "$cos8x"` -gt 0 ]; then distro='rhe8x' mariadist='rhel8' rhel=8 elif [ `echo "$release" | egrep -c "$rocky8x"` -gt 0 ]; then distro='rhe8x' mariadist='rhel8' rhel=8 elif [ `echo "$release" | egrep -c "$rhe8x"` -gt 0 ]; then distro='rhe8x' mariadist='rhel8' rhel=8 elif [ `echo "$release" | egrep -c "$rhe8xs"` -gt 0 ]; then distro='rhe8x' mariadist='rhel8' rhel=8 fi if (( $rhel > 0 )); then target="rhe${rhel}x" fi ## # see if we can even install on this plat if [ "$target" = "unk" ]; then if [ $force_install -eq 0 ]; then error_print_die "$release not supported" fi fi } function ifacecheck { status_println "Checking network interface names" for f in `ls /sys/class/net` do if [ "${#f}" -gt 10 ]; then header_print "On some systems, network interface naming" header_print "conventions can vary, leading to potential issues" header_print "when InterWorx attempts to append identifiers to" header_print "longer names." header_print "" header_print "It has been detected your system may be" header_print "susceptible to this issue." header_print "" header_print "More info: https://www.interworx.com/support/faq/change-network-interface-centos-7/" header_print "" user_prompt_yn "Continue anyway? (Y/n): " OK=$? if [ $OK -eq 0 ]; then header_print "Aborting InterWorx-CP install...." exit; fi return fi done } function footer { echo -e "" echo -e "\033[0;40m\033[1;37m\033[1m-=-=-=-=-= Installation Complete! Next Step: License Activation! =-=-=-=-=-\033[0m" echo -e "" echo -e "\033[40m\033[001;033mTo activate your license, go to" echo -e "\033[40m\033[001;033mhttps://your-ip:2443/nodeworx/" echo -e "\033[40m\033[001;033mAlso, check out https://www.interworx.com for news, updates, and support!" echo -e "" echo -e "\033[0;40m\033[1;37m\033[1m-=-=-=-=-= THANK YOU FOR USING \033[0;40m\033[1m\033[4m\033[1;36mINTERWORX!\033[0;40m\033[1;37m\033[1m\033[0;40m\033[1;37m\033[1m =-=-=-=-=-\033[0m" echo -e "" } ## # show the usage ## function usage { cat < /dev/null 2>&1 if [ $? -gt 0 ]; then error_print_die "$0 requires 'rpm' to be installed" fi qmailidfix qmailcheck selinuxcheck firewallcheck } ## # fix qmail u/gids ## function qmailidfix { rpm --quiet -q qmail qmail_missing=$? baduids='101 102 103 104 105 106 107 108' badgids='102 103 104' newid="200" for id in $baduids; do if [ `egrep -c "x:$id:[0-9]+" /etc/passwd` -gt 0 -a $qmail_missing -gt 0 ]; then while [ `egrep -c "x:$newid:[0-9]+" /etc/passwd` -gt 0 ]; do newid=`expr $newid + 1` done /usr/sbin/usermod -u $newid `egrep "x:$id:[0-9]+" /etc/passwd | sed 's|:| |g' | awk '{print $1}'` fi done newid="200" for id in $badgids; do if [ `egrep -c "x:$id" /etc/group` -gt 0 -a $qmail_missing -gt 0 ]; then while [ `egrep -c "x:$newid" /etc/group` -gt 0 ]; do newid=`expr $newid + 1` done /usr/sbin/groupmod -g $newid `egrep "x:$id" /etc/group | sed 's|:| |g' | awk '{print $1}'` if [ `egrep -c "x:[0-9]+:$id:" /etc/passwd` -gt 0 ]; then /usr/sbin/usermod -g $newid `egrep "x:[0-9]+:$id:" /etc/passwd | sed 's|:| |g' | awk '{print $1}'` fi fi done } ## # disable iptables (APF will replace) ## function firewallcheck { chkconfig --level 012345 iptables off >/dev/null 2>&1 service iptables stop > /dev/null 2>&1 chkconfig --level 012345 firewalld off >/dev/null 2>&1 service firewalld stop > /dev/null 2>&1 # we are suppressing new network device naming conventions until further notice rules_symlink="/etc/udev/rules.d/80-net-name-slot.rules" [[ ! -L "$rules_symlink" ]] && ln -s /dev/null "$rules_symlink" } ## # check for and possibly disable selinux ## function selinuxcheck { selinux_config="" if [[ -f /etc/sysconfig/selinux ]]; then if [[ `egrep -c "SELINUX[:space:]*=[:space:]*disabled" /etc/sysconfig/selinux 2>/dev/null` -eq 0 ]]; then selinux_config="/etc/sysconfig/selinux" fi elif [[ -f /etc/selinux/config ]]; then if [ `egrep -c "SELINUX[:space:]*=[:space:]*disabled" /etc/selinux/config 2>/dev/null` -eq 0 ]; then selinux_config="/etc/selinux/config" fi fi if [[ "$selinux_config" != "" ]]; then echo -e "" header_print "SELINUX conflicts with some of InterWorx-CP's" header_print "functions and for this reason it must be disabled." header_print "If SELINUX must be enabled in your environment, press" header_print "ctrl-c now to exit the installation." sleep 5 status_println "Disabing SELINUX for next boot" debug_print_read "About to edit selinux config" sed --in-place 's/SELINUX=.*/SELINUX=disabled/' /etc/sysconfig/selinux sed --in-place 's/SELINUX=.*/SELINUX=disabled/' /etc/selinux/config fi status_println "Turning off SELINUX for current session" setenforce 0 2>/dev/null chkconfig --level 012345 setroubleshoot off 2>/dev/null } ## # see if qmail is installed with the correct UID/GID OR # make sure that the UID/GIDs are available that we need. ## function qmailcheck { ## # qmail uid/gid check ## rpm --quiet -q qmail qmail_missing=$? if [ `egrep -c "x:10[2-7]:[0-9]+" /etc/passwd` -gt 0 -a $qmail_missing -gt 0 ]; then error_print_die "$0 requires UIDs 102 -> 107 to be unused" fi if [ `egrep -c "x:10[2-3]:" /etc/group` -gt 0 -a $qmail_missing -gt 0 ]; then error_print_die "$0 requires GIDs 102 -> 103 to be unused" fi } function check_system_requirements() { URL="http://appendix.interworx.com/current/getting_started/setup_information/requirements-interworx-control-panel.html" REQUIRED_DISK_SPACE=$((20971440)) REQUIRED_RAM=$((1048572)) REQUIRED_SWAP=$((3145724)) AVAILABLE_DISK_SPACE=$(df / | tail -1 | awk '{print $4}') AVAILABLE_RAM=$(grep MemFree /proc/meminfo | awk '{print $2}') AVAILABLE_SWAP=$(grep SwapFree /proc/meminfo | awk '{print $2}') requirements_met=true if [ "$AVAILABLE_DISK_SPACE" -lt "$REQUIRED_DISK_SPACE" ]; then echo -e "\033[40m\033[001;031mDISK SPACE : \033[40m\033[001;031m$AVAILABLE_DISK_SPACE / $REQUIRED_DISK_SPACE # 2.5GB installation, 20GB recommended\033[0m\033[0m" requirements_met=false else echo -e "\033[40m\033[001;032mDISK SPACE : \033[40m\033[001;032m$AVAILABLE_DISK_SPACE / $REQUIRED_DISK_SPACE\033[0m\033[0m" fi if [ "$AVAILABLE_RAM" -lt "$REQUIRED_RAM" ]; then echo -e "\033[40m\033[001;031mRAM : \033[40m\033[001;031m$AVAILABLE_RAM / $REQUIRED_RAM # 1GB recommended\033[0m\033[0m" requirements_met=false else echo -e "\033[40m\033[001;032mRAM : \033[40m\033[001;032m$AVAILABLE_RAM / $REQUIRED_RAM\033[0m\033[0m" fi if [ "$AVAILABLE_SWAP" -lt "$REQUIRED_SWAP" ]; then echo -e "\033[40m\033[001;031mSWAP : \033[40m\033[001;031m$AVAILABLE_SWAP / $REQUIRED_SWAP # 3GB recommended\033[0m\033[0m" requirements_met=false else echo -e "\033[40m\033[001;032mSWAP : \033[40m\033[001;032m$AVAILABLE_SWAP / $REQUIRED_SWAP\033[0m\033[0m" fi if [ "$requirements_met" = true ]; then echo -e "\033[40m\033[001;032mServer meets minimum system recommendations.\033[0m" else echo echo -e "\033[40m\033[001;031mServer does not meet minimum system requirements.\033[0m" echo "For more information on system requirements: $URL" echo fi } ## # Validates if the current hostname is a valid domain. # # Returns: # 0 - If the hostname is a valid domain. # 1 - If the hostname is not valid. ## validate_hostname() { # Retrieve the current hostname hostname=$(hostname) # Regular expression for valid hostname local regex='^([a-zA-Z0-9]([a-zA-Z0-9\-]{0,61}[a-zA-Z0-9])?\.)+[a-zA-Z0-9]([a-zA-Z0-9\-]{0,61}[a-zA-Z0-9])?$' # Check if the hostname matches the regular expression if [[ ${hostname} =~ ${regex} ]]; then echo "The hostname '${hostname}' is valid." return 0 else echo "The hostname '${hostname}' is not valid." return 1 fi } ## # Prompt for hostname change if invalid. Or exit if in headless mode with error. ## function check_and_change_hostname() { local validation_status=1 while [[ $validation_status -ne 0 ]]; do validate_hostname validation_status=$? if [[ $validation_status -ne 0 ]]; then if [[ $headless -eq 1 ]]; then echo "Valid domain structure: domain.com sub.domain.com sub.sub.domain.com" echo "Valid Characters: a-z, 0-1, - is the only allowed special character" echo "Error: Invalid hostname. Exiting script." exit 1 else echo "Valid domain structure: domain.com sub.domain.com sub.sub.domain.com" echo "Valid Characters: a-z, 0-1, - is the only allowed special character" read -p "Enter a valid hostname: " new_hostname hostnamectl set-hostname "$new_hostname" fi fi done } ## # show the pretty banner ## function banner { ## # barf out what we're doing ## echo echo -e "\033[0;40m\033[1;37m\033[1m-=-=-=-=-= Installing \033[0;40m\033[1m\033[4m\033[1;36mInterWorx-CP\033[0;40m\033[1;37m\033[1m =-=-=-=-=-\033[0m" echo header_print "This script will install InterWorx-CP on your system." header_print "Please make sure that you have backed up any critical" header_print "data!" echo header_print "This script may be run multiple times without any" header_print "problems. This is helpful if you find an error" header_print "during installation, you can safely ctrl-c out of" header_print "this script, fix the error and re-start the script." echo status_println "Checking Hostname" check_and_change_hostname echo header_print "Details of this installation will be logged in iworx-install.log" echo echo -e "\033[40m\033[001;031mHOSTNAME : \033[40m\033[001;033m$hostname\033[0m\033[0m" echo -e "\033[40m\033[001;031mTARGET : \033[40m\033[001;033m$release\033[0m\033[0m" echo -e "\033[40m\033[001;031mPLATFORM : \033[40m\033[001;033m$opsys\033[0m\033[0m" echo -e "\033[40m\033[001;031mPROCESSOR : \033[40m\033[001;033m$processor\033[0m\033[0m" echo -e "\033[40m\033[001;031mRPM TARGET : \033[40m\033[001;033m$target\033[0m\033[0m" echo -e "\033[40m\033[001;031mRPM DISTRO : \033[40m\033[001;033m$distro\033[0m\033[0m" echo -e "\033[40m\033[001;031mRPM DIR : \033[40m\033[001;033m$rpmdir\033[0m\033[0m" echo -e "\033[40m\033[001;031mSRPM DIR : \033[40m\033[001;033m$srpmdir\033[0m\033[0m" echo -e "\033[40m\033[001;031mSRPM HOST : \033[40m\033[001;033m$install_source_server\033[0m\033[0m" echo -e "\033[40m\033[001;031mIWORX REPO : \033[40m\033[001;033m$iworxrepo\033[0m\033[0m" echo -e "\033[40m\033[001;031mDEFAULT PHP: \033[40m\033[001;033mPHP $phpvers\033[0m\033[0m" echo -e "\033[40m\033[001;031mMYSQL : \033[40m\033[001;033mMARIADB $mariavers\033[0m\033[0m" echo header_print "System Resource Recommendations" echo check_system_requirements openvznotice1 header_print "Press to begin the install, ctrl+c to quit..." [ $headless -eq 0 ] && read } ## # some distros needs some 'extra help' package wise # so installed needed packages ## function distrofix { ## # some platforms needs some special care ## status_print "Installing the LVS Load Balancer" _ipvsadm="ipvsadm" checkrpm $_ipvsadm || runyum $yumargs install $_ipvsadm _resource_agents="resource-agents" checkrpm $__resource_agents || runyum $yumargs install $_resource_agents _ldirectord="ldirectord" checkrpm $_ldirectord || runyum $yumargs install $_ldirectord chkconfig --level 345 ipvsadm off > /dev/null 2>&1 } ## # configure YUM ## function yumconfig { status_println "Checking for YUM" rpm --quiet -q yum if [ $? -gt 0 ]; then status_println "Installing yum" rpm -ivh \ https://$install_source_server/iworx/RPMS/noarch/yum-2.0.7-1.noarch.rpm fi status_print "Updating yum (if needed)" runyum -y update yum status_print "Installing yum-utils" runyum -y install yum-utils status_println "Installing InterWorx YUM repository" if [[ "$iworxrepo" == "alpha" ]]; then orig_repo="alpha" iworxrepo="beta" fi local_repo=/etc/yum.repos.d/interworx-${iw_major_version}.repo remote_repo=https://$install_source_server/interworx/${iw_major_version}/interworx.repo wget -O $local_repo $remote_repo > /dev/null 2>&1 sed -i "s/$default_source_server/$install_source_server/g" $local_repo yum-config-manager --enable interworx-${iw_major_version}-${iworxrepo} > /dev/null 2>&1 if [[ "$orig_repo" == "alpha" ]]; then runyum -y install interworx-alpha-repo fi if [[ "$testrepo" != "" ]]; then wget -O /etc/yum.repos.d/iworx-build-test.repo $testrepo fi yumargs="-y" # if [ $debug -gt 0 ]; then # yumargs='' # fi # the extras and testing repositories are nothing but # trouble. if [ -d /etc/yum.repos.d ]; then rm -f /etc/yum.repos.d/*extras* rm -f /etc/yum.repos.d/*testing* rm -f /etc/yum.repos.d/*devel* fi # install remi & update, the one we distribute is older runyum -y install remi-release runyum -y update remi-release setupphprepo setupmariarepo } function mariadefinedefault { # Accept whatever the user passed in if [ "$maria_user_vers" != "" ]; then mariavers=$maria_user_vers return fi # Finally, set the actual default version mariavers="10.6" } function mariaverscheck { case "$mariavers" in "5.5" | "10.2") if (( $rhel >= 8 )); then error_print_die "MariaDB $mariavers is not supported on $target-based systems" fi ;; "10.3" | "10.4" | "10.5" | "10.6" | "10.7" | "10.8") ;; "system") return 0 ;; *) # Failboat error_print_die "Unknown or unsupported MariaDB version $mariavers" esac } function mariapwnative { installeddbvers=$(mysql -V | cut -d ' ' -f 6 | cut -d '.' -f 1,2) case "$installeddbvers" in "5.5" | "10.2" | "10.3") ;; "10.4" | "10.5" | "10.6" | "10.7" | "10.8") # Requires a pw reset to blank for goiworx to work. mysql -u root -e "ALTER USER root@localhost IDENTIFIED VIA mysql_native_password USING PASSWORD('');" status_println "Mariadb Authentication Plugin updated for $installeddbvers." ;; *) # Fail error_print_die "Unknown or unsupported MariaDB version $installeddbvers" esac } function setupmariarepo { [[ "$mariavers" == "system" ]] && return mariaverscheck if [ "$mariadist" = "unk" ] ; then error_print "Unable to resolve MariaDB yum repo for ${distro}" error_print "Using available system version instead" return fi mariaarch=x86 if [ "$arch" = "x86_64" ] ; then mariaarch="amd64" fi echo "# MariaDB ${mariavers} repository [mariadb-${mariavers}] name=MariaDB ${mariavers} baseurl=http://yum.mariadb.org/${mariavers}/${mariadist}-${mariaarch} module_hotfixes=1 gpgkey=https://yum.mariadb.org/RPM-GPG-KEY-MariaDB gpgcheck=1 " > /etc/yum.repos.d/MariaDB.repo if [[ "$mariavers" == "10.2" ]] ; then ARCH_URL="https://archive.mariadb.org/mariadb-10.2/yum/${mariadist}-${mariaarch}/" REPO_ID="mariadb-10.2" /usr/bin/yum-config-manager \ --setopt=${REPO_ID}.baseurl=$ARCH_URL \ --setopt=${REPO_ID}.skip_if_unavailable=1 \ --setopt=${REPO_ID}.enabled=1 \ --save | grep -e "^baseurl = ${ARCH_URL}" 2>&1 > /dev/null retval=$? if [ "$retval" != "0" ]; then error_print_die "Unable to switch Mariadb to $ARCH_URL" else echo "Warning: Archive yum repository setup for EOL Mariadb version 10.2, please upgrade asap!" fi fi } function phpdefinedefault { # Accept whatever the user passed in if [ "$php_user_vers" != "" ] ; then phpvers=$php_user_vers return fi # Otherwise, the default could be different based on OS if [ "$target" == "rhe6x" ] ; then phpvers="7.3" return fi # Finally, set the actual default version phpvers="8.1" } function phpverscheck { case "$phpvers" in "7.1") phprepo=remi-php71 phpmodule=php:remi-7.1 ;; "7.2") phprepo=remi-php72 phpmodule=php:remi-7.2 ;; "7.3") phprepo=remi-php73 phpmodule=php:remi-7.3 ;; "7.4") phprepo=remi-php74 phpmodule=php:remi-7.4 ;; "8.0") phprepo=remi-php80 phpmodule=php:remi-8.0 ;; "8.1") phprepo=remi-php81 phpmodule=php:remi-8.1 ;; "8.2") phprepo=remi-php82 phpmodule=php:remi-8.2 ;; "system") return 0 ;; *) error_print_die "Unknown or unsupported php version $php" esac } function setupphprepo { [[ "$phpverscheck" == "system" ]] && return phpverscheck # Enabling the module also installs, so that happens in the phpinstall function if (( $rhel <= 7 )); then enablerepo $phprepo fi } function enablemodule { $module = $@ } function enablerepo { repo=$@ # Yum config manager returns true even if the requested repo is bogus yum-config-manager --enable "$repo" | grep baseurl 2>&1 > /dev/null retval=$? if [ "$retval" != "0" ]; then echo "Unknown yum repo $repo" fi return $retval } ## # kill any conflicting RPMs from the base system ## function killconflicts { if [ -f .killconflicts ]; then return 0 fi # # see if we have any conflicts at all eval pack_var=\$${target}_conflicts header_print "InterWorx-CP needs to remove some packages that may conflict" header_print "The following packages will be removed (if they exist)" for pack in $pack_var; do status_println "- $pack" done OK=1 if [ $force_killconflict -eq 0 ]; then user_prompt_yn "Is this ok? (Y/n): " OK=$? fi if [ $OK -eq 0 ]; then header_print "Aborting InterWorx-CP install...." exit; fi if [ `cat /etc/resolv.conf | egrep -c "nameserver 127.0.0.1"` -gt 0 ]; then cp /etc/resolv.conf /etc/resolv.conf.backup chmod 644 /etc/resolv.conf.backup sed -i 's|nameserver 127.0.0.1|nameserver 8.8.8.8|' /etc/resolv.conf resolv=1 fi status_print "Removing conflicting packages" runyum $yumargs \ remove \ $pack_var if [ $? -gt 0 ]; then error_print_die "YUM removed failed. You may need to manually remove some packages (YUM should give output to aid you)" fi rpm -e --noscripts bind-chroot > /dev/null 2>&1 if [ -f /etc/yum.repos.d/remi-modular.repo ] ; then if (( $rhel >= 8 )) ; then status_print "Disabling upstream mailman module" dnf -y module disable mailman fi fi touch .killconflicts status_println "Conflict resolution complete" } ## # Download and import a rpm gpg file. ## function rpm_import { wget $@ -O - > .gpgtmp 2>/dev/null rpm --import .gpgtmp 2>/dev/null rm -f .gpgtmp 2>/dev/null } ## # grab the relavent gpg keys ## function gpgkeys { status_println "Importing RPM GPG keys" gpghost="updates.interworx.com" ## always import these rpm_import https://$gpghost/iworx/RPM-GPG-KEY-NEXCESS 2> /dev/null rpm_import https://$gpghost/redhat/9/en/os/i386/RPM-GPG-KEY 2> /dev/null } ## # bring the system up to date ## function updatesystem { ## # at this point we have our yum.conf and yum headers # installed for this OS, so we can *try* to do a # yum update on the rest of the stuff and if it's # there (and we have headers generated for it) then # it should all 'just work' ## debug_print_read "About to do a 'yum update' to sync the system" status_print "Performing a YUM update to bring the system up to date" runyum $yumargs update debug_print_read "^^^^ check above for YUM errors" } ## # install httpd ## function httpdinstall { debug_print_read "About to install Apache" # make sure we backup their httpd.conf if there # is one and move it out of the way so that our # httpd.conf can be used instead # only do this if our httpd isn't already installed if [ `rpm -q httpd | egrep -c "iworx"` -eq 0 ]; then if [ -f /etc/httpd/conf/httpd.conf ]; then mv -f /etc/httpd/conf/httpd.conf \ /etc/httpd/conf/httpd.conf.iworxsave fi fi # install httpd # rht90 has subversion issues since it includes apr status_print "Installing the Apache webserver" _rpms="httpd httpd-devel mod_ssl apr-devel apr-util-devel" checkrpm $_rpms || runyum $yumargs \ --exclude httpd-iworx \ --exclude subversion \ --exclude httpd-devel-2.2.3 \ install \ $_rpms if [ $? -ne 0 ]; then error_print "Apache could not be installed." error_print "YUM may have given some reasonable errors and" error_print "you can try re-running the installer as it may" error_print_die "just be a network and/or update server problem" fi ## # startup apache ## service httpd stop >/dev/null 2>&1 service httpd start >/dev/null 2>&1 chkconfig --level 345 httpd on >/dev/null 2>&1 # re-check qmail uid/gid (httpd does a useradd) qmailcheck } ## # install PHP ## function phpinstall { debug_print_read "About to install PHP" # install php status_print "Installing PHP" if (( $rhel > 7 )); then if [ -f /etc/yum.repos.d/remi-modular.repo ]; then dnf -y module install $phpmodule fi fi _rpms="php php-mysql php-gd php-xml php-cli php-pdo php-mbstring php-xmlrpc php-mhash php-pear php-fpm" checkrpm $_rpms || runyum $yumargs install $_rpms if [ $? -ne 0 ]; then error_print "PHP could not be installed." error_print "YUM may have given some reasonable errors and" error_print "you can try re-running the installer as it may" error_print_die "just be a network and/or update server problem" fi } ## # install iptables ## function iptablesinstall { debug_print_read "About to install iptables" # install php status_print "Installing iptables" _rpms="iptables iptables-services" checkrpm $_rpms || runyum $yumargs install $_rpms if [ $? -ne 0 ]; then error_print "iptables could not be installed." error_print "YUM may have given some reasonable errors and" error_print "you can try re-running the installer as it may" error_print_die "just be a network and/or update server problem" fi } ## # install MySQL ## function mysqlinstall { debug_print_read "About to install MySQL" ## # install mysql. the naming scheme has been verified on all major distros. ## status_print "Installing MySQL server" ## # If requested MariaDB version is archived we need to import the key # first to avoid warning and install key prompt. ## rpm --import https://yum.mariadb.org/RPM-GPG-KEY-MariaDB if (( $rhel >= 8 )) && [ "$mariavers" != "system" ]; then status_print "Disabling upstream mysql module" dnf -y module disable mysql mariadb fi if (( $rhel >= 7 )); then yum install -y mariadb mariadb-server MariaDB-devel if [ $? -ne 0 ]; then error_print "MariaDB could not be installed." error_print "YUM may have given some reasonable errors and" error_print "you can try re-running the installer as it may" error_print_die "just be a network and/or update server problem" fi else _rpms="mysql mysql-server mysql-devel" checkrpm $_rpms || runyum $yumargs install $_rpms if [ $? -ne 0 ]; then error_print "MySQL could not be installed." error_print "YUM may have given some reasonable errors and" error_print "you can try re-running the installer as it may" error_print_die "just be a network and/or update server problem" fi fi ## # initialize the system mysql dbs & # make sure mysql is running for iworx ## if [[ -e /etc/init.d/mysql ]]; then sed -i '/Initializing MySQL database:/s/--initialize/&-insecure/' /etc/init.d/mysql fi if (( $rhel >= 7 )); then service mariadb stop >/dev/null 2>&1 service mariadb start >/dev/null 2>&1 chkconfig --level 345 mariadb on >/dev/null 2>&1 ln -s /usr/lib/systemd/system/mariadb.service /usr/lib/systemd/system/mysqld.service else servicename=mysqld if [ -e /etc/init.d/mysql ]; then servicename=mysql fi service $servicename stop >/dev/null 2>&1 service $servicename start >/dev/null 2>&1 chkconfig --level 345 $servicename on >/dev/null 2>&1 fi # Starting with MariaDB 10.4, a default password is set. This ensures InterWorx can get in passwordlessly.. mariapwnative # re-check qmail uid/gid (mysql does a useradd) qmailcheck } ## # update the local clock and sync it to the # BIOS clock (good for initial iworx lic activation) ## function updatetime { # don't do on virtuozzo if [ ! -f /proc/user_beancounters ]; then servicename="ntpd" rpmname="ntp" ntpserver="ntp.interworx.com" if (($rhel > 7)); then servicename="chronyd"; rpmname="chrony"; fi debug_print_read "About to update the system time" rpm --quiet -q $rpmname if [ $? -gt 0 ]; then status_print "Installing $rpmname" _rpms="$rpmname" checkrpm $_rpms || runyum $yumargs install $_rpms fi status_println "Setting server time / syncing BIOS" service $servicename stop > /dev/null 2>&1 if (($rhel > 7)); then chronyd -q "server $ntpserver iburst" > /dev/null 2>&1 else ntpdate $ntpserver > /dev/null 2>&1 fi hwclock --systohc > /dev/null 2>&1 service $servicename start > /dev/null 2>&1 chkconfig --level 345 $servicename on >/dev/null 2>&1 fi } ## # helper functions ## ## # print an error and die ## function error_print_die { echo echo -e "\033[40m\033[001;031mERROR: $@\033[0m" echo [ -f $LOG ] && tail -n15 $LOG exit 1 } ## # print an error ## function error_print { echo -e "\033[40m\033[001;031mERROR: $@\033[0m" } ## # print a warning message ## function warning_print { echo echo -e "\033[40m\033[001;033mWARNING: $@\033[0m" echo sleep 2 } ## # print a status message ## function status_println { echo -e "\033[40m\033[1m\033[1;35mSTATUS: $@\033[0m" } ## # print a status message without newline ## function status_print { echo -e -n "\033[40m\033[1m\033[1;35mSTATUS: $@\033[0m" } ## # print a status message and hang out # for input ## function status_print_read { status_print $@ [ $headless -eq 0 ] && read } ## # print a header (used for making # things more visible ## function header_print { echo -e "\033[0;40m\033[1;37m\033[1m$@\033[0m" } ## # prompt the user, return the result. ## function user_prompt_yn { [ $headless -eq 1 ] && return 1 echo -e -n "\033[0;40m\033[1;37m\033[1m$@\033[0m" read INPUT if [ "$INPUT" != 'y' -a "$INPUT" != 'Y' -a "$INPUT" != '' ]; then return 0; fi return 1; } ## # print a debug message ## function debug_print { if [ $debug -gt 0 ]; then echo echo -e "\033[0;32mDEBUG: $@\033[0m" echo fi } ## # print a debug message and then # chill for a keypress ## function debug_print_read { if [ $debug -gt 0 ]; then echo echo -e "\033[0;32mDEBUG: $@\033[0m" echo -e -n "\033[0;32mDEBUG: Press --ENTER-- to continue... \033[0m" [ $headless -eq 0 ] && read fi } ## # Install the InterWorx-CP RPMs # # Use YUM here since otherwise we'd have to RPM # each package in the correct order, and YUM is # just better. ## function iworxinstall { yum clean metadata ## # make sure qmail gets its uids ## debug_print_read "About to install the Qmail MTA" status_print "Installing Qmail" _rpms="qmail" checkrpm $_rpms || runyum $yumargs install $_rpms status_print "Installing vpopmail" _rpms="vpopmail" checkrpm $_rpms || runyum $yumargs install $_rpms status_print "Installing php-iworx, iworx-db-server, and httpd-iworx" _rpms="php-iworx iworx-db-server httpd-iworx" checkrpm $_rpms || runyum $yumargs install $_rpms ldconfigfix debug_print_read "About to install the InterWorx-CP core packages" status_print "Installing InterWorx-CP" _rpms="interworx interworx-smarty interworx-roundcube interworx-phpmyadmin interworx-horde" checkrpm _rpms || runyum $yumargs install $_rpms # Make sure permissions, users, and groups are set correctly for interworx. runrpm --setperms interworx if [ $? -ne 0 ]; then error_print "InterWorx-CP could not be installed." error_print "YUM may have given some reasonable errors and" error_print "you can try re-running the installer as it may" error_print "just be a network and/or update server problem" error_print "" error_print "If after re-running the installer you still" error_print "receive an error please open a support ticket at:" error_print_die "https://www.interworx.com/support/helpdesk/" fi # debug_print_read "About to install the optional InterWorx-CP packages" # status_print "Installing InterWorx-CP CLI Tools" # runyum $yumargs interworx-cli # # status_print "Installing InterWorx-CP Clustering Tools" # runyum $yumargs interworx-cluster if [ $resolv -eq 1 ]; then mv -f /etc/resolv.conf.backup /etc/resolv.conf 2>/dev/null fi service crond restart >/dev/null 2>&1 return $? } function spinner { local pid=$1 local delay=0.25 local spinstr='|/-\' while [ "$(ps a 2>/dev/null | awk '{print $1}' | grep $pid)" ]; do local temp=${spinstr#?} printf " [%c] " "$spinstr" local spinstr=$temp${spinstr%"$temp"} sleep $delay printf "\b\b\b\b\b\b" done printf " \b\b\b\b" wait $pid return $? } function checkrpm { if [[ "$dorpmcheck" == "0" ]]; then return 1 fi rpm -q --quiet $@ ret=$? if [[ "$ret" == "0" ]]; then echo fi return $ret } function runyum { if [[ "$debug" == "1" || "$verbose" == "1" ]]; then echo (yum $@ 2>&1 | tee -a $LOG ; exit ${PIPESTATUS[0]}) ret=$? else (yum $@ 2>&1 | tee -a $LOG >$LOG_REDIR 2>&1; exit ${PIPESTATUS[0]}) & pid=$! spinner $pid ret=$? echo fi return $ret } function runrpm { if [[ "$debug" == "1" || "$verbose" == "1" ]]; then echo (rpm $@ 2>&1 | tee -a $LOG ; exit ${PIPESTATUS[0]}) ret=$? else (rpm $@ 2>&1 | tee -a $LOG >$LOG_REDIR 2>&1; exit ${PIPESTATUS[0]}) & pid=$! spinner $pid ret=$? echo fi return $ret } ## # kill any unneeded services on the box ## function killservices { [ -f /etc/init.d/yum ] && chkconfig --level 345 yum off >/dev/null 2>&1 [ -f /etc/cron.daily/yum ] && chmod 000 /etc/cron.daily/yum10111 } ## # we are so happy!!! ## function happy { distrocheck cat < /tmp/ili goiworx install successful: DISTRO: $release OPSYS : $opsys EOF mail -s "[GOIWORX] :D" info@interworx.com < /tmp/ili rm -f /tmp/ili } if [ "$1" = ":D" ]; then happy exit 0 fi goiworx # Copy the release file into release-install, which marks the version installed originally cp /usr/local/interworx/etc/env/release /usr/local/interworx/etc/env/release-install cp /usr/local/interworx/etc/env/build /usr/local/interworx/etc/env/build-install # Archive the log file into interworx's log folder for posterity cp ${LOG} /usr/local/interworx/var/log/ exit $?