diff --git a/elfinder_install_update.sh b/elfinder_install_update.sh
new file mode 100644
index 0000000000000000000000000000000000000000..69123e950ab3fdf512e6c650822a1a8b8fbf4502
--- /dev/null
+++ b/elfinder_install_update.sh
@@ -0,0 +1,401 @@
+#!/bin/bash
+# Name: elfinder_install_update.sh
+# Description: Setup or update elFinder File Manager in ISPConfig web server.
+# Author: Hj Ahmad Rasyid bin Hj Ismail
+# BSD 3 License
+# Updated on 20230919-103405
+# Should work on systems that were installed according to HowToForge's Perfect Server guides for auto/manual install
+
+
+## SETUP / UPDATE ELFINDER AS ISPCONFIG FILE MANAGER
+
+# Always start working from /tmp folder, so no messing up
+cd /tmp
+
+# Define latest elfinder source url, get its version and tar.gz file
+ef_github_url=https://api.github.com/repos/Studio-42/elFinder/releases/latest
+ef_latest_ver=$(curl -s $ef_github_url | grep "tag_name*" | cut -d : -f 2,3 | cut -d '"' -f2)
+ef_tar_gz=https://github.com/Studio-42/elFinder/archive/$ef_latest_ver.tar.gz
+# Define elfinder main & temp (extract) dir & temp log file
+ef_main_dir=/usr/share/elfinder
+ef_temp_dir=/tmp/elfinder
+ef_temp_log=$ef_main_dir/ef-temp.log
+
+# Function to download and extract latest elFinder
+get_elfinder () {
+ # Create elfinder main and temp dir, if they don't exist
+ if [ ! -d "$ef_temp_dir" ]; then mkdir -p $ef_temp_dir; fi
+ if [ ! -d "$ef_main_dir" ]; then mkdir -p $ef_main_dir; fi
+ # Go to the temp extract dir, get latest elfinder & extract it
+ cd $ef_temp_dir && wget -q --show-progress $ef_tar_gz && tar -xzf $ef_latest_ver.tar.gz --strip-components=1
+ # Make elfinder open full in browser
+ sed -i "/defaultOpts/a \\\t\t\t\t\twidth: '100%',\n\t\t\t\t\theight: '99.7%',\n\t\t\t\t\tresizable: false," elfinder.html
+ # index.html is web server default, so symlink is preferred
+ ln -sf elfinder.html index.html
+ cp php/connector.minimal.php-dist php/connector.minimal.php
+ rm $ef_latest_ver.tar.gz
+}
+
+# Function to setup elFinder or update (overwrite)
+set_elfinder () {
+ if [ -d $ef_temp_dir ]; then
+ cp -R $ef_temp_dir/* $ef_main_dir
+ if [ ! -z "$ef_json" ]; then
+ echo -e "\n"$ef_exist" "$ef_setup_ver"\n"$ef_outdated" "$ef_latest_ver"." | tee $ef_temp_log
+ else
+ echo -e "\n"$ef_none" "$ef_latest_ver"." | tee $ef_temp_log
+ fi
+ else
+ echo "\n"$ef_failed""
+ fi
+}
+
+# Define elFinder setup / update messages
+ef_word="filemanager"
+ef_exist="elFinder $ef_word setup exists with version"
+ef_uptodate="It is up-to-date. Neither new setup nor update is needed."
+ef_outdated="This old setup has been updated to latest version"
+ef_none="We've setup latest elFinder as none existed i.e. version"
+ef_failed="Failed to download and setup / download elFinder $ef_word."
+
+# Run elFinder setup / update here if it is not up-to-date
+if [ -d "$ef_main_dir" ]; then
+ ef_json=$ef_main_dir/package.json
+ if [ -f "$ef_json" ]; then
+ ef_setup_ver=$(grep -i "version" $ef_json | cut -d : -f 2,3 | cut -d '"' -f2)
+ if [[ "$ef_setup_ver" == "$ef_latest_ver" ]]; then
+ # Existing elFinder is up-to-date
+ echo -e "\n"$ef_exist" "$ef_latest_ver".\n"$ef_uptodate"" | tee $ef_temp_log
+ else
+ get_elfinder
+ set_elfinder
+ fi
+ else
+ get_elfinder
+ set_elfinder
+ fi
+else
+ get_elfinder
+ set_elfinder
+fi
+
+# Define filemanager folder and its backup, backup if needed, then force create its symlink
+ef_fm_dir=/usr/share/$ef_word
+ef_fm_bak=/usr/share/$ef_wordbak-$(date +"%Y%m%d-%H%M%S")
+if [ -d $ef_fm_dir ]; then
+ # Backup then force symlink if folder exist but not empty and also not a link
+ if [ ! -z $ef_fm_dir ] || [ ! -L $ef_fm_dir ]; then cp -R $ef_fm_dir $ef_fm_bak; fi
+ ln -sf $ef_main_dir $ef_fm_dir
+else
+ ln -sf $ef_main_dir $ef_fm_dir
+fi
+
+
+## ADD CONFIGS IF THEY DON'T EXIST IN VHOST & CONF FILES
+
+# Define conf folders, cat dummy files and other messages
+ispc_conf_dir=/usr/local/ispconfig/server/conf
+ispc_custom_dir=/usr/local/ispconfig/server/conf-custom
+ispc_install_dir=/usr/local/ispconfig/server/conf-custom/install
+ef_temp_conf=ef-temp.conf
+ef_exist="Not overwriting as string ($ef_word) exists in the"
+ef_added="Added elFinder $ef_word config successfully in the"
+ef_reload="has been successfully reloaded."
+ef_failed="configuration test failed."
+ef_manual="Please double check and manually fix the vhost file(s), if needed."
+ef_browse="Your may now try browsing the elfinder file manager at \nhttps://$(hostname -f):"
+ef_nosupport="You are not on a supported ISPConfig web server!"
+ef_old_setup="Previous setup could have set this up BUT who knows!?"
+ef_oops="Something is wrong!"
+
+# Function to create, copy & symlink custom conf dir, file and/or sub install dir
+set_custom_conf () {
+ # Create conf-custom directory if it doesn't exist
+ if [ ! -d $ispc_custom_dir ]; then mkdir -p $ispc_custom_dir; fi
+ # Copy the specified .vhost / .conf file from conf to conf-custom, if it doesn't exist
+ if [ ! -f $ispc_custom_dir/$master_vhost ]; then
+ cp $ispc_conf_dir/$master_vhost $ispc_custom_dir/
+ # Check conf-custom/install directory
+ if [ ! -d $isp_cust_inst_dir ]; then
+ # Force symlink to install directory, if it doesn't exist
+ ln -sf $ispc_custom_dir $isp_cust_inst_dir
+ else
+ # Force symlink apps file from custom-conf to install directory
+ ln -sf $ispc_custom_dir/$master_vhost $isp_cust_inst_dir/
+ fi
+ fi
+}
+
+# Function to create nginx config
+set_nginx_conf () {
+ cat <<"EOT" > $ef_temp_conf
+
+
+ ## ELFINDER FILE MANAGER CONFIG STARTS ##
+
+ location /filemanager {
+ root /usr/share/;
+ index index.php index.html index.htm;
+ location ~ ^/filemanager/(.+\.php)$ {
+ try_files $uri =404;
+ root /usr/share/;
+ include /etc/nginx/fastcgi_params;
+
+ # To access filemanager, create ftp users in ISPConfig UI
+ {use_tcp}fastcgi_pass 127.0.0.1:9000;
+ {use_socket}fastcgi_pass unix:{fpm_socket};
+ fastcgi_index index.php;
+ fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
+ fastcgi_buffer_size 128k;
+ fastcgi_buffers 256 4k;
+ fastcgi_busy_buffers_size 256k;
+ fastcgi_temp_file_write_size 256k;
+ fastcgi_read_timeout 1200;
+ }
+ location ~* ^/filemanager/(.+\.(ogg|ogv|svg|svgz|eot|ttf|otf|woff|woff2|mp4|mp3|ttf|css|rss|atom|js|jpg|jpeg|gif|png|ico|html|xml|txt|zip|tgz|gz|rar|bz2|doc|xls|exe|ppt|tar|mid|midi|wav|bmp|rtf)(\?ver=[0-9.]+)?$) {
+ root /usr/share/;
+ access_log off;
+ log_not_found off;
+ expires max;
+ }
+ }
+ location /file {
+ rewrite ^/* /filemanager last;
+ }
+
+ ## ELFINDER FILE MANAGER CONFIG STARTS ##
+
+
+EOT
+}
+
+# Function to add config in the custom-conf master file
+add_master_conf () {
+ if grep -q $ef_word $master_vhost; then
+ echo -e "\n"$ef_exist" "$master_vhost" file.\n"$ef_old_setup"\n"$ef_manual""
+ else
+ # First modify the conf vhost file and report result
+ sed -i "/$sm_search/e cat "$ef_temp_conf"" $master_vhost
+ if grep -q $ef_word $master_vhost; then echo -e "\n"$ef_added" "$master_vhost" file."; else echo -e "\n"$ef_oops" "$ef_manual"" && exit; fi
+ fi
+}
+
+# Function to add config in the custom-conf target file
+add_target_conf () {
+ # Then search for filemanager in the vhost / conf file, before we proceed further
+ if grep -q $ef_word $target_vhost; then
+ echo -e "\n"$ef_exist" "$target_base" file.\n"$ef_old_setup"\n"$ef_manual"\n"
+ # Finally, if it is safe, modify the vhost / conf file, with some edits for it to work
+ else
+ # Change for nginx only output to dev null
+ sed -i 's/{use_tcp}/#/g' $ef_temp_conf >/dev/null 2>&1
+ phpfpm="\t\t\tfastcgi_pass unix:/var/lib/php$(php -v | head -n 1 | cut -d ' ' -f 2 | cut -f1-2 -d'.')-fpm/apps.sock"
+ sed -i "/{fpm_socket}/c\\"$phpfpm";" $ef_temp_conf >/dev/null 2>&1
+
+ # Change for both nginx and apache
+ sed -i "/$sm_search/e cat "$ef_temp_conf"" $target_vhost
+ if grep -q $ef_word $target_vhost; then echo -e "\n"$ef_added" "$target_base" file.\n"; else echo -e "\n"$ef_oops" "$ef_manual"\n" && exit; fi
+ fi
+
+ # All modifications are done. Remove the unneeded files
+ rm -rf $ef_temp_conf $ef_temp_log $ef_temp_dir
+}
+
+# Nginx write to custom and apps vhost files function
+write_nginx_vhost () {
+ # Define nginx master & target files & edit string
+ master_vhost=nginx_apps.vhost.master
+ target_vhost=/etc/nginx/sites-available/apps.vhost
+ target_base=$(basename $target_vhost)
+ ef_port=$(grep -i "\*:" $target_vhost | cut -d : -f 2,3 | cut -d " " -f1)
+ sm_search="location \/squirrelmail"
+
+ # Run custom conf function
+ set_custom_conf
+
+ if [ -f $ispc_custom_dir/$master_vhost ]; then
+ # Go to the conf-custom folder
+ cd $ispc_custom_dir
+
+ set_nginx_conf
+ add_master_conf
+ add_target_conf
+
+ # Reload nginx if all good and report result
+ if nginx -t 2>/dev/null; then
+ systemctl reload nginx
+ echo -e "Nginx "$ef_reload"\n\n"$ef_browse""$ef_port"/$ef_word\n"
+ else
+ echo -e "Nginx "$ef_failed"\n\n"$ef_manual"\n"
+ fi
+ fi
+
+}
+
+# Function to create nginx config
+set_apache_conf () {
+ tee $ef_temp_conf >/dev/null << END
+
+## ELFINDER FILE MANAGER ##
+
+
+
+ Require all granted
+
+ Order allow,deny
+ Allow from all
+
+
+
+
+END
+}
+
+# Function to create apache config 2
+set_apache_vhost () {
+ tee $ef_temp_conf >/dev/null << END
+
+## ELFINDER FILE MANAGER ##
+
+
+ Require all granted
+
+
+
+END
+}
+
+# Function to download and extract latest elFinder
+set_elfinder_conf () {
+ # Create basic filemanager config.file
+ ef_avail_dir=/etc/apache2/conf-available
+ ef_enabl_dir=/etc/apache2/conf-enabled
+ ef_fm_conf=$ef_word.conf
+ tee $ef_avail_dir/$ef_fm_conf >/dev/null << END
+# elFinder default Apache configuration
+
+Alias /filemanager /usr/share/filemanager
+
+
+ Options FollowSymLinks
+ DirectoryIndex index.html
+
+ AllowOverride All
+
+ = 2.3>
+ Require all granted
+
+
+
+ Order allow,deny
+ Allow from all
+
+
+ # Clear PHP settings of this website
+ #
+ # SetHandler None
+ #
+
+ Require all granted
+
+
+
+
+
+
+ SetHandler php-fcgi
+
+
+
+
+
+
+
+ SetHandler php-fcgi
+
+
+
+
+ Action php-fcgi /php-fcgi virtual
+
+
+
+
+ Header set Content-Security-Policy "script-src 'self' https://cdnjs.cloudflare.com/"
+ Header set Content-Security-Policy "img-src 'self'"
+
+
+
+ AddType application/x-httpd-php .php
+ php_flag magic_quotes_gpc Off
+ php_flag track_vars On
+ php_flag register_globals Off
+ php_value include_path .
+
+
+
+
+
+ SSLStaplingCache shmcb:/var/run/ocsp(128000)
+
+END
+
+ if [ ! -f $ef_enabl_dir/$ef_fm_conf ]; then a2enconf $ef_word; fi
+}
+
+# Apache write to custom and ispconfig vhost files function
+write_apache_vhost () {
+ # Define custom and ispconfig vhost files
+ master_vhost=apache_ispconfig.conf.master
+ target_vhost=/etc/apache2/sites-available/ispconfig.conf
+ target_base=$(basename $target_vhost)
+ ef_port=$(grep -i "\*:" $target_vhost | cut -d : -f 2,3 | cut -d " " -f1)
+ sm_search="\/squirrelmail"
+
+ # Run custom conf function
+ set_custom_conf
+
+ if [ -f $ispc_custom_dir/$master_vhost ]; then
+ # Go to the conf-custom folder
+ cd $ispc_custom_dir
+
+ set_apache_conf
+ add_master_conf
+ set_apache_vhost
+ add_target_conf
+ set_elfinder_conf
+
+ # Reload apache2 if all good and report result
+ ispcvhost=/etc/apache2/sites-available/ispconfig.vhost
+ ef_port=$(grep -i "\*:" $ispcvhost | cut -d : -f 2,3 | cut -d " " -f1)
+ if AOUTPUT=$(/usr/sbin/apache2ctl -t 2>&1); then
+ systemctl reload apache2
+ echo -e "Apache2 "$ef_reload"\n\n"$ef_browse""$ef_port"/$ef_word\n"
+ else
+ echo -e "Apache2 "$ef_failed"\n\n"$ef_manual"\n"
+ fi
+ fi
+}
+
+
+# For Debian, Ubuntu & derivatives
+if apt-get -v >/dev/null 2>&1; then
+ # If web server is nginx, check and modify apps vhost accordingly
+ if [ $(dpkg-query -W -f='${Status}' nginx 2>/dev/null | grep -c "ok installed") -eq 1 ]; then
+ write_nginx_vhost
+ # If web server is apache2, check and modify ispconfig vhost accordingly
+ elif [ $(dpkg-query -W -f='${Status}' apache2 2>/dev/null | grep -c "ok installed") -eq 1 ]; then
+ write_apache_vhost
+ fi
+# For Red Hat, Centos & derivatives
+elif which yum &> /dev/null 2>&1; then
+ # If web server is nginx, check and modify apps vhost accordingly
+ if ( rpm -q nginx ); then
+ write_nginx_vhost
+ # If web server is apache2, check and modify ispconfig vhost accordingly
+ elif ( rpm -q httpd ); then
+ write_apache_vhost
+ fi
+else
+ echo $ef_nosupport
+fi