feat: convert WordOps from Nginx to OpenLiteSpeed + LSPHP + LSCache
Some checks failed
CI / test WordOps (ubuntu-22.04) (push) Has been cancelled
CI / test WordOps (ubuntu-24.04) (push) Has been cancelled

Complete conversion of the WordOps stack from Nginx + PHP-FPM to
OpenLiteSpeed + LSPHP + LSCache. This is a full rewrite across all 7
phases of the codebase:

- Foundation: OLS paths, variables, services, removed pynginxconfig dep
- Templates: 11 new OLS mustache templates, removed nginx-specific ones
- Stack: stack_pref, stack, stack_services, stack_upgrade, stack_migrate
- Site: site_functions, site, site_create, site_update
- Plugins: debug, info, log, clean rewritten for OLS
- SSL/ACME: acme.sh deploy uses lswsctrl, OLS vhssl blocks
- Other: secure, backup, clone, install script

Additional features:
- Debian 13 (trixie) support
- PHP 8.5 support
- WP Fort Knox mu-plugin integration (wo secure --lockdown/--unlock)
- --nginx CLI flag preserved for backward compatibility

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-02-08 18:55:16 +01:00
parent aa127070e1
commit fa5bf17eb8
42 changed files with 2328 additions and 2926 deletions

191
install
View File

@@ -141,7 +141,7 @@ wo_init_variables() {
readonly TIME_FORMAT='%d-%b-%Y-%H%M%S'
TIME=$(date +"$TIME_FORMAT")
readonly TIME
readonly NGINX_BACKUP_FILE="/var/lib/wo-backup/nginx-backup.$TIME.tar.zst"
readonly OLS_BACKUP_FILE="/var/lib/wo-backup/ols-backup.$TIME.tar.zst"
readonly EE_BACKUP_FILE="/var/lib/wo-backup/ee-backup.$TIME.tar.zst"
readonly WO_BACKUP_FILE="/var/lib/wo-backup/wo-backup.$TIME.tar.zst"
@@ -168,9 +168,9 @@ wo_check_distro() {
wo_lib_echo_fail "Feel free to open a pull-request if you want to add support for another Linux distributions"
exit 100
else
check_wo_linux_distro=$(lsb_release -sc | grep -E "buster|focal|jammy|bullseye|bookworm|noble")
check_wo_linux_distro=$(lsb_release -sc | grep -E "buster|focal|jammy|bullseye|bookworm|trixie|noble")
if [ -z "$check_wo_linux_distro" ]; then
wo_lib_echo_fail "WordOps (wo) only supports Ubuntu 20.04/22.04/24.04 LTS, Debian 10.x/11.x/12.x and Raspbian 10x./11.x/12.x \n
wo_lib_echo_fail "WordOps (wo) only supports Ubuntu 20.04/22.04/24.04 LTS, Debian 10.x/11.x/12.x/13.x and Raspbian 10x./11.x/12.x/13.x \n
You can bypass this warning by adding the flag --force to the install command"
exit 100
fi
@@ -250,13 +250,8 @@ wo_download_gpg_keys() {
# mariadb
curl -o /etc/apt/keyrings/mariadb-keyring.pgp 'https://mariadb.org/mariadb_release_signing_key.pgp'
# nginx
if [ "$wo_linux_distro" == "Debian" ]; then
curl -fsSL "https://raw.githubusercontent.com/WordOps/WordOps/refs/heads/master/repo.key" | gpg --dearmor | tee /usr/share/keyrings/wordops-archive-keyring.gpg >/dev/null 2>&1
fi
if [ "$wo_linux_distro" == "Raspbian" ]; then
curl -fsSL "https://download.opensuse.org/repositories/home:virtubox:WordOps/Raspbian_$wo_distro_version/Release.key" | gpg --dearmor | tee /usr/share/keyrings/wordops-archive-keyring.gpg >/dev/null 2>&1
fi
# openlitespeed
curl -fsSL https://rpms.litespeedtech.com/debian/lst_debian_repo.gpg | gpg --dearmor | tee /usr/share/keyrings/openlitespeed-archive-keyring.gpg >/dev/null 2>&1
}
wo_update_repo() {
@@ -283,10 +278,9 @@ wo_update_repo() {
if grep -q redis /etc/apt/sources.list.d/wo-repo.list; then
echo "deb [signed-by=/usr/share/keyrings/redis-archive-keyring.gpg] https://packages.redis.io/deb $wo_linux_codename main" >/etc/apt/sources.list.d/redis.list
fi
# properly define WordOps nginx repository
# properly define OpenLiteSpeed repository
if grep -q WordOps /etc/apt/sources.list.d/wo-repo.list; then
wo_repo=$(grep WordOps /etc/apt/sources.list.d/wo-repo.list | awk -F\ '{ print $2 }')
echo "deb [signed-by=/usr/share/keyrings/wordops-archive-keyring.gpg] $wo_repo /" >/etc/apt/sources.list.d/wordops.list
echo "deb [signed-by=/usr/share/keyrings/openlitespeed-archive-keyring.gpg] http://rpms.litespeedtech.com/debian/ $wo_linux_codename main" >/etc/apt/sources.list.d/openlitespeed.list
fi
# cleanup wo-repo.list
if grep -Eqv "WordOps|mariadb|sury|redis" /etc/apt/sources.list.d/wo-repo.list; then
@@ -328,7 +322,7 @@ wo_sync_db() {
# Copy ee database
cp /var/lib/ee/ee.db /var/lib/wo/dbase.db
else
if [ -d /etc/nginx/sites-available ] && [ -d /var/www ]; then
if [ -d /usr/local/lsws/conf/vhosts ] && [ -d /var/www ]; then
# Create an empty database for WordOps
echo "CREATE TABLE sites (
@@ -350,58 +344,40 @@ wo_sync_db() {
php_version VARCHAR
);" | sqlite3 /var/lib/wo/dbase.db
# Check site is enable/live or disable
AV_SITES="$(basename -a /etc/nginx/sites-available/* | grep -v default)"
for site in $AV_SITES; do
if [ -h "/etc/nginx/sites-enabled/$site" ]; then
wo_site_status='1'
else
wo_site_status='0'
fi
# Check OLS vhosts
if [ -d /usr/local/lsws/conf/vhosts ]; then
for vhost_dir in /usr/local/lsws/conf/vhosts/*/; do
site=$(basename "$vhost_dir")
[ "$site" = "22222" ] && continue
[ "$site" = "*" ] && continue
# Acquire information about the current nginx configuration
# Check if vhost is mapped in httpd_config.conf (enabled)
if grep -q "map.*$site" /usr/local/lsws/conf/httpd_config.conf 2>/dev/null; then
wo_site_status='1'
else
wo_site_status='0'
fi
wo_site_current_type=$(grep "common/" "/etc/nginx/sites-available/$site" | awk -F "/" '{print $2}')
if echo "$wo_site_current_type" | grep -q "redis"; then
wo_site_current_cache="wpredis"
elif echo "$wo_site_current_type" | grep -q wpsc; then
wo_site_current_cache="wpsc"
elif echo "$wo_site_current_type" | grep -q wpfc; then
wo_site_current_cache="wpfc"
else
# Default cache type for OLS is LSCache
wo_site_current_cache="basic"
fi
if echo "$wo_site_current_type" | grep -q wp; then
if echo "$wo_site_current_type" | grep -q wpsubdir; then
wo_site_current="wpsubdir"
elif echo "$wo_site_current_type" | grep -q wpsudomain; then
wo_site_current="wpsubdomain"
else
# Determine site type
if [ -f "/var/www/${site}/htdocs/wp-config.php" ]; then
wo_site_current="wp"
fi
else
if echo "$wo_site_current_type" | grep -q location; then
wo_site_current="proxy"
elif echo "$wo_site_current_type" | grep -q php; then
wo_site_current="html"
elif [ -f "/var/www/${site}/wo-config.php" ]; then
wo_site_current="mysql"
else
if [ -f "/var/www/${site}/ee-config.php" ] || [ -f "/var/www/${site}/wo-config.php" ]; then
wo_site_current="mysql"
else
wo_site_current="php"
fi
wo_site_current="php"
fi
fi
wo_webroot="/var/www/$site"
wo_webroot="/var/www/$site"
# Import the configuration into the WordOps SQLite database
echo "INSERT INTO sites (sitename, site_type, cache_type, site_path, is_enabled, is_ssl, storage_fs, storage_db)
# Import the configuration into the WordOps SQLite database
echo "INSERT INTO sites (sitename, site_type, cache_type, site_path, is_enabled, is_ssl, storage_fs, storage_db)
VALUES (\"$site\", \"$wo_site_current\", \"$wo_site_current_cache\", \"$wo_webroot\", \"$wo_site_status\", 0, 'ext4', 'mysql');" | sqlite3 /var/lib/wo/dbase.db
done
done
fi
fi
fi
@@ -532,6 +508,8 @@ wo_install() {
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@2.2.1#egg=python-apt
elif [ "$wo_distro_codename" = "bookworm" ]; then
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@2.5.3#egg=python-apt
elif [ "$wo_distro_codename" = "trixie" ]; then
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@2.9.y#egg=python-apt
else
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@1.8.4.y#egg=python-apt
fi
@@ -599,6 +577,8 @@ wo_travis_install() {
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@2.2.1#egg=python-apt
elif [ "$wo_distro_codename" = "bookworm" ]; then
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@2.5.3#egg=python-apt
elif [ "$wo_distro_codename" = "trixie" ]; then
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@2.9.y#egg=python-apt
else
/opt/wo/bin/pip install git+https://salsa.debian.org/apt-team/python-apt.git@1.8.4.y#egg=python-apt
fi
@@ -626,84 +606,44 @@ wo_travis_install() {
deactivate
}
wo_upgrade_nginx() {
wo_upgrade_ols() {
local wo_linux_distro
wo_linux_distro=$(lsb_release -is)
local wo_distro_version
wo_distro_version=$(lsb_release -sc)
if [ -d /var/lib/wo-backup/nginx ]; then
/bin/tar -I zstd "$NGINX_BACKUP_FILE" /var/lib/wo-backup/nginx
rm -rf /var/lib/wo-backup/nginx
# backup OLS conf
if [ -d /usr/local/lsws/conf ]; then
mkdir -p /var/lib/wo-backup/ols
/usr/bin/rsync -a --noatime /usr/local/lsws/conf/ /var/lib/wo-backup/ols/
fi
# backup nginx conf
if [ -d /etc/nginx ]; then
/usr/bin/rsync -a --noatime /etc/nginx/ /var/lib/wo-backup/nginx/
if [ -d /var/lib/wo-backup/ols ]; then
/bin/tar -I zstd -cf "$OLS_BACKUP_FILE" /var/lib/wo-backup/ols
rm -rf /var/lib/wo-backup/ols
fi
if [ -d /etc/php ]; then
/usr/bin/rsync -a --noatime /etc/php/ /var/lib/wo-backup/php/
fi
# chec if the package nginx-ee is installed
CHECK_NGINX_EE=$(dpkg --list | grep nginx-ee)
CHECK_PHP72=$(command -v php-fpm7.2)
# install new nginx package
if {
if [ -n "$CHECK_NGINX_EE" ]; then
if [ -x /usr/local/bin/wo ]; then
[ -f /etc/apt/preferences.d/nginx-block ] && { mv /etc/apt/preferences.d/nginx-block /var/lib/wo/tmp/nginx-block; }
# stop nginx
service nginx stop
# remove previous package
apt-mark unhold nginx-ee nginx-common nginx-custom
apt-get autoremove nginx-ee nginx-common nginx-custom --allow-change-held-packages --purge -qq
# remove previous php-fpm pool configuration
if [ -n "$CHECK_PHP72" ]; then
apt-get purge php7.2-fpm -y -qq
rm -f /etc/php/7.2/fpm/pool.d/{www.conf,www-two.conf,debug.conf}
fi
if [ -d /etc/nginx ]; then
rm -rf /etc/nginx
fi
/usr/local/bin/wo stack install --nginx --php
rm -f /etc/nginx/common/acl.conf /etc/nginx/htpasswd-wo
/usr/bin/rsync -au --noatime /var/lib/wo-backup/nginx/ /etc/nginx/
/usr/local/bin/wo stack upgrade --nginx --force
fi
# Check if old nginx-ee/nginx-custom is installed and migrate to OLS
CHECK_NGINX_EE=$(dpkg --list 2>/dev/null | grep -E "nginx-ee|nginx-custom")
if [ -n "$CHECK_NGINX_EE" ]; then
if [ -x /usr/local/bin/wo ]; then
# stop and remove nginx
service nginx stop 2>/dev/null
apt-mark unhold nginx-ee nginx-common nginx-custom 2>/dev/null
apt-get autoremove nginx-ee nginx-common nginx-custom --allow-change-held-packages --purge -qq 2>/dev/null
# install OLS
/usr/local/bin/wo stack install --nginx --php
fi
}; then
# restore sites and configuration
[ -f /etc/nginx/htpasswd-ee ] && { cp -f /etc/nginx/htpasswd-ee /etc/nginx/htpasswd-wo; }
sed -i "s/locations.conf/locations-wo.conf/" /etc/nginx/sites-available/*
sed -i "s/locations-php7.conf/locations-wo.conf/" /etc/nginx/sites-available/*
sed -i "s/locations-php71.conf/locations-wo.conf/" /etc/nginx/sites-available/*
sed -i "s/locations-php72.conf/locations-wo.conf/" /etc/nginx/sites-available/*
sed -i "s/locations-php73.conf/locations-wo.conf/" /etc/nginx/sites-available/*
sed -i "s/htpasswd-ee/htpasswd-wo/" /etc/nginx/common/acl.conf
sed -i 's/ssl on;/#ssl on;/' /var/www/*/conf/nginx/ssl.conf
fi
# update redis.conf headers
if [ -f /etc/nginx/common/redis.conf ]; then
sed -i "s/X-Cache /X-SRCache-Fetch-Status /g" /etc/nginx/common/redis.conf
sed -i "s/X-Cache-2 /X-SRCache-Store-Status /g" /etc/nginx/common/redis.conf
fi
VERIFY_NGINX_CONFIG=$(nginx -t 2>&1 | grep failed)
# check if nginx -t do not return errors
if [ -z "$VERIFY_NGINX_CONFIG" ]; then
systemctl stop nginx
systemctl start nginx
else
VERIFY_NGINX_BUCKET=$(nginx -t 2>&1 | grep "server_names_hash_bucket_size")
if [ -n "$VERIFY_NGINX_BUCKET" ]; then
sed -i "s/# server_names_hash_bucket_size 64;/server_names_hash_bucket_size 128;/g" /etc/nginx/nginx.conf
# Verify OLS config and restart
if [ -x /usr/local/lsws/bin/openlitespeed ]; then
VERIFY_OLS_CONFIG=$(/usr/local/lsws/bin/openlitespeed -t 2>&1 | grep -i "error")
if [ -z "$VERIFY_OLS_CONFIG" ]; then
/usr/local/lsws/bin/lswsctrl restart 2>/dev/null
else
wo_lib_echo_fail "OLS configuration test failed. Check /usr/local/lsws/logs/error.log"
fi
systemctl stop nginx
systemctl start nginx
fi
[ -f /var/lib/wo/tmp/nginx-block ] && { mv /var/lib/wo/tmp/nginx-block /etc/apt/preferences.d/nginx-block; }
return 0
}
@@ -731,14 +671,15 @@ wo_update_latest() {
wo_backup_ee() {
local BACKUP_EE=""
[ -d /etc/nginx ] && { BACKUP_EE="$BACKUP_EE /etc/nginx"; }
[ -d /usr/local/lsws/conf ] && { BACKUP_EE="$BACKUP_EE /usr/local/lsws/conf"; }
[ -d /etc/letsencrypt ] && { BACKUP_EE="$BACKUP_EE /etc/letsencrypt"; }
/bin/tar -I zstd -cf "$EE_BACKUP_FILE" /usr/local/bin/ee /usr/lib/ee/templates /etc/ee /var/lib/ee "$BACKUP_EE"
return 0
}
wo_backup_wo() {
if [ -d /etc/nginx ] && [ -d /etc/wo ] && [ -d /var/lib/wo ]; then
/bin/tar -I zstd -cf "$WO_BACKUP_FILE" /etc/nginx /etc/wo /var/lib/wo
if [ -d /usr/local/lsws/conf ] && [ -d /etc/wo ] && [ -d /var/lib/wo ]; then
/bin/tar -I zstd -cf "$WO_BACKUP_FILE" /usr/local/lsws/conf /etc/wo /var/lib/wo
fi
return 0
}
@@ -929,7 +870,7 @@ else
_run wo_travis_install "Installing WordOps"
fi
if [ -x /usr/local/bin/ee ]; then
_run wo_upgrade_nginx "Upgrading Nginx"
_run wo_upgrade_ols "Upgrading to OpenLiteSpeed"
_run wo_clean_ee "Cleaning previous EasyEngine install"
fi
_run wo_install_acme_sh "Running post-install steps"
@@ -952,8 +893,8 @@ else
echo
version_to_check="v3.21"
if echo "$wo_version_new" | grep -q "$version_to_check"; then
wo_lib_echo "To upgrade Nginx package and configuration for HTTP/3 QUIC, use the following command"
wo_lib_echo_info "wo stack migrate --nginx"
wo_lib_echo "To upgrade OpenLiteSpeed package and configuration, use the following command"
wo_lib_echo_info "wo stack upgrade --nginx"
fi
echo
wo_lib_echo "To upgrade WordOps web stacks, you can use the command:"

View File

@@ -1,5 +1,4 @@
cement==2.10.14
pynginxconfig==0.3.4
PyMySQL==1.1.2
psutil==7.0.0
sh==2.2.2

View File

@@ -40,7 +40,7 @@ setup(name='wordops',
"Natural Language :: English",
"Topic :: System :: Systems Administration",
],
keywords='nginx automation wordpress deployment CLI',
keywords='openlitespeed automation wordpress deployment CLI',
author='WordOps',
author_email='contact@wordops.io',
url='https://github.com/WordOps/WordOps',
@@ -63,7 +63,6 @@ setup(name='wordops',
# Required to function
'cement == 2.10.14',
'pystache',
'pynginxconfig',
'PyMySQL >= 1.0.2',
'psutil',
'sh',
@@ -79,6 +78,8 @@ setup(name='wordops',
data_files=[('/etc/wo', ['config/wo.conf']),
('/etc/wo/plugins.d', conf),
('/usr/lib/wo/templates', templates),
('/var/lib/wo',
['wo/cli/templates/wp-fort-knox.php']),
('/etc/bash_completion.d/',
['config/bash_completion.d/wo_auto.rc']),
('/usr/share/man/man8/', ['docs/wo.8'])],

View File

@@ -16,7 +16,7 @@ class WOBaseController(CementBaseController):
class Meta:
label = 'base'
description = ("An essential toolset that eases WordPress "
"site and server administration with Nginx")
"site and server administration with OpenLiteSpeed")
arguments = [
(['-v', '--version'], dict(action='version', version=BANNER)),
]

View File

@@ -22,12 +22,12 @@ class WOCleanController(CementBaseController):
stacked_on = 'base'
stacked_type = 'nested'
description = (
'Clean NGINX FastCGI cache, Opcache, Redis Cache')
'Clean LSCache, Opcache, Redis Cache')
arguments = [
(['--all'],
dict(help='Clean all cache', action='store_true')),
(['--fastcgi'],
dict(help='Clean FastCGI cache', action='store_true')),
dict(help='Clean LSCache', action='store_true')),
(['--opcache'],
dict(help='Clean OpCache', action='store_true')),
(['--redis'],
@@ -63,18 +63,18 @@ class WOCleanController(CementBaseController):
@expose(hide=True)
def clean_fastcgi(self):
if (os.path.isdir("/var/run/nginx-cache") and
os.path.exists('/usr/sbin/nginx')):
Log.info(self, "Cleaning NGINX FastCGI cache")
WOShellExec.cmd_exec(self, "rm -rf /var/run/nginx-cache/*")
WOService.restart_service(self, 'nginx')
if (os.path.isdir("/tmp/lshttpd/") and
os.path.exists(WOVar.wo_ols_bin)):
Log.info(self, "Cleaning LSCache")
WOShellExec.cmd_exec(self, "rm -rf /tmp/lshttpd/cache/*")
WOService.restart_service(self, 'lsws')
else:
Log.error(self, "Unable to clean FastCGI cache", False)
Log.error(self, "Unable to clean LSCache", False)
@expose(hide=True)
def clean_opcache(self):
opcache_dir = '/var/www/22222/htdocs/cache/opcache/'
if (os.path.exists('/usr/sbin/nginx') and
if (os.path.exists(WOVar.wo_ols_bin) and
os.path.exists(
'/var/www/22222/htdocs/cache/opcache')):
try:

View File

@@ -1,15 +1,12 @@
"""Debug Plugin for WordOps"""
import configparser
import glob
import os
import signal
from cement.core.controller import CementBaseController, expose
from pynginxconfig import NginxConfig
from wo.cli.plugins.site_functions import logwatch
from wo.core.aptget import WOAptGet
from wo.core.fileutils import WOFileUtils
from wo.core.logging import Log
from wo.core.mysql import WOMysql
@@ -37,24 +34,8 @@ class WODebugController(CementBaseController):
dict(help='Import MySQL slow log to Anemometer database',
action='store_true')),
(['--nginx'],
dict(help='start/stop debugging nginx server '
'configuration for site',
action='store' or 'store_const',
choices=('on', 'off'), const='on', nargs='?')),
(['--php'],
dict(help='start/stop debugging server PHP 7.2 configuration',
action='store' or 'store_const',
choices=('on', 'off'), const='on', nargs='?')),
(['--fpm'],
dict(help='start/stop debugging fastcgi configuration',
action='store' or 'store_const',
choices=('on', 'off'), const='on', nargs='?')),
(['--php73'],
dict(help='start/stop debugging server PHP 7.3 configuration',
action='store' or 'store_const',
choices=('on', 'off'), const='on', nargs='?')),
(['--fpm73'],
dict(help='start/stop debugging fastcgi 7.3 configuration',
dict(help='start/stop debugging OpenLiteSpeed server '
'configuration',
action='store' or 'store_const',
choices=('on', 'off'), const='on', nargs='?')),
(['--mysql'],
@@ -65,10 +46,6 @@ class WODebugController(CementBaseController):
dict(help='start/stop wordpress debugging for site',
action='store' or 'store_const', choices=('on', 'off'),
const='on', nargs='?')),
(['--rewrite'],
dict(help='start/stop debugging nginx rewrite rules for site',
action='store' or 'store_const', choices=('on', 'off'),
const='on', nargs='?')),
(['--all'],
dict(help='start/stop debugging all server parameters',
action='store' or 'store_const', choices=('on', 'off'),
@@ -84,325 +61,80 @@ class WODebugController(CementBaseController):
usage = "wo debug [<site_name>] [options] "
@expose(hide=True)
def debug_nginx(self):
"""Start/Stop Nginx debug"""
def debug_ols(self):
"""Start/Stop OpenLiteSpeed debug"""
ols_conf = "{0}/httpd_config.conf".format(WOVar.wo_ols_conf_dir)
# start global debug
if (self.app.pargs.nginx == 'on' and not self.app.pargs.site_name):
try:
debug_address = (self.app.config.get('stack', 'ip-address')
.split())
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_address = ['0.0.0.0/0']
if not WOFileUtils.grepcheck(self, ols_conf, 'logLevel DEBUG'):
Log.info(self, "Setting up OpenLiteSpeed debug log level")
WOFileUtils.searchreplace(
self, ols_conf,
'logLevel NOTICE', 'logLevel DEBUG')
self.trigger_ols = True
else:
Log.info(self, "OpenLiteSpeed debug already enabled")
# Check if IP address is 127.0.0.1 then enable debug globally
if debug_address == ['127.0.0.1'] or debug_address == []:
debug_address = ['0.0.0.0/0']
for ip_addr in debug_address:
if not ("debug_connection "+ip_addr in open('/etc/nginx/'
'nginx.conf',
encoding='utf-8').read()):
Log.info(self, "Setting up Nginx debug connection"
" for "+ip_addr)
WOShellExec.cmd_exec(self, "sed -i \"/events {{/a\\ \\ \\ "
"\\ $(echo debug_connection "
"{ip}\;)\" /etc/nginx/"
"nginx.conf".format(ip=ip_addr))
self.trigger_nginx = True
if not self.trigger_nginx:
Log.info(self, "Nginx debug connection already enabled")
self.msg = self.msg + ["/var/log/nginx/*.error.log"]
self.msg = self.msg + [
'/usr/local/lsws/logs/error.log']
# stop global debug
elif (self.app.pargs.nginx == 'off' and not self.app.pargs.site_name):
if "debug_connection " in open('/etc/nginx/nginx.conf',
encoding='utf-8').read():
Log.info(self, "Disabling Nginx debug connections")
WOShellExec.cmd_exec(self, "sed -i \"/debug_connection.*/d\""
" /etc/nginx/nginx.conf")
self.trigger_nginx = True
elif (self.app.pargs.nginx == 'off' and
not self.app.pargs.site_name):
if WOFileUtils.grepcheck(self, ols_conf, 'logLevel DEBUG'):
Log.info(self, "Disabling OpenLiteSpeed debug log level")
WOFileUtils.searchreplace(
self, ols_conf,
'logLevel DEBUG', 'logLevel NOTICE')
self.trigger_ols = True
else:
Log.info(self, "Nginx debug connection already disabled")
Log.info(self, "OpenLiteSpeed debug already disabled")
# start site specific debug
# start site-specific debug
elif (self.app.pargs.nginx == 'on' and self.app.pargs.site_name):
config_path = ("/etc/nginx/sites-available/{0}"
.format(self.app.pargs.site_name))
if os.path.isfile(config_path):
if not WOShellExec.cmd_exec(self, "grep \"error.log debug\" "
"{0}".format(config_path)):
Log.info(self, "Starting NGINX debug connection for "
vhconf = "{0}/{1}/vhconf.conf".format(
WOVar.wo_ols_vhost_dir, self.app.pargs.site_name)
if os.path.isfile(vhconf):
if not WOFileUtils.grepcheck(
self, vhconf, 'logLevel DEBUG'):
Log.info(self, "Starting OpenLiteSpeed debug for "
"{0}".format(self.app.pargs.site_name))
WOShellExec.cmd_exec(self, "sed -i \"s/error.log;/"
"error.log "
"debug;/\" {0}".format(config_path))
self.trigger_nginx = True
WOFileUtils.searchreplace(
self, vhconf,
'logLevel NOTICE', 'logLevel DEBUG')
self.trigger_ols = True
else:
Log.info(self, "Nginx debug for site already enabled")
Log.info(self, "OpenLiteSpeed debug for site "
"already enabled")
self.msg = self.msg + ['{0}{1}/logs/error.log'
.format(WOVar.wo_webroot,
self.app.pargs.site_name)]
else:
Log.info(self, "{0} domain not valid"
.format(self.app.pargs.site_name))
# stop site specific debug
# stop site-specific debug
elif (self.app.pargs.nginx == 'off' and self.app.pargs.site_name):
config_path = ("/etc/nginx/sites-available/{0}"
.format(self.app.pargs.site_name))
if os.path.isfile(config_path):
if WOShellExec.cmd_exec(self, "grep \"error.log debug\" {0}"
.format(config_path)):
Log.info(self, "Stoping NGINX debug connection for {0}"
.format(self.app.pargs.site_name))
WOShellExec.cmd_exec(self, "sed -i \"s/error.log debug;/"
"error.log;/\" {0}"
.format(config_path))
self.trigger_nginx = True
vhconf = "{0}/{1}/vhconf.conf".format(
WOVar.wo_ols_vhost_dir, self.app.pargs.site_name)
if os.path.isfile(vhconf):
if WOFileUtils.grepcheck(
self, vhconf, 'logLevel DEBUG'):
Log.info(self, "Stopping OpenLiteSpeed debug for "
"{0}".format(self.app.pargs.site_name))
WOFileUtils.searchreplace(
self, vhconf,
'logLevel DEBUG', 'logLevel NOTICE')
self.trigger_ols = True
else:
Log.info(self, "Nginx debug for site already disabled")
Log.info(self, "OpenLiteSpeed debug for site "
"already disabled")
else:
Log.info(self, "{0} domain not valid"
.format(self.app.pargs.site_name))
@expose(hide=True)
def debug_php(self):
"""Start/Stop PHP debug"""
# PHP global debug start
if (self.app.pargs.php == 'on' and not self.app.pargs.site_name):
if not (WOShellExec.cmd_exec(self, "sed -n \"/upstream php"
"{/,/}/p \" /etc/nginx/"
"conf.d/upstream.conf "
"| grep 9001")):
Log.info(self, "Enabling PHP debug")
# Change upstream.conf
nc = NginxConfig()
nc.loadf('/etc/nginx/conf.d/upstream.conf')
nc.set([('upstream', 'php',), 'server'], '127.0.0.1:9001')
nc.savef('/etc/nginx/conf.d/upstream.conf')
# Enable xdebug
WOFileUtils.searchreplace(self, "/etc/{0}/"
"mods-available/".format("php/7.2") +
"xdebug.ini",
";zend_extension",
"zend_extension")
# Fix slow log is not enabled default in PHP5.6
config = configparser.ConfigParser()
config.read('/etc/{0}/fpm/pool.d/debug.conf'.format("php/7.2"))
config['debug']['slowlog'] = '/var/log/{0}/slow.log'.format(
"php/7.2")
config['debug']['request_slowlog_timeout'] = '10s'
with open('/etc/{0}/fpm/pool.d/debug.conf'.format("php/7.2"),
encoding='utf-8', mode='w') as confifile:
Log.debug(self, "Writting debug.conf configuration into "
"/etc/{0}/fpm/pool.d/debug.conf".format("php/7.2"))
config.write(confifile)
self.trigger_php = True
self.trigger_nginx = True
else:
Log.info(self, "PHP debug is already enabled")
self.msg = self.msg + ['/var/log/{0}/slow.log'.format("php/7.2")]
# PHP global debug stop
elif (self.app.pargs.php == 'off' and not self.app.pargs.site_name):
if WOShellExec.cmd_exec(self, " sed -n \"/upstream php {/,/}/p\" "
"/etc/nginx/conf.d/upstream.conf "
"| grep 9001"):
Log.info(self, "Disabling PHP debug")
# Change upstream.conf
nc = NginxConfig()
nc.loadf('/etc/nginx/conf.d/upstream.conf')
nc.set([('upstream', 'php',), 'server'], '127.0.0.1:9000')
nc.savef('/etc/nginx/conf.d/upstream.conf')
# Disable xdebug
WOFileUtils.searchreplace(self, "/etc/{0}/"
"mods-available/".format("php/7.2") +
"xdebug.ini",
"zend_extension",
";zend_extension")
self.trigger_php = True
self.trigger_nginx = True
else:
Log.info(self, "PHP debug is already disabled")
@expose(hide=True)
def debug_fpm(self):
"""Start/Stop PHP5-FPM debug"""
# PHP5-FPM start global debug
if (self.app.pargs.fpm == 'on' and not self.app.pargs.site_name):
if not WOShellExec.cmd_exec(self, "grep \"log_level = debug\" "
"/etc/{0}/"
"fpm/php-fpm.conf".format("php/7.2")):
Log.info(self, "Setting up PHP5-FPM log_level = debug")
config = configparser.ConfigParser()
config.read('/etc/{0}/fpm/php-fpm.conf'.format("php/7.2"))
config.remove_option('global', 'include')
config['global']['log_level'] = 'debug'
config['global']['include'] = '/etc/{0}/fpm/pool.d/*.conf'.format(
"php/7.2")
with open('/etc/{0}/fpm/php-fpm.conf'.format("php/7.2"),
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "Writting php5-FPM configuration into "
"/etc/{0}/fpm/php-fpm.conf".format("php/7.2"))
config.write(configfile)
self.trigger_php = True
else:
Log.info(self, "PHP5-FPM log_level = debug already setup")
self.msg = self.msg + ['/var/log/{0}/fpm.log'.format("php/7.2")]
# PHP5-FPM stop global debug
elif (self.app.pargs.fpm == 'off' and not self.app.pargs.site_name):
if WOShellExec.cmd_exec(self, "grep \"log_level = debug\" "
"/etc/{0}/fpm/php-fpm.conf".format("php/7.2")):
Log.info(self, "Disabling PHP5-FPM log_level = debug")
config = configparser.ConfigParser()
config.read('/etc/{0}/fpm/php-fpm.conf'.format("php/7.2"))
config.remove_option('global', 'include')
config['global']['log_level'] = 'notice'
config['global']['include'] = '/etc/{0}/fpm/pool.d/*.conf'.format(
"php/7.2")
with open('/etc/{0}/fpm/php-fpm.conf'.format("php/7.2"),
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "writting php5 configuration into "
"/etc/{0}/fpm/php-fpm.conf".format("php/7.2"))
config.write(configfile)
self.trigger_php = True
else:
Log.info(self, "PHP5-FPM log_level = debug already disabled")
@expose(hide=True)
def debug_php73(self):
"""Start/Stop PHP debug"""
# PHP global debug start
if (self.app.pargs.php73 == 'on' and not self.app.pargs.site_name):
if not (WOShellExec.cmd_exec(self, "sed -n \"/upstream php73"
"{/,/}/p \" /etc/nginx/"
"conf.d/upstream.conf "
"| grep 9173")):
Log.info(self, "Enabling PHP 7.3 debug")
# Change upstream.conf
nc = NginxConfig()
nc.loadf('/etc/nginx/conf.d/upstream.conf')
nc.set([('upstream', 'php73',), 'server'], '127.0.0.1:9173')
nc.savef('/etc/nginx/conf.d/upstream.conf')
# Enable xdebug
WOFileUtils.searchreplace(self, "/etc/php/7.3/mods-available/"
"xdebug.ini",
";zend_extension",
"zend_extension")
# Fix slow log is not enabled default in PHP5.6
config = configparser.ConfigParser()
config.read('/etc/php/7.3/fpm/pool.d/debug.conf')
config['debug']['slowlog'] = '/var/log/php/7.3/slow.log'
config['debug']['request_slowlog_timeout'] = '10s'
with open('/etc/php/7.3/fpm/pool.d/debug.conf',
encoding='utf-8', mode='w') as confifile:
Log.debug(self, "Writting debug.conf configuration into "
"/etc/php/7.3/fpm/pool.d/debug.conf")
config.write(confifile)
self.trigger_php = True
self.trigger_nginx = True
else:
Log.info(self, "PHP debug is already enabled")
self.msg = self.msg + ['/var/log/php/7.3/slow.log']
# PHP global debug stop
elif (self.app.pargs.php73 == 'off' and not self.app.pargs.site_name):
if WOShellExec.cmd_exec(self, " sed -n \"/upstream "
"php73 {/,/}/p\" "
"/etc/nginx/conf.d/upstream.conf "
"| grep 9173"):
Log.info(self, "Disabling PHP 7.3 debug")
# Change upstream.conf
nc = NginxConfig()
nc.loadf('/etc/nginx/conf.d/upstream.conf')
nc.set([('upstream', 'php73',), 'server'],
'unix:/var/run/php/php73-fpm.sock')
nc.savef('/etc/nginx/conf.d/upstream.conf')
# Disable xdebug
WOFileUtils.searchreplace(self, "/etc/php/7.3/mods-available/"
"xdebug.ini",
"zend_extension",
";zend_extension")
self.trigger_php = True
self.trigger_nginx = True
else:
Log.info(self, "PHP 7.3 debug is already disabled")
@expose(hide=True)
def debug_fpm73(self):
"""Start/Stop PHP5-FPM debug"""
# PHP5-FPM start global debug
if (self.app.pargs.fpm73 == 'on' and not self.app.pargs.site_name):
if not WOShellExec.cmd_exec(self, "grep \"log_level = debug\" "
"/etc/php/7.3/fpm/php-fpm.conf"):
Log.info(self, "Setting up PHP7.3-FPM log_level = debug")
config = configparser.ConfigParser()
config.read('/etc/php/7.3/fpm/php-fpm.conf')
config.remove_option('global', 'include')
config['global']['log_level'] = 'debug'
config['global']['include'] = '/etc/php/7.3/fpm/pool.d/*.conf'
with open('/etc/php/7.3/fpm/php-fpm.conf',
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "Writing the PHP configuration into "
"/etc/php/7.3/fpm/php-fpm.conf")
config.write(configfile)
self.trigger_php = True
else:
Log.info(self, "PHP7.3-FPM log_level = debug already setup")
self.msg = self.msg + ['/var/log/php/7.3/fpm.log']
# PHP5-FPM stop global debug
elif (self.app.pargs.fpm73 == 'off' and not self.app.pargs.site_name):
if WOShellExec.cmd_exec(self, "grep \"log_level = debug\" "
"/etc/php/7.3/fpm/php-fpm.conf"):
Log.info(self, "Disabling PHP7.3-FPM log_level = debug")
config = configparser.ConfigParser()
config.read('/etc/php/7.3/fpm/php-fpm.conf')
config.remove_option('global', 'include')
config['global']['log_level'] = 'notice'
config['global']['include'] = '/etc/php/7.3/fpm/pool.d/*.conf'
with open('/etc/php/7.3/fpm/php-fpm.conf',
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "Writing the php7.3 configuration into "
"/etc/php/7.3/fpm/php-fpm.conf")
config.write(configfile)
self.trigger_php = True
else:
Log.info(self, "PHP7.3-FPM log_level "
"= debug already disabled")
@expose(hide=True)
def debug_mysql(self):
"""Start/Stop MySQL debug"""
@@ -520,91 +252,13 @@ class WODebugController(CementBaseController):
else:
Log.error(self, "Missing argument site name")
@expose(hide=True)
def debug_rewrite(self):
"""Start/Stop Nginx rewrite rules debug"""
# Start Nginx rewrite debug globally
if (self.app.pargs.rewrite == 'on' and not self.app.pargs.site_name):
if not WOShellExec.cmd_exec(self, "grep \"rewrite_log on;\" "
"/etc/nginx/nginx.conf"):
Log.info(self, "Setting up Nginx rewrite logs")
WOShellExec.cmd_exec(self, "sed -i \'/http {/a \\\\t"
"rewrite_log on;\' /etc/nginx/nginx.conf")
self.trigger_nginx = True
else:
Log.info(self, "Nginx rewrite logs already enabled")
if '/var/log/nginx/*.error.log' not in self.msg:
self.msg = self.msg + ['/var/log/nginx/*.error.log']
# Stop Nginx rewrite debug globally
elif (self.app.pargs.rewrite == 'off' and
not self.app.pargs.site_name):
if WOShellExec.cmd_exec(self, "grep \"rewrite_log on;\" "
"/etc/nginx/nginx.conf"):
Log.info(self, "Disabling Nginx rewrite logs")
WOShellExec.cmd_exec(self, "sed -i \"/rewrite_log.*/d\""
" /etc/nginx/nginx.conf")
self.trigger_nginx = True
else:
Log.info(self, "Nginx rewrite logs already disabled")
# Start Nginx rewrite for site
elif (self.app.pargs.rewrite == 'on' and self.app.pargs.site_name):
config_path = ("/etc/nginx/sites-available/{0}"
.format(self.app.pargs.site_name))
if not WOShellExec.cmd_exec(self, "grep \"rewrite_log on;\" {0}"
.format(config_path)):
Log.info(self, "Setting up Nginx rewrite logs for {0}"
.format(self.app.pargs.site_name))
WOShellExec.cmd_exec(self, "sed -i \"/access_log/i \\\\\\t"
"rewrite_log on;\" {0}"
.format(config_path))
self.trigger_nginx = True
else:
Log.info(self, "Nginx rewrite logs for {0} already setup"
.format(self.app.pargs.site_name))
if ('{0}{1}/logs/error.log'.format(WOVar.wo_webroot,
self.app.pargs.site_name)
not in self.msg):
self.msg = self.msg + ['{0}{1}/logs/error.log'
.format(WOVar.wo_webroot,
self.app.pargs.site_name)]
# Stop Nginx rewrite for site
elif (self.app.pargs.rewrite == 'off' and self.app.pargs.site_name):
config_path = ("/etc/nginx/sites-available/{0}"
.format(self.app.pargs.site_name))
if WOShellExec.cmd_exec(self, "grep \"rewrite_log on;\" {0}"
.format(config_path)):
Log.info(self, "Disabling Nginx rewrite logs for {0}"
.format(self.app.pargs.site_name))
WOShellExec.cmd_exec(self, "sed -i \"/rewrite_log.*/d\" {0}"
.format(config_path))
self.trigger_nginx = True
else:
Log.info(self, "Nginx rewrite logs for {0} already "
" disabled".format(self.app.pargs.site_name))
@expose(hide=True)
def signal_handler(self, app, signal, frame):
"""Handle Ctrl+c hevent for -i option of debug"""
"""Handle Ctrl+c event for -i option of debug"""
self.start = False
if self.app.pargs.nginx:
self.app.pargs.nginx = 'off'
self.debug_nginx()
if self.app.pargs.php:
self.app.pargs.php = 'off'
self.debug_php()
if self.app.pargs.php73:
self.app.pargs.php73 = 'off'
self.debug_php73()
if self.app.pargs.fpm:
self.app.pargs.fpm = 'off'
self.debug_fpm()
if self.app.pargs.fpm73:
self.app.pargs.fpm73 = 'off'
self.debug_fpm73()
self.debug_ols()
if self.app.pargs.mysql:
# MySQL debug will not work for remote MySQL
if WOVar.wo_mysql_host == "localhost":
@@ -616,20 +270,11 @@ class WODebugController(CementBaseController):
if self.app.pargs.wp:
self.app.pargs.wp = 'off'
self.debug_wp()
if self.app.pargs.rewrite:
self.app.pargs.rewrite = 'off'
self.debug_rewrite()
# Reload Nginx
if self.trigger_nginx:
WOService.reload_service(self, 'nginx')
# Reload OpenLiteSpeed
if self.trigger_ols:
WOService.reload_service(self, 'lsws')
# Reload PHP
if self.trigger_php:
if WOAptGet.is_installed(self, 'php7.2-fpm'):
WOService.reload_service(self, 'php7.2-fpm')
if WOAptGet.is_installed(self, 'php7.3-fpm'):
WOService.reload_service(self, 'php7.3-fpm')
self.app.close(0)
@expose(hide=True)
@@ -638,13 +283,10 @@ class WODebugController(CementBaseController):
# self.start = True
self.interactive = False
self.msg = []
self.trigger_nginx = False
self.trigger_php = False
self.trigger_ols = False
if ((not self.app.pargs.nginx) and (not self.app.pargs.php) and
(not self.app.pargs.php73) and (not self.app.pargs.fpm) and
(not self.app.pargs.fpm73) and (not self.app.pargs.mysql) and
(not self.app.pargs.wp) and (not self.app.pargs.rewrite) and
if ((not self.app.pargs.nginx) and (not self.app.pargs.mysql) and
(not self.app.pargs.wp) and
(not self.app.pargs.all) and (not self.app.pargs.site_name) and
(not self.app.pargs.import_slow_log) and
(not self.app.pargs.interval)):
@@ -712,46 +354,21 @@ class WODebugController(CementBaseController):
if self.app.pargs.site_name:
self.app.pargs.wp = 'on'
self.app.pargs.nginx = 'on'
self.app.pargs.php = 'on'
self.app.pargs.fpm = 'on'
if WOAptGet.is_installed(self, 'php7.2-fpm'):
self.app.pargs.php73 = 'on'
self.app.pargs.fpm73 = 'on'
self.app.pargs.mysql = 'on'
self.app.pargs.rewrite = 'on'
if self.app.pargs.all == 'off':
if self.app.pargs.site_name:
self.app.pargs.wp = 'off'
self.app.pargs.nginx = 'off'
self.app.pargs.php = 'off'
self.app.pargs.fpm = 'off'
if WOAptGet.is_installed(self, 'php7.2-fpm'):
self.app.pargs.php73 = 'off'
self.app.pargs.fpm73 = 'off'
self.app.pargs.mysql = 'off'
self.app.pargs.rewrite = 'off'
if ((not self.app.pargs.nginx) and (not self.app.pargs.php) and
(not self.app.pargs.php73) and (not self.app.pargs.fpm) and
(not self.app.pargs.fpm73) and (not self.app.pargs.mysql) and
(not self.app.pargs.wp) and (not self.app.pargs.rewrite) and
if ((not self.app.pargs.nginx) and (not self.app.pargs.mysql) and
(not self.app.pargs.wp) and
self.app.pargs.site_name):
self.app.args.print_help()
# self.app.pargs.nginx = 'on'
# self.app.pargs.wp = 'on'
# self.app.pargs.rewrite = 'on'
if self.app.pargs.nginx:
self.debug_nginx()
if self.app.pargs.php:
self.debug_php()
if self.app.pargs.fpm:
self.debug_fpm()
if self.app.pargs.php73:
self.debug_php73()
if self.app.pargs.fpm73:
self.debug_fpm73()
self.debug_ols()
if self.app.pargs.mysql:
# MySQL debug will not work for remote MySQL
if WOVar.wo_mysql_host == "localhost":
@@ -761,21 +378,13 @@ class WODebugController(CementBaseController):
"debugging remote servers")
if self.app.pargs.wp:
self.debug_wp()
if self.app.pargs.rewrite:
self.debug_rewrite()
if self.app.pargs.interactive:
self.interactive = True
# Reload Nginx
if self.trigger_nginx:
WOService.reload_service(self, 'nginx')
# Reload PHP
if self.trigger_php:
if WOAptGet.is_installed(self, 'php7.2-fpm'):
WOService.restart_service(self, 'php7.2-fpm')
if WOAptGet.is_installed(self, 'php7.3-fpm'):
WOService.restart_service(self, 'php7.3-fpm')
# Reload OpenLiteSpeed
if self.trigger_ols:
WOService.reload_service(self, 'lsws')
if len(self.msg) > 0:
if not self.app.pargs.interactive:

View File

@@ -4,7 +4,6 @@ import configparser
import os
from cement.core.controller import CementBaseController, expose
from pynginxconfig import NginxConfig
from wo.core.aptget import WOAptGet
from wo.core.logging import Log
@@ -21,8 +20,8 @@ class WOInfoController(CementBaseController):
label = 'info'
stacked_on = 'base'
stacked_type = 'nested'
description = ('Display configuration information related to Nginx,'
' PHP and MySQL')
description = ('Display configuration information related to '
'OpenLiteSpeed, PHP and MySQL')
arguments = [
(['--mysql'],
dict(help='Get MySQL configuration information',
@@ -31,7 +30,7 @@ class WOInfoController(CementBaseController):
dict(help='Get PHP configuration information',
action='store_true')),
(['--nginx'],
dict(help='Get Nginx configuration information',
dict(help='Get OpenLiteSpeed configuration information',
action='store_true')),
]
usage = "wo info [options]"
@@ -41,593 +40,132 @@ class WOInfoController(CementBaseController):
action='store_true')))
@expose(hide=True)
def info_nginx(self):
"""Display Nginx information"""
version = os.popen("/usr/sbin/nginx -v 2>&1 | "
"awk -F '/' '{print $2}' | "
"awk -F ' ' '{print $1}' | tr '\n' ' '").read()
allow = os.popen("grep ^allow /etc/nginx/common/acl.conf | "
"cut -d' ' -f2 | cut -d';' -f1 | tr '\n' ' '").read()
nc = NginxConfig()
nc.loadf('/etc/nginx/nginx.conf')
user = nc.get('user')[1]
worker_processes = nc.get('worker_processes')[1]
worker_connections = nc.get([('events',), 'worker_connections'])[1]
keepalive_timeout = nc.get([('http',), 'keepalive_timeout'])[1]
fastcgi_read_timeout = nc.get([('http',),
'fastcgi_read_timeout'])[1]
client_max_body_size = nc.get([('http',),
'client_max_body_size'])[1]
data = dict(version=version, allow=allow, user=user,
worker_processes=worker_processes,
def info_ols(self):
"""Display OpenLiteSpeed information"""
version = os.popen("{0} -v 2>&1 | head -1"
.format(WOVar.wo_ols_bin)).read().strip()
httpd_conf = '{0}/httpd_config.conf'.format(WOVar.wo_ols_conf_dir)
server_name = os.popen("hostname -f 2>/dev/null || hostname"
).read().strip()
# Parse OLS httpd_config.conf for key settings
max_connections = ''
max_ssl_connections = ''
keepalive_timeout = ''
gzip_compress = ''
brotli_compress = ''
quic_enabled = ''
if os.path.isfile(httpd_conf):
with open(httpd_conf, 'r', encoding='utf-8') as f:
for line in f:
stripped = line.strip()
parts = stripped.split(None, 1)
if len(parts) == 2:
key, val = parts
if key == 'maxConnections':
max_connections = val
elif key == 'maxSSLConnections':
max_ssl_connections = val
elif key == 'keepAliveTimeout':
keepalive_timeout = val
elif key == 'enableGzipCompress':
gzip_compress = 'On' if val == '1' else 'Off'
elif key == 'enableBr':
brotli_compress = 'On' if val == '1' else 'Off'
elif key == 'enableQuic':
quic_enabled = 'On' if val == '1' else 'Off'
data = dict(version=version, server_name=server_name,
max_connections=max_connections,
max_ssl_connections=max_ssl_connections,
keepalive_timeout=keepalive_timeout,
worker_connections=worker_connections,
fastcgi_read_timeout=fastcgi_read_timeout,
client_max_body_size=client_max_body_size)
self.app.render((data), 'info_nginx.mustache')
gzip_compress=gzip_compress,
brotli_compress=brotli_compress,
quic_enabled=quic_enabled)
self.app.render((data), 'info_ols.mustache')
@expose(hide=True)
def info_php(self):
"""Display PHP information"""
pargs = self.app.pargs
if WOAptGet.is_installed(self, 'php7.4-fpm'):
pargs.php74 = True
else:
Log.info(self, "PHP 7.4 is not installed")
if WOAptGet.is_installed(self, 'php8.0-fpm'):
pargs.php80 = True
else:
Log.info(self, "PHP 8.0 is not installed")
if WOAptGet.is_installed(self, 'php8.1-fpm'):
pargs.php81 = True
else:
Log.info(self, "PHP 8.1 is not installed")
if WOAptGet.is_installed(self, 'php8.2-fpm'):
pargs.php82 = True
else:
Log.info(self, "PHP 8.2 is not installed")
if WOAptGet.is_installed(self, 'php8.3-fpm'):
pargs.php83 = True
else:
Log.info(self, "PHP 8.3 is not installed")
if WOAptGet.is_installed(self, 'php8.4-fpm'):
pargs.php84 = True
else:
Log.info(self, "PHP 8.4 is not installed")
for parg_version, dot_ver in WOVar.wo_php_versions.items():
short_ver = dot_ver.replace('.', '')
if WOAptGet.is_installed(self, 'lsphp{0}'.format(short_ver)):
setattr(pargs, parg_version, True)
else:
Log.info(self, "PHP {0} is not installed".format(dot_ver))
if pargs.php74:
self.info_php74()
if pargs.php80:
self.info_php80()
if pargs.php81:
self.info_php81()
if pargs.php82:
self.info_php82()
if pargs.php83:
self.info_php83()
if pargs.php84:
self.info_php84()
for parg_version, dot_ver in WOVar.wo_php_versions.items():
if getattr(pargs, parg_version, False):
short_ver = dot_ver.replace('.', '')
self._info_lsphp(short_ver, dot_ver)
@expose(hide=True)
def info_php74(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php7.4 -v 2>/dev/null | "
def _info_lsphp(self, short_ver, dot_ver):
"""Display LSPHP information for a given version"""
php_bin = '/usr/local/lsws/lsphp{0}/bin/php'.format(short_ver)
php_ini = ('/usr/local/lsws/lsphp{0}/etc/php/{1}'
'/litespeed/php.ini'.format(short_ver, dot_ver))
version = os.popen("{0} -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").read
" cut -d'+' -f1 | tr -d '\\n'"
.format(php_bin)).read()
config = configparser.ConfigParser()
config.read('/etc/php/7.4/fpm/php.ini')
expose_php = config['PHP']['expose_php']
memory_limit = config['PHP']['memory_limit']
post_max_size = config['PHP']['post_max_size']
upload_max_filesize = config['PHP']['upload_max_filesize']
max_execution_time = config['PHP']['max_execution_time']
if os.path.exists('/etc/php/7.4/fpm/pool.d/www.conf'):
config.read('/etc/php/7.4/fpm/pool.d/www.conf')
if os.path.isfile(php_ini):
config.read(php_ini)
else:
Log.error(self, 'php-fpm pool config not found')
if config.has_section('www'):
wconfig = config['www']
elif config.has_section('www-php74'):
wconfig = config['www-php74']
else:
Log.error(self, 'Unable to parse configuration')
www_listen = wconfig['listen']
www_ping_path = wconfig['ping.path']
www_pm_status_path = wconfig['pm.status_path']
www_pm = wconfig['pm']
www_pm_max_requests = wconfig['pm.max_requests']
www_pm_max_children = wconfig['pm.max_children']
www_pm_start_servers = wconfig['pm.start_servers']
www_pm_min_spare_servers = wconfig['pm.min_spare_servers']
www_pm_max_spare_servers = wconfig['pm.max_spare_servers']
www_request_terminate_time = (wconfig
['request_terminate_timeout'])
try:
www_xdebug = (wconfig
['php_admin_flag[xdebug.profiler_enable'
'_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
www_xdebug = 'off'
Log.info(self, "LSPHP {0} php.ini not found at {1}"
.format(dot_ver, php_ini))
return
config.read('/etc/php/7.4/fpm/pool.d/debug.conf')
debug_listen = config['debug']['listen']
debug_ping_path = config['debug']['ping.path']
debug_pm_status_path = config['debug']['pm.status_path']
debug_pm = config['debug']['pm']
debug_pm_max_requests = config['debug']['pm.max_requests']
debug_pm_max_children = config['debug']['pm.max_children']
debug_pm_start_servers = config['debug']['pm.start_servers']
debug_pm_min_spare_servers = config['debug']['pm.min_spare_servers']
debug_pm_max_spare_servers = config['debug']['pm.max_spare_servers']
debug_request_terminate = (config['debug']
['request_terminate_timeout'])
try:
debug_xdebug = (config['debug']['php_admin_flag[xdebug.profiler_'
'enable_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_xdebug = 'off'
expose_php = config['PHP']['expose_php']
except KeyError:
expose_php = 'N/A'
try:
memory_limit = config['PHP']['memory_limit']
except KeyError:
memory_limit = 'N/A'
try:
post_max_size = config['PHP']['post_max_size']
except KeyError:
post_max_size = 'N/A'
try:
upload_max_filesize = config['PHP']['upload_max_filesize']
except KeyError:
upload_max_filesize = 'N/A'
try:
max_execution_time = config['PHP']['max_execution_time']
except KeyError:
max_execution_time = 'N/A'
data = dict(version=version, expose_php=expose_php,
memory_limit=memory_limit, post_max_size=post_max_size,
upload_max_filesize=upload_max_filesize,
max_execution_time=max_execution_time,
www_listen=www_listen, www_ping_path=www_ping_path,
www_pm_status_path=www_pm_status_path, www_pm=www_pm,
www_pm_max_requests=www_pm_max_requests,
www_pm_max_children=www_pm_max_children,
www_pm_start_servers=www_pm_start_servers,
www_pm_min_spare_servers=www_pm_min_spare_servers,
www_pm_max_spare_servers=www_pm_max_spare_servers,
www_request_terminate_timeout=www_request_terminate_time,
www_xdebug_profiler_enable_trigger=www_xdebug,
debug_listen=debug_listen, debug_ping_path=debug_ping_path,
debug_pm_status_path=debug_pm_status_path,
debug_pm=debug_pm,
debug_pm_max_requests=debug_pm_max_requests,
debug_pm_max_children=debug_pm_max_children,
debug_pm_start_servers=debug_pm_start_servers,
debug_pm_min_spare_servers=debug_pm_min_spare_servers,
debug_pm_max_spare_servers=debug_pm_max_spare_servers,
debug_request_terminate_timeout=debug_request_terminate,
debug_xdebug_profiler_enable_trigger=debug_xdebug)
self.app.render((data), 'info_php.mustache')
@expose(hide=True)
def info_php80(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php8.0 -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").read
config = configparser.ConfigParser()
config.read('/etc/php/8.0/fpm/php.ini')
expose_php = config['PHP']['expose_php']
memory_limit = config['PHP']['memory_limit']
post_max_size = config['PHP']['post_max_size']
upload_max_filesize = config['PHP']['upload_max_filesize']
max_execution_time = config['PHP']['max_execution_time']
if os.path.exists('/etc/php/8.0/fpm/pool.d/www.conf'):
config.read('/etc/php/8.0/fpm/pool.d/www.conf')
else:
Log.error(self, 'php-fpm pool config not found')
if config.has_section('www'):
wconfig = config['www']
elif config.has_section('www-php80'):
wconfig = config['www-php80']
else:
Log.error(self, 'Unable to parse configuration')
www_listen = wconfig['listen']
www_ping_path = wconfig['ping.path']
www_pm_status_path = wconfig['pm.status_path']
www_pm = wconfig['pm']
www_pm_max_requests = wconfig['pm.max_requests']
www_pm_max_children = wconfig['pm.max_children']
www_pm_start_servers = wconfig['pm.start_servers']
www_pm_min_spare_servers = wconfig['pm.min_spare_servers']
www_pm_max_spare_servers = wconfig['pm.max_spare_servers']
www_request_terminate_time = (wconfig
['request_terminate_timeout'])
try:
www_xdebug = (wconfig
['php_admin_flag[xdebug.profiler_enable'
'_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
www_xdebug = 'off'
config.read('/etc/php/8.0/fpm/pool.d/debug.conf')
debug_listen = config['debug']['listen']
debug_ping_path = config['debug']['ping.path']
debug_pm_status_path = config['debug']['pm.status_path']
debug_pm = config['debug']['pm']
debug_pm_max_requests = config['debug']['pm.max_requests']
debug_pm_max_children = config['debug']['pm.max_children']
debug_pm_start_servers = config['debug']['pm.start_servers']
debug_pm_min_spare_servers = config['debug']['pm.min_spare_servers']
debug_pm_max_spare_servers = config['debug']['pm.max_spare_servers']
debug_request_terminate = (config['debug']
['request_terminate_timeout'])
try:
debug_xdebug = (config['debug']['php_admin_flag[xdebug.profiler_'
'enable_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_xdebug = 'off'
data = dict(version=version, expose_php=expose_php,
memory_limit=memory_limit, post_max_size=post_max_size,
upload_max_filesize=upload_max_filesize,
max_execution_time=max_execution_time,
www_listen=www_listen, www_ping_path=www_ping_path,
www_pm_status_path=www_pm_status_path, www_pm=www_pm,
www_pm_max_requests=www_pm_max_requests,
www_pm_max_children=www_pm_max_children,
www_pm_start_servers=www_pm_start_servers,
www_pm_min_spare_servers=www_pm_min_spare_servers,
www_pm_max_spare_servers=www_pm_max_spare_servers,
www_request_terminate_timeout=www_request_terminate_time,
www_xdebug_profiler_enable_trigger=www_xdebug,
debug_listen=debug_listen, debug_ping_path=debug_ping_path,
debug_pm_status_path=debug_pm_status_path,
debug_pm=debug_pm,
debug_pm_max_requests=debug_pm_max_requests,
debug_pm_max_children=debug_pm_max_children,
debug_pm_start_servers=debug_pm_start_servers,
debug_pm_min_spare_servers=debug_pm_min_spare_servers,
debug_pm_max_spare_servers=debug_pm_max_spare_servers,
debug_request_terminate_timeout=debug_request_terminate,
debug_xdebug_profiler_enable_trigger=debug_xdebug)
self.app.render((data), 'info_php.mustache')
@expose(hide=True)
def info_php81(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php8.1 -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").read
config = configparser.ConfigParser()
config.read('/etc/php/8.1/fpm/php.ini')
expose_php = config['PHP']['expose_php']
memory_limit = config['PHP']['memory_limit']
post_max_size = config['PHP']['post_max_size']
upload_max_filesize = config['PHP']['upload_max_filesize']
max_execution_time = config['PHP']['max_execution_time']
if os.path.exists('/etc/php/8.1/fpm/pool.d/www.conf'):
config.read('/etc/php/8.1/fpm/pool.d/www.conf')
else:
Log.error(self, 'php-fpm pool config not found')
if config.has_section('www'):
wconfig = config['www']
elif config.has_section('www-php81'):
wconfig = config['www-php81']
else:
Log.error(self, 'Unable to parse configuration')
www_listen = wconfig['listen']
www_ping_path = wconfig['ping.path']
www_pm_status_path = wconfig['pm.status_path']
www_pm = wconfig['pm']
www_pm_max_requests = wconfig['pm.max_requests']
www_pm_max_children = wconfig['pm.max_children']
www_pm_start_servers = wconfig['pm.start_servers']
www_pm_min_spare_servers = wconfig['pm.min_spare_servers']
www_pm_max_spare_servers = wconfig['pm.max_spare_servers']
www_request_terminate_time = (wconfig
['request_terminate_timeout'])
try:
www_xdebug = (wconfig
['php_admin_flag[xdebug.profiler_enable'
'_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
www_xdebug = 'off'
config.read('/etc/php/8.1/fpm/pool.d/debug.conf')
debug_listen = config['debug']['listen']
debug_ping_path = config['debug']['ping.path']
debug_pm_status_path = config['debug']['pm.status_path']
debug_pm = config['debug']['pm']
debug_pm_max_requests = config['debug']['pm.max_requests']
debug_pm_max_children = config['debug']['pm.max_children']
debug_pm_start_servers = config['debug']['pm.start_servers']
debug_pm_min_spare_servers = config['debug']['pm.min_spare_servers']
debug_pm_max_spare_servers = config['debug']['pm.max_spare_servers']
debug_request_terminate = (config['debug']
['request_terminate_timeout'])
try:
debug_xdebug = (config['debug']['php_admin_flag[xdebug.profiler_'
'enable_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_xdebug = 'off'
data = dict(version=version, expose_php=expose_php,
memory_limit=memory_limit, post_max_size=post_max_size,
upload_max_filesize=upload_max_filesize,
max_execution_time=max_execution_time,
www_listen=www_listen, www_ping_path=www_ping_path,
www_pm_status_path=www_pm_status_path, www_pm=www_pm,
www_pm_max_requests=www_pm_max_requests,
www_pm_max_children=www_pm_max_children,
www_pm_start_servers=www_pm_start_servers,
www_pm_min_spare_servers=www_pm_min_spare_servers,
www_pm_max_spare_servers=www_pm_max_spare_servers,
www_request_terminate_timeout=www_request_terminate_time,
www_xdebug_profiler_enable_trigger=www_xdebug,
debug_listen=debug_listen, debug_ping_path=debug_ping_path,
debug_pm_status_path=debug_pm_status_path,
debug_pm=debug_pm,
debug_pm_max_requests=debug_pm_max_requests,
debug_pm_max_children=debug_pm_max_children,
debug_pm_start_servers=debug_pm_start_servers,
debug_pm_min_spare_servers=debug_pm_min_spare_servers,
debug_pm_max_spare_servers=debug_pm_max_spare_servers,
debug_request_terminate_timeout=debug_request_terminate,
debug_xdebug_profiler_enable_trigger=debug_xdebug)
self.app.render((data), 'info_php.mustache')
@expose(hide=True)
def info_php82(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php8.2 -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").read
config = configparser.ConfigParser()
config.read('/etc/php/8.2/fpm/php.ini')
expose_php = config['PHP']['expose_php']
memory_limit = config['PHP']['memory_limit']
post_max_size = config['PHP']['post_max_size']
upload_max_filesize = config['PHP']['upload_max_filesize']
max_execution_time = config['PHP']['max_execution_time']
if os.path.exists('/etc/php/8.2/fpm/pool.d/www.conf'):
config.read('/etc/php/8.2/fpm/pool.d/www.conf')
else:
Log.error(self, 'php-fpm pool config not found')
if config.has_section('www'):
wconfig = config['www']
elif config.has_section('www-php82'):
wconfig = config['www-php82']
else:
Log.error(self, 'Unable to parse configuration')
www_listen = wconfig['listen']
www_ping_path = wconfig['ping.path']
www_pm_status_path = wconfig['pm.status_path']
www_pm = wconfig['pm']
www_pm_max_requests = wconfig['pm.max_requests']
www_pm_max_children = wconfig['pm.max_children']
www_pm_start_servers = wconfig['pm.start_servers']
www_pm_min_spare_servers = wconfig['pm.min_spare_servers']
www_pm_max_spare_servers = wconfig['pm.max_spare_servers']
www_request_terminate_time = (wconfig
['request_terminate_timeout'])
try:
www_xdebug = (wconfig
['php_admin_flag[xdebug.profiler_enable'
'_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
www_xdebug = 'off'
config.read('/etc/php/8.2/fpm/pool.d/debug.conf')
debug_listen = config['debug']['listen']
debug_ping_path = config['debug']['ping.path']
debug_pm_status_path = config['debug']['pm.status_path']
debug_pm = config['debug']['pm']
debug_pm_max_requests = config['debug']['pm.max_requests']
debug_pm_max_children = config['debug']['pm.max_children']
debug_pm_start_servers = config['debug']['pm.start_servers']
debug_pm_min_spare_servers = config['debug']['pm.min_spare_servers']
debug_pm_max_spare_servers = config['debug']['pm.max_spare_servers']
debug_request_terminate = (config['debug']
['request_terminate_timeout'])
try:
debug_xdebug = (config['debug']['php_admin_flag[xdebug.profiler_'
'enable_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_xdebug = 'off'
data = dict(version=version, expose_php=expose_php,
memory_limit=memory_limit, post_max_size=post_max_size,
upload_max_filesize=upload_max_filesize,
max_execution_time=max_execution_time,
www_listen=www_listen, www_ping_path=www_ping_path,
www_pm_status_path=www_pm_status_path, www_pm=www_pm,
www_pm_max_requests=www_pm_max_requests,
www_pm_max_children=www_pm_max_children,
www_pm_start_servers=www_pm_start_servers,
www_pm_min_spare_servers=www_pm_min_spare_servers,
www_pm_max_spare_servers=www_pm_max_spare_servers,
www_request_terminate_timeout=www_request_terminate_time,
www_xdebug_profiler_enable_trigger=www_xdebug,
debug_listen=debug_listen, debug_ping_path=debug_ping_path,
debug_pm_status_path=debug_pm_status_path,
debug_pm=debug_pm,
debug_pm_max_requests=debug_pm_max_requests,
debug_pm_max_children=debug_pm_max_children,
debug_pm_start_servers=debug_pm_start_servers,
debug_pm_min_spare_servers=debug_pm_min_spare_servers,
debug_pm_max_spare_servers=debug_pm_max_spare_servers,
debug_request_terminate_timeout=debug_request_terminate,
debug_xdebug_profiler_enable_trigger=debug_xdebug)
self.app.render((data), 'info_php.mustache')
@expose(hide=True)
def info_php83(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php8.3 -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").read
config = configparser.ConfigParser()
config.read('/etc/php/8.3/fpm/php.ini')
expose_php = config['PHP']['expose_php']
memory_limit = config['PHP']['memory_limit']
post_max_size = config['PHP']['post_max_size']
upload_max_filesize = config['PHP']['upload_max_filesize']
max_execution_time = config['PHP']['max_execution_time']
if os.path.exists('/etc/php/8.3/fpm/pool.d/www.conf'):
config.read('/etc/php/8.3/fpm/pool.d/www.conf')
else:
Log.error(self, 'php-fpm pool config not found')
if config.has_section('www'):
wconfig = config['www']
elif config.has_section('www-php83'):
wconfig = config['www-php83']
else:
Log.error(self, 'Unable to parse configuration')
www_listen = wconfig['listen']
www_ping_path = wconfig['ping.path']
www_pm_status_path = wconfig['pm.status_path']
www_pm = wconfig['pm']
www_pm_max_requests = wconfig['pm.max_requests']
www_pm_max_children = wconfig['pm.max_children']
www_pm_start_servers = wconfig['pm.start_servers']
www_pm_min_spare_servers = wconfig['pm.min_spare_servers']
www_pm_max_spare_servers = wconfig['pm.max_spare_servers']
www_request_terminate_time = (wconfig
['request_terminate_timeout'])
try:
www_xdebug = (wconfig
['php_admin_flag[xdebug.profiler_enable'
'_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
www_xdebug = 'off'
config.read('/etc/php/8.3/fpm/pool.d/debug.conf')
debug_listen = config['debug']['listen']
debug_ping_path = config['debug']['ping.path']
debug_pm_status_path = config['debug']['pm.status_path']
debug_pm = config['debug']['pm']
debug_pm_max_requests = config['debug']['pm.max_requests']
debug_pm_max_children = config['debug']['pm.max_children']
debug_pm_start_servers = config['debug']['pm.start_servers']
debug_pm_min_spare_servers = config['debug']['pm.min_spare_servers']
debug_pm_max_spare_servers = config['debug']['pm.max_spare_servers']
debug_request_terminate = (config['debug']
['request_terminate_timeout'])
try:
debug_xdebug = (config['debug']['php_admin_flag[xdebug.profiler_'
'enable_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_xdebug = 'off'
data = dict(version=version, expose_php=expose_php,
memory_limit=memory_limit, post_max_size=post_max_size,
upload_max_filesize=upload_max_filesize,
max_execution_time=max_execution_time,
www_listen=www_listen, www_ping_path=www_ping_path,
www_pm_status_path=www_pm_status_path, www_pm=www_pm,
www_pm_max_requests=www_pm_max_requests,
www_pm_max_children=www_pm_max_children,
www_pm_start_servers=www_pm_start_servers,
www_pm_min_spare_servers=www_pm_min_spare_servers,
www_pm_max_spare_servers=www_pm_max_spare_servers,
www_request_terminate_timeout=www_request_terminate_time,
www_xdebug_profiler_enable_trigger=www_xdebug,
debug_listen=debug_listen, debug_ping_path=debug_ping_path,
debug_pm_status_path=debug_pm_status_path,
debug_pm=debug_pm,
debug_pm_max_requests=debug_pm_max_requests,
debug_pm_max_children=debug_pm_max_children,
debug_pm_start_servers=debug_pm_start_servers,
debug_pm_min_spare_servers=debug_pm_min_spare_servers,
debug_pm_max_spare_servers=debug_pm_max_spare_servers,
debug_request_terminate_timeout=debug_request_terminate,
debug_xdebug_profiler_enable_trigger=debug_xdebug)
self.app.render((data), 'info_php.mustache')
@expose(hide=True)
def info_php84(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php8.4 -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").read
config = configparser.ConfigParser()
config.read('/etc/php/8.4/fpm/php.ini')
expose_php = config['PHP']['expose_php']
memory_limit = config['PHP']['memory_limit']
post_max_size = config['PHP']['post_max_size']
upload_max_filesize = config['PHP']['upload_max_filesize']
max_execution_time = config['PHP']['max_execution_time']
if os.path.exists('/etc/php/8.4/fpm/pool.d/www.conf'):
config.read('/etc/php/8.4/fpm/pool.d/www.conf')
else:
Log.error(self, 'php-fpm pool config not found')
if config.has_section('www'):
wconfig = config['www']
elif config.has_section('www-php84'):
wconfig = config['www-php84']
else:
Log.error(self, 'Unable to parse configuration')
www_listen = wconfig['listen']
www_ping_path = wconfig['ping.path']
www_pm_status_path = wconfig['pm.status_path']
www_pm = wconfig['pm']
www_pm_max_requests = wconfig['pm.max_requests']
www_pm_max_children = wconfig['pm.max_children']
www_pm_start_servers = wconfig['pm.start_servers']
www_pm_min_spare_servers = wconfig['pm.min_spare_servers']
www_pm_max_spare_servers = wconfig['pm.max_spare_servers']
www_request_terminate_time = (wconfig
['request_terminate_timeout'])
try:
www_xdebug = (wconfig
['php_admin_flag[xdebug.profiler_enable'
'_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
www_xdebug = 'off'
config.read('/etc/php/8.4/fpm/pool.d/debug.conf')
debug_listen = config['debug']['listen']
debug_ping_path = config['debug']['ping.path']
debug_pm_status_path = config['debug']['pm.status_path']
debug_pm = config['debug']['pm']
debug_pm_max_requests = config['debug']['pm.max_requests']
debug_pm_max_children = config['debug']['pm.max_children']
debug_pm_start_servers = config['debug']['pm.start_servers']
debug_pm_min_spare_servers = config['debug']['pm.min_spare_servers']
debug_pm_max_spare_servers = config['debug']['pm.max_spare_servers']
debug_request_terminate = (config['debug']
['request_terminate_timeout'])
try:
debug_xdebug = (config['debug']['php_admin_flag[xdebug.profiler_'
'enable_trigger]'])
except Exception as e:
Log.debug(self, "{0}".format(e))
debug_xdebug = 'off'
data = dict(version=version, expose_php=expose_php,
memory_limit=memory_limit, post_max_size=post_max_size,
upload_max_filesize=upload_max_filesize,
max_execution_time=max_execution_time,
www_listen=www_listen, www_ping_path=www_ping_path,
www_pm_status_path=www_pm_status_path, www_pm=www_pm,
www_pm_max_requests=www_pm_max_requests,
www_pm_max_children=www_pm_max_children,
www_pm_start_servers=www_pm_start_servers,
www_pm_min_spare_servers=www_pm_min_spare_servers,
www_pm_max_spare_servers=www_pm_max_spare_servers,
www_request_terminate_timeout=www_request_terminate_time,
www_xdebug_profiler_enable_trigger=www_xdebug,
debug_listen=debug_listen, debug_ping_path=debug_ping_path,
debug_pm_status_path=debug_pm_status_path,
debug_pm=debug_pm,
debug_pm_max_requests=debug_pm_max_requests,
debug_pm_max_children=debug_pm_max_children,
debug_pm_start_servers=debug_pm_start_servers,
debug_pm_min_spare_servers=debug_pm_min_spare_servers,
debug_pm_max_spare_servers=debug_pm_max_spare_servers,
debug_request_terminate_timeout=debug_request_terminate,
debug_xdebug_profiler_enable_trigger=debug_xdebug)
www_listen='LSAPI (managed by OLS)',
www_ping_path='N/A',
www_pm_status_path='N/A', www_pm='N/A',
www_pm_max_requests='N/A',
www_pm_max_children='N/A',
www_pm_start_servers='N/A',
www_pm_min_spare_servers='N/A',
www_pm_max_spare_servers='N/A',
www_request_terminate_timeout='N/A',
www_xdebug_profiler_enable_trigger='N/A',
debug_listen='N/A', debug_ping_path='N/A',
debug_pm_status_path='N/A',
debug_pm='N/A',
debug_pm_max_requests='N/A',
debug_pm_max_children='N/A',
debug_pm_start_servers='N/A',
debug_pm_min_spare_servers='N/A',
debug_pm_max_spare_servers='N/A',
debug_request_terminate_timeout='N/A',
debug_xdebug_profiler_enable_trigger='N/A')
self.app.render((data), 'info_php.mustache')
@expose(hide=True)
@@ -673,19 +211,17 @@ class WOInfoController(CementBaseController):
def default(self):
"""default function for info"""
pargs = self.app.pargs
if (not pargs.nginx and not pargs.php and
not pargs.mysql and not pargs.php74 and not pargs.php80 and
not pargs.php81 and not pargs.php82 and not pargs.php83):
if (not pargs.nginx and not pargs.php and not pargs.mysql):
pargs.nginx = True
pargs.mysql = True
pargs.php = True
if pargs.nginx:
if ((not WOAptGet.is_installed(self, 'nginx-custom')) and
(not os.path.exists('/usr/bin/nginx'))):
Log.info(self, "Nginx is not installed")
if ((not WOAptGet.is_installed(self, 'openlitespeed')) and
(not os.path.exists(WOVar.wo_ols_bin))):
Log.info(self, "OpenLiteSpeed is not installed")
else:
self.info_nginx()
self.info_ols()
if pargs.php:
self.info_php()

View File

@@ -22,7 +22,7 @@ def wo_log_hook(app):
class WOLogController(CementBaseController):
class Meta:
label = 'log'
description = 'Perform operations on Nginx, PHP and MySQL log files'
description = 'Perform operations on OpenLiteSpeed, PHP and MySQL log files'
stacked_on = 'base'
stacked_type = 'nested'
usage = "wo log [<site_name>] [options]"
@@ -35,18 +35,18 @@ class WOLogController(CementBaseController):
class WOLogShowController(CementBaseController):
class Meta:
label = 'show'
description = 'Show Nginx, PHP, MySQL log file'
description = 'Show OpenLiteSpeed, PHP, MySQL log file'
stacked_on = 'log'
stacked_type = 'nested'
arguments = [
(['--all'],
dict(help='Show All logs file', action='store_true')),
(['--nginx'],
dict(help='Show Nginx Error logs file', action='store_true')),
dict(help='Show OpenLiteSpeed Error logs file', action='store_true')),
(['--php'],
dict(help='Show PHP Error logs file', action='store_true')),
(['--fpm'],
dict(help='Show PHP-FPM slow logs file',
dict(help='Show LSPHP logs file',
action='store_true')),
(['--mysql'],
dict(help='Show MySQL logs file', action='store_true')),
@@ -54,7 +54,7 @@ class WOLogShowController(CementBaseController):
dict(help='Show Site specific WordPress logs file',
action='store_true')),
(['--access'],
dict(help='Show Nginx access log file',
dict(help='Show OpenLiteSpeed access log file',
action='store_true')),
(['site_name'],
dict(help='Website Name', nargs='?', default=None))
@@ -86,16 +86,13 @@ class WOLogShowController(CementBaseController):
self.app.pargs.mysql = True
if self.app.pargs.nginx and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*error.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/error.log"]
if self.app.pargs.access and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*access.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/access.log"]
if self.app.pargs.fpm:
#open('/var/log/php/7.2/slow.log', 'a').close()
#open('/var/log/php7.2-fpm.log', 'a').close()
self.msg = self.msg + ['/var/log/php/*/slow.log',
'/var/log/php*-fpm.log']
self.msg = self.msg + ['/usr/local/lsws/logs/lsphp*.log']
if self.app.pargs.mysql:
# MySQL debug will not work for remote MySQL
if WOVar.wo_mysql_host == "localhost":
@@ -160,18 +157,18 @@ class WOLogShowController(CementBaseController):
class WOLogResetController(CementBaseController):
class Meta:
label = 'reset'
description = 'Reset Nginx, PHP, MySQL log file'
description = 'Reset OpenLiteSpeed, PHP, MySQL log file'
stacked_on = 'log'
stacked_type = 'nested'
arguments = [
(['--all'],
dict(help='Reset All logs file', action='store_true')),
(['--nginx'],
dict(help='Reset Nginx Error logs file', action='store_true')),
dict(help='Reset OpenLiteSpeed Error logs file', action='store_true')),
(['--php'],
dict(help='Reset PHP Error logs file', action='store_true')),
(['--fpm'],
dict(help='Reset PHP-FPM slow logs file',
dict(help='Reset LSPHP logs file',
action='store_true')),
(['--mysql'],
dict(help='Reset MySQL logs file', action='store_true')),
@@ -179,7 +176,7 @@ class WOLogResetController(CementBaseController):
dict(help='Reset Site specific WordPress logs file',
action='store_true')),
(['--access'],
dict(help='Reset Nginx access log file',
dict(help='Reset OpenLiteSpeed access log file',
action='store_true')),
(['--slow-log-db'],
dict(help='Drop all rows from slowlog table in database',
@@ -225,16 +222,13 @@ class WOLogResetController(CementBaseController):
"slow_query_log.global_query_review")
if self.app.pargs.nginx and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*error.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/error.log"]
if self.app.pargs.access and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*access.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/access.log"]
if self.app.pargs.fpm:
#open('/var/log/php/7.2/slow.log', 'a').close()
#open('/var/log/php7.2-fpm.log', 'a').close()
self.msg = self.msg + ['/var/log/php/*/slow.log',
'/var/log/php*-fpm.log']
self.msg = self.msg + ['/usr/local/lsws/logs/lsphp*.log']
if self.app.pargs.mysql:
# MySQL debug will not work for remote MySQL
if WOVar.wo_mysql_host == "localhost":
@@ -302,18 +296,18 @@ class WOLogResetController(CementBaseController):
class WOLogGzipController(CementBaseController):
class Meta:
label = 'gzip'
description = 'GZip Nginx, PHP, MySQL log file'
description = 'GZip OpenLiteSpeed, PHP, MySQL log file'
stacked_on = 'log'
stacked_type = 'nested'
arguments = [
(['--all'],
dict(help='GZip All logs file', action='store_true')),
(['--nginx'],
dict(help='GZip Nginx Error logs file', action='store_true')),
dict(help='GZip OpenLiteSpeed Error logs file', action='store_true')),
(['--php'],
dict(help='GZip PHP Error logs file', action='store_true')),
(['--fpm'],
dict(help='GZip PHP-FPM slow logs file',
dict(help='GZip LSPHP logs file',
action='store_true')),
(['--mysql'],
dict(help='GZip MySQL logs file', action='store_true')),
@@ -321,7 +315,7 @@ class WOLogGzipController(CementBaseController):
dict(help='GZip Site specific WordPress logs file',
action='store_true')),
(['--access'],
dict(help='GZip Nginx access log file',
dict(help='GZip OpenLiteSpeed access log file',
action='store_true')),
(['site_name'],
dict(help='Website Name', nargs='?', default=None))
@@ -353,16 +347,13 @@ class WOLogGzipController(CementBaseController):
self.app.pargs.mysql = True
if self.app.pargs.nginx and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*error.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/error.log"]
if self.app.pargs.access and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*access.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/access.log"]
if self.app.pargs.fpm:
#open('/var/log/php/7.2/slow.log', 'a').close()
#open('/var/log/php7.2-fpm.log', 'a').close()
self.msg = self.msg + ['/var/log/php/*/slow.log',
'/var/log/php*-fpm.log']
self.msg = self.msg + ['/usr/local/lsws/logs/lsphp*.log']
if self.app.pargs.mysql:
# MySQL debug will not work for remote MySQL
if WOVar.wo_mysql_host == "localhost":
@@ -436,19 +427,19 @@ class WOLogGzipController(CementBaseController):
class WOLogMailController(CementBaseController):
class Meta:
label = 'mail'
description = 'Mail Nginx, PHP, MySQL log file'
description = 'Mail OpenLiteSpeed, PHP, MySQL log file'
stacked_on = 'log'
stacked_type = 'nested'
arguments = [
(['--all'],
dict(help='Mail All logs file', action='store_true')),
(['--nginx'],
dict(help='Mail Nginx Error logs file', action='store_true')),
dict(help='Mail OpenLiteSpeed Error logs file', action='store_true')),
(['--php'],
dict(help='Mail PHP Error logs file',
action='store_true')),
(['--fpm'],
dict(help='Mail PHP fpm slow logs file',
dict(help='Mail LSPHP logs file',
action='store_true')),
(['--mysql'],
dict(help='Mail MySQL logs file', action='store_true')),
@@ -456,7 +447,7 @@ class WOLogMailController(CementBaseController):
dict(help='Mail Site specific WordPress logs file',
action='store_true')),
(['--access'],
dict(help='Mail Nginx access log file',
dict(help='Mail OpenLiteSpeed access log file',
action='store_true')),
(['site_name'],
dict(help='Website Name', nargs='?', default=None)),
@@ -491,16 +482,13 @@ class WOLogMailController(CementBaseController):
self.app.pargs.mysql = True
if self.app.pargs.nginx and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*error.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/error.log"]
if self.app.pargs.access and (not self.app.pargs.site_name):
self.msg = self.msg + ["/var/log/nginx/*access.log"]
self.msg = self.msg + ["/usr/local/lsws/logs/access.log"]
if self.app.pargs.fpm:
#open('/var/log/php/7.2/slow.log', 'a').close()
#open('/var/log/php7.2-fpm.log', 'a').close()
self.msg = self.msg + ['/var/log/php/*/slow.log',
'/var/log/php*-fpm.log']
self.msg = self.msg + ['/usr/local/lsws/logs/lsphp*.log']
if self.app.pargs.mysql:
# MySQL debug will not work for remote MySQL
if WOVar.wo_mysql_host == "localhost":

View File

@@ -1,5 +1,6 @@
import getpass
import os
import shutil
from cement.core.controller import CementBaseController, expose
@@ -40,6 +41,12 @@ class WOSecureController(CementBaseController):
(['--allowpassword'], dict(
help='allow password authentification '
'when hardening ssh security', action='store_true')),
(['--lockdown'], dict(
help='enable WP Fort Knox lockdown on a site',
action='store_true')),
(['--unlock'], dict(
help='disable WP Fort Knox lockdown on a site',
action='store_true')),
(['--force'],
dict(help='force execution without being prompt',
action='store_true')),
@@ -62,12 +69,16 @@ class WOSecureController(CementBaseController):
self.secure_ssh_port()
if pargs.ssh:
self.secure_ssh()
if pargs.lockdown:
self.secure_lockdown()
if pargs.unlock:
self.secure_unlock()
@expose(hide=True)
def secure_auth(self):
"""This function secures authentication"""
WOGit.add(self, ["/etc/nginx"],
msg="Add Nginx to into Git")
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Add OLS config to Git")
pargs = self.app.pargs
passwd = RANDOM.long(self)
if not pargs.user_input:
@@ -82,25 +93,21 @@ class WOSecureController(CementBaseController):
pargs.user_pass = password
if password == "":
pargs.user_pass = passwd
Log.debug(self, "printf username:"
"$(openssl passwd --apr1 "
"password 2> /dev/null)\n\""
"> /etc/nginx/htpasswd-wo 2>/dev/null")
WOShellExec.cmd_exec(self, "printf \"{username}:"
"$(openssl passwd -apr1 "
"{password} 2> /dev/null)\n\""
"> /etc/nginx/htpasswd-wo 2>/dev/null"
.format(username=pargs.user_input,
password=pargs.user_pass),
log=False)
WOGit.add(self, ["/etc/nginx"],
# Set OLS admin password using admpass.sh
WOShellExec.cmd_exec(
self, "/usr/local/lsws/admin/misc/admpass.sh "
"{username} {password}"
.format(username=pargs.user_input,
password=pargs.user_pass),
log=False)
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Adding changed secure auth into Git")
@expose(hide=True)
def secure_port(self):
"""This function Secures port"""
WOGit.add(self, ["/etc/nginx"],
msg="Add Nginx to into Git")
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Add OLS config to Git")
pargs = self.app.pargs
if pargs.user_input:
while ((not pargs.user_input.isdigit()) and
@@ -117,25 +124,27 @@ class WOSecureController(CementBaseController):
Log.info(self, "Please Enter valid port number :")
port = input("WordOps admin port [22222]:")
pargs.user_input = port
data = dict(release=WOVar.wo_version,
port=pargs.user_input, webroot='/var/www/')
WOTemplate.deploy(
self, '/etc/nginx/sites-available/22222',
'22222.mustache', data)
WOGit.add(self, ["/etc/nginx"],
# Update OLS backend listener port
httpd_conf = '{0}/httpd_config.conf'.format(WOVar.wo_ols_conf_dir)
if os.path.isfile(httpd_conf):
WOFileUtils.searchreplace(
self, httpd_conf,
'address *:22222',
'address *:{0}'.format(pargs.user_input))
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Adding changed secure port into Git")
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with `{0} -t` command"
.format(WOVar.wo_ols_bin))
Log.info(self, "Successfully port changed {port}"
.format(port=pargs.user_input))
@expose(hide=True)
def secure_ip(self):
"""IP whitelisting"""
if os.path.exists('/etc/nginx'):
WOGit.add(self, ["/etc/nginx"],
msg="Add Nginx to into Git")
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Add OLS config to Git")
pargs = self.app.pargs
if not pargs.user_input:
ip = input("Enter the comma separated IP addresses "
@@ -146,17 +155,98 @@ class WOSecureController(CementBaseController):
except Exception as e:
Log.debug(self, "{0}".format(e))
user_ip = ['127.0.0.1']
for ip_addr in user_ip:
if not ("exist_ip_address " + ip_addr in open('/etc/nginx/common/'
'acl.conf').read()):
WOShellExec.cmd_exec(self, "sed -i "
"\"/deny/i allow {whitelist_address}\;\""
" /etc/nginx/common/acl.conf"
.format(whitelist_address=ip_addr))
WOGit.add(self, ["/etc/nginx"],
# Update OLS ACL configuration
acl_conf = '{0}/22222/vhconf.conf'.format(WOVar.wo_ols_vhost_dir)
if os.path.isfile(acl_conf):
for ip_addr in user_ip:
ip_addr = ip_addr.strip()
if not WOFileUtils.grepcheck(self, acl_conf, ip_addr):
WOFileUtils.searchreplace(
self, acl_conf,
'allowList',
'allowList\n {0}'.format(ip_addr))
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Adding changed secure ip into Git")
Log.info(self, "Successfully added IP address in access control")
Log.info(self, "Successfully added IP address in acl.conf file")
@expose(hide=True)
def secure_lockdown(self):
"""Enable WP Fort Knox lockdown on a WordPress site"""
pargs = self.app.pargs
if not pargs.user_input:
site_name = input("Enter the site name to lockdown: ")
pargs.user_input = site_name
site_name = pargs.user_input
webroot = '{0}{1}'.format(WOVar.wo_webroot, site_name)
mu_plugins_dir = '{0}/htdocs/wp-content/mu-plugins'.format(webroot)
fort_knox_src = '/var/lib/wo/wp-fort-knox.php'
if not os.path.isdir(webroot):
Log.error(self, "Site {0} not found".format(site_name))
# Check if it's a WordPress site
if not os.path.isfile(
'{0}/htdocs/wp-config.php'.format(webroot)):
Log.error(self, "Site {0} is not a WordPress site"
.format(site_name))
# Check if Fort Knox source exists
if not os.path.isfile(fort_knox_src):
Log.error(self, "WP Fort Knox plugin not found at {0}. "
"Please reinstall WordOps.".format(fort_knox_src))
# Create mu-plugins directory if it doesn't exist
if not os.path.isdir(mu_plugins_dir):
WOFileUtils.mkdir(self, mu_plugins_dir)
fort_knox_dest = '{0}/wp-fort-knox.php'.format(mu_plugins_dir)
if os.path.isfile(fort_knox_dest):
Log.info(self, "WP Fort Knox is already enabled for {0}"
.format(site_name))
return
Log.wait(self, "Enabling WP Fort Knox lockdown")
shutil.copy2(fort_knox_src, fort_knox_dest)
WOFileUtils.chown(
self, fort_knox_dest,
WOVar.wo_php_user, WOVar.wo_php_user)
Log.valide(self, "Enabling WP Fort Knox lockdown")
Log.info(self, "WP Fort Knox enabled for {0}\n"
" File modifications and plugin management "
"are now disabled in wp-admin.\n"
" Use WP-CLI for all administrative tasks.\n"
" To disable: wo secure --unlock {0}"
.format(site_name))
@expose(hide=True)
def secure_unlock(self):
"""Disable WP Fort Knox lockdown on a WordPress site"""
pargs = self.app.pargs
if not pargs.user_input:
site_name = input("Enter the site name to unlock: ")
pargs.user_input = site_name
site_name = pargs.user_input
webroot = '{0}{1}'.format(WOVar.wo_webroot, site_name)
fort_knox_path = ('{0}/htdocs/wp-content/mu-plugins/'
'wp-fort-knox.php'.format(webroot))
if not os.path.isdir(webroot):
Log.error(self, "Site {0} not found".format(site_name))
if not os.path.isfile(fort_knox_path):
Log.info(self, "WP Fort Knox is not enabled for {0}"
.format(site_name))
return
Log.wait(self, "Disabling WP Fort Knox lockdown")
WOFileUtils.rm(self, fort_knox_path)
Log.valide(self, "Disabling WP Fort Knox lockdown")
Log.info(self, "WP Fort Knox disabled for {0}\n"
" Plugin management is now available in wp-admin."
.format(site_name))
@expose(hide=True)
def secure_ssh(self):

View File

@@ -4,7 +4,8 @@ import subprocess
from cement.core.controller import CementBaseController, expose
from wo.cli.plugins.site_functions import (
check_domain_exists, deleteDB, deleteWebRoot, removeNginxConf, logwatch)
check_domain_exists, deleteDB, deleteWebRoot, removeOLSConf, logwatch,
addOLSListenerMap, removeOLSListenerMap)
from wo.cli.plugins.sitedb import (deleteSiteInfo, getAllsites,
getSiteInfo, updateSiteInfo)
from wo.cli.plugins.site_create import WOSiteCreateController
@@ -61,24 +62,20 @@ class WOSiteController(CementBaseController):
# check if site exists
if not check_domain_exists(self, wo_domain):
Log.error(self, "site {0} does not exist".format(wo_domain))
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
if os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.info(self, "Enable domain {0:10} \t".format(wo_domain), end='')
WOFileUtils.create_symlink(self,
['/etc/nginx/sites-available/{0}'
.format(wo_domain),
'/etc/nginx/sites-enabled/{0}'
.format(wo_domain)])
WOGit.add(self, ["/etc/nginx"],
addOLSListenerMap(self, wo_domain)
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Enabled {0} "
.format(wo_domain))
updateSiteInfo(self, wo_domain, enabled=True)
Log.info(self, "[" + Log.ENDC + "OK" + Log.OKBLUE + "]")
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service OpenLiteSpeed reload failed. "
"check issues with OpenLiteSpeed configuration")
else:
Log.error(self, 'nginx configuration file does not exist')
Log.error(self, 'OpenLiteSpeed vhost configuration does not exist')
@expose(help="Disable site example.com")
def disable(self):
@@ -98,28 +95,21 @@ class WOSiteController(CementBaseController):
if not check_domain_exists(self, wo_domain):
Log.error(self, "site {0} does not exist".format(wo_domain))
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
if os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.info(self, "Disable domain {0:10} \t"
.format(wo_domain), end='')
if not os.path.isfile('/etc/nginx/sites-enabled/{0}'
.format(wo_domain)):
Log.debug(self, "Site {0} already disabled".format(wo_domain))
Log.info(self, "[" + Log.FAIL + "Failed" + Log.OKBLUE + "]")
else:
WOFileUtils.remove_symlink(self,
'/etc/nginx/sites-enabled/{0}'
.format(wo_domain))
WOGit.add(self, ["/etc/nginx"],
msg="Disabled {0} "
.format(wo_domain))
updateSiteInfo(self, wo_domain, enabled=False)
Log.info(self, "[" + Log.ENDC + "OK" + Log.OKBLUE + "]")
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
removeOLSListenerMap(self, wo_domain)
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Disabled {0} "
.format(wo_domain))
updateSiteInfo(self, wo_domain, enabled=False)
Log.info(self, "[" + Log.ENDC + "OK" + Log.OKBLUE + "]")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service OpenLiteSpeed reload failed. "
"check issues with OpenLiteSpeed configuration")
else:
Log.error(self, "nginx configuration file does not exist")
Log.error(self, "OpenLiteSpeed vhost configuration does not exist")
@expose(help="Get example.com information")
def info(self):
@@ -142,8 +132,8 @@ class WOSiteController(CementBaseController):
if not check_domain_exists(self, wo_domain):
Log.error(self, "site {0} does not exist".format(wo_domain))
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
if os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
siteinfo = getSiteInfo(self, wo_domain)
sitetype = siteinfo.site_type
cachetype = siteinfo.cache_type
@@ -175,7 +165,7 @@ class WOSiteController(CementBaseController):
"disabled"))
self.app.render((data), 'siteinfo.mustache')
else:
Log.error(self, "nginx configuration file does not exist")
Log.error(self, "OpenLiteSpeed vhost configuration does not exist")
@expose(help="Monitor example.com logs")
def log(self):
@@ -190,7 +180,7 @@ class WOSiteController(CementBaseController):
if logfiles:
logwatch(self, logfiles)
@expose(help="Display Nginx configuration of example.com")
@expose(help="Display OpenLiteSpeed configuration of example.com")
def show(self):
pargs = self.app.pargs
if not pargs.site_name:
@@ -208,17 +198,18 @@ class WOSiteController(CementBaseController):
if not check_domain_exists(self, wo_domain):
Log.error(self, "site {0} does not exist".format(wo_domain))
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
Log.info(self, "Display NGINX configuration for {0}"
if os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.info(self, "Display OpenLiteSpeed configuration for {0}"
.format(wo_domain))
f = open('/etc/nginx/sites-available/{0}'.format(wo_domain),
f = open('{0}/{1}/vhconf.conf'
.format(WOVar.wo_ols_vhost_dir, wo_domain),
encoding='utf-8', mode='r')
text = f.read()
Log.info(self, Log.ENDC + text)
f.close()
else:
Log.error(self, "nginx configuration file does not exists")
Log.error(self, "OpenLiteSpeed vhost configuration does not exist")
@expose(help="Change directory to site webroot")
def cd(self):
@@ -255,7 +246,7 @@ class WOSiteEditController(CementBaseController):
label = 'edit'
stacked_on = 'site'
stacked_type = 'nested'
description = ('Edit Nginx configuration of site')
description = ('Edit OpenLiteSpeed configuration of site')
arguments = [
(['site_name'],
dict(help='domain name for the site',
@@ -279,25 +270,28 @@ class WOSiteEditController(CementBaseController):
if not check_domain_exists(self, wo_domain):
Log.error(self, "site {0} does not exist".format(wo_domain))
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
if os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
try:
WOShellExec.invoke_editor(self, '/etc/nginx/sites-availa'
'ble/{0}'.format(wo_domain))
WOShellExec.invoke_editor(self, '{0}/{1}/vhconf.conf'
.format(WOVar.wo_ols_vhost_dir,
wo_domain))
except CommandExecutionError as e:
Log.debug(self, str(e))
Log.error(self, "Failed invoke editor")
if (WOGit.checkfilestatus(self, "/etc/nginx",
'/etc/nginx/sites-available/{0}'
.format(wo_domain))):
WOGit.add(self, ["/etc/nginx"], msg="Edit website: {0}"
if (WOGit.checkfilestatus(self, WOVar.wo_ols_conf_dir,
'{0}/{1}/vhconf.conf'
.format(WOVar.wo_ols_vhost_dir,
wo_domain))):
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Edit website: {0}"
.format(wo_domain))
# Reload NGINX
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
# Reload OpenLiteSpeed
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service OpenLiteSpeed reload failed. "
"check issues with OpenLiteSpeed configuration")
else:
Log.error(self, "nginx configuration file does not exists")
Log.error(self, "OpenLiteSpeed vhost configuration does not exist")
class WOSiteDeleteController(CementBaseController):
@@ -340,7 +334,7 @@ class WOSiteDeleteController(CementBaseController):
wo_domain = WODomain.validate(self, pargs.site_name)
wo_db_name = ''
wo_prompt = ''
wo_nginx_prompt = ''
wo_ols_prompt = ''
mark_db_delete_prompt = False
mark_webroot_delete_prompt = False
mark_db_deleted = False
@@ -430,8 +424,8 @@ class WOSiteDeleteController(CementBaseController):
if not pargs.force:
if (mark_webroot_deleted and mark_db_deleted):
# TODO Delete nginx conf
removeNginxConf(self, wo_domain)
# TODO Delete OLS conf
removeOLSConf(self, wo_domain)
deleteSiteInfo(self, wo_domain)
WOAcme.removeconf(self, wo_domain)
Log.info(self, "Deleted site {0}".format(wo_domain))
@@ -441,12 +435,13 @@ class WOSiteDeleteController(CementBaseController):
else:
if (mark_db_delete_prompt or mark_webroot_delete_prompt or
(mark_webroot_deleted and mark_db_deleted)):
# TODO Delete nginx conf
removeNginxConf(self, wo_domain)
# TODO Delete OLS conf
removeOLSConf(self, wo_domain)
deleteSiteInfo(self, wo_domain)
# To improve
if not WOFileUtils.grepcheck(
self, '/var/www/22222/conf/nginx/ssl.conf', wo_domain):
self, '{0}/22222/vhconf.conf'
.format(WOVar.wo_ols_vhost_dir), wo_domain):
WOAcme.removeconf(self, wo_domain)
Log.info(self, "Deleted site {0}".format(wo_domain))

View File

@@ -12,7 +12,7 @@ from wo.core.acme import WOAcme
from wo.core.domainvalidate import WODomain
from wo.core.git import WOGit
from wo.core.logging import Log
from wo.core.nginxhashbucket import hashbucket
from wo.core.fileutils import WOFileUtils
from wo.core.services import WOService
from wo.core.sslutils import SSL
from wo.core.variables import WOVar
@@ -67,19 +67,18 @@ class WOSiteBackupController(CementBaseController):
if not check_domain_exists(self, wo_domain):
Log.error(self, "site {0} already exists".format(wo_domain))
elif os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
Log.error(self, "Nginx configuration /etc/nginx/sites-available/"
"{0} already exists".format(wo_domain))
elif os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.error(self, "OLS vhost configuration already exists "
"for {0}".format(wo_domain))
try:
try:
# setup NGINX configuration, and webroot
# setup OLS configuration, and webroot
setupdomain(self, data)
# Fix Nginx Hashbucket size error
hashbucket(self)
pass
except SiteError as e:
# call cleanup actions on failure
Log.info(self, Log.FAIL +
@@ -94,15 +93,15 @@ class WOSiteBackupController(CementBaseController):
if 'proxy' in data.keys() and data['proxy']:
addNewSite(self, wo_domain, stype, cache, wo_site_webroot)
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain)
deleteSiteInfo(self, wo_domain)
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
Log.error(self, "service lsws reload failed. "
"check issues with `{0} -t` command".format(WOVar.wo_ols_bin))
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
@@ -206,8 +205,8 @@ class WOSiteBackupController(CementBaseController):
"`tail /var/log/wo/wordops.log` "
"and please try again")
# Service Nginx Reload call cleanup if failed to reload nginx
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload call cleanup if failed to reload lsws
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
@@ -219,13 +218,13 @@ class WOSiteBackupController(CementBaseController):
dbuser=data['wo_db_user'],
dbhost=data['wo_mysql_grant_host'])
deleteSiteInfo(self, wo_domain)
Log.info(self, Log.FAIL + "service nginx reload failed."
" check issues with `nginx -t` command.")
Log.info(self, Log.FAIL + "service lsws reload failed."
" check issues with `{0} -t` command.".format(WOVar.wo_ols_bin))
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
WOGit.add(self, ["/etc/nginx"],
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="{0} created with {1} {2}"
.format(wo_www_domain, stype, cache))
# Setup Permissions for webroot
@@ -367,14 +366,14 @@ class WOSiteBackupController(CementBaseController):
SSL.httpsredirect(self, wo_domain, acme_domains, True)
SSL.siteurlhttps(self, wo_domain)
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with `{0} -t` command".format(WOVar.wo_ols_bin))
Log.info(self, "Congratulations! Successfully Configured "
"SSL on https://{0}".format(wo_domain))
# Add nginx conf folder into GIT
WOGit.add(self, ["{0}/conf/nginx".format(wo_site_webroot)],
# Add OLS conf folder into GIT
WOGit.add(self, ["{0}/{1}".format(WOVar.wo_ols_vhost_dir, wo_domain)],
msg="Adding letsencrypts config of site: {0}"
.format(wo_domain))
updateSiteInfo(self, wo_domain, ssl=letsencrypt)

View File

@@ -12,7 +12,7 @@ from wo.core.acme import WOAcme
from wo.core.domainvalidate import WODomain
from wo.core.git import WOGit
from wo.core.logging import Log
from wo.core.nginxhashbucket import hashbucket
from wo.core.fileutils import WOFileUtils
from wo.core.services import WOService
from wo.core.sslutils import SSL
from wo.core.variables import WOVar
@@ -54,7 +54,7 @@ class WOSiteCloneController(CementBaseController):
action='store_true')),
(['--wpfc'],
dict(help="create WordPress single/multi site with "
"Nginx fastcgi_cache",
"LSCache",
action='store_true')),
(['--wpsc'],
dict(help="create WordPress single/multi site with wpsc cache",
@@ -153,10 +153,10 @@ class WOSiteCloneController(CementBaseController):
if check_domain_exists(self, wo_domain):
Log.error(self, "site {0} already exists".format(wo_domain))
elif os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
Log.error(self, "Nginx configuration /etc/nginx/sites-available/"
"{0} already exists".format(wo_domain))
elif os.path.isdir('{0}/{1}'
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.error(self, "OLS vhost configuration already exists "
"for {0}".format(wo_domain))
if stype == 'proxy':
data = dict(
@@ -262,15 +262,14 @@ class WOSiteCloneController(CementBaseController):
pre_run_checks(self)
except SiteError as e:
Log.debug(self, str(e))
Log.error(self, "NGINX configuration check failed.")
Log.error(self, "OLS configuration check failed.")
try:
try:
# setup NGINX configuration, and webroot
# setup OLS configuration, and webroot
setupdomain(self, data)
# Fix Nginx Hashbucket size error
hashbucket(self)
pass
except SiteError as e:
# call cleanup actions on failure
Log.info(self, Log.FAIL +
@@ -285,15 +284,15 @@ class WOSiteCloneController(CementBaseController):
if 'proxy' in data.keys() and data['proxy']:
addNewSite(self, wo_domain, stype, cache, wo_site_webroot)
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain)
deleteSiteInfo(self, wo_domain)
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
Log.error(self, "service lsws reload failed. "
"check issues with `{0} -t` command".format(WOVar.wo_ols_bin))
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
@@ -397,8 +396,8 @@ class WOSiteCloneController(CementBaseController):
"`tail /var/log/wo/wordops.log` "
"and please try again")
# Service Nginx Reload call cleanup if failed to reload nginx
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload call cleanup if failed to reload lsws
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
@@ -410,13 +409,13 @@ class WOSiteCloneController(CementBaseController):
dbuser=data['wo_db_user'],
dbhost=data['wo_mysql_grant_host'])
deleteSiteInfo(self, wo_domain)
Log.info(self, Log.FAIL + "service nginx reload failed."
" check issues with `nginx -t` command.")
Log.info(self, Log.FAIL + "service lsws reload failed."
" check issues with `{0} -t` command.".format(WOVar.wo_ols_bin))
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
WOGit.add(self, ["/etc/nginx"],
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="{0} created with {1} {2}"
.format(wo_www_domain, stype, cache))
# Setup Permissions for webroot
@@ -558,14 +557,14 @@ class WOSiteCloneController(CementBaseController):
SSL.httpsredirect(self, wo_domain, acme_domains, True)
SSL.siteurlhttps(self, wo_domain)
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with `{0} -t` command".format(WOVar.wo_ols_bin))
Log.info(self, "Congratulations! Successfully Configured "
"SSL on https://{0}".format(wo_domain))
# Add nginx conf folder into GIT
WOGit.add(self, ["{0}/conf/nginx".format(wo_site_webroot)],
# Add OLS conf folder into GIT
WOGit.add(self, ["{0}/{1}".format(WOVar.wo_ols_vhost_dir, wo_domain)],
msg="Adding letsencrypts config of site: {0}"
.format(wo_domain))
updateSiteInfo(self, wo_domain, ssl=letsencrypt)

View File

@@ -12,7 +12,6 @@ from wo.core.acme import WOAcme
from wo.core.domainvalidate import WODomain
from wo.core.git import WOGit
from wo.core.logging import Log
from wo.core.nginxhashbucket import hashbucket
from wo.core.services import WOService
from wo.core.sslutils import SSL
from wo.core.variables import WOVar
@@ -46,7 +45,7 @@ class WOSiteCreateController(CementBaseController):
action='store_true')),
(['--wpfc'],
dict(help="create WordPress single/multi site with "
"Nginx fastcgi_cache",
"LSCache",
action='store_true')),
(['--wpsc'],
dict(help="create WordPress single/multi site with wpsc cache",
@@ -85,9 +84,6 @@ class WOSiteCreateController(CementBaseController):
(['--hsts'],
dict(help="enable HSTS for site secured with letsencrypt",
action='store_true')),
(['--ngxblocker'],
dict(help="enable HSTS for site secured with letsencrypt",
action='store_true')),
(['--user'],
dict(help="provide user for WordPress site")),
(['--email'],
@@ -169,10 +165,10 @@ class WOSiteCreateController(CementBaseController):
if check_domain_exists(self, wo_domain):
Log.error(self, "site {0} already exists".format(wo_domain))
elif os.path.isfile('/etc/nginx/sites-available/{0}'
.format(wo_domain)):
Log.error(self, "Nginx configuration /etc/nginx/sites-available/"
"{0} already exists".format(wo_domain))
elif os.path.isdir('{0}/{1}'.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.error(self, "OpenLiteSpeed vhost configuration "
"{0}/{1} already exists"
.format(WOVar.wo_ols_vhost_dir, wo_domain))
if stype == 'proxy':
data = dict(
@@ -225,7 +221,7 @@ class WOSiteCreateController(CementBaseController):
data['subsiteof_webroot'] = parent_site_info.site_path
if (pargs.php74 or pargs.php80 or pargs.php81 or
pargs.php82 or pargs.php83 or pargs.php84):
pargs.php82 or pargs.php83 or pargs.php84 or pargs.php85):
data = dict(
site_name=wo_domain, www_domain=wo_www_domain,
static=False, basic=False,
@@ -311,15 +307,13 @@ class WOSiteCreateController(CementBaseController):
pre_run_checks(self)
except SiteError as e:
Log.debug(self, str(e))
Log.error(self, "NGINX configuration check failed.")
Log.error(self, "OpenLiteSpeed configuration check failed.")
try:
try:
# setup NGINX configuration, and webroot
# setup OpenLiteSpeed configuration, and webroot
setupdomain(self, data)
# Fix Nginx Hashbucket size error
hashbucket(self)
except SiteError as e:
# call cleanup actions on failure
Log.info(self, Log.FAIL +
@@ -334,15 +328,15 @@ class WOSiteCreateController(CementBaseController):
if 'proxy' in data.keys() and data['proxy']:
addNewSite(self, wo_domain, stype, cache, wo_site_webroot)
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain)
deleteSiteInfo(self, wo_domain)
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
@@ -354,15 +348,15 @@ class WOSiteCreateController(CementBaseController):
elif 'alias' in data.keys() and data['alias']:
addNewSite(self, wo_domain, stype, cache, wo_site_webroot)
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain)
deleteSiteInfo(self, wo_domain)
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
@@ -374,15 +368,15 @@ class WOSiteCreateController(CementBaseController):
elif 'subsite' in data.keys() and data['subsite']:
addNewSite(self, wo_domain, stype, cache, wo_site_webroot)
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain)
deleteSiteInfo(self, wo_domain)
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
@@ -481,8 +475,8 @@ class WOSiteCreateController(CementBaseController):
"`tail /var/log/wo/wordops.log` "
"and please try again")
# Service Nginx Reload call cleanup if failed to reload nginx
if not WOService.reload_service(self, 'nginx'):
# Service OpenLiteSpeed Reload call cleanup if failed to reload lsws
if not WOService.reload_service(self, 'lsws'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
@@ -494,13 +488,13 @@ class WOSiteCreateController(CementBaseController):
dbuser=data['wo_db_user'],
dbhost=data['wo_mysql_grant_host'])
deleteSiteInfo(self, wo_domain)
Log.info(self, Log.FAIL + "service nginx reload failed."
" check issues with `nginx -t` command.")
Log.info(self, Log.FAIL + "service lsws reload failed."
" check issues with OpenLiteSpeed config.")
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
WOGit.add(self, ["/etc/nginx"],
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="{0} created with {1} {2}"
.format(wo_www_domain, stype, cache))
# Setup Permissions for webroot
@@ -642,14 +636,14 @@ class WOSiteCreateController(CementBaseController):
SSL.httpsredirect(self, wo_domain, acme_domains, True)
SSL.siteurlhttps(self, wo_domain)
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
Log.info(self, "Congratulations! Successfully Configured "
"SSL on https://{0}".format(wo_domain))
# Add nginx conf folder into GIT
WOGit.add(self, ["{0}/conf/nginx".format(wo_site_webroot)],
# Add OLS vhost conf folder into GIT
WOGit.add(self, ["{0}/{1}".format(WOVar.wo_ols_vhost_dir, wo_domain)],
msg="Adding letsencrypts config of site: {0}"
.format(wo_domain))
updateSiteInfo(self, wo_domain, ssl=letsencrypt)

View File

@@ -37,17 +37,17 @@ class SiteError(Exception):
def pre_run_checks(self):
# Check nginx configuration
# Check OpenLiteSpeed configuration
Log.wait(self, "Running pre-run checks")
try:
Log.debug(self, "checking NGINX configuration ...")
Log.debug(self, "checking OpenLiteSpeed configuration ...")
fnull = open('/dev/null', 'w')
subprocess.check_call(["/usr/sbin/nginx", "-t"], stdout=fnull,
subprocess.check_call([WOVar.wo_ols_bin, "-t"], stdout=fnull,
stderr=subprocess.STDOUT)
except CalledProcessError as e:
Log.failed(self, "Running pre-update checks")
Log.debug(self, "{0}".format(str(e)))
raise SiteError("nginx configuration check failed.")
raise SiteError("OpenLiteSpeed configuration check failed.")
else:
Log.valide(self, "Running pre-update checks")
@@ -58,55 +58,133 @@ def check_domain_exists(self, domain):
return False
def setupdomain(self, data):
def addOLSVhost(self, domain, webroot):
"""Add virtualHost block and listener maps to httpd_config.conf"""
httpd_conf = '{0}/httpd_config.conf'.format(WOVar.wo_ols_conf_dir)
# for debug purpose
# for key, value in data.items() :
# print (key, value)
vhost_block = (
'\nvirtualHost {domain} {{\n'
' vhRoot {webroot}\n'
' configFile {vhost_dir}/{domain}/vhconf.conf\n'
' allowSymbolLink 1\n'
' enableScript 1\n'
' restrained 0\n'
'}}\n'
).format(domain=domain, webroot=webroot,
vhost_dir=WOVar.wo_ols_vhost_dir)
with open(httpd_conf, 'a') as f:
f.write(vhost_block)
addOLSListenerMap(self, domain)
def addOLSListenerMap(self, domain):
"""Add map entries for domain to listener blocks in httpd_config.conf"""
httpd_conf = '{0}/httpd_config.conf'.format(WOVar.wo_ols_conf_dir)
map_line = ' map {0} {0}\n'.format(domain)
with open(httpd_conf, 'r') as f:
lines = f.readlines()
new_lines = []
in_listener = False
for line in lines:
if line.strip().startswith('listener '):
in_listener = True
if in_listener and line.strip() == '}':
# Check if map for this domain already exists
if not any(domain in l and 'map' in l for l in new_lines):
new_lines.append(map_line)
in_listener = False
new_lines.append(line)
with open(httpd_conf, 'w') as f:
f.writelines(new_lines)
def removeOLSListenerMap(self, domain):
"""Remove map entries for domain from listener blocks"""
httpd_conf = '{0}/httpd_config.conf'.format(WOVar.wo_ols_conf_dir)
with open(httpd_conf, 'r') as f:
lines = f.readlines()
with open(httpd_conf, 'w') as f:
for line in lines:
if 'map' in line and domain in line:
continue
f.write(line)
def removeOLSVhost(self, domain):
"""Remove virtualHost block and listener maps from httpd_config.conf"""
httpd_conf = '{0}/httpd_config.conf'.format(WOVar.wo_ols_conf_dir)
removeOLSListenerMap(self, domain)
# Remove virtualHost block
with open(httpd_conf, 'r') as f:
lines = f.readlines()
in_vhost_block = False
new_lines = []
for line in lines:
if line.strip().startswith('virtualHost') and domain in line:
in_vhost_block = True
continue
if in_vhost_block:
if line.strip() == '}':
in_vhost_block = False
continue
else:
new_lines.append(line)
with open(httpd_conf, 'w') as f:
f.writelines(new_lines)
def setupdomain(self, data):
wo_domain_name = data['site_name']
wo_site_webroot = data['webroot']
# Check if nginx configuration already exists
# if os.path.isfile('/etc/nginx/sites-available/{0}'
# .format(wo_domain_name)):
# raise SiteError("nginx configuration already exists for site")
Log.info(self, "Setting up NGINX configuration \t", end='')
# write nginx config for file
Log.info(self, "Setting up OpenLiteSpeed configuration \t", end='')
# Create OLS vhost directory and write vhconf.conf
try:
wo_site_nginx_conf = open('/etc/nginx/sites-available/{0}'
.format(wo_domain_name), encoding='utf-8',
mode='w')
self.app.render((data), 'virtualconf.mustache',
out=wo_site_nginx_conf)
wo_site_nginx_conf.close()
vhost_dir = '{0}/{1}'.format(WOVar.wo_ols_vhost_dir, wo_domain_name)
if not os.path.exists(vhost_dir):
os.makedirs(vhost_dir)
wo_site_ols_conf = open('{0}/vhconf.conf'.format(vhost_dir),
encoding='utf-8', mode='w')
self.app.render((data), 'ols-vhost.mustache',
out=wo_site_ols_conf)
wo_site_ols_conf.close()
except IOError as e:
Log.debug(self, str(e))
raise SiteError("create nginx configuration failed for site")
raise SiteError("create OpenLiteSpeed configuration failed for site")
except Exception as e:
Log.debug(self, str(e))
raise SiteError("create nginx configuration failed for site")
raise SiteError("create OpenLiteSpeed configuration failed for site")
finally:
# Check nginx -t and return status over it
# Check OLS config and return status
try:
Log.debug(self, "Checking generated nginx conf, please wait...")
Log.debug(self, "Checking generated OLS conf, please wait...")
fnull = open('/dev/null', 'w')
subprocess.check_call(["/usr/sbin/nginx", "-t"], stdout=fnull,
subprocess.check_call([WOVar.wo_ols_bin, "-t"], stdout=fnull,
stderr=subprocess.STDOUT)
Log.info(self, "[" + Log.ENDC + "Done" + Log.OKBLUE + "]")
except CalledProcessError as e:
Log.debug(self, "{0}".format(str(e)))
Log.info(self, "[" + Log.ENDC + Log.FAIL + "Fail" +
Log.OKBLUE + "]")
raise SiteError("created nginx configuration failed for site."
" check with `nginx -t`")
raise SiteError("created OpenLiteSpeed configuration failed "
"for site. check with `{0} -t`"
.format(WOVar.wo_ols_bin))
# create symbolic link for
WOFileUtils.create_symlink(self, ['/etc/nginx/sites-available/{0}'
.format(wo_domain_name),
'/etc/nginx/sites-enabled/{0}'
.format(wo_domain_name)])
# Add virtualHost mapping to httpd_config.conf
addOLSVhost(self, wo_domain_name, wo_site_webroot)
# Creating htdocs & logs directory
Log.info(self, "Setting up webroot \t\t", end='')
@@ -115,22 +193,10 @@ def setupdomain(self, data):
os.makedirs('{0}/htdocs'.format(wo_site_webroot))
if not os.path.exists('{0}/logs'.format(wo_site_webroot)):
os.makedirs('{0}/logs'.format(wo_site_webroot))
if not os.path.exists('{0}/conf/nginx'.format(wo_site_webroot)):
os.makedirs('{0}/conf/nginx'.format(wo_site_webroot))
WOFileUtils.create_symlink(self, ['/var/log/nginx/{0}.access.log'
.format(wo_domain_name),
'{0}/logs/access.log'
.format(wo_site_webroot)])
WOFileUtils.create_symlink(self, ['/var/log/nginx/{0}.error.log'
.format(wo_domain_name),
'{0}/logs/error.log'
.format(wo_site_webroot)])
except Exception as e:
Log.debug(self, str(e))
raise SiteError("setup webroot failed for site")
finally:
# TODO Check if directories are setup
if (os.path.exists('{0}/htdocs'.format(wo_site_webroot)) and
os.path.exists('{0}/logs'.format(wo_site_webroot))):
Log.info(self, "[" + Log.ENDC + "Done" + Log.OKBLUE + "]")
@@ -526,60 +592,8 @@ def setupwordpress(self, data, vhostonly=False):
Log.debug(self, str(e))
raise SiteError("Update wordpress permalinks failed")
"""Install nginx-helper plugin """
installwp_plugin(self, 'nginx-helper', data)
if data['wpfc']:
plugin_data_object = {"log_level": "INFO",
"log_filesize": 5,
"enable_purge": 1,
"enable_map": "0",
"enable_log": 0,
"enable_stamp": 1,
"purge_homepage_on_new": 1,
"purge_homepage_on_edit": 1,
"purge_homepage_on_del": 1,
"purge_archive_on_new": 1,
"purge_archive_on_edit": 1,
"purge_archive_on_del": 1,
"purge_archive_on_new_comment": 0,
"purge_archive_on_deleted_comment": 0,
"purge_page_on_mod": 1,
"purge_page_on_new_comment": 1,
"purge_page_on_deleted_comment": 1,
"cache_method": "enable_fastcgi",
"purge_method": "get_request",
"redis_hostname": "127.0.0.1",
"redis_port": "6379",
"redis_prefix": "nginx-cache:"}
plugin_data = json.dumps(plugin_data_object)
setupwp_plugin(self, "nginx-helper",
"rt_wp_nginx_helper_options", plugin_data, data)
elif data['wpredis']:
plugin_data_object = {"log_level": "INFO",
"log_filesize": 5,
"enable_purge": 1,
"enable_map": "0",
"enable_log": 0,
"enable_stamp": 1,
"purge_homepage_on_new": 1,
"purge_homepage_on_edit": 1,
"purge_homepage_on_del": 1,
"purge_archive_on_new": 1,
"purge_archive_on_edit": 1,
"purge_archive_on_del": 1,
"purge_archive_on_new_comment": 0,
"purge_archive_on_deleted_comment": 0,
"purge_page_on_mod": 1,
"purge_page_on_new_comment": 1,
"purge_page_on_deleted_comment": 1,
"cache_method": "enable_redis",
"purge_method": "get_request",
"redis_hostname": "127.0.0.1",
"redis_port": "6379",
"redis_prefix": "nginx-cache:"}
plugin_data = json.dumps(plugin_data_object)
setupwp_plugin(self, 'nginx-helper',
'rt_wp_nginx_helper_options', plugin_data, data)
"""Install LiteSpeed Cache plugin (built-in caching for OLS)"""
installwp_plugin(self, 'litespeed-cache', data)
"""Install Wp Super Cache"""
if data['wpsc']:
@@ -771,11 +785,14 @@ def sitebackup(self, data):
if not WOFileUtils.isexist(self, backup_path):
WOFileUtils.mkdir(self, backup_path)
Log.info(self, "Backup location : {0}".format(backup_path))
WOFileUtils.copyfile(self, '/etc/nginx/sites-available/{0}'
.format(data['site_name']), backup_path)
vhost_conf = '{0}/{1}/vhconf.conf'.format(
WOVar.wo_ols_vhost_dir, data['site_name'])
if os.path.isfile(vhost_conf):
WOFileUtils.copyfile(self, vhost_conf, backup_path)
if data['currsitetype'] in ['html', 'php', 'php72', 'php74',
'php73', 'php80', 'php81', 'php82', 'php83', 'php84'
'php73', 'php80', 'php81', 'php82',
'php83', 'php84', 'php85',
'proxy', 'mysql']:
if not data['wp']:
Log.info(self, "Backing up Webroot \t\t", end='')
@@ -836,70 +853,47 @@ def site_package_check(self, stype):
stack.app = self.app
pargs = self.app.pargs
if stype in ['html', 'proxy', 'php', 'mysql', 'wp', 'wpsubdir',
'wpsubdomain', 'php74', 'php80', 'php81', 'php82', 'php83', 'php84', 'alias', 'subsite']:
Log.debug(self, "Setting apt_packages variable for Nginx")
'wpsubdomain', 'php74', 'php80', 'php81', 'php82',
'php83', 'php84', 'php85', 'alias', 'subsite']:
Log.debug(self, "Setting apt_packages variable for OpenLiteSpeed")
# Check if server has nginx-custom package
if not (WOAptGet.is_installed(self, 'nginx-custom') or
WOAptGet.is_installed(self, 'nginx-mainline')):
# check if Server has nginx-plus installed
if WOAptGet.is_installed(self, 'nginx-plus'):
# do something
# do post nginx installation configuration
Log.info(self, "NGINX PLUS Detected ...")
apt = ["nginx-plus"] + WOVar.wo_nginx
# apt_packages = apt_packages + WOVar.wo_nginx
post_pref(self, apt, packages)
elif WOAptGet.is_installed(self, 'nginx'):
Log.info(self, "WordOps detected a previously"
"installed Nginx package. "
"It may or may not have required modules. "
"\nIf you need help, please create an issue at "
"https://github.com/WordOps/WordOps/issues/ \n")
apt = ["nginx"] + WOVar.wo_nginx
# apt_packages = apt_packages + WOVar.wo_nginx
post_pref(self, apt, packages)
elif os.path.isfile('/usr/sbin/nginx'):
post_pref(self, WOVar.wo_nginx, [])
# Check if server has OpenLiteSpeed installed
if not WOAptGet.is_installed(self, 'openlitespeed'):
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
post_pref(self, WOVar.wo_ols, [])
else:
apt_packages = apt_packages + WOVar.wo_nginx
else:
# Fix for Nginx white screen death
if not WOFileUtils.grep(self, '/etc/nginx/fastcgi_params',
'SCRIPT_FILENAME'):
with open('/etc/nginx/fastcgi_params', encoding='utf-8',
mode='a') as wo_nginx:
wo_nginx.write('fastcgi_param \tSCRIPT_FILENAME '
'\t$request_filename;\n')
apt_packages = apt_packages + WOVar.wo_ols
php_versions = ['php74', 'php80', 'php81', 'php82', 'php83', 'php84']
php_versions = list(WOVar.wo_php_versions.keys())
selected_versions = [version for version in php_versions if getattr(pargs, version)]
selected_versions = [version for version in php_versions
if getattr(pargs, version, False)]
if len(selected_versions) > 1:
Log.error(self, "Error: two different PHP versions cannot be "
"combined within the same WordOps site")
if ((not pargs.php74) and (not pargs.php80) and
(not pargs.php81) and (not pargs.php82) and
(not pargs.php83) and (not pargs.php84) and
stype in ['php', 'mysql', 'wp', 'wpsubdir',
'wpsubdomain']):
Log.debug(self, "Setting apt_packages variable for PHP")
if (not any(getattr(pargs, v, False) for v in WOVar.wo_php_versions) and
stype in ['php', 'mysql', 'wp', 'wpsubdir',
'wpsubdomain']):
Log.debug(self, "Setting apt_packages variable for LSPHP")
for version_key, version_number in WOVar.wo_php_versions.items():
if (self.app.config.has_section('php') and
self.app.config.get('php', 'version') == version_number):
Log.debug(
self,
f"Setting apt_packages variable for PHP {version_number}")
if not WOAptGet.is_installed(self, f'php{version_number}-fpm'):
f"Setting apt_packages variable for LSPHP {version_number}")
short_ver = version_number.replace('.', '')
if not WOAptGet.is_installed(self, f'lsphp{short_ver}'):
apt_packages += getattr(
WOVar, f'wo_{version_key}') + WOVar.wo_php_extra
for version_key, version_number in WOVar.wo_php_versions.items():
if getattr(pargs, version_key) and stype in [version_key, 'mysql', 'wp', 'wpsubdir', 'wpsubdomain']:
Log.debug(self, f"Setting apt_packages variable for PHP {version_number}")
if not WOAptGet.is_installed(self, f'php{version_number}-fpm'):
if getattr(pargs, version_key, False) and stype in [
version_key, 'mysql', 'wp', 'wpsubdir', 'wpsubdomain']:
Log.debug(self, f"Setting apt_packages variable for LSPHP {version_number}")
short_ver = version_number.replace('.', '')
if not WOAptGet.is_installed(self, f'lsphp{short_ver}'):
apt_packages += getattr(WOVar, f'wo_{version_key}') + WOVar.wo_php_extra
if stype in ['mysql', 'wp', 'wpsubdir', 'wpsubdomain']:
@@ -917,16 +911,6 @@ def site_package_check(self, stype):
if not WOAptGet.is_installed(self, 'redis-server'):
apt_packages = apt_packages + WOVar.wo_redis
if pargs.ngxblocker:
if not os.path.isdir('/etc/nginx/bots.d'):
Log.debug(self, "Setting packages variable for ngxblocker")
packages = packages + \
[["https://raw.githubusercontent.com/"
"mitchellkrogza/nginx-ultimate-bad-bot-blocker"
"/master/install-ngxblocker",
"/usr/local/sbin/install-ngxblocker",
"ngxblocker"]]
return (stack.install(apt_packages=apt_packages, packages=packages,
disp_msg=False))
@@ -1023,13 +1007,13 @@ def display_cache_settings(self, data):
if data['wpfc']:
if data['multisite']:
Log.info(self, "Nginx-Helper configuration :"
"\thttp://{0}/wp-admin/network/settings.php?"
"page=nginx".format(data['site_name']))
Log.info(self, "LiteSpeed Cache configuration :"
"\thttp://{0}/wp-admin/network/admin.php?"
"page=litespeed".format(data['site_name']))
else:
Log.info(self, "Nginx-Helper configuration :"
"\thttp://{0}/wp-admin/options-general.php?"
"page=nginx".format(data['site_name']))
Log.info(self, "LiteSpeed Cache configuration :"
"\thttp://{0}/wp-admin/admin.php?"
"page=litespeed".format(data['site_name']))
if data['wpce']:
if data['multisite']:
@@ -1080,7 +1064,8 @@ def detSitePar(opts):
for key, val in opts.items():
if val and key in ['html', 'php', 'mysql', 'wp',
'wpsubdir', 'wpsubdomain',
'php74', 'php80', 'php81', 'php82', 'php83', 'php84']:
'php74', 'php80', 'php81', 'php82',
'php83', 'php84', 'php85']:
typelist.append(key)
elif val and key in ['wpfc', 'wpsc', 'wpredis', 'wprocket', 'wpce']:
cachelist.append(key)
@@ -1132,6 +1117,12 @@ def detSitePar(opts):
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('php85', 'mysql', 'html') for x in typelist]:
sitetype = 'mysql'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('php', 'mysql') for x in typelist]:
sitetype = 'mysql'
if not cachelist:
@@ -1174,6 +1165,12 @@ def detSitePar(opts):
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('php85', 'mysql') for x in typelist]:
sitetype = 'mysql'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('html', 'mysql') for x in typelist]:
sitetype = 'mysql'
if not cachelist:
@@ -1234,6 +1231,12 @@ def detSitePar(opts):
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wp', 'php85') for x in typelist]:
sitetype = 'wp'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdir', 'php74') for x in typelist]:
sitetype = 'wpsubdir'
if not cachelist:
@@ -1270,6 +1273,12 @@ def detSitePar(opts):
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdir', 'php85') for x in typelist]:
sitetype = 'wpsubdir'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdomain', 'php74') for x in typelist]:
sitetype = 'wpsubdomain'
if not cachelist:
@@ -1306,6 +1315,12 @@ def detSitePar(opts):
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdomain', 'php85') for x in typelist]:
sitetype = 'wpsubdomain'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
else:
raise RuntimeError("could not determine site and cache type")
else:
@@ -1330,6 +1345,9 @@ def detSitePar(opts):
elif (not typelist or "php84" in typelist) and cachelist:
sitetype = 'wp'
cachetype = cachelist[0]
elif (not typelist or "php85" in typelist) and cachelist:
sitetype = 'wp'
cachetype = cachelist[0]
elif typelist and (not cachelist):
sitetype = typelist[0]
cachetype = 'basic'
@@ -1419,16 +1437,14 @@ def deleteWebRoot(self, webroot):
return False
def removeNginxConf(self, domain):
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(domain)):
Log.debug(self, "Removing Nginx configuration")
WOFileUtils.rm(self, '/etc/nginx/sites-enabled/{0}'
.format(domain))
WOFileUtils.rm(self, '/etc/nginx/sites-available/{0}'
.format(domain))
WOService.reload_service(self, 'nginx')
WOGit.add(self, ["/etc/nginx"],
def removeOLSConf(self, domain):
vhost_dir = '{0}/{1}'.format(WOVar.wo_ols_vhost_dir, domain)
if os.path.isdir(vhost_dir):
Log.debug(self, "Removing OpenLiteSpeed configuration")
removeOLSVhost(self, domain)
WOFileUtils.rm(self, vhost_dir)
WOService.reload_service(self, 'lsws')
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="Deleted {0} "
.format(domain))
@@ -1436,14 +1452,14 @@ def removeNginxConf(self, domain):
def doCleanupAction(self, domain='', webroot='', dbname='', dbuser='',
dbhost=''):
"""
Removes the nginx configuration and database for the domain provided.
Removes the OLS configuration and database for the domain provided.
doCleanupAction(self, domain='sitename', webroot='',
dbname='', dbuser='', dbhost='')
"""
if domain:
if os.path.isfile('/etc/nginx/sites-available/{0}'
.format(domain)):
removeNginxConf(self, domain)
vhost_dir = '{0}/{1}'.format(WOVar.wo_ols_vhost_dir, domain)
if os.path.isdir(vhost_dir):
removeOLSConf(self, domain)
WOAcme.removeconf(self, domain)
if webroot:
@@ -1463,23 +1479,27 @@ def doCleanupAction(self, domain='', webroot='', dbname='', dbuser='',
def copyWildcardCert(self, wo_domain_name, wo_root_domain):
if os.path.isfile("/var/www/{0}/conf/nginx/ssl.conf"
.format(wo_root_domain)):
root_vhost_dir = '{0}/{1}'.format(
WOVar.wo_ols_vhost_dir, wo_root_domain)
domain_vhost_dir = '{0}/{1}'.format(
WOVar.wo_ols_vhost_dir, wo_domain_name)
if os.path.isfile("{0}/ssl.conf".format(root_vhost_dir)):
try:
if not os.path.isdir("/etc/letsencrypt/shared"):
WOFileUtils.mkdir(self, "/etc/letsencrypt/shared")
if not os.path.isfile("/etc/letsencrypt/shared/{0}.conf"
.format(wo_root_domain)):
WOFileUtils.copyfile(self, "/var/www/{0}/conf/nginx/ssl.conf"
.format(wo_root_domain),
WOFileUtils.copyfile(self,
"{0}/ssl.conf".format(root_vhost_dir),
"/etc/letsencrypt/shared/{0}.conf"
.format(wo_root_domain))
if not os.path.isdir(domain_vhost_dir):
os.makedirs(domain_vhost_dir)
WOFileUtils.create_symlink(self, ["/etc/letsencrypt/shared/"
"{0}.conf"
.format(wo_root_domain),
'/var/www/{0}/conf/nginx/'
'ssl.conf'
.format(wo_domain_name)])
'{0}/ssl.conf'
.format(domain_vhost_dir)])
except IOError as e:
Log.debug(self, str(e))
Log.debug(self, "Error occured while "
@@ -1549,32 +1569,3 @@ def setuprocketchat(self):
return False
def setupngxblocker(self, domain, block=True):
if block:
if os.path.isdir('/var/www/{0}/conf/nginx'.format(domain)):
if not os.path.isfile(
'/var/www/{0}/conf/nginx/ngxblocker.conf.disabled'
.format(domain)):
ngxconf = open(
"/var/www/{0}/conf/nginx/ngxblocker.conf"
.format(domain),
encoding='utf-8', mode='w')
ngxconf.write(
"# Bad Bot Blocker\n"
"include /etc/nginx/bots.d/ddos.conf;\n"
"include /etc/nginx/bots.d/blockbots.conf;\n")
ngxconf.close()
else:
WOFileUtils.mvfile(
self, '/var/www/{0}/conf/nginx/ngxblocker.conf.disabled'
.format(domain), '/var/www/{0}/conf/nginx/ngxblocker.conf'
.format(domain))
else:
if os.path.isfile('/var/www/{0}/conf/nginx/ngxblocker.conf'
.format(domain)):
WOFileUtils.mvfile(
self, '/var/www/{0}/conf/nginx/ngxblocker.conf'
.format(domain),
'/var/www/{0}/conf/nginx/ngxblocker.conf.disabled'
.format(domain))
return 0

View File

@@ -9,7 +9,7 @@ from wo.cli.plugins.site_functions import (
pre_run_checks, setupdomain, SiteError,
setupdatabase, setupwordpress, setwebrootpermissions,
display_cache_settings, copyWildcardCert,
updatewpuserpassword, setupngxblocker, setupwp_plugin,
updatewpuserpassword, setupwp_plugin,
setupwordpressnetwork, installwp_plugin, sitebackup, uninstallwp_plugin)
from wo.cli.plugins.sitedb import (getAllsites,
getSiteInfo, updateSiteInfo)
@@ -88,11 +88,6 @@ class WOSiteUpdateController(CementBaseController):
action='store' or 'store_const',
choices=('on', 'off'),
const='on', nargs='?')),
(['--ngxblocker'],
dict(help="enable Ultimate Nginx bad bot blocker",
action='store' or 'store_const',
choices=('on', 'off'),
const='on', nargs='?')),
(['--proxy'],
dict(help="update to proxy site", nargs='+')),
(['--all'],
@@ -195,10 +190,11 @@ class WOSiteUpdateController(CementBaseController):
check_php_version = check_site.php_version
if ((pargs.password or pargs.hsts or
pargs.ngxblocker or pargs.letsencrypt == 'renew') and not (
pargs.letsencrypt == 'renew') and not (
pargs.html or pargs.php or pargs.php74 or pargs.php80 or
pargs.php81 or pargs.php82 or
pargs.php83 or pargs.php84 or pargs.mysql or pargs.wp or pargs.wpfc or pargs.wpsc or
pargs.php83 or pargs.php84 or pargs.php85 or
pargs.mysql or pargs.wp or pargs.wpfc or pargs.wpsc or
pargs.wprocket or pargs.wpce or
pargs.wpsubdir or pargs.wpsubdomain)):
@@ -217,38 +213,13 @@ class WOSiteUpdateController(CementBaseController):
SSL.setuphsts(self, wo_domain, enable=True)
elif pargs.hsts == "off":
SSL.setuphsts(self, wo_domain, enable=False)
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.error(
self, "service nginx reload failed. "
"check issues with `nginx -t` command")
self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
else:
return 0
# setup ngxblocker
if (pargs.ngxblocker):
if pargs.ngxblocker == "on":
if os.path.isdir('/etc/nginx/bots.d'):
try:
setupngxblocker(self, wo_domain)
except SiteError as e:
Log.debug(self, str(e))
Log.info(self, "\nngxblocker not enabled.")
else:
Log.error(self, 'ngxblocker stack is not installed')
elif pargs.ngxblocker == "off":
try:
setupngxblocker(self, wo_domain, False)
except SiteError as e:
Log.debug(self, str(e))
Log.info(self, "\nngxblocker not enabled.")
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
else:
return 0
# letsencryot rebew
if (pargs.letsencrypt == 'renew'):
if WOAcme.cert_check(self, wo_domain):
@@ -268,19 +239,22 @@ class WOSiteUpdateController(CementBaseController):
if (((stype == 'php' and
oldsitetype not in ['html', 'proxy', 'php', 'php74', 'php80',
'php81', 'php82', 'php83', 'php84']) or
'php81', 'php82', 'php83', 'php84',
'php85']) or
(stype == 'mysql' and oldsitetype not in [
'html', 'php', 'php74', 'php80', 'php81',
'php82', 'php83', 'php84', 'proxy']) or
'php82', 'php83', 'php84', 'php85', 'proxy']) or
(stype == 'wp' and oldsitetype not in [
'html', 'php', 'php74', 'php80', 'php81',
'php82', 'php83', 'php84', 'mysql', 'proxy', 'wp']) or
'php82', 'php83', 'php84', 'php85',
'mysql', 'proxy', 'wp']) or
(stype == 'wpsubdir' and oldsitetype in ['wpsubdomain']) or
(stype == 'wpsubdomain' and oldsitetype in ['wpsubdir']) or
(stype == oldsitetype and cache == oldcachetype)) and
not (pargs.php74 or pargs.php80 or
pargs.php81 or pargs.php82 or
pargs.php83 or pargs.php84 or pargs.alias)):
pargs.php83 or pargs.php84 or
pargs.php85 or pargs.alias)):
Log.info(self, Log.FAIL + "can not update {0} {1} to {2} {3}".
format(oldsitetype, oldcachetype, stype, cache))
return 1
@@ -338,7 +312,7 @@ class WOSiteUpdateController(CementBaseController):
site_name=wo_domain, www_domain=wo_www_domain,
static=False, basic=True, wp=False, wpfc=False,
php74=False, php80=False, php81=False, php82=False, php83=False,
php84=False, wpsc=False, wpredis=False, wprocket=False, wpce=False,
php84=False, php85=False, wpsc=False, wpredis=False, wprocket=False, wpce=False,
multisite=False, wpsubdir=False, webroot=wo_site_webroot,
currsitetype=oldsitetype, currcachetype=oldcachetype)
@@ -362,8 +336,8 @@ class WOSiteUpdateController(CementBaseController):
data['wpsubdir'] = True
if ((pargs.php74 or pargs.php80 or pargs.php81 or
pargs.php82 or pargs.php83 or pargs.php84) and
(not data)):
pargs.php82 or pargs.php83 or pargs.php84 or
pargs.php85) and (not data)):
Log.debug(
self, "pargs php74, "
"or php80, or php81 or php82 or php83 or php84 enabled")
@@ -384,7 +358,7 @@ class WOSiteUpdateController(CementBaseController):
oldsitetype == 'php73' or oldsitetype == 'php74' or
oldsitetype == 'php80' or oldsitetype == 'php81' or
oldsitetype == 'php82' or oldsitetype == 'php83' or
oldsitetype == 'php84'):
oldsitetype == 'php84' or oldsitetype == 'php85'):
data['static'] = False
data['wp'] = False
data['multisite'] = False
@@ -436,7 +410,8 @@ class WOSiteUpdateController(CementBaseController):
if (data and (not pargs.php74) and
(not pargs.php80) and (not pargs.php81) and (not pargs.php82)
and (not pargs.php83) and (not pargs.php84)):
and (not pargs.php83) and (not pargs.php84)
and (not pargs.php85)):
data[pargs_version] = bool(old_version_var is True)
Log.debug(
self, f"data {pargs_version} = {data[pargs_version]}")
@@ -546,19 +521,19 @@ class WOSiteUpdateController(CementBaseController):
data['wo_db_pass'] = check_site.db_password
data['wo_db_host'] = check_site.db_host
if not (pargs.letsencrypt or pargs.hsts or pargs.ngxblocker):
if not (pargs.letsencrypt or pargs.hsts):
try:
pre_run_checks(self)
except SiteError as e:
Log.debug(self, str(e))
Log.error(self, "NGINX configuration check failed.")
Log.error(self, "OpenLiteSpeed configuration check failed.")
try:
sitebackup(self, data)
except Exception as e:
Log.debug(self, str(e))
# setup NGINX configuration, and webroot
# setup OpenLiteSpeed configuration, and webroot
try:
setupdomain(self, data)
except SiteError as e:
@@ -677,9 +652,9 @@ class WOSiteUpdateController(CementBaseController):
self, wo_domain, acme_domains, redirect=True)
SSL.siteurlhttps(self, wo_domain)
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
Log.info(self, "Congratulations! Successfully "
"Configured SSL on https://{0}".format(wo_domain))
letsencrypt = True
@@ -694,29 +669,29 @@ class WOSiteUpdateController(CementBaseController):
elif data['letsencrypt'] is False:
if pargs.letsencrypt == "off":
if os.path.islink("{0}/conf/nginx/ssl.conf"
.format(wo_site_webroot)):
if os.path.islink("{0}/{1}/ssl.conf"
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
WOFileUtils.remove_symlink(self,
"{0}/conf/nginx/ssl.conf"
.format(wo_site_webroot))
elif os.path.isfile("{0}/conf/nginx/ssl.conf"
.format(wo_site_webroot)):
Log.info(self, 'Setting Nginx configuration')
WOFileUtils.mvfile(self, "{0}/conf/nginx/ssl.conf"
.format(wo_site_webroot),
'{0}/conf/nginx/ssl.conf.disabled'
.format(wo_site_webroot))
"{0}/{1}/ssl.conf"
.format(WOVar.wo_ols_vhost_dir, wo_domain))
elif os.path.isfile("{0}/{1}/ssl.conf"
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
Log.info(self, 'Setting OpenLiteSpeed configuration')
WOFileUtils.mvfile(self, "{0}/{1}/ssl.conf"
.format(WOVar.wo_ols_vhost_dir, wo_domain),
'{0}/{1}/ssl.conf.disabled'
.format(WOVar.wo_ols_vhost_dir, wo_domain))
SSL.httpsredirect(
self, wo_domain, acmedata, redirect=False)
if os.path.isfile("{0}/conf/nginx/hsts.conf"
.format(wo_site_webroot)):
WOFileUtils.mvfile(self, "{0}/conf/nginx/hsts.conf"
.format(wo_site_webroot),
'{0}/conf/nginx/'
if os.path.isfile("{0}/{1}/hsts.conf"
.format(WOVar.wo_ols_vhost_dir, wo_domain)):
WOFileUtils.mvfile(self, "{0}/{1}/hsts.conf"
.format(WOVar.wo_ols_vhost_dir, wo_domain),
'{0}/{1}/'
'hsts.conf.disabled'
.format(wo_site_webroot))
.format(WOVar.wo_ols_vhost_dir, wo_domain))
# find all broken symlinks
sympath = (f'{wo_site_webroot}/conf')
sympath = ('{0}/{1}'.format(WOVar.wo_ols_vhost_dir, wo_domain))
WOFileUtils.findBrokenSymlink(self, sympath)
elif (pargs.letsencrypt == "clean" or
@@ -730,9 +705,9 @@ class WOSiteUpdateController(CementBaseController):
sympath = "{0}/conf".format(site.site_path)
WOFileUtils.findBrokenSymlink(self, sympath)
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
# Log.info(self,"Removing Cron Job set for cert
# auto-renewal") WOCron.remove_cron(self,'wo site
# update {0} --le=renew --min_expiry_limit 30
@@ -741,8 +716,8 @@ class WOSiteUpdateController(CementBaseController):
" http://{0}".format(wo_domain))
letsencrypt = False
# Add nginx conf folder into GIT
WOGit.add(self, ["{0}/conf/nginx".format(wo_site_webroot)],
# Add OLS conf folder into GIT
WOGit.add(self, ["{0}/{1}".format(WOVar.wo_ols_vhost_dir, wo_domain)],
msg="Adding letsencrypts config of site: {0}"
.format(wo_domain))
updateSiteInfo(self, wo_domain, ssl=letsencrypt)
@@ -750,10 +725,10 @@ class WOSiteUpdateController(CementBaseController):
if stype == oldsitetype and cache == oldcachetype:
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
updateSiteInfo(self, wo_domain, stype=stype, cache=cache,
ssl=(bool(check_site.is_ssl)),
@@ -796,7 +771,8 @@ class WOSiteUpdateController(CementBaseController):
# Setup WordPress if old sites are html/php/mysql sites
if data['wp'] and oldsitetype in ['html', 'proxy', 'php', 'php72',
'mysql', 'php73', 'php74', 'php80',
'php81', 'php82', 'php83', 'php84']:
'php81', 'php82', 'php83', 'php84',
'php85']:
try:
wo_wp_creds = setupwordpress(self, data)
except SiteError as e:
@@ -827,35 +803,27 @@ class WOSiteUpdateController(CementBaseController):
data['multisite'] and data['wpfc'])):
try:
plugin_data_object = {
"log_level": "INFO",
"log_filesize": 5,
"enable_purge": 1,
"enable_map": "0",
"enable_log": 0,
"enable_stamp": 1,
"purge_homepage_on_new": 1,
"purge_homepage_on_edit": 1,
"purge_homepage_on_del": 1,
"purge_archive_on_new": 1,
"purge_archive_on_edit": 0,
"purge_archive_on_del": 0,
"purge_archive_on_new_comment": 0,
"purge_archive_on_deleted_comment": 0,
"purge_page_on_mod": 1,
"purge_page_on_new_comment": 1,
"purge_page_on_deleted_comment": 1,
"cache_method": "enable_fastcgi",
"purge_method": "get_request",
"redis_hostname": "127.0.0.1",
"redis_port": "6379",
"redis_prefix": "nginx-cache:"}
"cache-lscwp": "on",
"cache-pub_priv_ttl": 604800,
"cache-commenter": "on",
"cache-rest": "on",
"cache-page_login": "on",
"cache-favicon": "on",
"cache-resources": "on",
"cache-mobile": "on",
"cache-nocache_cookies": "",
"cache-nocache_useragents": "",
"purge-purge_on_upgrade": "on",
"purge-auto_purge": "on",
"purge-stale": "on",
"purge-hook_all": "on"}
plugin_data = json.dumps(plugin_data_object)
setupwp_plugin(self, 'nginx-helper',
'rt_wp_nginx_helper_options',
setupwp_plugin(self, 'litespeed-cache',
'litespeed-cache-conf',
plugin_data, data)
except SiteError as e:
Log.debug(self, str(e))
Log.info(self, Log.FAIL + "Update nginx-helper "
Log.info(self, Log.FAIL + "Update litespeed-cache "
"settings failed. "
"Check the log for details:"
" `tail /var/log/wo/wordops.log` "
@@ -869,35 +837,31 @@ class WOSiteUpdateController(CementBaseController):
data['wpredis'])):
try:
plugin_data_object = {
"log_level": "INFO",
"log_filesize": 5,
"enable_purge": 1,
"enable_map": "0",
"enable_log": 0,
"enable_stamp": 1,
"purge_homepage_on_new": 1,
"purge_homepage_on_edit": 1,
"purge_homepage_on_del": 1,
"purge_archive_on_new": 1,
"purge_archive_on_edit": 0,
"purge_archive_on_del": 0,
"purge_archive_on_new_comment": 0,
"purge_archive_on_deleted_comment": 0,
"purge_page_on_mod": 1,
"purge_page_on_new_comment": 1,
"purge_page_on_deleted_comment": 1,
"cache_method": "enable_redis",
"purge_method": "get_request",
"redis_hostname": "127.0.0.1",
"redis_port": "6379",
"redis_prefix": "nginx-cache:"}
"cache-lscwp": "on",
"cache-pub_priv_ttl": 604800,
"cache-commenter": "on",
"cache-rest": "on",
"cache-page_login": "on",
"cache-favicon": "on",
"cache-resources": "on",
"cache-mobile": "on",
"cache-nocache_cookies": "",
"cache-nocache_useragents": "",
"purge-purge_on_upgrade": "on",
"purge-auto_purge": "on",
"purge-stale": "on",
"purge-hook_all": "on",
"cache-object": "on",
"cache-object_kind": "redis",
"cache-object_host": "127.0.0.1",
"cache-object_port": "6379"}
plugin_data = json.dumps(plugin_data_object)
setupwp_plugin(self, 'nginx-helper',
'rt_wp_nginx_helper_options',
setupwp_plugin(self, 'litespeed-cache',
'litespeed-cache-conf',
plugin_data, data)
except SiteError as e:
Log.debug(self, str(e))
Log.info(self, Log.FAIL + "Update nginx-helper "
Log.info(self, Log.FAIL + "Update litespeed-cache "
"settings failed. "
"Check the log for details:"
" `tail /var/log/wo/wordops.log` "
@@ -905,37 +869,27 @@ class WOSiteUpdateController(CementBaseController):
return 1
else:
try:
# disable nginx-helper
# disable litespeed-cache
plugin_data_object = {
"log_level": "INFO",
"log_filesize": 5,
"enable_purge": 0,
"enable_map": 0,
"enable_log": 0,
"enable_stamp": 0,
"purge_homepage_on_new": 1,
"purge_homepage_on_edit": 1,
"purge_homepage_on_del": 1,
"purge_archive_on_new": 1,
"purge_archive_on_edit": 0,
"purge_archive_on_del": 0,
"purge_archive_on_new_comment": 0,
"purge_archive_on_deleted_comment": 0,
"purge_page_on_mod": 1,
"purge_page_on_new_comment": 1,
"purge_page_on_deleted_comment": 1,
"cache_method": "enable_redis",
"purge_method": "get_request",
"redis_hostname": "127.0.0.1",
"redis_port": "6379",
"redis_prefix": "nginx-cache:"}
"cache-lscwp": "off",
"cache-pub_priv_ttl": 0,
"cache-commenter": "off",
"cache-rest": "off",
"cache-page_login": "off",
"cache-favicon": "off",
"cache-resources": "off",
"cache-mobile": "off",
"purge-purge_on_upgrade": "off",
"purge-auto_purge": "off",
"purge-stale": "off",
"purge-hook_all": "off"}
plugin_data = json.dumps(plugin_data_object)
setupwp_plugin(
self, 'nginx-helper',
'rt_wp_nginx_helper_options', plugin_data, data)
self, 'litespeed-cache',
'litespeed-cache-conf', plugin_data, data)
except SiteError as e:
Log.debug(self, str(e))
Log.info(self, Log.FAIL + "Update nginx-helper "
Log.info(self, Log.FAIL + "Update litespeed-cache "
"settings failed. "
"Check the log for details:"
" `tail /var/log/wo/wordops.log` "
@@ -1026,12 +980,12 @@ class WOSiteUpdateController(CementBaseController):
"`tail /var/log/wo/wordops.log` and please try again")
return 1
# Service Nginx Reload
if not WOService.reload_service(self, 'nginx'):
Log.error(self, "service nginx reload failed. "
"check issues with `nginx -t` command")
# Service OLS Reload
if not WOService.reload_service(self, 'lsws'):
Log.error(self, "service lsws reload failed. "
"check issues with OpenLiteSpeed config")
WOGit.add(self, ["/etc/nginx"],
WOGit.add(self, [WOVar.wo_ols_conf_dir],
msg="{0} updated with {1} {2}"
.format(wo_www_domain, stype, cache))
# Setup Permissions for webroot

View File

@@ -16,8 +16,6 @@ from wo.core.mysql import WOMysql
from wo.core.services import WOService
from wo.core.shellexec import WOShellExec
from wo.core.variables import WOVar
from wo.core.nginx import check_config
from wo.core.git import WOGit
def wo_stack_hook(app):
@@ -40,7 +38,7 @@ class WOStackController(CementBaseController):
(['--security'],
dict(help='Install security tools stack', action='store_true')),
(['--nginx'],
dict(help='Install Nginx stack', action='store_true')),
dict(help='Install OpenLiteSpeed stack', action='store_true')),
(['--php'],
dict(help='Install PHP 7.2 stack', action='store_true')),
(['--mysql'],
@@ -84,16 +82,13 @@ class WOStackController(CementBaseController):
dict(help='Install phpRedisAdmin', action='store_true')),
(['--proftpd'],
dict(help='Install ProFTPd', action='store_true')),
(['--ngxblocker'],
dict(help='Install Nginx Ultimate Bad Bot Blocker',
action='store_true')),
(['--cheat'],
dict(help='Install cheat.sh', action='store_true')),
(['--nanorc'],
dict(help='Install nanorc syntax highlighting',
action='store_true')),
(['--brotli'],
dict(help='Enable/Disable Brotli compression for Nginx',
dict(help='Enable/Disable Brotli compression for OpenLiteSpeed',
action='store_true')),
(['--force'],
dict(help='Force install/remove/purge without prompt',
@@ -136,6 +131,7 @@ class WOStackController(CementBaseController):
pargs.php82 = True
pargs.php83 = True
pargs.php84 = True
pargs.php85 = True
pargs.redis = True
pargs.proftpd = True
@@ -162,7 +158,6 @@ class WOStackController(CementBaseController):
if pargs.security:
pargs.fail2ban = True
pargs.clamav = True
pargs.ngxblocker = True
if pargs.php:
if self.app.config.has_section('php'):
@@ -171,13 +166,13 @@ class WOStackController(CementBaseController):
current_php = config_php_ver.replace(".", "")
setattr(self.app.pargs, 'php{0}'.format(current_php), True)
# Nginx
# OpenLiteSpeed
if pargs.nginx:
Log.debug(self, "Setting apt_packages variable for Nginx")
if not WOAptGet.is_exec(self, 'nginx'):
apt_packages = apt_packages + WOVar.wo_nginx
Log.debug(self, "Setting apt_packages variable for OpenLiteSpeed")
if not os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
apt_packages = apt_packages + WOVar.wo_ols
else:
Log.debug(self, "Nginx already installed")
Log.debug(self, "OpenLiteSpeed already installed")
# Redis
if pargs.redis:
@@ -194,12 +189,14 @@ class WOStackController(CementBaseController):
'php82': WOVar.wo_php82,
'php83': WOVar.wo_php83,
'php84': WOVar.wo_php84,
'php85': WOVar.wo_php85,
}
for parg_version, version in WOVar.wo_php_versions.items():
if getattr(pargs, parg_version, False):
short_ver = version.replace('.', '')
Log.debug(self, f"Setting apt_packages variable for PHP {version}")
if not WOAptGet.is_installed(self, f'php{version}-fpm'):
if not WOAptGet.is_installed(self, f'lsphp{short_ver}'):
apt_packages = apt_packages + wo_vars[parg_version] + WOVar.wo_php_extra
else:
Log.debug(self, f"PHP {version} already installed")
@@ -287,23 +284,25 @@ class WOStackController(CementBaseController):
# brotli
if pargs.brotli:
Log.wait(self, "Enabling Brotli")
WOGit.add(self, ["/etc/nginx"], msg="Commiting pending changes")
if os.path.exists('/etc/nginx/conf.d/brotli.conf.disabled'):
WOFileUtils.mvfile(self, '/etc/nginx/conf.d/brotli.conf.disabled',
'/etc/nginx/conf.d/brotli.conf')
ols_conf = '/usr/local/lsws/conf/httpd_config.conf'
if os.path.isfile(ols_conf):
if WOFileUtils.grepcheck(self, ols_conf, 'enableBr.*0'):
WOFileUtils.searchreplace(
self, ols_conf,
'enableBr 0',
'enableBr 1')
WOFileUtils.searchreplace(
self, ols_conf,
'enableGzipCompress 1',
'enableGzipCompress 0')
Log.valide(self, "Enabling Brotli")
WOService.restart_service(self, "lsws")
else:
Log.failed(self, "Enabling Brotli")
Log.error(self, "Brotli is already enabled")
else:
Log.failed(self, "Enabling Brotli")
Log.error(self, "Brotli is already enabled")
if os.path.exists('/etc/nginx/conf.d/gzip.conf'):
WOFileUtils.mvfile(self, '/etc/nginx/conf.d/gzip.conf',
'/etc/nginx/conf.d/gzip.conf.disabled')
if check_config(self):
Log.valide(self, "Enabling Brotli")
WOGit.add(self, ["/etc/nginx"], msg="Enabling Brotli")
WOService.reload_service(self, "nginx")
else:
Log.failed(self, "Enabling Brotli")
WOGit.rollback(self, ["/etc/nginx"])
Log.error(self, "OpenLiteSpeed is not installed")
# PHPMYADMIN
if pargs.phpmyadmin:
@@ -433,22 +432,6 @@ class WOStackController(CementBaseController):
Log.debug(self, "eXtplorer is already installed")
Log.info(self, "eXtplorer is already installed")
# ultimate ngx_blocker
if pargs.ngxblocker:
if not WOAptGet.is_exec(self, 'nginx'):
pargs.nginx = True
if not os.path.isdir('/etc/nginx/bots.d'):
Log.debug(self, "Setting packages variable for ngxblocker")
packages = packages + \
[["https://raw.githubusercontent.com/"
"mitchellkrogza/nginx-ultimate-bad-bot-blocker"
"/master/install-ngxblocker",
"/usr/local/sbin/install-ngxblocker",
"ngxblocker"]]
else:
Log.debug(self, "ngxblocker is already installed")
Log.info(self, "ngxblocker is already installed")
# cheat.sh
if pargs.cheat:
if ((not os.path.exists('/usr/local/bin/cht.sh')) and
@@ -473,28 +456,18 @@ class WOStackController(CementBaseController):
if pargs.utils:
if not WOMysql.mariadb_ping(self):
pargs.mysql = True
if not (WOAptGet.is_installed(self, 'php7.2-fpm') or
WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.4-fpm') or
WOAptGet.is_installed(self, 'php8.0-fpm') or
WOAptGet.is_installed(self, 'php8.1-fpm') or
WOAptGet.is_installed(self, 'php8.2-fpm') or
WOAptGet.is_installed(self, 'php8.3-fpm') or
WOAptGet.is_installed(self, 'php8.4-fpm')):
# Check if any LSPHP version is installed
if not any(WOAptGet.is_installed(
self, 'lsphp{0}'.format(v.replace('.', '')))
for v in WOVar.wo_php_versions.values()):
pargs.php = True
Log.debug(self, "Setting packages variable for utils")
packages = packages + [[
"https://raw.githubusercontent.com"
"/rtCamp/eeadmin/master/cache/nginx/"
"clean.php",
"{0}22222/htdocs/cache/nginx/clean.php"
"https://raw.github.com/rlerdorf/"
"opcache-status/master/opcache.php",
"{0}22222/htdocs/cache/opcache/opcache.php"
.format(WOVar.wo_webroot),
"clean.php"],
["https://raw.github.com/rlerdorf/"
"opcache-status/master/opcache.php",
"{0}22222/htdocs/cache/opcache/opcache.php"
.format(WOVar.wo_webroot),
"opcache.php"],
"opcache.php"],
["https://raw.github.com/amnuts/"
"opcache-gui/master/index.php",
"{0}22222/htdocs/cache/opcache/opgui.php"
@@ -522,12 +495,6 @@ class WOStackController(CementBaseController):
if (apt_packages):
Log.debug(self, "Calling pre_pref")
pre_pref(self, apt_packages)
# meminfo = (os.popen('/bin/cat /proc/meminfo '
# '| grep MemTotal').read()).split(":")
# memsplit = re.split(" kB", meminfo[1])
# wo_mem = int(memsplit[0])
# if (wo_mem < 4000000):
# WOSwap.add(self)
Log.wait(self, "Updating apt-cache ")
WOAptGet.update(self)
Log.valide(self, "Updating apt-cache ")
@@ -574,13 +541,13 @@ class WOStackController(CementBaseController):
if pargs.all:
pargs.web = True
pargs.admin = True
pargs.php73 = True
pargs.php74 = True
pargs.php80 = True
pargs.php81 = True
pargs.php82 = True
pargs.php83 = True
pargs.php84 = True
pargs.php85 = True
pargs.fail2ban = True
pargs.proftpd = True
pargs.utils = True
@@ -607,13 +574,12 @@ class WOStackController(CementBaseController):
pargs.fail2ban = True
pargs.clamav = True
pargs.ufw = True
pargs.ngxblocker = True
# NGINX
# OpenLiteSpeed
if pargs.nginx:
if WOAptGet.is_installed(self, 'nginx-custom'):
Log.debug(self, "Removing apt_packages variable of Nginx")
apt_packages = apt_packages + WOVar.wo_nginx
if WOAptGet.is_installed(self, 'openlitespeed'):
Log.debug(self, "Removing apt_packages variable of OpenLiteSpeed")
apt_packages = apt_packages + WOVar.wo_ols
# Create a dictionary that maps PHP versions to corresponding variables.
wo_vars = {
@@ -623,20 +589,25 @@ class WOStackController(CementBaseController):
'php82': WOVar.wo_php82,
'php83': WOVar.wo_php83,
'php84': WOVar.wo_php84,
'php85': WOVar.wo_php85,
}
# Loop through all versions.
for parg_version, version in WOVar.wo_php_versions.items():
# Check if this version is present in pargs.
if getattr(pargs, parg_version):
short_ver = version.replace('.', '')
Log.debug(self, f"Setting apt_packages variable for PHP {version}")
if WOAptGet.is_installed(self, f'php{version}-fpm'):
if WOAptGet.is_installed(self, f'lsphp{short_ver}'):
apt_packages += wo_vars[parg_version]
# Check if other versions are installed.
if not any(WOAptGet.is_installed(self, f'php{other_version}-fpm') for
other_version in WOVar.wo_php_versions.values() if other_version != version):
if not any(WOAptGet.is_installed(
self, 'lsphp{0}'.format(
other_version.replace('.', '')))
for other_version in WOVar.wo_php_versions.values()
if other_version != version):
apt_packages += WOVar.wo_php_extra
else:
@@ -689,23 +660,25 @@ class WOStackController(CementBaseController):
# brotli
if pargs.brotli:
Log.wait(self, "Disabling Brotli")
WOGit.add(self, ["/etc/nginx"], msg="Commiting pending changes")
if os.path.exists('/etc/nginx/conf.d/brotli.conf'):
WOFileUtils.mvfile(self, '/etc/nginx/conf.d/brotli.conf',
'/etc/nginx/conf.d/brotli.conf.disabled')
ols_conf = '/usr/local/lsws/conf/httpd_config.conf'
if os.path.isfile(ols_conf):
if WOFileUtils.grepcheck(self, ols_conf, 'enableBr.*1'):
WOFileUtils.searchreplace(
self, ols_conf,
'enableBr 1',
'enableBr 0')
WOFileUtils.searchreplace(
self, ols_conf,
'enableGzipCompress 0',
'enableGzipCompress 1')
Log.valide(self, "Disabling Brotli")
WOService.restart_service(self, "lsws")
else:
Log.failed(self, "Disabling Brotli")
Log.error(self, "Brotli is already disabled")
else:
Log.failed(self, "Disabling Brotli")
Log.error(self, "Brotli is already disabled")
if os.path.exists('/etc/nginx/conf.d/gzip.conf.disabled'):
WOFileUtils.mvfile(self, '/etc/nginx/conf.d/gzip.conf.disabled',
'/etc/nginx/conf.d/gzip.conf')
if check_config(self):
Log.valide(self, "Disabling Brotli")
WOGit.add(self, ["/etc/nginx"], msg="Disabling Brotli")
WOService.reload_service(self, "nginx")
else:
Log.failed(self, "Disabling Brotli")
WOGit.rollback(self, ["/etc/nginx"])
Log.error(self, "OpenLiteSpeed is not installed")
# UFW
if pargs.ufw:
@@ -774,8 +747,6 @@ class WOStackController(CementBaseController):
.format(WOVar.wo_webroot),
'{0}22222/htdocs/cache/opcache'
.format(WOVar.wo_webroot),
'{0}22222/htdocs/cache/nginx/'
'clean.php'.format(WOVar.wo_webroot),
'/usr/bin/pt-query-advisor',
'{0}22222/htdocs/db/anemometer'
.format(WOVar.wo_webroot)]
@@ -800,16 +771,6 @@ class WOStackController(CementBaseController):
.format(WOVar.wo_webroot),
'{0}22222/htdocs/index.html'
.format(WOVar.wo_webroot)]
# ngxblocker
if pargs.ngxblocker:
if os.path.isfile('/usr/local/sbin/setup-ngxblocker'):
packages = packages + [
'/usr/local/sbin/setup-ngxblocker',
'/usr/local/sbin/install-ngxblocker',
'/usr/local/sbin/update-ngxblocker',
'/etc/nginx/conf.d/globalblacklist.conf',
'/etc/nginx/conf.d/botblocker-nginx-settings.conf',
'/etc/nginx/bots.d']
if (packages) or (apt_packages):
if (not pargs.force):
@@ -821,8 +782,8 @@ class WOStackController(CementBaseController):
if start_remove != "Y" and start_remove != "y":
Log.error(self, "Not starting stack removal")
if 'nginx-custom' in apt_packages:
WOService.stop_service(self, 'nginx')
if 'openlitespeed' in apt_packages:
WOService.stop_service(self, 'lsws')
if 'mariadb-server' in apt_packages:
WOMysql.backupAll(self)
@@ -904,6 +865,7 @@ class WOStackController(CementBaseController):
pargs.php82 = True
pargs.php83 = True
pargs.php84 = True
pargs.php85 = True
pargs.fail2ban = True
pargs.proftpd = True
pargs.utils = True
@@ -929,15 +891,14 @@ class WOStackController(CementBaseController):
pargs.fail2ban = True
pargs.clamav = True
pargs.ufw = True
pargs.ngxblocker = True
# NGINX
# OpenLiteSpeed
if pargs.nginx:
if WOAptGet.is_installed(self, 'nginx-custom'):
Log.debug(self, "Add Nginx to apt_packages list")
apt_packages = apt_packages + WOVar.wo_nginx
if WOAptGet.is_installed(self, 'openlitespeed'):
Log.debug(self, "Add OpenLiteSpeed to apt_packages list")
apt_packages = apt_packages + WOVar.wo_ols
else:
Log.info(self, "Nginx is not installed")
Log.info(self, "OpenLiteSpeed is not installed")
wo_vars = {
'php74': WOVar.wo_php74,
@@ -946,12 +907,14 @@ class WOStackController(CementBaseController):
'php82': WOVar.wo_php82,
'php83': WOVar.wo_php83,
'php84': WOVar.wo_php84,
'php85': WOVar.wo_php85,
}
for parg_version, version in WOVar.wo_php_versions.items():
if getattr(pargs, parg_version, False):
short_ver = version.replace('.', '')
Log.debug(self, f"Setting apt_packages variable for PHP {version}")
if not WOAptGet.is_installed(self, f'php{version}-fpm'):
if WOAptGet.is_installed(self, f'lsphp{short_ver}'):
apt_packages = apt_packages + wo_vars[parg_version]
else:
Log.debug(self, f"PHP {version} already purged")
@@ -1075,8 +1038,6 @@ class WOStackController(CementBaseController):
.format(WOVar.wo_webroot),
'{0}22222/htdocs/cache/opcache'
.format(WOVar.wo_webroot),
'{0}22222/htdocs/cache/nginx/'
'clean.php'.format(WOVar.wo_webroot),
'/usr/bin/pt-query-advisor',
'{0}22222/htdocs/db/anemometer'
.format(WOVar.wo_webroot)
@@ -1096,17 +1057,6 @@ class WOStackController(CementBaseController):
'{0}22222/htdocs/index.php'
.format(WOVar.wo_webroot)]
# ngxblocker
if pargs.ngxblocker:
if os.path.isfile('/usr/local/sbin/setup-ngxblocker'):
packages = packages + [
'/usr/local/sbin/setup-ngxblocker',
'/usr/local/sbin/install-ngxblocker',
'/usr/local/sbin/update-ngxblocker',
'/etc/nginx/conf.d/globalblacklist.conf',
'/etc/nginx/conf.d/botblocker-nginx-settings.conf',
'/etc/nginx/bots.d']
if (packages) or (apt_packages):
if (not pargs.force):
start_purge = input('Are you sure you to want to'
@@ -1118,8 +1068,8 @@ class WOStackController(CementBaseController):
if start_purge != "Y" and start_purge != "y":
Log.error(self, "Not starting stack purge")
if "nginx-custom" in apt_packages:
WOService.stop_service(self, 'nginx')
if "openlitespeed" in apt_packages:
WOService.stop_service(self, 'lsws')
if "fail2ban" in apt_packages:
WOService.stop_service(self, 'fail2ban')

View File

@@ -25,7 +25,7 @@ class WOStackMigrateController(CementBaseController):
dict(help="Migrate/Upgrade database to MariaDB",
action='store_true')),
(['--nginx'],
dict(help="Migrate Nginx TLS configuration to HTTP/3 QUIC",
dict(help="Migrate OpenLiteSpeed configuration",
action='store_true')),
(['--force'],
dict(help="Force Packages upgrade without any prompt",
@@ -102,41 +102,34 @@ class WOStackMigrateController(CementBaseController):
post_pref(self, WOVar.wo_mysql, [])
@expose(hide=True)
def migrate_nginx(self):
def migrate_ols(self):
# Add Nginx repo
pre_pref(self, WOVar.wo_nginx)
# Install Nginx
# Add OLS repo
pre_pref(self, WOVar.wo_ols)
# Install/Upgrade OpenLiteSpeed
Log.wait(self, "Updating apt-cache ")
WOAptGet.update(self)
Log.valide(self, "Updating apt-cache ")
Log.wait(self, "Upgrading Nginx ")
if WOAptGet.install(self, WOVar.wo_nginx):
Log.valide(self, "Upgrading Nginx ")
Log.wait(self, "Upgrading OpenLiteSpeed ")
if WOAptGet.install(self, WOVar.wo_ols):
Log.valide(self, "Upgrading OpenLiteSpeed ")
else:
Log.failed(self, "Upgrading Nginx ")
Log.failed(self, "Upgrading OpenLiteSpeed ")
# Update vhost SSL configs to enable QUIC
allsites = getAllsites(self)
for site in allsites:
if not site:
pass
if os.path.exists(f'/var/www/{site.sitename}/conf/nginx/ssl.conf'):
if not os.path.islink(f'/var/www/{site.sitename}/conf/nginx/ssl.conf'):
data = dict(ssl_live_path=WOVar.wo_ssl_live,
domain=site.sitename, quic=True)
WOTemplate.deploy(
self, f'/var/www/{site.sitename}/conf/nginx/ssl.conf',
'ssl.mustache', data, overwrite=True)
else:
(_, wo_root_domain) = WODomain.getlevel(
self, site.sitename)
if (site.sitename != wo_root_domain and
os.path.exists(f'/etc/letsencrypt/shared/{wo_root_domain}.conf')):
data = dict(ssl_live_path=WOVar.wo_ssl_live,
domain=wo_root_domain, quic=True)
WOTemplate.deploy(
self, f'/etc/letsencrypt/shared/{wo_root_domain}.conf',
'ssl.mustache', data, overwrite=True)
post_pref(self, WOVar.wo_nginx, [])
vhost_conf = '{0}/{1}/vhconf.conf'.format(
WOVar.wo_ols_vhost_dir, site.sitename)
if os.path.exists(vhost_conf):
# Enable QUIC in vhost SSL config
if WOFileUtils.grepcheck(self, vhost_conf, 'enableQuic'):
WOFileUtils.searchreplace(
self, vhost_conf,
'enableQuic 0',
'enableQuic 1')
post_pref(self, WOVar.wo_ols, [])
@expose(hide=True)
def default(self):
@@ -154,7 +147,7 @@ class WOStackMigrateController(CementBaseController):
Log.info(self, "If your database size is big, "
"migration may take some time.")
Log.info(self, "During migration non nginx-cached parts of "
Log.info(self, "During migration non-cached parts of "
"your site may remain down")
if not pargs.force:
start_upgrade = input("Do you want to continue:[y/N]")
@@ -168,7 +161,7 @@ class WOStackMigrateController(CementBaseController):
Log.error(self, "Your current MySQL is not alive or "
"you allready installed MariaDB")
if pargs.nginx:
if os.path.exists('/usr/sbin/nginx'):
self.migrate_nginx()
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
self.migrate_ols()
else:
Log.error(self, "Unable to connect to MariaDB")
Log.error(self, "OpenLiteSpeed is not installed")

View File

@@ -13,7 +13,6 @@ from wo.core.fileutils import WOFileUtils
from wo.core.git import WOGit
from wo.core.logging import Log
from wo.core.mysql import WOMysql
from wo.core.nginxhashbucket import hashbucket
from wo.core.services import WOService
from wo.core.shellexec import CommandExecutionError, WOShellExec
from wo.core.sslutils import SSL
@@ -66,46 +65,26 @@ def pre_pref(self, apt_packages):
with os.fdopen(os.open(conf_path, os.O_WRONLY | os.O_CREAT, 0o600), 'w', encoding='utf-8') as configfile:
config.write(configfile)
# add nginx repository
if set(WOVar.wo_nginx).issubset(set(apt_packages)):
if (WOVar.wo_distro == 'ubuntu'):
Log.info(self, "Adding repository for NGINX, please wait...")
WORepo.add(self, ppa=WOVar.wo_nginx_repo)
Log.debug(self, 'Adding ppa for Nginx')
else:
if not os.path.exists('/etc/apt/sources.list.d/wordops.list'):
Log.info(self, "Adding repository for NGINX, please wait...")
Log.debug(self, 'Adding repository for Nginx')
WORepo.add(self, repo_url=WOVar.wo_nginx_repo, repo_name="wordops")
# add OpenLiteSpeed repository
if set(WOVar.wo_ols).issubset(set(apt_packages)):
if not os.path.exists('/etc/apt/sources.list.d/openlitespeed.list'):
Log.info(self, "Adding repository for OpenLiteSpeed, please wait...")
Log.debug(self, 'Adding repository for OpenLiteSpeed')
WORepo.add(self, repo_url=WOVar.wo_ols_repo, repo_name="openlitespeed")
# add php repository
if (('php7.3-fpm' in apt_packages) or
('php7.2-fpm' in apt_packages) or
('php7.4-fpm' in apt_packages) or
('php8.0-fpm' in apt_packages) or
('php8.1-fpm' in apt_packages) or
('php8.2-fpm' in apt_packages) or
('php8.3-fpm' in apt_packages) or
('php8.4-fpm' in apt_packages)):
if (WOVar.wo_distro == 'ubuntu'):
Log.debug(self, 'Adding ppa for PHP')
Log.info(self, "Adding repository for PHP, please wait...")
WORepo.add(self, ppa=WOVar.wo_php_repo)
else:
# Add repository for php
if (WOVar.wo_platform_codename == 'buster'):
php_pref = ("Package: *\nPin: origin "
"packages.sury.org"
"\nPin-Priority: 1000\n")
with open(
'/etc/apt/preferences.d/'
'PHP.pref', mode='w',
encoding='utf-8') as php_pref_file:
php_pref_file.write(php_pref)
if not os.path.exists('/etc/apt/sources.list.d/php.list'):
Log.debug(self, 'Adding repo_url of php for debian')
Log.info(self, "Adding repository for PHP, please wait...")
WORepo.add(self, repo_url=WOVar.wo_php_repo, repo_name="php")
# add LSPHP repository (same as OLS repo)
lsphp_in_packages = False
for version in list(WOVar.wo_php_versions.values()):
short_ver = version.replace('.', '')
if 'lsphp{0}'.format(short_ver) in apt_packages:
lsphp_in_packages = True
break
if lsphp_in_packages:
if not os.path.exists('/etc/apt/sources.list.d/openlitespeed.list'):
Log.info(self, "Adding repository for LSPHP, please wait...")
Log.debug(self, 'Adding repository for LSPHP')
WORepo.add(self, repo_url=WOVar.wo_ols_repo, repo_name="openlitespeed")
# add redis repository
if set(WOVar.wo_redis).issubset(set(apt_packages)):
@@ -116,287 +95,133 @@ def pre_pref(self, apt_packages):
def post_pref(self, apt_packages, packages, upgrade=False):
"""Post activity after installation of packages"""
if (apt_packages):
# Nginx configuration
if set(WOVar.wo_nginx).issubset(set(apt_packages)):
Log.wait(self, "Configuring Nginx")
# Nginx main configuration
ngxcnf = '/etc/nginx/conf.d'
ngxcom = '/etc/nginx/common'
# OpenLiteSpeed configuration
if set(WOVar.wo_ols).issubset(set(apt_packages)):
Log.wait(self, "Configuring OpenLiteSpeed")
ols_conf = WOVar.wo_ols_conf_dir
ols_vhost = WOVar.wo_ols_vhost_dir
ngxroot = '/var/www/'
WOGit.add(self, ["/etc/nginx"], msg="Adding Nginx into Git")
data = dict(tls13=True, release=WOVar.wo_version)
WOGit.add(self, ["/usr/local/lsws/conf"],
msg="Adding OpenLiteSpeed into Git")
# Create vhost directory structure
if not os.path.exists(ols_vhost):
os.makedirs(ols_vhost)
# Determine default PHP version
default_php_short = '84'
for ver_key, ver_num in WOVar.wo_php_versions.items():
short = ver_num.replace('.', '')
if os.path.exists('/usr/local/lsws/lsphp{0}/bin/lsphp'.format(short)):
default_php_short = short
break
# Deploy main httpd_config.conf
data = dict(
server_name=WOVar.wo_fqdn,
release=WOVar.wo_version,
backend_port='22222',
default_php_short=default_php_short)
WOTemplate.deploy(self,
'/etc/nginx/nginx.conf',
'nginx-core.mustache', data, overwrite=True)
'{0}/httpd_config.conf'.format(ols_conf),
'ols-httpd.mustache', data, overwrite=True)
if not os.path.isfile('{0}/gzip.conf.disabled'.format(ngxcnf)):
data = dict(release=WOVar.wo_version)
WOTemplate.deploy(self, '{0}/gzip.conf'.format(ngxcnf),
'gzip.mustache', data)
# Deploy extApp configs for all PHP versions
WOConf.olscommon(self)
if not os.path.isfile('{0}/brotli.conf'.format(ngxcnf)):
WOTemplate.deploy(self,
'{0}/brotli.conf.disabled'
.format(ngxcnf),
'brotli.mustache', data)
# Create log and cert folder for backend
if not os.path.exists('{0}22222/logs'.format(ngxroot)):
Log.debug(self, "Creating directory "
"{0}22222/logs".format(ngxroot))
os.makedirs('{0}22222/logs'.format(ngxroot))
WOTemplate.deploy(self, '{0}/tweaks.conf'.format(ngxcnf),
'tweaks.mustache', data)
if not os.path.exists('{0}22222/cert'.format(ngxroot)):
Log.debug(self, "Creating directory "
"{0}22222/cert".format(ngxroot))
os.makedirs('{0}22222/cert'.format(ngxroot))
# Fix for white screen death with NGINX PLUS
if not WOFileUtils.grep(self, '/etc/nginx/fastcgi_params',
'SCRIPT_FILENAME'):
with open('/etc/nginx/fastcgi_params',
encoding='utf-8', mode='a') as wo_nginx:
wo_nginx.write('fastcgi_param \tSCRIPT_FILENAME '
'\t$request_filename;\n')
if not WOFileUtils.grep(self, '/etc/nginx/fastcgi_params',
'HTTP_HOST'):
WOFileUtils.textappend(self, '/etc/nginx/fastcgi_params',
'# Fix for HTTP/3 QUIC HTTP_HOST\n'
'fastcgi_param\tHTTP_HOST\t$host;\n')
if not WOFileUtils.grep(self, '/etc/nginx/proxy_params',
'X-Forwarded-Host'):
WOFileUtils.textappend(self, '/etc/nginx/proxy_params',
'proxy_set_header X-Forwarded-Host $host;\n')
if not WOFileUtils.grep(self, '/etc/nginx/proxy_params',
'X-Forwarded-Port'):
WOFileUtils.textappend(self, '/etc/nginx/proxy_params',
'proxy_set_header X-Forwarded-Port $server_port;\n')
try:
data = dict(php="9000", debug="9001",
php7="9070", debug7="9170",
release=WOVar.wo_version)
WOTemplate.deploy(
self, '{0}/upstream.conf'.format(ngxcnf),
'upstream.mustache', data, overwrite=True)
data = dict(phpconf=(
bool(WOAptGet.is_installed(self, 'php7.2-fpm'))),
release=WOVar.wo_version)
WOTemplate.deploy(
self, '{0}/stub_status.conf'.format(ngxcnf),
'stub_status.mustache', data)
data = dict(release=WOVar.wo_version)
WOTemplate.deploy(
self, '{0}/webp.conf'.format(ngxcnf),
'webp.mustache', data, overwrite=False)
WOTemplate.deploy(
self, '{0}/avif.conf'.format(ngxcnf),
'avif.mustache', data, overwrite=False)
WOTemplate.deploy(
self,
'{0}/map-wp-fastcgi-cache.conf'.format(ngxcnf),
'map-wp.mustache', data)
except CommandExecutionError as e:
Log.debug(self, "{0}".format(e))
# Setup Nginx common directory
if not os.path.exists('{0}'.format(ngxcom)):
Log.debug(self, 'Creating directory'
'/etc/nginx/common')
os.makedirs('/etc/nginx/common')
try:
data = dict(release=WOVar.wo_version)
# Common Configuration
WOTemplate.deploy(self,
'{0}/locations-wo.conf'
.format(ngxcom),
'locations.mustache', data)
# traffic advice file
WOTemplate.deploy(self,
'/var/www/html/'
'.well-known/traffic-advice',
'traffic-advice.mustache', data)
WOTemplate.deploy(self,
'{0}/wpsubdir.conf'
.format(ngxcom),
'wpsubdir.mustache', data)
for wo_php in WOVar.wo_php_versions:
data = dict(upstream="{0}".format(wo_php),
release=WOVar.wo_version)
WOConf.nginxcommon(self)
except CommandExecutionError as e:
Log.debug(self, "{0}".format(e))
with open("/etc/nginx/common/release",
"w", encoding='utf-8') as release_file:
release_file.write("v{0}"
.format(WOVar.wo_version))
release_file.close()
# Following files should not be overwrited
data = dict(webroot=ngxroot, release=WOVar.wo_version)
WOTemplate.deploy(self,
'{0}/acl.conf'
.format(ngxcom),
'acl.mustache', data, overwrite=False)
WOTemplate.deploy(self,
'{0}/blockips.conf'
.format(ngxcnf),
'blockips.mustache', data, overwrite=False)
WOTemplate.deploy(self,
'{0}/fastcgi.conf'
.format(ngxcnf),
'fastcgi.mustache', data, overwrite=True)
# add redis cache format if not already done
if (os.path.isfile("/etc/nginx/nginx.conf") and
not os.path.isfile("/etc/nginx/conf.d"
"/redis.conf")):
with open("/etc/nginx/conf.d/"
"redis.conf", "a") as redis_file:
redis_file.write(
"# Log format Settings\n"
"log_format rt_cache_redis "
"'$remote_addr "
"$upstream_response_time "
"$srcache_fetch_status "
"[$time_local] '\n"
"'$host \"$request\" $status"
" $body_bytes_sent '\n"
"'\"$http_referer\" "
"\"$http_user_agent\"';\n")
if not os.path.exists('/etc/nginx/bots.d'):
WOFileUtils.textwrite(
self, '/etc/nginx/conf.d/variables-hash.conf',
'variables_hash_max_size 4096;\n'
'variables_hash_bucket_size 4096;')
# Nginx-Plus does not have nginx
# package structure like this
# So creating directories
if not os.path.exists('/etc/nginx/sites-available'):
Log.debug(self, 'Creating directory'
'/etc/nginx/sites-available')
os.makedirs('/etc/nginx/sites-available')
if not os.path.exists('/etc/nginx/sites-enabled'):
Log.debug(self, 'Creating directory'
'/etc/nginx/sites-available')
os.makedirs('/etc/nginx/sites-enabled')
# 22222 port settings
if os.path.exists('/etc/nginx/sites-available/22222'):
Log.debug(self, "looking for the current backend port")
for line in open('/etc/nginx/sites-available/22222',
encoding='utf-8'):
if 'listen' in line:
listen_line = line.strip()
break
port = (listen_line).split(' ')
current_backend_port = (port[1]).strip()
else:
current_backend_port = '22222'
if 'current_backend_port' not in locals():
current_backend_port = '22222'
if not os.path.isdir('{0}22222/conf/ols'.format(ngxroot)):
Log.debug(self, "Creating directory "
"{0}22222/conf/ols".format(ngxroot))
os.makedirs('{0}22222/conf/ols'.format(ngxroot))
# Deploy backend vhost
data = dict(webroot=ngxroot,
release=WOVar.wo_version, port=current_backend_port)
release=WOVar.wo_version,
port='22222',
default_php_short=default_php_short)
backend_vhost_dir = '{0}/_backend'.format(ols_vhost)
if not os.path.exists(backend_vhost_dir):
os.makedirs(backend_vhost_dir)
WOTemplate.deploy(
self,
'/etc/nginx/sites-available/22222',
'22222.mustache', data, overwrite=True)
'{0}/vhconf.conf'.format(backend_vhost_dir),
'ols-backend.mustache', data, overwrite=True)
# Setup admin password
passwd = ''.join([random.choice
(string.ascii_letters + string.digits)
for n in range(24)])
if not os.path.isfile('/etc/nginx/htpasswd-wo'):
if not os.path.isfile('{0}/htpasswd-wo'.format(ols_conf)):
try:
WOShellExec.cmd_exec(
self, "printf \"WordOps:"
"$(openssl passwd -apr1 "
"{password} 2> /dev/null)\n\""
"> /etc/nginx/htpasswd-wo "
"> {conf}/htpasswd-wo "
"2>/dev/null"
.format(password=passwd))
.format(password=passwd, conf=ols_conf))
except CommandExecutionError as e:
Log.debug(self, "{0}".format(e))
Log.error(self, "Failed to save HTTP Auth")
if not os.path.islink('/etc/nginx/sites-enabled/22222'):
# Create Symbolic link for 22222
WOFileUtils.create_symlink(
self, ['/etc/nginx/'
'sites-available/'
'22222',
'/etc/nginx/'
'sites-enabled/'
'22222'])
# Create log and cert folder and softlinks
if not os.path.exists('{0}22222/logs'
.format(ngxroot)):
Log.debug(self, "Creating directory "
"{0}22222/logs "
.format(ngxroot))
os.makedirs('{0}22222/logs'
.format(ngxroot))
if not os.path.exists('{0}22222/cert'
.format(ngxroot)):
Log.debug(self, "Creating directory "
"{0}22222/cert"
.format(ngxroot))
os.makedirs('{0}22222/cert'
.format(ngxroot))
if not os.path.isdir('{0}22222/conf/nginx'
.format(ngxroot)):
Log.debug(self, "Creating directory "
"{0}22222/conf/nginx"
.format(ngxroot))
os.makedirs('{0}22222/conf/nginx'
.format(ngxroot))
WOFileUtils.create_symlink(
self,
['/var/log/nginx/'
'22222.access.log',
'{0}22222/'
'logs/access.log'
.format(ngxroot)]
)
WOFileUtils.create_symlink(
self,
['/var/log/nginx/'
'22222.error.log',
'{0}22222/'
'logs/error.log'
.format(ngxroot)]
)
# Generate self-signed cert for backend if missing
if (not os.path.isfile('{0}22222/cert/22222.key'
.format(ngxroot))):
SSL.selfsignedcert(self, proftpd=False, backend=True)
if not os.path.exists('{0}22222/conf/nginx/ssl.conf'
.format(ngxroot)):
with open("/var/www/22222/conf/nginx/"
"ssl.conf", "w") as php_file:
php_file.write("ssl_certificate "
"/var/www/22222/cert/22222.crt;\n"
"ssl_certificate_key "
"/var/www/22222/cert/22222.key;\n"
"ssl_stapling off;\n")
# Deploy OLS admin password via admpass.sh
if os.path.isfile('/usr/local/lsws/admin/misc/admpass.sh'):
try:
WOShellExec.cmd_exec(
self,
'/usr/local/lsws/admin/misc/admpass.sh '
'--password "{0}"'.format(passwd))
except CommandExecutionError as e:
Log.debug(self, "{0}".format(e))
# traffic advice file
data = dict(release=WOVar.wo_version)
WOTemplate.deploy(self,
'/var/www/html/'
'.well-known/traffic-advice',
'traffic-advice.mustache', data)
# Start/Restart OLS
if not WOService.restart_service(self, 'lsws'):
Log.info(self, "Rolling back to previous configuration")
WOGit.rollback(self, ["/usr/local/lsws/conf"])
if not WOService.restart_service(self, 'lsws'):
Log.error(
self, "There is an error in OpenLiteSpeed configuration.\n"
"Use the command '/usr/local/lsws/bin/openlitespeed -t' to identify "
"the cause of this issue", False)
else:
Log.valide(self, "Configuring OpenLiteSpeed")
WOGit.add(self, ["/usr/local/lsws/conf"],
msg="Adding OpenLiteSpeed into Git")
server_ip = WOFqdn.get_server_ip(self)
if server_ip is None:
server_ip = WOVar.wo_fqdn
if set(["nginx"]).issubset(set(apt_packages)):
if set(["openlitespeed"]).issubset(set(apt_packages)):
print("WordOps backend configuration was successful\n"
"You can access it on : https://{0}:22222"
.format(server_ip))
print("HTTP Auth User Name: WordOps" +
"\nHTTP Auth Password : {0}".format(passwd))
WOService.reload_service(self, 'nginx')
else:
self.msg = (self.msg + ["HTTP Auth User "
"Name: WordOps"] +
@@ -405,177 +230,69 @@ def post_pref(self, apt_packages, packages, upgrade=False):
self.msg = (self.msg + [f'WordOps backend is available on https://{server_ip}:22222 '
f'or https://{WOVar.wo_fqdn}:22222'])
data = dict(release=WOVar.wo_version)
WOTemplate.deploy(self, '/opt/cf-update.sh',
'cf-update.mustache',
data, overwrite=True)
WOFileUtils.chmod(self, "/opt/cf-update.sh", 0o775)
Log.debug(self, 'Creating Cloudflare.conf')
WOShellExec.cmd_exec(self, '/opt/cf-update.sh')
WOCron.setcron_weekly(self, '/opt/cf-update.sh '
'> /dev/null 2>&1',
comment='Cloudflare IP refresh cronjob '
'added by WordOps')
# Nginx Configation into GIT
if not WOService.restart_service(self, 'nginx'):
try:
hashbucket(self)
WOService.restart_service(self, 'nginx')
except Exception:
Log.warn(
self, "increasing nginx server_names_hash_bucket_size "
"do not fix the issue")
Log.info(self, "Rolling back to previous configuration")
WOGit.rollback(self, ["/etc/nginx"])
if not WOService.restart_service(self, 'nginx'):
Log.error(
self, "There is an error in Nginx configuration.\n"
"Use the command nginx -t to identify "
"the cause of this issue", False)
else:
Log.valide(self, "Configuring Nginx")
WOGit.add(self, ["/etc/nginx"], msg="Adding Nginx into Git")
if not os.path.isdir('/etc/systemd/system/nginx.service.d'):
WOFileUtils.mkdir(self,
'/etc/systemd/system/nginx.service.d')
if not os.path.isdir(
'/etc/systemd/system/nginx.service.d/limits.conf'):
with open(
'/etc/systemd/system/nginx.service.d/limits.conf',
encoding='utf-8', mode='w') as ngx_limit:
ngx_limit.write('[Service]\nLimitNOFILE=500000')
WOShellExec.cmd_exec(self, 'systemctl daemon-reload')
WOService.restart_service(self, 'nginx')
# php conf
# LSPHP configuration
php_list = []
for version in list(WOVar.wo_php_versions.values()):
package_name = 'php' + version + '-fpm'
short_ver = version.replace('.', '')
package_name = 'lsphp{0}'.format(short_ver)
if package_name in apt_packages:
php_list.append([version])
php_list.append([version, short_ver])
for php_version in php_list:
WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git")
Log.wait(self, "Configuring php{0}-fpm".format(php_version[0]))
for php_info in php_list:
php_version = php_info[0]
php_short = php_info[1]
Log.wait(self, "Configuring lsphp{0}".format(php_short))
ngxroot = '/var/www/'
# Create log directories
if not os.path.exists('/var/log/php/{0}/'.format(php_version[0])):
if not os.path.exists('/var/log/php/{0}/'.format(php_version)):
Log.debug(
self, 'Creating directory /var/log/php/{0}/'
.format(php_version[0]))
os.makedirs('/var/log/php/{0}/'.format(php_version[0]))
.format(php_version))
os.makedirs('/var/log/php/{0}/'.format(php_version))
if not os.path.isfile(
'/etc/php/{0}/fpm/php.ini.orig'.format(php_version[0])):
WOFileUtils.copyfile(self,
'/etc/php/{0}/fpm/php.ini'.format(
php_version[0]),
'/etc/php/{0}/fpm/php.ini.orig'
.format(php_version[0]))
# Configure LSPHP php.ini
lsphp_ini = '/usr/local/lsws/lsphp{0}/etc/php/{1}/litespeed/php.ini'.format(
php_short, php_version)
lsphp_ini_orig = lsphp_ini + '.orig'
# Parse etc/php/x.x/fpm/php.ini
config = configparser.ConfigParser()
Log.debug(self, "configuring php file "
"/etc/php/{0}/fpm/php.ini".format(php_version[0]))
config.read('/etc/php/{0}/fpm/php.ini.orig'.format(php_version[0]))
config['PHP']['expose_php'] = 'Off'
config['PHP']['post_max_size'] = '100M'
config['PHP']['upload_max_filesize'] = '100M'
config['PHP']['max_execution_time'] = '300'
config['PHP']['max_input_time'] = '300'
config['PHP']['max_input_vars'] = '20000'
config['Date']['date.timezone'] = WOVar.wo_timezone
config['opcache']['opcache.enable'] = '1'
config['opcache']['opcache.interned_strings_buffer'] = '8'
config['opcache']['opcache.max_accelerated_files'] = '10000'
config['opcache']['opcache.memory_consumption'] = '256'
config['opcache']['opcache.save_comments'] = '1'
config['opcache']['opcache.revalidate_freq'] = '5'
config['opcache']['opcache.consistency_checks'] = '0'
config['opcache']['opcache.validate_timestamps'] = '1'
with open('/etc/php/{0}/fpm/php.ini'.format(php_version[0]),
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "Writting php configuration into "
"/etc/php/{0}/fpm/php.ini".format(php_version[0]))
config.write(configfile)
if os.path.isfile(lsphp_ini):
if not os.path.isfile(lsphp_ini_orig):
WOFileUtils.copyfile(self, lsphp_ini, lsphp_ini_orig)
# Render php-fpm pool template for phpx.x
data = dict(pid="/run/php/php{0}-fpm.pid".format(php_version[0]),
error_log="/var/log/php{0}-fpm.log".format(
php_version[0]),
include="/etc/php/{0}/fpm/pool.d/*.conf"
.format(php_version[0]))
WOTemplate.deploy(
self, '/etc/php/{0}/fpm/php-fpm.conf'.format(php_version[0]),
'php-fpm.mustache', data)
php_short = php_version[0].replace(".", "")
data = dict(pool='www-php{0}'.format(php_short),
listen='php{0}-fpm.sock'.format(php_short),
user='www-data',
group='www-data', listenuser='root',
listengroup='www-data', openbasedir=True)
WOTemplate.deploy(self, '/etc/php/{0}/fpm/pool.d/www.conf'
.format(php_version[0]),
'php-pool.mustache', data)
data = dict(pool='www-two-php{0}'.format(php_short),
listen='php{0}-two-fpm.sock'.format(php_short),
user='www-data',
group='www-data', listenuser='root',
listengroup='www-data', openbasedir=True)
config = configparser.ConfigParser()
Log.debug(self, "configuring php file {0}".format(lsphp_ini))
config.read(lsphp_ini_orig)
config['PHP']['expose_php'] = 'Off'
config['PHP']['post_max_size'] = '100M'
config['PHP']['upload_max_filesize'] = '100M'
config['PHP']['max_execution_time'] = '300'
config['PHP']['max_input_time'] = '300'
config['PHP']['max_input_vars'] = '20000'
config['Date']['date.timezone'] = WOVar.wo_timezone
config['opcache']['opcache.enable'] = '1'
config['opcache']['opcache.interned_strings_buffer'] = '8'
config['opcache']['opcache.max_accelerated_files'] = '10000'
config['opcache']['opcache.memory_consumption'] = '256'
config['opcache']['opcache.save_comments'] = '1'
config['opcache']['opcache.revalidate_freq'] = '5'
config['opcache']['opcache.consistency_checks'] = '0'
config['opcache']['opcache.validate_timestamps'] = '1'
with open(lsphp_ini,
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "Writing php configuration into "
"{0}".format(lsphp_ini))
config.write(configfile)
# Deploy extApp config for this PHP version
data = dict(
php_version=php_version,
short_version=php_short,
release=WOVar.wo_version)
WOTemplate.deploy(self,
'/etc/php/{0}/fpm/pool.d/www-two.conf'.format(
php_version[0]),
'php-pool.mustache', data)
# Generate /etc/php/x.x/fpm/pool.d/debug.conf
WOFileUtils.copyfile(self,
"/etc/php/{0}/fpm/pool.d/www.conf".format(
php_version[0]),
"/etc/php/{0}/fpm/pool.d/debug.conf"
.format(php_version[0]))
WOFileUtils.searchreplace(self,
"/etc/php/{0}/fpm/pool.d/"
"debug.conf".format(php_version[0]),
"[www-php{0}]".format(php_short),
"[debug]")
config = configparser.ConfigParser()
config.read(
'/etc/php/{0}/fpm/pool.d/debug.conf'.format(php_version[0]))
config['debug']['listen'] = '127.0.0.1:91{0}'.format(php_short)
config['debug']['rlimit_core'] = 'unlimited'
config['debug']['slowlog'] = '/var/log/php/{0}/slow.log'.format(
php_version[0])
config['debug']['request_slowlog_timeout'] = '10s'
with open('/etc/php/{0}/fpm/pool.d/debug.conf'
.format(php_version[0]),
encoding='utf-8', mode='w') as confifile:
Log.debug(self,
"writting PHP configuration into "
"/etc/php/{0}/fpm/pool.d/debug.conf"
.format(php_version[0]))
config.write(confifile)
with open("/etc/php/{0}/fpm/pool.d/debug.conf"
.format(php_version[0]),
encoding='utf-8', mode='a') as myfile:
myfile.write("php_admin_value[xdebug.profiler_output_dir] "
"= /tmp/ \nphp_admin_value[xdebug.profiler_"
"output_name] = cachegrind.out.%p-%H-%R "
"\nphp_admin_flag[xdebug.profiler_enable"
"_trigger] = on \nphp_admin_flag[xdebug."
"profiler_enable] = off\n")
# Disable xdebug
if not WOShellExec.cmd_exec(self, "grep -q \';zend_extension\'"
" /etc/php/{0}/mods-available/"
"xdebug.ini".format(php_version[0])):
WOFileUtils.searchreplace(self, "/etc/php/{0}/"
"mods-available/"
"xdebug.ini".format(php_version[0]),
"zend_extension",
";zend_extension")
'{0}/lsphp{1}.conf'
.format(WOVar.wo_ols_conf_dir, php_short),
'ols-extapp.mustache', data)
# PHP and Debug pull configuration
if not os.path.exists('{0}22222/htdocs/fpm/status/'
@@ -585,12 +302,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
.format(ngxroot))
os.makedirs('{0}22222/htdocs/fpm/status/'
.format(ngxroot))
open('{0}22222/htdocs/fpm/status/debug{1}'
.format(ngxroot, php_short),
encoding='utf-8', mode='a').close()
open('{0}22222/htdocs/fpm/status/php{1}'
.format(ngxroot, php_short),
encoding='utf-8', mode='a').close()
# Write info.php
if not os.path.exists('{0}22222/htdocs/php/'
@@ -621,31 +332,10 @@ def post_pref(self, apt_packages, packages, upgrade=False):
'www-data',
'www-data', recursive=True)
# enable imagick php extension
WOShellExec.cmd_exec(self, 'phpenmod -v ALL imagick')
# check service restart or rollback configuration
if not WOService.restart_service(self,
'php{0}-fpm'
.format(php_version[0])):
WOGit.rollback(self, ["/etc/php"], msg="Rollback PHP")
else:
Log.valide(
self, "Configuring php{0}-fpm".format(php_version[0]))
WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git")
if os.path.exists('/etc/nginx/conf.d/upstream.conf'):
if not WOFileUtils.grepcheck(
self, '/etc/nginx/conf.d/upstream.conf',
'php{0}'.format(php_short)):
data = dict(php="9000", debug="9001",
php7="9070", debug7="9170",
php8="9080", debug8="9180",
release=WOVar.wo_version)
WOTemplate.deploy(
self, '/etc/nginx/conf.d/upstream.conf',
'upstream.mustache', data, True)
WOConf.nginxcommon(self)
# Restart OLS to pick up new PHP config
WOService.restart_service(self, 'lsws')
Log.valide(
self, "Configuring lsphp{0}".format(php_short))
# create mysql config if it doesn't exist
if "mariadb-server" in apt_packages:
@@ -707,7 +397,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
WOFileUtils.copyfile(self, "/etc/mysql/my.cnf",
"/etc/mysql/my.cnf.default-pkg")
wo_ram = psutil.virtual_memory().total / (1024 * 1024)
# set InnoDB variable depending on the RAM available
wo_ram_innodb = int(wo_ram * 0.3)
wo_ram_log_buffer = int(wo_ram_innodb * 0.25)
wo_ram_log_size = int(wo_ram_log_buffer * 0.5)
@@ -735,7 +424,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
else:
WOTemplate.deploy(
self, '/etc/mysql/my.cnf', 'my.mustache', data)
# replacing default values
Log.debug(self, "Tuning MySQL configuration")
if os.path.isdir('/etc/systemd/system/mariadb.service.d'):
if not os.path.isfile(
@@ -748,16 +436,9 @@ def post_pref(self, apt_packages, packages, upgrade=False):
'[Service]\nLimitNOFILE=500000')
WOShellExec.cmd_exec(self, 'systemctl daemon-reload')
Log.valide(self, "Tuning MySQL configuration")
# set innodb_buffer_pool_instances depending
# on the amount of RAM
WOService.restart_service(self, 'mariadb')
# WOFileUtils.mvfile(self, '/var/lib/mysql/ib_logfile0',
# '/var/lib/mysql/ib_logfile0.bak')
# WOFileUtils.mvfile(self, '/var/lib/mysql/ib_logfile1',
# '/var/lib/mysql/ib_logfile1.bak')
WOCron.setcron_weekly(self, 'mysqlcheck -Aos --auto-repair '
'> /dev/null 2>&1',
comment='MySQL optimization cronjob '
@@ -771,8 +452,8 @@ def post_pref(self, apt_packages, packages, upgrade=False):
WOGit.add(self, ["/etc/fail2ban"],
msg="Adding Fail2ban into Git")
Log.wait(self, "Configuring Fail2Ban")
nginxf2b = bool(os.path.exists('/var/log/nginx'))
data = dict(release=WOVar.wo_version, nginx=nginxf2b)
olsf2b = bool(os.path.exists('/usr/local/lsws/bin/openlitespeed'))
data = dict(release=WOVar.wo_version, ols=olsf2b)
WOTemplate.deploy(
self,
'/etc/fail2ban/jail.d/custom.conf',
@@ -820,7 +501,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
WOService.restart_service(self, 'proftpd')
if os.path.isfile('/etc/ufw/ufw.conf'):
# add rule for proftpd with UFW
if WOFileUtils.grepcheck(
self, '/etc/ufw/ufw.conf', 'ENABLED=yes'):
try:
@@ -861,18 +541,15 @@ def post_pref(self, apt_packages, packages, upgrade=False):
Log.failed(self, "Configuring Sendmail")
if "ufw" in apt_packages:
# check if ufw is already enabled
if not WOFileUtils.grep(self,
'/etc/ufw/ufw.conf', 'ENABLED=yes'):
Log.wait(self, "Configuring UFW")
# check if ufw script is already created
if not os.path.isfile("/opt/ufw.sh"):
data = dict()
WOTemplate.deploy(self, '/opt/ufw.sh',
'ufw.mustache',
data, overwrite=False)
WOFileUtils.chmod(self, "/opt/ufw.sh", 0o700)
# setup ufw rules
WOShellExec.cmd_exec(self, "bash /opt/ufw.sh")
Log.valide(self, "Configuring UFW")
else:
@@ -880,31 +557,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
# Redis configuration
if "redis-server" in apt_packages:
if os.path.isfile("/etc/nginx/conf.d/upstream.conf"):
if not WOFileUtils.grep(self, "/etc/nginx/conf.d/"
"upstream.conf",
"redis"):
with open("/etc/nginx/conf.d/upstream.conf",
"a") as redis_file:
redis_file.write("upstream redis {\n"
" server 127.0.0.1:6379;\n"
" keepalive 10;\n}\n")
if os.path.isfile("/etc/nginx/nginx.conf"):
if not os.path.isfile("/etc/nginx/conf.d/redis.conf"):
with open("/etc/nginx/conf.d/redis.conf",
"a") as redis_file:
redis_file.write(
"# Log format Settings\n"
"log_format rt_cache_redis '$remote_addr "
"$upstream_response_time $srcache_fetch_status "
"[$time_local] '\n '$host \"$request\" "
"$status $body_bytes_sent '\n'\"$http_referer\" "
"\"$http_user_agent\"';\n")
# set redis.conf parameter
# set maxmemory 10% for ram below 512MB and 20% for others
# set maxmemory-policy allkeys-lru
# enable systemd service
WOGit.add(self, ["/etc/redis"],
msg="Adding Redis into Git")
Log.debug(self, "Enabling redis systemd service")
@@ -1157,7 +809,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
wo_grant_host = self.app.config.get('mysql', 'grant-host')
else:
wo_grant_host = 'localhost'
# check if mysql credentials are available
if (WOMysql.mariadb_ping(self)
and wo_grant_host == 'localhost'):
try:
@@ -1284,20 +935,6 @@ def post_pref(self, apt_packages, packages, upgrade=False):
for x in packages):
WOFileUtils.chmod(self, "/usr/bin/pt-query-advisor", 0o775)
# ngxblocker
if any('/usr/local/sbin/install-ngxblocker' == x[1]
for x in packages):
# remove duplicate directives
if os.path.exists('/etc/nginx/conf.d/variables-hash.conf'):
WOFileUtils.rm(self, '/etc/nginx/conf.d/variables-hash.conf')
WOFileUtils.chmod(
self, "/usr/local/sbin/install-ngxblocker", 0o700)
WOShellExec.cmd_exec(self, '/usr/local/sbin/install-ngxblocker -x')
WOFileUtils.chmod(
self, "/usr/local/sbin/update-ngxblocker", 0o700)
if not WOService.restart_service(self, 'nginx'):
Log.error(self, 'ngxblocker install failed')
def pre_stack(self):
"""Inital server configuration and tweak"""
@@ -1309,20 +946,15 @@ def pre_stack(self):
if os.path.exists('/var/lib/wo/version.txt'):
with open('/var/lib/wo/version.txt',
mode='r', encoding='utf-8') as wo_ver:
# check version written in version.txt
wo_check = bool(wo_ver.read().strip() ==
'{0}'.format(WOVar.wo_version))
else:
wo_check = False
if wo_check is False:
# wo sysctl tweaks
# check system type
wo_arch = bool((os.uname()[4]) == 'x86_64')
if os.path.isfile('/proc/1/environ'):
# detect lxc containers
wo_lxc = WOFileUtils.grepcheck(
self, '/proc/1/environ', 'container=lxc')
# detect wsl
wo_wsl = WOFileUtils.grepcheck(
self, '/proc/1/environ', 'wsl')
else:
@@ -1334,12 +966,12 @@ def pre_stack(self):
WOTemplate.deploy(
self, '/etc/sysctl.d/60-wo-tweaks.conf',
'sysctl.mustache', data, True)
# use tcp_bbr congestion algorithm only on new kernels
if (WOVar.wo_platform_codename == 'focal' or
WOVar.wo_platform_codename == 'buster' or
WOVar.wo_platform_codename == 'jammy' or
WOVar.wo_platform_codename == 'bullseye' or
WOVar.wo_platform_codename == 'bookworm'):
WOVar.wo_platform_codename == 'bookworm' or
WOVar.wo_platform_codename == 'trixie'):
try:
WOShellExec.cmd_exec(
self, 'modprobe tcp_bbr')
@@ -1373,7 +1005,6 @@ def pre_stack(self):
Log.debug(self, str(e))
Log.warn(self, "failed to tweak sysctl")
# apply sysctl tweaks
WOShellExec.cmd_exec(
self, 'sysctl -eq -p /etc/sysctl.d/60-wo-tweaks.conf')
@@ -1401,9 +1032,7 @@ def pre_stack(self):
'root soft nofile 500000\n')
# custom motd-news
data = dict()
# check if update-motd.d directory exist
if os.path.isdir('/etc/update-motd.d/'):
# render custom motd template
WOTemplate.deploy(
self, '/etc/update-motd.d/98-wo-update',
'wo-update.mustache', data)

View File

@@ -18,7 +18,6 @@ class WOStackStatusController(CementBaseController):
def start(self):
"""Start services"""
services = []
wo_system = "/lib/systemd/system/"
pargs = self.app.pargs
if all(value is None or value is False for value in vars(pargs).values()):
pargs.nginx = True
@@ -28,30 +27,23 @@ class WOStackStatusController(CementBaseController):
pargs.netdata = True
pargs.ufw = True
if pargs.php:
if self.app.config.has_section('php'):
config_php_ver = self.app.config.get(
'php', 'version')
current_php = config_php_ver.replace(".", "")
setattr(self.app.pargs, 'php{0}'.format(current_php), True)
if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
services = services + ['nginx']
if pargs.nginx or pargs.php:
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "Nginx is not installed")
if pargs.php:
for parg_version, version in WOVar.wo_php_versions.items():
if os.path.exists(f'{wo_system}' + f'php{version}-fpm.service'):
services = services + [f'php{version}-fpm']
if pargs.nginx:
Log.info(self, "OpenLiteSpeed is not installed")
if pargs.php:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
for parg_version, version in WOVar.wo_php_versions.items():
if (getattr(pargs, parg_version, False) and
os.path.exists(f'{wo_system}' + f'php{version}-fpm.service')):
services = services + [f'php{version}-fpm']
else:
Log.info(self, f"PHP{version}-FPM is not installed")
if getattr(pargs, parg_version, False):
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or
@@ -65,14 +57,13 @@ class WOStackStatusController(CementBaseController):
"Unable to check MySQL service status")
if pargs.redis:
if os.path.exists('{0}'.format(wo_system) +
'redis-server.service'):
if os.path.exists('/lib/systemd/system/redis-server.service'):
services = services + ['redis-server']
else:
Log.info(self, "Redis server is not installed")
if pargs.fail2ban:
if os.path.exists('{0}'.format(wo_system) + 'fail2ban.service'):
if os.path.exists('/lib/systemd/system/fail2ban.service'):
services = services + ['fail2ban']
else:
Log.info(self, "fail2ban is not installed")
@@ -86,7 +77,7 @@ class WOStackStatusController(CementBaseController):
# netdata
if pargs.netdata:
if os.path.exists('{0}'.format(wo_system) + 'netdata.service'):
if os.path.exists('/lib/systemd/system/netdata.service'):
services = services + ['netdata']
else:
Log.info(self, "Netdata is not installed")
@@ -99,37 +90,29 @@ class WOStackStatusController(CementBaseController):
def stop(self):
"""Stop services"""
services = []
wo_system = "/lib/systemd/system/"
pargs = self.app.pargs
if all(value is None or value is False for value in vars(pargs).values()):
pargs.nginx = True
pargs.php = True
pargs.mysql = True
if pargs.php:
if self.app.config.has_section('php'):
config_php_ver = self.app.config.get(
'php', 'version')
current_php = config_php_ver.replace(".", "")
setattr(self.app.pargs, 'php{0}'.format(current_php), True)
if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
services = services + ['nginx']
if pargs.nginx or pargs.php:
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "Nginx is not installed")
if pargs.php:
for parg_version, version in WOVar.wo_php_versions.items():
if os.path.exists(f'{wo_system}' + f'php{version}-fpm.service'):
services = services + [f'php{version}-fpm']
if pargs.nginx:
Log.info(self, "OpenLiteSpeed is not installed")
if pargs.php:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
for parg_version, version in WOVar.wo_php_versions.items():
if (getattr(pargs, parg_version, False) and
os.path.exists(f'{wo_system}' + f'php{version}-fpm.service')):
services = services + [f'php{version}-fpm']
else:
Log.info(self, f"PHP{version}-FPM is not installed")
if getattr(pargs, parg_version, False):
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or
@@ -143,14 +126,13 @@ class WOStackStatusController(CementBaseController):
"Unable to check MySQL service status")
if pargs.redis:
if os.path.exists('{0}'.format(wo_system) +
'redis-server.service'):
if os.path.exists('/lib/systemd/system/redis-server.service'):
services = services + ['redis-server']
else:
Log.info(self, "Redis server is not installed")
if pargs.fail2ban:
if os.path.exists('{0}'.format(wo_system) + 'fail2ban.service'):
if os.path.exists('/lib/systemd/system/fail2ban.service'):
services = services + ['fail2ban']
else:
Log.info(self, "fail2ban is not installed")
@@ -164,7 +146,7 @@ class WOStackStatusController(CementBaseController):
# netdata
if pargs.netdata:
if os.path.exists('{0}'.format(wo_system) + 'netdata.service'):
if os.path.exists('/lib/systemd/system/netdata.service'):
services = services + ['netdata']
else:
Log.info(self, "Netdata is not installed")
@@ -177,7 +159,6 @@ class WOStackStatusController(CementBaseController):
def restart(self):
"""Restart services"""
services = []
wo_system = "/lib/systemd/system/"
pargs = self.app.pargs
if all(value is None or value is False for value in vars(pargs).values()):
pargs.nginx = True
@@ -185,30 +166,23 @@ class WOStackStatusController(CementBaseController):
pargs.mysql = True
pargs.netdata = True
if pargs.php:
if self.app.config.has_section('php'):
config_php_ver = self.app.config.get(
'php', 'version')
current_php = config_php_ver.replace(".", "")
setattr(self.app.pargs, 'php{0}'.format(current_php), True)
if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
services = services + ['nginx']
if pargs.nginx or pargs.php:
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "Nginx is not installed")
if pargs.php:
for parg_version, version in WOVar.wo_php_versions.items():
if os.path.exists(f'{wo_system}' + f'php{version}-fpm.service'):
services = services + [f'php{version}-fpm']
if pargs.nginx:
Log.info(self, "OpenLiteSpeed is not installed")
if pargs.php:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
for parg_version, version in WOVar.wo_php_versions.items():
if (getattr(pargs, parg_version, False) and
os.path.exists(f'{wo_system}' + f'php{version}-fpm.service')):
services = services + [f'php{version}-fpm']
else:
Log.info(self, f"PHP{version}-FPM is not installed")
if getattr(pargs, parg_version, False):
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or
@@ -222,14 +196,13 @@ class WOStackStatusController(CementBaseController):
"Unable to check MySQL service status")
if pargs.redis:
if os.path.exists('{0}'.format(wo_system) +
'redis-server.service'):
if os.path.exists('/lib/systemd/system/redis-server.service'):
services = services + ['redis-server']
else:
Log.info(self, "Redis server is not installed")
if pargs.fail2ban:
if os.path.exists('{0}'.format(wo_system) + 'fail2ban.service'):
if os.path.exists('/lib/systemd/system/fail2ban.service'):
services = services + ['fail2ban']
else:
Log.info(self, "fail2ban is not installed")
@@ -243,7 +216,7 @@ class WOStackStatusController(CementBaseController):
# netdata
if pargs.netdata:
if os.path.exists('{0}'.format(wo_system) + 'netdata.service'):
if os.path.exists('/lib/systemd/system/netdata.service'):
services = services + ['netdata']
else:
Log.info(self, "Netdata is not installed")
@@ -256,7 +229,6 @@ class WOStackStatusController(CementBaseController):
def status(self):
"""Status of services"""
services = []
wo_system = "/lib/systemd/system/"
pargs = self.app.pargs
if all(value is None or value is False for value in vars(pargs).values()):
pargs.nginx = True
@@ -267,15 +239,17 @@ class WOStackStatusController(CementBaseController):
pargs.ufw = True
if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
services = services + ['nginx']
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
services = services + ['lsws']
else:
Log.info(self, "Nginx is not installed")
Log.info(self, "OpenLiteSpeed is not installed")
if pargs.php:
for parg_version, version in WOVar.wo_php_versions.items():
if os.path.exists(f'{wo_system}' + f'php{version}-fpm.service'):
services = services + [f'php{version}-fpm']
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or
@@ -289,14 +263,13 @@ class WOStackStatusController(CementBaseController):
"Unable to check MySQL service status")
if pargs.redis:
if os.path.exists('{0}'.format(wo_system) +
'redis-server.service'):
if os.path.exists('/lib/systemd/system/redis-server.service'):
services = services + ['redis-server']
else:
Log.info(self, "Redis server is not installed")
if pargs.fail2ban:
if os.path.exists('{0}'.format(wo_system) + 'fail2ban.service'):
if os.path.exists('/lib/systemd/system/fail2ban.service'):
services = services + ['fail2ban']
else:
Log.info(self, "fail2ban is not installed")
@@ -310,7 +283,7 @@ class WOStackStatusController(CementBaseController):
# netdata
if pargs.netdata:
if os.path.exists('{0}'.format(wo_system) + 'netdata.service'):
if os.path.exists('/lib/systemd/system/netdata.service'):
services = services + ['netdata']
else:
Log.info(self, "Netdata is not installed")
@@ -334,7 +307,6 @@ class WOStackStatusController(CementBaseController):
def reload(self):
"""Reload service"""
services = []
wo_system = "/lib/systemd/system/"
pargs = self.app.pargs
if all(value is None or value is False for value in vars(pargs).values()):
pargs.nginx = True
@@ -342,30 +314,23 @@ class WOStackStatusController(CementBaseController):
pargs.mysql = True
pargs.fail2ban = True
if pargs.php:
if self.app.config.has_section('php'):
config_php_ver = self.app.config.get(
'php', 'version')
current_php = config_php_ver.replace(".", "")
setattr(self.app.pargs, 'php{0}'.format(current_php), True)
if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
services = services + ['nginx']
if pargs.nginx or pargs.php:
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "Nginx is not installed")
if pargs.php:
for parg_version, version in WOVar.wo_php_versions.items():
if os.path.exists(f'{wo_system}' + f'php{version}-fpm.service'):
services = services + [f'php{version}-fpm']
if pargs.nginx:
Log.info(self, "OpenLiteSpeed is not installed")
if pargs.php:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
for parg_version, version in WOVar.wo_php_versions.items():
if (getattr(pargs, parg_version, False) and
os.path.exists(f'{wo_system}' + f'php{version}-fpm.service')):
services = services + [f'php{version}-fpm']
else:
Log.info(self, f"PHP{version}-FPM is not installed")
if getattr(pargs, parg_version, False):
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
if 'lsws' not in services:
services = services + ['lsws']
else:
Log.info(self, "LSPHP is managed by OpenLiteSpeed")
if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or
@@ -379,14 +344,13 @@ class WOStackStatusController(CementBaseController):
"Unable to check MySQL service status")
if pargs.redis:
if os.path.exists('{0}'.format(wo_system) +
'redis-server.service'):
if os.path.exists('/lib/systemd/system/redis-server.service'):
services = services + ['redis-server']
else:
Log.info(self, "Redis server is not installed")
if pargs.fail2ban:
if os.path.exists('{0}'.format(wo_system) + 'fail2ban.service'):
if os.path.exists('/lib/systemd/system/fail2ban.service'):
services = services + ['fail2ban']
else:
Log.info(self, "fail2ban is not installed")
@@ -400,7 +364,7 @@ class WOStackStatusController(CementBaseController):
# netdata
if pargs.netdata:
if os.path.exists('{0}'.format(wo_system) + 'netdata.service'):
if os.path.exists('/lib/systemd/system/netdata.service'):
services = services + ['netdata']
else:
Log.info(self, "Netdata is not installed")

View File

@@ -31,7 +31,7 @@ class WOStackUpgradeController(CementBaseController):
(['--security'],
dict(help='Upgrade security stack', action='store_true')),
(['--nginx'],
dict(help='Upgrade Nginx stack', action='store_true')),
dict(help='Upgrade OpenLiteSpeed stack', action='store_true')),
(['--php'],
dict(help='Upgrade PHP stack', action='store_true')),
(['--mysql'],
@@ -52,13 +52,11 @@ class WOStackUpgradeController(CementBaseController):
(['--composer'],
dict(help='Upgrade Composer', action='store_true')),
(['--mysqltuner'],
dict(help='Upgrade Composer', action='store_true')),
dict(help='Upgrade MySQLTuner', action='store_true')),
(['--phpmyadmin'],
dict(help='Upgrade phpMyAdmin', action='store_true')),
(['--adminer'],
dict(help='Upgrade Adminer', action='store_true')),
(['--ngxblocker'],
dict(help='Upgrade phpMyAdmin', action='store_true')),
(['--no-prompt'],
dict(help="Upgrade Packages without any prompt",
action='store_true')),
@@ -108,6 +106,7 @@ class WOStackUpgradeController(CementBaseController):
pargs.php82 = True
pargs.php83 = True
pargs.php84 = True
pargs.php85 = True
pargs.mysql = True
pargs.wpcli = True
@@ -121,19 +120,18 @@ class WOStackUpgradeController(CementBaseController):
pargs.mysqltuner = True
if pargs.security:
pargs.ngxblocker = True
pargs.fail2ban = True
# nginx
# OpenLiteSpeed
if pargs.nginx:
if WOAptGet.is_installed(self, 'nginx-custom'):
apt_packages = apt_packages + WOVar.wo_nginx
if WOAptGet.is_installed(self, 'openlitespeed'):
apt_packages = apt_packages + WOVar.wo_ols
else:
if os.path.isfile('/usr/sbin/nginx'):
Log.info(self, "Updating Nginx templates")
post_pref(self, WOVar.wo_nginx, [])
if os.path.isfile('/usr/local/lsws/bin/openlitespeed'):
Log.info(self, "Updating OpenLiteSpeed templates")
post_pref(self, WOVar.wo_ols, [])
else:
Log.info(self, "Nginx Stable is not already installed")
Log.info(self, "OpenLiteSpeed is not already installed")
wo_vars = {
'php74': WOVar.wo_php74,
@@ -142,12 +140,14 @@ class WOStackUpgradeController(CementBaseController):
'php82': WOVar.wo_php82,
'php83': WOVar.wo_php83,
'php84': WOVar.wo_php84,
'php85': WOVar.wo_php85,
}
for parg_version, version in WOVar.wo_php_versions.items():
if getattr(pargs, parg_version, False):
short_ver = version.replace('.', '')
Log.debug(self, f"Setting apt_packages variable for PHP {version}")
if WOAptGet.is_installed(self, f'php{version}-fpm'):
if WOAptGet.is_installed(self, f'lsphp{short_ver}'):
apt_packages = apt_packages + wo_vars[parg_version] + WOVar.wo_php_extra
else:
Log.debug(self, f"PHP {version} not installed")
@@ -259,54 +259,36 @@ class WOStackUpgradeController(CementBaseController):
"/usr/bin/mysqltuner",
"MySQLTuner"]]
# ngxblocker
if pargs.ngxblocker:
if os.path.exists('/usr/local/sbin/install-ngxblocker'):
packages = packages + [[
'https://raw.githubusercontent.com/mitchellkrogza/'
'nginx-ultimate-bad-bot-blocker/master/update-ngxblocker',
'/usr/local/sbin/update-ngxblocker',
'ngxblocker'
]]
if not apt_packages and not packages:
self.app.args.print_help()
else:
pre_stack(self)
if apt_packages:
if not ("php7.2-fpm" in apt_packages or
"php7.3-fpm" in apt_packages or
"php7.4-fpm" in apt_packages or
"php8.0-fpm" in apt_packages or
"php8.1-fpm" in apt_packages or
"php8.2-fpm" in apt_packages or
"php8.3-fpm" in apt_packages or
"php8.4-fpm" in apt_packages or
"redis-server" in apt_packages or
"nginx-custom" in apt_packages or
"mariadb-server" in apt_packages):
pass
else:
# Check if critical packages are being upgraded
has_critical = False
for pkg in apt_packages:
if pkg in ['openlitespeed', 'redis-server',
'mariadb-server'] or pkg.startswith('lsphp'):
has_critical = True
break
if has_critical:
Log.warn(
self, "Your sites may be down for few seconds if "
"you are upgrading Nginx, PHP-FPM, MariaDB or Redis")
"you are upgrading OpenLiteSpeed, LSPHP, "
"MariaDB or Redis")
# Check prompt
if not (pargs.no_prompt or pargs.force):
start_upgrade = input("Do you want to continue:[y/N]")
if start_upgrade != "Y" and start_upgrade != "y":
Log.error(self, "Not starting package update")
# additional pre_pref
if "nginx-custom" in apt_packages:
pre_pref(self, WOVar.wo_nginx)
if "openlitespeed" in apt_packages:
pre_pref(self, WOVar.wo_ols)
Log.wait(self, "Updating APT cache")
# apt-get update
WOAptGet.update(self)
Log.valide(self, "Updating APT cache")
# check if nginx upgrade is blocked
if os.path.isfile(
'/etc/apt/preferences.d/nginx-block'):
post_pref(self, WOVar.wo_nginx, [], True)
# redis pre_pref
if "redis-server" in apt_packages:
pre_pref(self, WOVar.wo_redis)
@@ -324,9 +306,6 @@ class WOStackUpgradeController(CementBaseController):
if WOAptGet.is_selected(self, 'Netdata', packages):
WOFileUtils.rm(self, '/var/lib/wo/tmp/kickstart.sh')
if WOAptGet.is_selected(self, 'ngxblocker', packages):
WOFileUtils.rm(self, '/usr/local/sbin/update-ngxblocker')
if WOAptGet.is_selected(self, 'WordOps Dashboard', packages):
if os.path.isfile('/var/www/22222/htdocs/index.php'):
WOFileUtils.rm(self, '/var/www/22222/htdocs/index.php')
@@ -340,15 +319,6 @@ class WOStackUpgradeController(CementBaseController):
if WOAptGet.is_selected(self, 'WP-CLI', packages):
WOFileUtils.chmod(self, "/usr/local/bin/wp", 0o775)
if WOAptGet.is_selected(self, 'ngxblocker', packages):
if os.path.exists('/etc/nginx/conf.d/variables-hash.conf'):
WOFileUtils.rm(
self, '/etc/nginx/conf.d/variables-hash.conf')
WOFileUtils.chmod(
self, '/usr/local/sbin/update-ngxblocker', 0o775)
WOShellExec.cmd_exec(
self, '/usr/local/sbin/update-ngxblocker -nq')
if WOAptGet.is_selected(self, 'MySQLTuner', packages):
WOFileUtils.chmod(self, "/usr/bin/mysqltuner", 0o775)
if os.path.exists('/usr/local/bin/mysqltuner'):

View File

@@ -1,3 +1,4 @@
[Definition]
failregex = ^ \[error\] \d+#\d+: .* forbidden .*, client: <HOST>, .*$
failregex = ^ \[error\] .* forbidden .*, client: <HOST>, .*$
^\S+ \S+ \[.*\] .* 403 .* <HOST> .*$
ignoreregex =

View File

@@ -4,23 +4,17 @@ ignoreip = 127.0.0.1/8 ::1
[recidive]
enabled = true
{{#nginx}}[nginx-http-auth]
enabled = true
logpath = /var/log/nginx/*error*.log
[nginx-botsearch]
enabled = true
logpath = /var/log/nginx/*access*.log
[wo-wordpress]
{{#ols}}[wo-wordpress]
enabled = true
filter = wo-wordpress
action = iptables-multiport[name="wo-wordpress", port="http,https"]
logpath = /var/log/nginx/*access*.log
logpath = /usr/local/lsws/logs/access.log
/usr/local/lsws/conf/vhosts/*/logs/ols.access_log
maxretry = 5
[nginx-forbidden]
[ols-forbidden]
enabled = true
filter = nginx-forbidden
action = iptables-multiport[name="nginx-forbidden", port="http,https"]
logpath = /var/log/nginx/*error*.log{{/nginx}}
action = iptables-multiport[name="ols-forbidden", port="http,https"]
logpath = /usr/local/lsws/logs/error.log
/usr/local/lsws/conf/vhosts/*/logs/ols.error_log{{/ols}}

View File

@@ -0,0 +1,9 @@
OpenLiteSpeed ({{version}}):
server_name {{server_name}}
max_connections {{max_connections}}
max_ssl_connections {{max_ssl_connections}}
keepalive_timeout {{keepalive_timeout}}
gzip_compress {{gzip_compress}}
brotli_compress {{brotli_compress}}
quic_enabled {{quic_enabled}}

View File

@@ -0,0 +1,16 @@
# WordOps (wo) Access Control - OpenLiteSpeed
# Protect locations using HTTP authentication or IP address
realm WordOpsAdmin {
userDB {
location /usr/local/lsws/conf/htpasswd-wo
}
}
context / {
realm WordOpsAdmin
authName "Restricted Area"
required valid-user
accessControl {
allow 127.0.0.1, ::1
}
}

View File

@@ -0,0 +1,104 @@
# WordOps Admin Backend Virtual Host - WordOps {{release}}
# Port {{port}}
docRoot {{webroot}}22222/htdocs
vhDomain _backend
enableGzip 1
enableBr 1
errorlog {{webroot}}22222/logs/ols.error_log {
useServer 0
logLevel ERROR
rollingSize 10M
}
accesslog {{webroot}}22222/logs/ols.access_log {
useServer 0
rollingSize 10M
keepDays 30
compressArchive 0
}
index {
useServer 0
indexFiles index.php, index.html, index.htm
autoIndex 1
}
# PHP handler
scripthandler {
add lsapi:lsphp{{default_php_short}} php
}
extprocessor lsphp{{default_php_short}} {
type lsapi
address uds://tmp/lshttpd/lsphp{{default_php_short}}.sock
maxConns 10
env PHP_LSAPI_CHILDREN=10
env LSAPI_AVOID_FORK=200M
initTimeout 60
retryTimeout 0
pcKeepAliveTimeout 60
respBuffer 0
autoStart 2
path /usr/local/lsws/lsphp{{default_php_short}}/bin/lsphp
backlog 100
instances 1
priority 0
memSoftLimit 2047M
memHardLimit 2047M
procSoftLimit 1400
procHardLimit 1500
}
# Rewrite rules
rewrite {
enable 1
autoLoadHtaccess 1
rules <<<END_rules
RewriteRule ^(.*)$ /index.php?$1 [QSA,L]
END_rules
}
# HTTP Auth realm for backend
realm WordOpsBackend {
userDB {
location /usr/local/lsws/conf/htpasswd-wo
}
}
# Require auth for the whole backend
context / {
realm WordOpsBackend
authName "Restricted Area"
required valid-user
allowBrowse 1
addDefaultCharset off
}
# Netdata proxy context
context /netdata/ {
type proxy
handler netdata_backend
addDefaultCharset off
}
extprocessor netdata_backend {
type proxy
address 127.0.0.1:19999
maxConns 100
pcKeepAliveTimeout 60
initTimeout 60
retryTimeout 0
respBuffer 0
}
# SSL Configuration
vhssl {
keyFile /var/www/22222/cert/22222.key
certFile /var/www/22222/cert/22222.crt
sslProtocol 24
}
# Include custom configs
include {{webroot}}22222/conf/ols/*.conf

View File

@@ -0,0 +1,23 @@
# LSPHP {{php_version}} External App Configuration - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
extprocessor lsphp{{short_version}} {
type lsapi
address uds://tmp/lshttpd/lsphp{{short_version}}.sock
maxConns 10
env PHP_LSAPI_CHILDREN=10
env LSAPI_AVOID_FORK=200M
initTimeout 60
retryTimeout 0
pcKeepAliveTimeout 60
respBuffer 0
autoStart 2
path /usr/local/lsws/lsphp{{short_version}}/bin/lsphp
backlog 100
instances 1
priority 0
memSoftLimit 2047M
memHardLimit 2047M
procSoftLimit 1400
procHardLimit 1500
}

View File

@@ -0,0 +1,208 @@
# OpenLiteSpeed Main Configuration - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
serverName {{server_name}}
user nobody
group nogroup
priority 0
inMemBufSize 60M
swappingDir /tmp/lshttpd/swap
autoFix503 1
gracefulRestartTimeout 300
mime conf/mime.properties
showVersionNumber 0
adminEmails root@localhost
errorlog /usr/local/lsws/logs/error.log {
logLevel DEBUG
debugLevel 0
rollingSize 10M
enableStderrLog 1
}
accesslog /usr/local/lsws/logs/access.log {
rollingSize 10M
keepDays 30
compressArchive 0
}
indexFiles index.php, index.html, index.htm
expires {
enableExpires 1
expiresByType image/*=A604800,text/css=A604800,application/x-javascript=A604800,application/javascript=A604800,font/*=A604800,application/x-font-ttf=A604800
}
tuning {
maxConnections 10000
maxSSLConnections 10000
connTimeout 300
maxKeepAliveReq 10000
keepAliveTimeout 5
sndBufSize 0
rcvBufSize 0
maxReqURLLen 32768
maxReqHeaderSize 65536
maxReqBodySize 2047M
maxDynRespHeaderSize 32768
maxDynRespSize 2047M
maxCachedFileSize 4096
totalInMemCacheSize 20M
maxMMapFileSize 256K
totalMMapCacheSize 40M
useSendfile 1
fileETag 28
enableGzipCompress 1
enableBrCompress 1
enableDynGzipCompress 1
gzipCompressLevel 6
brStaticCompressLevel 6
gzipAutoUpdateStatic 1
gzipStaticCompressLevel 6
gzipMaxFileSize 10M
gzipMinFileSize 300
enableQuic 1
quicShmDir /dev/shm
}
fileAccessControl {
followSymbolLink 1
checkSymbolLink 0
requiredPermissionMask 000
restrictedPermissionMask 000
}
perClientConnLimit {
staticReqPerSec 0
dynReqPerSec 0
outBandwidth 0
inBandwidth 0
softLimit 10000
hardLimit 10000
gracePeriod 15
banPeriod 300
}
CGIRLimit {
maxCGIInstances 20
minUID 11
minGID 10
priority 0
CPUSoftLimit 10
CPUHardLimit 50
memSoftLimit 1460M
memHardLimit 1470M
procSoftLimit 400
procHardLimit 450
}
accessDenyDir {
dir /
dir /etc/*
dir /dev/*
dir conf/*
dir admin/conf/*
}
scripthandler {
add lsapi:lsphp{{default_php_short}} php
}
railsDefaults {
maxConns 1
env LSAPI_MAX_IDLE=60
initTimeout 60
retryTimeout 0
pcKeepAliveTimeout 60
respBuffer 0
backlog 50
runOnStartUp 3
extMaxIdleTime 300
priority 3
memSoftLimit 2047M
memHardLimit 2047M
procSoftLimit 500
procHardLimit 600
}
wsgiDefaults {
maxConns 5
env LSAPI_MAX_IDLE=60
initTimeout 60
retryTimeout 0
pcKeepAliveTimeout 60
respBuffer 0
backlog 50
runOnStartUp 3
extMaxIdleTime 300
priority 3
memSoftLimit 2047M
memHardLimit 2047M
procSoftLimit 500
procHardLimit 600
}
nodeDefaults {
maxConns 5
env LSAPI_MAX_IDLE=60
initTimeout 60
retryTimeout 0
pcKeepAliveTimeout 60
respBuffer 0
backlog 50
runOnStartUp 3
extMaxIdleTime 300
priority 3
memSoftLimit 2047M
memHardLimit 2047M
procSoftLimit 500
procHardLimit 600
}
module cache {
ls_enabled 1
checkPrivateCache 1
checkPublicCache 1
maxCacheObjSize 10000000
maxStaleAge 200
qsCache 1
reqCookieCache 1
respCookieCache 1
ignoreReqCacheCtrl 1
ignoreRespCacheCtrl 0
enableCache 0
expireInSeconds 3600
enablePrivateCache 0
privateExpireInSeconds 3600
}
# Listener for HTTP on port 80
listener Default {
address *:80
secure 0
}
# Listener for HTTPS on port 443
listener Secure {
address *:443
secure 1
keyFile /usr/local/lsws/conf/example.key
certFile /usr/local/lsws/conf/example.crt
sslProtocol 24
enableQuic 1
}
# Listener for backend on port 22222
listener Backend {
address *:{{backend_port}}
secure 1
keyFile /var/www/22222/cert/22222.key
certFile /var/www/22222/cert/22222.crt
sslProtocol 24
}
# Include external app definitions
include /usr/local/lsws/conf/lsphp*.conf
# Include virtual host mappings
include /usr/local/lsws/conf/vhosts/*/vhconf.conf

View File

@@ -0,0 +1,53 @@
# General Security .htaccess Rules - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# Deny access to hidden files (except .well-known)
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule "(^|/)\.(?!well-known\/)" - [F]
</IfModule>
# Deny access to backup, log, and config files
<FilesMatch "\.(old|orig|original|php#|php~|php_bak|save|swo|aspx?|tpl|sh|bash|bak?|cfg|cgi|dll|exe|git|hg|ini|jsp|log|mdb|out|sql|svn|swp|tar|rdf|gz|zip|bz2|7z|pem|asc|conf|dump)$">
Order Deny,Allow
Deny from all
</FilesMatch>
# Deny access to readme, license, and similar files
<FilesMatch "(readme|license|example|README|LEGALNOTICE|INSTALLATION|CHANGELOG)\.(txt|html|md)$">
Order Deny,Allow
Deny from all
</FilesMatch>
# Cache static files
<IfModule mod_expires.c>
ExpiresActive On
ExpiresByType image/jpeg "access plus 1 year"
ExpiresByType image/gif "access plus 1 year"
ExpiresByType image/png "access plus 1 year"
ExpiresByType image/webp "access plus 1 year"
ExpiresByType image/svg+xml "access plus 1 year"
ExpiresByType image/x-icon "access plus 1 year"
ExpiresByType text/css "access plus 1 year"
ExpiresByType application/javascript "access plus 1 year"
ExpiresByType application/x-javascript "access plus 1 year"
ExpiresByType font/ttf "access plus 1 year"
ExpiresByType font/otf "access plus 1 year"
ExpiresByType font/woff "access plus 1 year"
ExpiresByType font/woff2 "access plus 1 year"
</IfModule>
# CORS headers for static assets
<IfModule mod_headers.c>
<FilesMatch "\.(ttf|ttc|otf|eot|woff|woff2|font\.css|css|js|gif|png|jpe?g|svg|svgz|ico|webp)$">
Header set Access-Control-Allow-Origin "*"
</FilesMatch>
</IfModule>
# Security headers
<IfModule mod_headers.c>
Header set X-Frame-Options "SAMEORIGIN"
Header set X-Content-Type-Options "nosniff"
Header set Referrer-Policy "strict-origin-when-cross-origin"
Header set X-Powered-By "WordOps"
</IfModule>

View File

@@ -0,0 +1,10 @@
# OpenLiteSpeed SSL Configuration - WordOps
# Domain: {{domain}}
vhssl {
keyFile {{ssl_live_path}}/{{domain}}/key.pem
certFile {{ssl_live_path}}/{{domain}}/fullchain.pem
certChain 1
sslProtocol 24
enableQuic 1
}

View File

@@ -0,0 +1,17 @@
# Virtual Host Mapping for {{site_name}} - WordOps {{release}}
virtualhost {{site_name}} {
vhRoot {{webroot}}
configFile {{vhost_conf_path}}
allowSymbolLink 1
enableScript 1
restrained 0
}
# Listener mappings
listener Default {
map {{site_name}} {{site_name}}{{#www_alias}}, www.{{site_name}}{{/www_alias}}
}
listener Secure {
map {{site_name}} {{site_name}}{{#www_alias}}, www.{{site_name}}{{/www_alias}}
}

View File

@@ -0,0 +1,122 @@
# OpenLiteSpeed Virtual Host Configuration - WordOps {{release}}
# Domain: {{site_name}}
docRoot {{webroot}}/htdocs
vhDomain {{site_name}}
vhAliases www.{{site_name}}
enableGzip 1
enableBr 1
errorlog {{webroot}}/logs/ols.error_log {
useServer 0
logLevel ERROR
rollingSize 10M
}
accesslog {{webroot}}/logs/ols.access_log {
useServer 0
rollingSize 10M
keepDays 30
compressArchive 0
}
index {
useServer 0
indexFiles {{^static}}index.php, {{/static}}index.html, index.htm
autoIndex 0
}
{{^static}}
# PHP handler via LSAPI
scripthandler {
add lsapi:lsphp{{php_short}} php
}
{{/static}}
# External app - LSPHP
extprocessor lsphp{{php_short}} {
type lsapi
address uds://tmp/lshttpd/lsphp{{php_short}}.sock
maxConns 10
env PHP_LSAPI_CHILDREN=10
env LSAPI_AVOID_FORK=200M
initTimeout 60
retryTimeout 0
pcKeepAliveTimeout 60
respBuffer 0
autoStart 2
path /usr/local/lsws/lsphp{{php_short}}/bin/lsphp
backlog 100
instances 1
priority 0
memSoftLimit 2047M
memHardLimit 2047M
procSoftLimit 1400
procHardLimit 1500
}
# LSCache module configuration
module cache {
ls_enabled 1
checkPrivateCache 1
checkPublicCache 1
maxCacheObjSize 10000000
maxStaleAge 200
qsCache 1
reqCookieCache 1
respCookieCache 1
ignoreReqCacheCtrl 1
ignoreRespCacheCtrl 0
{{#wp}}
enableCache 1
{{/wp}}
{{^wp}}
enableCache 0
{{/wp}}
expireInSeconds 3600
enablePrivateCache 0
privateExpireInSeconds 3600
}
# Rewrite rules
rewrite {
enable 1
autoLoadHtaccess 1
}
# Security context for wp-admin
context /wp-admin/ {
location {{webroot}}/htdocs/wp-admin/
allowBrowse 1
{{^static}}
addDefaultCharset off
phpIniOverride {
}
{{/static}}
}
# Security - deny hidden files
context exp:/(\.(?!well-known)) {
allowBrowse 0
}
# Let's Encrypt validation
context /.well-known/acme-challenge/ {
location /var/www/html/.well-known/acme-challenge/
allowBrowse 1
addDefaultCharset off
}
# Include per-site custom configurations
include {{webroot}}/conf/ols/*.conf
{{#ssl}}
# SSL Configuration
vhssl {
keyFile {{ssl_live_path}}/{{site_name}}/key.pem
certFile {{ssl_live_path}}/{{site_name}}/fullchain.pem
certChain 1
sslProtocol 24
enableQuic 1
}
{{/ssl}}

View File

@@ -0,0 +1,49 @@
# WordPress Common Security Rules - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# This file is auto-generated and placed in the site's htdocs/.htaccess
# Limit access to wp-login.php to prevent brute force attacks
<Files wp-login.php>
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteCond %{REQUEST_METHOD} POST
RewriteCond %{HTTP_REFERER} !^https?://(.*)?{{site_name}} [NC]
RewriteRule .* - [F]
</IfModule>
</Files>
# Block xmlrpc.php except Jetpack IPs
<Files xmlrpc.php>
Order Deny,Allow
Deny from all
Allow from 122.248.245.244
Allow from 54.217.201.243
Allow from 54.232.116.4
Allow from 192.0.80.0/20
Allow from 192.0.96.0/20
Allow from 192.0.112.0/20
Allow from 195.234.108.0/22
</Files>
# Block wp-config.txt
<Files wp-config.txt>
Order Deny,Allow
Deny from all
</Files>
# Deny access to PHP files in uploads directory
<IfModule mod_rewrite.c>
RewriteEngine On
RewriteRule ^wp-content/uploads/.*\.php$ - [F]
RewriteRule ^wp-content/uploads/edd/.*\.zip$ / [R=301,L]
</IfModule>
# Mitigate DoS attack with WordPress script concatenation
<Files "load-scripts.php">
Order Deny,Allow
Deny from all
</Files>
<Files "load-styles.php">
Order Deny,Allow
Deny from all
</Files>

View File

@@ -0,0 +1,227 @@
<?php
/**
* Plugin Name: WP Fort Knox
* Description: Enhanced WordPress security plugin that disables file modifications and plugin management from wp-admin while preserving WP-CLI functionality.
* Version: 2.0.0
* Author: WEFIXIT
* Network: true
*
* Security Features:
* - Defines DISALLOW_FILE_MODS constant to block file changes from wp-admin
* - Filters plugin installation, upload, update, and deletion capabilities at runtime (non-destructive)
* - Blocks creation of administrator users through wp-admin interface
* - Prevents role elevation to administrator outside of WP-CLI
* - Hides administrator role from user role dropdown in wp-admin
* - Displays admin notices to inform users about restrictions
* - Preserves WP-CLI functionality for all operations
* - Can be disabled temporarily via constant or filter
*
* This is a Must-Use plugin - place directly in /wp-content/mu-plugins/
*
* Temporary Disable:
* Add to wp-config.php: define('WP_FORT_KNOX_DISABLED', true);
* Or use filter: add_filter('wp_fort_knox_disabled', '__return_true');
*
* WP-CLI Commands for Administrative Tasks:
*
* User Management:
* wp user create admin admin@example.com --role=administrator --user_pass=secure_password
* wp user set-role username administrator
* wp user list --fields=ID,user_login,roles
*
* Plugin Management:
* wp plugin install plugin-name --activate
* wp plugin update plugin-name
* wp plugin update --all
* wp plugin list
* wp plugin deactivate plugin-name
* wp plugin delete plugin-name
*
* Theme Management:
* wp theme install theme-name --activate
* wp theme update theme-name
* wp theme update --all
* wp theme list
*
* Core Updates:
* wp core update
* wp core update --version=6.4.1
* wp core check-update
*
* @package WPFortKnox
* @since 1.0.0
* @version 2.0.0
*/
// Prevent direct access
if ( ! defined( 'ABSPATH' ) ) {
exit;
}
class WP_Fort_Knox {
private $managed_capabilities = [
'install_plugins',
'upload_plugins',
'update_plugins',
'delete_plugins'
];
public function __construct() {
// Check if disabled
if ( $this->is_disabled() ) {
return;
}
// Apply security measures
$this->apply_security();
}
/**
* Check if plugin should be disabled
*/
private function is_disabled() {
// Always allow WP-CLI
if ( defined( 'WP_CLI' ) && WP_CLI ) {
return true;
}
// Check for disable constant
if ( defined( 'WP_FORT_KNOX_DISABLED' ) && WP_FORT_KNOX_DISABLED ) {
return true;
}
// Allow filter for programmatic control
if ( apply_filters( 'wp_fort_knox_disabled', false ) ) {
return true;
}
return false;
}
/**
* Apply all security measures
*/
private function apply_security() {
// Block file modifications
if ( ! defined( 'DISALLOW_FILE_MODS' ) ) {
define( 'DISALLOW_FILE_MODS', true );
}
// Remove plugin capabilities at runtime (non-destructive)
add_filter( 'user_has_cap', [ $this, 'filter_capabilities' ], 999, 4 );
// Hide administrator role from user creation/edit screens
add_filter( 'editable_roles', [ $this, 'hide_administrator_role' ] );
// Block admin user creation via wp-admin
add_filter( 'pre_insert_user_data', [ $this, 'block_admin_creation' ], 10, 3 );
// Prevent role elevation to administrator
add_action( 'set_user_role', [ $this, 'prevent_admin_elevation' ], 10, 3 );
// Show notice on plugins page
add_action( 'admin_notices', [ $this, 'show_admin_notice' ] );
}
/**
* Filter user capabilities at runtime
*/
public function filter_capabilities( $allcaps, $caps, $args, $user ) {
// Only filter for non-CLI requests
foreach ( $this->managed_capabilities as $cap ) {
if ( isset( $allcaps[ $cap ] ) ) {
$allcaps[ $cap ] = false;
}
}
return $allcaps;
}
/**
* Hide administrator role from dropdowns
*/
public function hide_administrator_role( $roles ) {
unset( $roles['administrator'] );
return $roles;
}
/**
* Block admin user creation
*/
public function block_admin_creation( $data, $update, $user_id ) {
// Allow updates to existing users
if ( $update ) {
return $data;
}
// Block new admin creation
if ( isset( $data['role'] ) && $data['role'] === 'administrator' ) {
wp_die(
'Administrator account creation is disabled. Use WP-CLI: wp user create username email@example.com --role=administrator',
'Security Policy',
[ 'back_link' => true ]
);
}
return $data;
}
/**
* Prevent elevation to administrator role
*/
public function prevent_admin_elevation( $user_id, $role, $old_roles ) {
// If trying to add administrator role
if ( $role === 'administrator' && ! in_array( 'administrator', $old_roles ) ) {
// Revert the change
$user = get_userdata( $user_id );
if ( $user ) {
$user->remove_role( 'administrator' );
$user->add_role( $old_roles[0] ?? 'subscriber' );
// Log the attempt
if ( defined( 'WP_DEBUG' ) && WP_DEBUG ) {
error_log( sprintf(
'[WP Fort Knox] Blocked administrator elevation for user %s (ID: %d)',
$user->user_login,
$user_id
) );
}
}
}
}
/**
* Show admin notice on relevant pages
*/
public function show_admin_notice() {
// Only show to users who would normally have capability
if ( ! current_user_can( 'manage_options' ) ) {
return;
}
$screen = get_current_screen();
// Show on plugins page
if ( $screen && $screen->id === 'plugins' ) {
?>
<div class="notice notice-info">
<p><strong>WP Fort Knox:</strong> Plugin management is disabled in wp-admin. Use WP-CLI for all plugin operations. To disable temporarily, contact support.</p>
</div>
<?php
}
// Show on users page when trying to add new
if ( $screen && $screen->id === 'user' && $screen->action === 'add' ) {
?>
<div class="notice notice-warning">
<p><strong>WP Fort Knox:</strong> Administrator role creation is disabled. Use WP-CLI for all user operations. To disable temporarily, contact support.</p>
</div>
<?php
}
}
}
// Initialize - no activation hooks needed for mu-plugins
new WP_Fort_Knox();

View File

@@ -128,33 +128,36 @@ class WOAcme:
self, "mkdir -p {0}/{1} && {2} --install-cert -d {1} --ecc "
"--cert-file {0}/{1}/cert.pem --key-file {0}/{1}/key.pem "
"--fullchain-file {0}/{1}/fullchain.pem "
"--ca-file {0}/{1}/ca.pem --reloadcmd \"nginx -t && "
"service nginx restart\" "
"--ca-file {0}/{1}/ca.pem --reloadcmd \"{3} restart\" "
.format(WOVar.wo_ssl_live,
wo_domain_name, WOAcme.wo_acme_exec)):
wo_domain_name, WOAcme.wo_acme_exec,
WOVar.wo_ols_ctrl)):
Log.valide(self, "Deploying SSL cert")
else:
Log.failed(self, "Deploying SSL cert")
Log.error(self, "Unable to deploy certificate")
if os.path.isdir('/var/www/{0}/conf/nginx'
.format(wo_domain_name)):
vhost_dir = '{0}/{1}'.format(
WOVar.wo_ols_vhost_dir, wo_domain_name)
if os.path.isdir(vhost_dir):
data = dict(ssl_live_path=WOVar.wo_ssl_live,
domain=wo_domain_name, quic=True)
WOTemplate.deploy(self,
'/var/www/{0}/conf/nginx/ssl.conf'
.format(wo_domain_name),
'ssl.mustache', data, overwrite=False)
'{0}/ssl.conf'.format(vhost_dir),
'ols-ssl.mustache', data, overwrite=False)
if not WOFileUtils.grep(self, '/var/www/22222/conf/nginx/ssl.conf',
'/etc/letsencrypt'):
backend_ssl = '{0}/22222/vhconf.conf'.format(
WOVar.wo_ols_vhost_dir)
if (os.path.isfile(backend_ssl) and
not WOFileUtils.grep(
self, backend_ssl, '/etc/letsencrypt')):
Log.info(self, "Securing WordOps backend with current cert")
data = dict(ssl_live_path=WOVar.wo_ssl_live,
domain=wo_domain_name, quic=False)
WOTemplate.deploy(self,
'/var/www/22222/conf/nginx/ssl.conf',
'ssl.mustache', data, overwrite=True)
'{0}/22222/ssl.conf'.format(
WOVar.wo_ols_vhost_dir),
'ols-ssl.mustache', data, overwrite=True)
WOGit.add(self, ["/etc/letsencrypt"],
msg="Adding letsencrypt folder")
@@ -223,16 +226,13 @@ class WOAcme:
return False
def removeconf(self, domain):
sslconf = ("/var/www/{0}/conf/nginx/ssl.conf"
.format(domain))
sslforce = ("/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(domain))
sslconf = ("{0}/{1}/ssl.conf"
.format(WOVar.wo_ols_vhost_dir, domain))
acmedir = [
'{0}'.format(sslforce), '{0}'.format(sslconf),
'{0}'.format(sslconf),
'{0}/{1}_ecc'.format(WOVar.wo_ssl_archive, domain),
'{0}.disabled'.format(sslconf), '{0}.disabled'
.format(sslforce), '{0}/{1}'
.format(WOVar.wo_ssl_live, domain),
'{0}.disabled'.format(sslconf),
'{0}/{1}'.format(WOVar.wo_ssl_live, domain),
'/etc/letsencrypt/shared/{0}.conf'.format(domain)]
wo_domain = domain
# check acme.sh is installed
@@ -255,16 +255,15 @@ class WOAcme:
else:
if os.path.islink("{0}".format(sslconf)):
WOFileUtils.remove_symlink(self, "{0}".format(sslconf))
WOFileUtils.rm(self, '{0}'.format(sslforce))
if WOFileUtils.grepcheck(self, '/var/www/22222/conf/nginx/ssl.conf',
'{0}'.format(domain)):
backend_ssl = '{0}/22222/ssl.conf'.format(WOVar.wo_ols_vhost_dir)
if (os.path.isfile(backend_ssl) and
WOFileUtils.grepcheck(self, backend_ssl,
'{0}'.format(domain))):
Log.info(
self, "Setting back default certificate for WordOps backend")
with open("/var/www/22222/conf/nginx/"
"ssl.conf", "w") as ssl_conf_file:
ssl_conf_file.write("ssl_certificate "
"/var/www/22222/cert/22222.crt;\n"
"ssl_certificate_key "
"/var/www/22222/cert/22222.key;\n"
"ssl_stapling off;\n")
with open(backend_ssl, "w") as ssl_conf_file:
ssl_conf_file.write("vhssl {\n"
" keyFile /var/www/22222/cert/22222.key\n"
" certFile /var/www/22222/cert/22222.crt\n"
"}\n")

View File

@@ -94,7 +94,7 @@ class WOMysql():
try:
Log.info(self, "Backing up database at location: "
"/var/lib/wo-backup/mysql")
# Setup Nginx common directory
# Setup backup directory
if not os.path.exists('/var/lib/wo-backup/mysql'):
Log.debug(self, 'Creating directory'
'/var/lib/wo-backup/mysql')

View File

@@ -1,19 +1,2 @@
"""WordOps Nginx Manager"""
import subprocess
from wo.core.logging import Log
def check_config(self):
"""Check Nginx configuration and return boolean"""
Log.debug(self, "Testing Nginx configuration ")
# Check Nginx configuration before executing command
sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
output, error_output = sub.communicate()
if 'emerg' in str(error_output):
Log.debug(self, "Nginx configuration check failed")
return False
else:
Log.debug(self, "Nginx configuration check was successful")
return True
"""WordOps Nginx compatibility module - redirects to OLS"""
from wo.core.ols import check_config # noqa: F401

View File

@@ -1,49 +1,6 @@
"""WordOps Hash Bucket Calculator"""
import fileinput
import math
import os
import subprocess
from wo.core.fileutils import WOFileUtils
"""Deprecated: OLS does not require hash bucket configuration"""
def hashbucket(self):
# Check Nginx Hashbucket error
sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
output, error_output = sub.communicate()
if 'server_names_hash_bucket_size' not in str(error_output):
return True
count = 0
# Get the list of sites-availble
sites_list = os.listdir("/etc/nginx/sites-enabled/")
# Count the number of characters in site names
for site in sites_list:
count = sum([count, len(site)])
# Calculate Nginx hash bucket size
ngx_calc = math.trunc(sum([math.log(count, 2), 2]))
ngx_hash = math.trunc(math.pow(2, ngx_calc))
# Replace hashbucket in Nginx.conf file
if WOFileUtils.grepcheck(self, "/etc/nginx/nginx.conf",
"# server_names_hash_bucket_size 64;"):
ngxconf = open("/etc/nginx/conf.d/hashbucket.conf",
encoding='utf-8', mode='w')
ngxconf.write("\tserver_names_hash_bucket_size {0};".format(ngx_hash))
ngxconf.close()
elif WOFileUtils.grepcheck(self, "/etc/nginx/nginx/conf",
"server_names_hash_bucket_size"):
for line in fileinput.FileInput("/etc/nginx/nginx.conf", inplace=1):
if "server_names_hash_bucket_size" in line:
print("\tserver_names_hash_bucket_size {0};".format(ngx_hash))
else:
print(line, end='')
else:
ngxconf = open("/etc/nginx/conf.d/hashbucket.conf",
encoding='utf-8', mode='w')
ngxconf.write("\tserver_names_hash_bucket_size {0};".format(ngx_hash))
ngxconf.close()
"""No-op: OpenLiteSpeed does not need hash bucket configuration"""
return True

19
wo/core/ols.py Normal file
View File

@@ -0,0 +1,19 @@
"""WordOps OpenLiteSpeed Manager"""
import subprocess
from wo.core.logging import Log
def check_config(self):
"""Check OpenLiteSpeed configuration and return boolean"""
Log.debug(self, "Testing OpenLiteSpeed configuration ")
sub = subprocess.Popen('/usr/local/lsws/bin/openlitespeed -t',
stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
output, error_output = sub.communicate()
if 'ERROR' in str(error_output) or sub.returncode != 0:
Log.debug(self, "OpenLiteSpeed configuration check failed")
return False
else:
Log.debug(self, "OpenLiteSpeed configuration check was successful")
return True

View File

@@ -15,24 +15,25 @@ class WOService():
Similar to `service xyz start`
"""
try:
if service_name in ['nginx']:
Log.wait(self, "Testing Nginx configuration ")
# Check Nginx configuration before executing command
sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
if service_name in ['lsws']:
Log.wait(self, "Testing OpenLiteSpeed configuration ")
sub = subprocess.Popen(
'/usr/local/lsws/bin/openlitespeed -t',
stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
output = sub.communicate()
if 'emerg' not in str(output):
Log.valide(self, "Testing Nginx configuration ")
Log.wait(self, "Starting Nginx")
service_cmd = ('service {0} start'.format(service_name))
if sub.returncode == 0:
Log.valide(self, "Testing OpenLiteSpeed configuration ")
Log.wait(self, "Starting OpenLiteSpeed")
service_cmd = ('/usr/local/lsws/bin/lswsctrl start')
retcode = subprocess.getstatusoutput(service_cmd)
if retcode[0] == 0:
Log.valide(self, "Starting Nginx ")
Log.valide(self, "Starting OpenLiteSpeed ")
return True
else:
Log.failed(self, "Starting Nginx")
Log.failed(self, "Starting OpenLiteSpeed")
else:
Log.failed(self, "Testing Nginx configuration ")
Log.failed(self, "Testing OpenLiteSpeed configuration ")
return False
else:
service_cmd = ('service {0} start'.format(service_name))
@@ -59,9 +60,14 @@ class WOService():
Similar to `service xyz stop`
"""
try:
Log.info(self, "Stop : {0:10}" .format(service_name), end='')
retcode = subprocess.getstatusoutput('service {0} stop'
.format(service_name))
if service_name in ['lsws']:
Log.info(self, "Stop : {0:10}" .format(service_name), end='')
retcode = subprocess.getstatusoutput(
'/usr/local/lsws/bin/lswsctrl stop')
else:
Log.info(self, "Stop : {0:10}" .format(service_name), end='')
retcode = subprocess.getstatusoutput('service {0} stop'
.format(service_name))
if retcode[0] == 0:
Log.info(self, "[" + Log.ENDC + Log.OKGREEN + "OK" +
Log.ENDC + Log.OKBLUE + "]")
@@ -81,22 +87,23 @@ class WOService():
Similar to `service xyz restart`
"""
try:
if service_name in ['nginx']:
Log.wait(self, "Testing Nginx configuration ")
# Check Nginx configuration before executing command
sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
if service_name in ['lsws']:
Log.wait(self, "Testing OpenLiteSpeed configuration ")
sub = subprocess.Popen(
'/usr/local/lsws/bin/openlitespeed -t',
stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
output, error_output = sub.communicate()
if 'emerg' not in str(error_output):
Log.valide(self, "Testing Nginx configuration ")
Log.wait(self, "Restarting Nginx")
service_cmd = ('service {0} restart'.format(service_name))
if sub.returncode == 0:
Log.valide(self, "Testing OpenLiteSpeed configuration ")
Log.wait(self, "Restarting OpenLiteSpeed")
service_cmd = ('/usr/local/lsws/bin/lswsctrl restart')
retcode = subprocess.getstatusoutput(service_cmd)
if retcode[0] == 0:
Log.valide(self, "Restarting Nginx")
Log.valide(self, "Restarting OpenLiteSpeed")
return True
else:
Log.failed(self, "Testing Nginx configuration ")
Log.failed(self, "Testing OpenLiteSpeed configuration ")
return False
else:
service_cmd = ('service {0} restart'.format(service_name))
@@ -123,22 +130,23 @@ class WOService():
Similar to `service xyz reload`
"""
try:
if service_name in ['nginx']:
# Check Nginx configuration before executing command
Log.wait(self, "Testing Nginx configuration ")
sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
if service_name in ['lsws']:
Log.wait(self, "Testing OpenLiteSpeed configuration ")
sub = subprocess.Popen(
'/usr/local/lsws/bin/openlitespeed -t',
stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True)
output, error_output = sub.communicate()
if 'emerg' not in str(error_output):
Log.valide(self, "Testing Nginx configuration ")
Log.wait(self, "Reloading Nginx")
service_cmd = ('service {0} reload'.format(service_name))
if sub.returncode == 0:
Log.valide(self, "Testing OpenLiteSpeed configuration ")
Log.wait(self, "Reloading OpenLiteSpeed")
service_cmd = ('/usr/local/lsws/bin/lswsctrl restart')
retcode = subprocess.getstatusoutput(service_cmd)
if retcode[0] == 0:
Log.valide(self, "Reloading Nginx")
Log.valide(self, "Reloading OpenLiteSpeed")
return True
else:
Log.failed(self, "Testing Nginx configuration ")
Log.failed(self, "Testing OpenLiteSpeed configuration ")
return False
else:
service_cmd = ('service {0} reload'.format(service_name))
@@ -162,26 +170,27 @@ class WOService():
def get_service_status(self, service_name):
try:
is_exist = subprocess.getstatusoutput('command -v {0}'
.format(service_name))
if is_exist[0] == 0 or service_name in ['php7.2-fpm',
'php7.3-fpm',
'php7.4-fpm',
'php8.0-fpm',
'php8.1-fpm',
'php8.2-fpm',
'php8.3-fpm',
'php8.4-fpm',
]:
retcode = subprocess.getstatusoutput('service {0} status'
.format(service_name))
if service_name in ['lsws']:
retcode = subprocess.getstatusoutput(
'/usr/local/lsws/bin/lswsctrl status')
if retcode[0] == 0:
return True
else:
Log.debug(self, "{0}".format(retcode[1]))
return False
else:
return False
is_exist = subprocess.getstatusoutput('command -v {0}'
.format(service_name))
if is_exist[0] == 0:
retcode = subprocess.getstatusoutput('service {0} status'
.format(service_name))
if retcode[0] == 0:
return True
else:
Log.debug(self, "{0}".format(retcode[1]))
return False
else:
return False
except OSError as e:
Log.debug(self, "{0}{1}".format(e.errno, e.strerror))
Log.error(self, "Unable to get services status of {0}"

View File

@@ -55,7 +55,8 @@ class SSL:
# check if exist
if not os.path.isfile('/etc/letsencrypt/live/{0}/cert.pem'
.format(domain)):
if os.path.exists('/var/www/{0}/conf/nginx/ssl.conf'):
if os.path.exists('{0}/{1}/ssl.conf'
.format(WOVar.wo_ols_vhost_dir, domain)):
split_domain = domain.split('.')
check_domain = ('.').join(split_domain[1:])
else:
@@ -135,36 +136,46 @@ class SSL:
return False
def setuphsts(self, wo_domain_name, enable=True):
"""Enable or disable htsts for a site"""
"""Enable or disable HSTS for a site via OLS vhost config"""
vhconf = '{0}/{1}/vhconf.conf'.format(
WOVar.wo_ols_vhost_dir, wo_domain_name)
if enable is True:
if WOFileUtils.enabledisable(
self, f'/var/www/{wo_domain_name}/conf/nginx/hsts.conf'
):
if os.path.isfile(vhconf):
if not WOFileUtils.grepcheck(
self, vhconf, 'Strict-Transport-Security'):
Log.info(
self, "Enabling HSTS for {0}"
.format(wo_domain_name))
# Add HSTS header via OLS context configuration
hsts_block = ('\nmodule header {\n'
' note {\n'
' Strict-Transport-Security '
'"max-age=31536000; '
'includeSubDomains; preload"\n'
' }\n'
'}\n')
with open(vhconf, 'a', encoding='utf-8') as f:
f.write(hsts_block)
return 0
else:
Log.info(
self, "Adding /var/www/{0}/conf/nginx/hsts.conf"
.format(wo_domain_name))
hstsconf = open(f"/var/www/{wo_domain_name}/conf/nginx/hsts.conf",
encoding='utf-8', mode='w')
hstsconf.write("more_set_headers "
"\"Strict-Transport-Security: "
"max-age=31536000; "
"includeSubDomains; "
"preload\";")
hstsconf.close()
return 0
Log.info(self, "Vhost config not found for {0}"
.format(wo_domain_name))
return 1
else:
if WOFileUtils.enabledisable(
self, f'/var/www/{wo_domain_name}/conf/nginx/hsts.conf',
enable=False
):
Log.info(self, "HSTS disabled")
return 0
else:
Log.info(self, "HSTS is not enabled")
return 0
if os.path.isfile(vhconf):
if WOFileUtils.grepcheck(
self, vhconf, 'Strict-Transport-Security'):
Log.info(self, "HSTS disabled")
# Remove HSTS header block
WOFileUtils.searchreplace(
self, vhconf,
'Strict-Transport-Security',
'# HSTS disabled')
return 0
else:
Log.info(self, "HSTS is not enabled")
return 0
return 0
def selfsignedcert(self, proftpd=False, backend=False):
"""issue a self-signed certificate"""
@@ -227,43 +238,40 @@ class SSL:
WOFileUtils.rm(self, selfs_tmp)
def httpsredirect(self, wo_domain_name, acme_domains, redirect=True):
"""Create Nginx redirection from http to https"""
wo_acme_domains = ' '.join(acme_domains)
data = dict(domains=wo_acme_domains)
"""Enable/disable HTTPS redirect in OLS vhost config"""
vhconf = '{0}/{1}/vhconf.conf'.format(
WOVar.wo_ols_vhost_dir, wo_domain_name)
if redirect:
Log.wait(self, "Adding HTTPS redirection")
if WOFileUtils.enabledisable(
self, '/etc/nginx/conf.d/force-ssl-{0}.conf'
.format(wo_domain_name), enable=True):
if os.path.isfile(vhconf):
if not WOFileUtils.grepcheck(
self, vhconf, 'forceSecure'):
# Add forceSecure directive to OLS vhost
WOFileUtils.searchreplace(
self, vhconf,
'docRoot',
'forceSecure 1\n docRoot')
Log.valide(self, "Adding HTTPS redirection")
return 0
else:
try:
WOTemplate.deploy(self,
f'/etc/nginx/conf.d/force-ssl-{wo_domain_name}.conf',
'force-ssl.mustache',
data)
except IOError as e:
Log.debug(self, str(e))
Log.debug(
self, "Error occured while generating "
"/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name))
return 1
Log.valide(self, "Adding HTTPS redirection")
return 0
Log.debug(
self, "Vhost config not found for {0}"
.format(wo_domain_name))
return 1
else:
if WOFileUtils.enabledisable(
self, "/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name), enable=False):
Log.info(
self, "Disabled HTTPS Force Redirection for site "
"{0}".format(wo_domain_name))
else:
Log.info(
self, "HTTPS redirection already disabled for site"
"{0}".format(wo_domain_name)
)
if os.path.isfile(vhconf):
if WOFileUtils.grepcheck(
self, vhconf, 'forceSecure'):
WOFileUtils.searchreplace(
self, vhconf,
'forceSecure 1\n', '')
Log.info(
self, "Disabled HTTPS Force Redirection for site "
"{0}".format(wo_domain_name))
else:
Log.info(
self, "HTTPS redirection already disabled for site "
"{0}".format(wo_domain_name))
return 0
def archivedcertificatehandle(self, domain, acme_domains):
@@ -305,12 +313,11 @@ class SSL:
else:
Log.error(self, "Operation cancelled by user.")
if os.path.isfile("{0}/conf/nginx/ssl.conf"
.format(domain)):
vhost_ssl = "{0}/{1}/ssl.conf".format(
WOVar.wo_ols_vhost_dir, domain)
if os.path.isfile(vhost_ssl):
Log.info(self, "Existing ssl.conf . Backing it up ..")
WOFileUtils.mvfile(self, "/var/www/{0}/conf/nginx/ssl.conf"
.format(domain),
'/var/www/{0}/conf/nginx/ssl.conf.bak'
.format(domain))
WOFileUtils.mvfile(self, vhost_ssl,
'{0}.bak'.format(vhost_ssl))
return ssl

View File

@@ -10,41 +10,18 @@ class WOConf():
def __init__():
pass
def nginxcommon(self):
"""nginx common configuration deployment"""
def olscommon(self):
"""OpenLiteSpeed common configuration deployment - deploy extApp configs"""
wo_php_version = list(WOVar.wo_php_versions.keys())
ngxcom = '/etc/nginx/common'
if not os.path.exists(ngxcom):
os.mkdir(ngxcom)
ols_conf = WOVar.wo_ols_conf_dir
for wo_php in wo_php_version:
Log.debug(self, 'deploying templates for {0}'.format(wo_php))
data = dict(upstream="{0}".format(wo_php),
release=WOVar.wo_version)
short_ver = WOVar.wo_php_versions[wo_php].replace('.', '')
Log.debug(self, 'deploying OLS extApp config for {0}'.format(wo_php))
data = dict(
php_version=WOVar.wo_php_versions[wo_php],
short_version=short_ver,
release=WOVar.wo_version)
WOTemplate.deploy(self,
'{0}/{1}.conf'
.format(ngxcom, wo_php),
'php.mustache', data)
WOTemplate.deploy(
self, '{0}/redis-{1}.conf'.format(ngxcom, wo_php),
'redis.mustache', data)
WOTemplate.deploy(
self, '{0}/wpcommon-{1}.conf'.format(ngxcom, wo_php),
'wpcommon.mustache', data)
WOTemplate.deploy(
self, '{0}/wpfc-{1}.conf'.format(ngxcom, wo_php),
'wpfc.mustache', data)
WOTemplate.deploy(
self, '{0}/wpsc-{1}.conf'.format(ngxcom, wo_php),
'wpsc.mustache', data)
WOTemplate.deploy(
self, '{0}/wprocket-{1}.conf'.format(ngxcom, wo_php),
'wprocket.mustache', data)
WOTemplate.deploy(
self, '{0}/wpce-{1}.conf'.format(ngxcom, wo_php),
'wpce.mustache', data)
'{0}/lsphp{1}.conf'
.format(ols_conf, short_ver),
'ols-extapp.mustache', data)

View File

@@ -115,10 +115,17 @@ class WOVar():
wo_mysql_host = "localhost"
# WordOps stack installation variables
# Nginx repo and packages
if wo_distro == 'ubuntu':
wo_nginx_repo = "ppa:wordops/nginx-wo"
# OpenLiteSpeed path constants
wo_ols_conf_dir = '/usr/local/lsws/conf'
wo_ols_vhost_dir = '/usr/local/lsws/conf/vhosts'
wo_ols_bin = '/usr/local/lsws/bin/openlitespeed'
wo_ols_ctrl = '/usr/local/lsws/bin/lswsctrl'
# OpenLiteSpeed repo and packages
if wo_distro == 'ubuntu':
wo_ols_repo = ("deb [signed-by=/usr/share/keyrings/openlitespeed-keyring.gpg] "
"http://rpms.litespeedtech.com/debian/ "
"{0} main".format(wo_platform_codename))
else:
if wo_distro == 'debian':
if wo_platform_codename == 'buster':
@@ -127,6 +134,8 @@ class WOVar():
wo_deb_repo = "Debian_11"
elif wo_platform_codename == 'bookworm':
wo_deb_repo = "Debian_12"
elif wo_platform_codename == 'trixie':
wo_deb_repo = "Debian_13"
elif wo_distro == 'raspbian':
if wo_platform_codename == 'buster':
wo_deb_repo = "Raspbian_10"
@@ -134,14 +143,14 @@ class WOVar():
wo_deb_repo = "Raspbian_11"
elif wo_platform_codename == 'bookworm':
wo_deb_repo = "Raspbian_12"
# debian/raspbian nginx repository
wo_nginx_repo = ("deb [signed-by=/usr/share/keyrings/wordops-archive-keyring.gpg] "
"http://download.opensuse.org"
f"/repositories/home:/virtubox:/WordOps/{wo_deb_repo}/ /")
wo_nginx_key = (f"https://download.opensuse.org/repositories/home:virtubox:WordOps/{wo_deb_repo}/Release.key")
elif wo_platform_codename == 'trixie':
wo_deb_repo = "Raspbian_13"
wo_ols_repo = ("deb [signed-by=/usr/share/keyrings/openlitespeed-keyring.gpg] "
"http://rpms.litespeedtech.com/debian/ "
"{0} main".format(wo_platform_codename))
wo_nginx = ["nginx-custom", "nginx-wo"]
wo_nginx_key = 'FB898660'
wo_ols = ["openlitespeed"]
wo_ols_repo_key = "https://rpms.litespeedtech.com/debian/lst_debian_repo.gpg"
wo_php_versions = {
'php74': '7.4',
@@ -150,27 +159,34 @@ class WOVar():
'php82': '8.2',
'php83': '8.3',
'php84': '8.4',
'php85': '8.5',
}
def generate_php_modules(version_prefix, version_number):
wo_module = ["bcmath", "cli", "common", "curl", "fpm", "gd", "igbinary",
def generate_lsphp_modules(version_prefix, version_number):
"""Generate LSPHP module package list for a given PHP version.
LSPHP packages use lsphpXX- naming (no dot in version)."""
short_ver = version_number.replace('.', '')
wo_module = ["common", "curl", "gd", "igbinary",
"imagick", "imap", "intl", "mbstring", "memcached", "msgpack",
"mysql", "opcache", "readline", "redis", "soap", "xdebug",
"mysql", "opcache", "redis", "soap",
"xml", "zip"]
php_modules = ["php{0}-{1}".format(version_number, module) for module in wo_module]
# lsphp packages: lsphpXX, lsphpXX-common, lsphpXX-curl, etc.
php_modules = ["lsphp{0}".format(short_ver)]
php_modules.extend(["lsphp{0}-{1}".format(short_ver, module) for module in wo_module])
if version_prefix == 'php74':
php_modules.extend(["php{0}-geoip".format(version_number),
"php{0}-json".format(version_number)])
php_modules.extend(["lsphp{0}-json".format(short_ver)])
return php_modules
wo_php74 = generate_php_modules('php74', '7.4')
wo_php80 = generate_php_modules('php80', '8.0')
wo_php81 = generate_php_modules('php81', '8.1')
wo_php82 = generate_php_modules('php82', '8.2')
wo_php83 = generate_php_modules('php83', '8.3')
wo_php84 = generate_php_modules('php84', '8.4')
wo_php74 = generate_lsphp_modules('php74', '7.4')
wo_php80 = generate_lsphp_modules('php80', '8.0')
wo_php81 = generate_lsphp_modules('php81', '8.1')
wo_php82 = generate_lsphp_modules('php82', '8.2')
wo_php83 = generate_lsphp_modules('php83', '8.3')
wo_php84 = generate_lsphp_modules('php84', '8.4')
wo_php85 = generate_lsphp_modules('php85', '8.5')
wo_php_extra = ["graphviz"]
@@ -194,14 +210,14 @@ class WOVar():
f"{mariadb_ver}/{wo_distro} {wo_platform_codename} main")
mariadb_repo_key = "https://mariadb.org/mariadb_release_signing_key.pgp"
if wo_distro == 'ubuntu':
wo_php_repo = "ppa:ondrej/php"
# LSPHP comes from LiteSpeed repo (same as OLS)
wo_php_repo = wo_ols_repo
wo_goaccess_repo = ("ppa:alex-p/goaccess")
else:
wo_php_repo = (
"deb [signed-by=/usr/share/keyrings/deb.sury.org-php.gpg] "
f"https://packages.sury.org/php/ {wo_platform_codename} main")
wo_php_key = '95BD4743'
# LSPHP comes from LiteSpeed repo (same as OLS)
wo_php_repo = wo_ols_repo
wo_php_key = wo_ols_repo_key
wo_redis_key_url = "https://packages.redis.io/gpg"
wo_redis_repo = (
"deb [signed-by=/usr/share/keyrings/redis-archive-keyring.gpg] "