- PHP 7.4 support
- Improved Webp images support with Cloudflare (Issue [#95](https://github.com/WordOps/WordOps/issues/95)). Nginx will not serve webp images alternative with Cloudflare IP ranges.
- Stack upgrade for adminer
- Check acme.sh installation and setup acme.sh if needed before issuing certificate
- Add `--ufw` to `wo stack status`
- Add Nginx directive `gzip_static on;` to serve precompressed assets with Cache-Enabler or WP-Rocket. (Issue [#207](https://github.com/WordOps/WordOps/issues/207))
- Previous `--php73` & `--php73=off` flags are replaced by `--php72`, `--php73`, `--php74` to switch site's php version
- phpMyAdmin updated to v4.9.2
- Adminer updated to v4.7.5
- Replace dot and dashes by underscores in database names (Issue [#206](https://github.com/WordOps/WordOps/issues/206))
- Increased database name length to 32 characters from domain name + 8 random characters
- typo error in motd-news script (Issue [#204](https://github.com/WordOps/WordOps/issues/204))
- Install Nginx before ngxblocker
- WordOps install/update script text color
- Issue with MySQL stack on Raspbian 9/10
- Typo error  (PR [#205](https://github.com/WordOps/WordOps/pull/205))
- php version in `wo debug` (PR [#209](https://github.com/WordOps/WordOps/pull/209))
- SSL certificates expiration display with shared wildcard certificates
This commit is contained in:
VirtuBox
2019-12-03 19:48:18 +01:00
committed by GitHub
parent 63d2acf7ba
commit 01ee8c0a13
72 changed files with 3222 additions and 2521 deletions

View File

@@ -18,7 +18,7 @@ before_script:
- sudo bash -c 'echo example.com > /etc/hostname' - sudo bash -c 'echo example.com > /etc/hostname'
- unset LANG - unset LANG
- sudo apt-get update --allow-releaseinfo-change -qq - sudo apt-get update --allow-releaseinfo-change -qq
- sudo apt-get -qq purge mysql* graphviz* redis* - sudo apt-get -qq purge mysql* graphviz* redis* php*
- sudo apt-get -qq autoremove --purge - sudo apt-get -qq autoremove --purge

View File

@@ -8,6 +8,35 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
### v3.9.x - [Unreleased] ### v3.9.x - [Unreleased]
### v3.11.0 - 2019-12-03
#### Added
- PHP 7.4 support
- Improved Webp images support with Cloudflare (Issue [#95](https://github.com/WordOps/WordOps/issues/95)). Nginx will not serve webp images alternative with Cloudflare IP ranges.
- Stack upgrade for adminer
- Check acme.sh installation and setup acme.sh if needed before issuing certificate
- Add `--ufw` to `wo stack status`
- Add Nginx directive `gzip_static on;` to serve precompressed assets with Cache-Enabler or WP-Rocket. (Issue [#207](https://github.com/WordOps/WordOps/issues/207))
#### Changed
- Previous `--php73` & `--php73=off` flags are replaced by `--php72`, `--php73`, `--php74` to switch site's php version
- phpMyAdmin updated to v4.9.2
- Adminer updated to v4.7.5
- Replace dot and dashes by underscores in database names (Issue [#206](https://github.com/WordOps/WordOps/issues/206))
- Increased database name length to 32 characters from domain name + 8 random characters
#### Fixed
- typo error in motd-news script (Issue [#204](https://github.com/WordOps/WordOps/issues/204))
- Install Nginx before ngxblocker
- WordOps install/update script text color
- Issue with MySQL stack on Raspbian 9/10
- Typo error (PR [#205](https://github.com/WordOps/WordOps/pull/205))
- php version in `wo debug` (PR [#209](https://github.com/WordOps/WordOps/pull/209))
- SSL certificates expiration display with shared wildcard certificates
### v3.10.3 - 2019-11-11 ### v3.10.3 - 2019-11-11
#### Added #### Added

View File

@@ -42,7 +42,7 @@
- **Easy to install** : One step automated installer with migration from EasyEngine v3 support - **Easy to install** : One step automated installer with migration from EasyEngine v3 support
- **Fast deployment** : Fast and automated WordPress, Nginx, PHP, MySQL & Redis installation - **Fast deployment** : Fast and automated WordPress, Nginx, PHP, MySQL & Redis installation
- **Custom Nginx build** : Nginx 1.16.1 - TLS v1.3 Cloudflare HTTP/2 HPACK & Brotli support - **Custom Nginx build** : Nginx 1.16.1 - TLS v1.3 Cloudflare HTTP/2 HPACK & Brotli support
- **Up-to-date** : PHP 7.2 & 7.3, MariaDB 10.3 & Redis 5.0 - **Up-to-date** : PHP 7.2, 7.3 & 7.4, MariaDB 10.3 & Redis 5.0
- **Secured** : Hardened WordPress security with strict Nginx location directives - **Secured** : Hardened WordPress security with strict Nginx location directives
- **Powerful** : Optimized Nginx configurations with multiple cache backends support - **Powerful** : Optimized Nginx configurations with multiple cache backends support
- **SSL** : Domain, Subdomain & Wildcard Let's Encrypt SSL certificates with DNS API support - **SSL** : Domain, Subdomain & Wildcard Let's Encrypt SSL certificates with DNS API support
@@ -67,11 +67,10 @@
- Debian 9 (Stretch) - Debian 9 (Stretch)
- Debian 10 (Buster) - Debian 10 (Buster)
- Raspbian 9 (Stretch) - Raspbian 9 (Stretch)
- Raspbian 10 (Buster) - Testing - Raspbian 10 (Buster)
## Getting Started ## Getting Started
```bash ```bash
wget -qO wo wops.cc && sudo bash wo # Install WordOps wget -qO wo wops.cc && sudo bash wo # Install WordOps
sudo wo site create example.com --wp # Install required packages & setup WordPress on example.com sudo wo site create example.com --wp # Install required packages & setup WordPress on example.com
@@ -86,6 +85,7 @@ Detailed Getting Started guide with additional installation methods can be found
```bash ```bash
wo site create example.com --wp # install wordpress without any page caching wo site create example.com --wp # install wordpress without any page caching
wo site create example.com --wp --php73 # install wordpress with PHP 7.3 without any page caching wo site create example.com --wp --php73 # install wordpress with PHP 7.3 without any page caching
wo site create example.com --wp --php74 # install wordpress with PHP 7.4 without any page caching
wo site create example.com --wpfc # install wordpress + nginx fastcgi_cache wo site create example.com --wpfc # install wordpress + nginx fastcgi_cache
wo site create example.com --wpredis # install wordpress + nginx redis_cache wo site create example.com --wpredis # install wordpress + nginx redis_cache
wo site create example.com --wprocket # install wordpress with WP-Rocket plugin wo site create example.com --wprocket # install wordpress with WP-Rocket plugin
@@ -121,11 +121,21 @@ wo site create example.com --wpsubdomain --wpce # install wpmu-subdomain + C
wo site create example.com --html # create example.com for static/html sites wo site create example.com --html # create example.com for static/html sites
wo site create example.com --php # create example.com with php support wo site create example.com --php # create example.com with php support
wo site create example.com --php73 # create example.com with php 7.3 support wo site create example.com --php73 # create example.com with php 7.3 support
wo site create example.com --php73 # create example.com with php 7.4 support
wo site create example.com --mysql # create example.com with php & mysql support wo site create example.com --mysql # create example.com with php & mysql support
wo site create example.com --mysql --php73 # create example.com with php 7.3 & mysql support wo site create example.com --mysql --php73 # create example.com with php 7.3 & mysql support
wo site create example.com --mysql --php74 # create example.com with php 7.4 & mysql support
wo site create example.com --proxy=127.0.0.1:3000 # create example.com with nginx as reverse-proxy wo site create example.com --proxy=127.0.0.1:3000 # create example.com with nginx as reverse-proxy
``` ```
### Switch between PHP versions
```bash
wo site update example/com --php72 # switch to PHP 7.2
wo site update example.com --php73 # switch to PHP 7.3
wo site update example.com --php74 # switch to PHP 7.4
```
### Sites secured with Let's Encrypt ### Sites secured with Let's Encrypt
```bash ```bash
@@ -148,7 +158,7 @@ For any other questions about WordOps or if you need support, please use the [Co
# Contributing # Contributing
If you'd like to contribute, please fork the repository and make changes as you'd like. Pull requests are warmly welcome. If you'd like to contribute, please fork the reposi7tory and make changes as you'd like. Pull requests are warmly welcome.
There is no need to be a developer or a system administrator to contribute to WordOps project. You can still contribute by helping us to improve [WordOps documentation](https://github.com/WordOps/docs.wordops.net). There is no need to be a developer or a system administrator to contribute to WordOps project. You can still contribute by helping us to improve [WordOps documentation](https://github.com/WordOps/docs.wordops.net).
## Credits ## Credits

View File

@@ -53,7 +53,7 @@ _wo_complete()
"info") "info")
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "--mysql --php --php73 --nginx" \ -W "--mysql --php --php73 --php74 --nginx" \
-- $cur) ) -- $cur) )
;; ;;
@@ -74,17 +74,17 @@ _wo_complete()
# HANDLE EVERYTHING AFTER THE THIRD LEVEL NAMESPACE # HANDLE EVERYTHING AFTER THE THIRD LEVEL NAMESPACE
"install" | "purge" | "remove" ) "install" | "purge" | "remove" )
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "--web --admin --security --nginx --php --php73 --mysql --wpcli --phpmyadmin --adminer --utils --redis --phpredisadmin --composer --netdata --fail2ban --ufw --dashboard --proftpd --clamav --ngxblocker --mysqlclient --mysqltuner --extplorer --all --force" \ -W "--web --admin --security --nginx --php --php73 --php74 --mysql --wpcli --phpmyadmin --adminer --utils --redis --phpredisadmin --composer --netdata --fail2ban --ufw --dashboard --proftpd --clamav --sendmail --ngxblocker --mysqlclient --mysqltuner --extplorer --nanorc --cheat --all --force" \
-- $cur) ) -- $cur) )
;; ;;
"upgrade" ) "upgrade" )
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "--web --admin --utils --nginx --php --php73 --mysql --all --netdata --composer --phpmyadmin --dashboard --mysqtuner --wpcli --force" \ -W "--web --admin --utils --nginx --php --php73 --php74 --mysql --all --netdata --composer --phpmyadmin --adminer --dashboard --mysqtuner --wpcli --force" \
-- $cur) ) -- $cur) )
;; ;;
"start" | "stop" | "reload" | "restart" | "status") "start" | "stop" | "reload" | "restart" | "status")
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "--nginx --php --php73 --mysql --redis --fail2ban --ufw --netdata -proftpd" \ -W "--nginx --php --php73 --php74 --mysql --redis --fail2ban --ufw --netdata -proftpd" \
-- $cur) ) -- $cur) )
;; ;;
"list") "list")
@@ -154,13 +154,13 @@ _wo_complete()
"create") "create")
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "--user --pass --email --html --php --php73 --mysql --wp --wpsubdir --wpsubdomain --wpfc --wpsc --proxy= --wpredis --wprocket --wpce -le --letsencrypt --letsencrypt=wildcard -le=wildcard --dns --dns=dns_cf --dns=dns_dgon" \ -W "--user --pass --email --html --php --php73 --php74 --mysql --wp --wpsubdir --wpsubdomain --wpfc --wpsc --proxy= --wpredis --wprocket --wpce -le --letsencrypt --letsencrypt=wildcard -le=wildcard --dns --dns=dns_cf --dns=dns_dgon" \
-- $cur) ) -- $cur) )
;; ;;
"update") "update")
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "--password --php --php73 --mysql --wp --wpsubdir --wpsubdomain --wpfc --wpsc --wpredis --wprocket --wpce -le -le=off --letsencrypt --letsencrypt=off --letsencrypt=clean -le=wildcard -le=clean --dns --dns=dns_cf --dns=dns_dgon --ngxblocker --ngxblocker=off" \ -W "--password --php --php72 --php73 --php74 --mysql --wp --wpsubdir --wpsubdomain --wpfc --wpsc --wpredis --wprocket --wpce -le -le=off --letsencrypt --letsencrypt=off --letsencrypt=clean -le=wildcard -le=clean --dns --dns=dns_cf --dns=dns_dgon --ngxblocker --ngxblocker=off" \
-- $cur) ) -- $cur) )
;; ;;
"delete") "delete")
@@ -206,9 +206,9 @@ _wo_complete()
"--wp") "--wp")
if [ "${COMP_WORDS[1]}" != "debug" ]; then if [ "${COMP_WORDS[1]}" != "debug" ]; then
if [ "${COMP_WORDS[2]}" == "create" ]; then if [ "${COMP_WORDS[2]}" == "create" ]; then
retlist="--wp --wpsc --wpfc --user --email --pass --wpredis --wprocket --wpce --letsencrypt -le --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon --php73" retlist="--wp --wpsc --wpfc --user --email --pass --wpredis --wprocket --wpce --letsencrypt -le --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon --php73 --php74"
elif [ "${COMP_WORDS[2]}" == "update" ]; then elif [ "${COMP_WORDS[2]}" == "update" ]; then
retlist="--wp --wpfc --wpsc --php73 --php73=off --wpredis --wprocket --wpce -le --letsencrypt --letsencrypt=wildcard -le=wildcard --dns --dns=dns_cf --dns=dns_dgon" retlist="--wp --wpfc --wpsc --php72 --php73 --php74 --wpredis --wprocket --wpce -le --letsencrypt --letsencrypt=wildcard -le=wildcard --dns --dns=dns_cf --dns=dns_dgon"
else else
retlist="" retlist=""
fi fi
@@ -225,9 +225,9 @@ _wo_complete()
"--wpsubdir" | "--wpsubdomain") "--wpsubdir" | "--wpsubdomain")
if [ "${COMP_WORDS[1]}" != "debug" ]; then if [ "${COMP_WORDS[1]}" != "debug" ]; then
if [ "${COMP_WORDS[2]}" == "create" ]; then if [ "${COMP_WORDS[2]}" == "create" ]; then
retlist="--wpsc --wpfc --user --email --pass --wpredis --wprocket --wpce -le -le=wildcard --letsencrypt --letsencrypt=wildcard --php73 --dns --dns=dns_cf --dns=dns_dgon" retlist="--wpsc --wpfc --user --email --pass --wpredis --wprocket --wpce -le -le=wildcard --letsencrypt --letsencrypt=wildcard --php73 --php74 --dns --dns=dns_cf --dns=dns_dgon"
elif [ "${COMP_WORDS[2]}" == "update" ]; then elif [ "${COMP_WORDS[2]}" == "update" ]; then
retlist="--wpfc --wpsc --php73 --php73=off --wpredis --wprocket --wpce -le -le=wildcard --letsencrypt --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon" retlist="--wpfc --wpsc --php72 --php73 --php74 --wpredis --wprocket --wpce -le -le=wildcard --letsencrypt --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon"
else else
retlist="" retlist=""
fi fi
@@ -243,7 +243,7 @@ _wo_complete()
"--wpredis" | "--wprocket" | "--wpce" | "--wpfc" | "--wpsc" | "--wpsubdir" | "--wpsubdomain" | "--user" | "--pass" | "--email" | "--wp") "--wpredis" | "--wprocket" | "--wpce" | "--wpfc" | "--wpsc" | "--wpsubdir" | "--wpsubdomain" | "--user" | "--pass" | "--email" | "--wp")
if [ "${COMP_WORDS[2]}" == "create" ]; then if [ "${COMP_WORDS[2]}" == "create" ]; then
retlist="--user --pass --email --wp --wpsubdir --wpsubdomain --wpfc --wpsc --wpredis --wprocket --wpce --php73 -le -le=wildcard --letsencrypt --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon" retlist="--user --pass --email --wp --wpsubdir --wpsubdomain --wpfc --wpsc --wpredis --wprocket --wpce --php73 --php74 -le -le=wildcard --letsencrypt --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon"
else else
retlist="" retlist=""
fi fi
@@ -254,9 +254,9 @@ _wo_complete()
-- $cur) ) -- $cur) )
;; ;;
"--wpredis" | "--wprocket" | "--wpce" | "--wpfc") "--wpredis" | "--wprocket" | "--wpce" | "--wpfc" | "--wpsc")
if [ "${COMP_WORDS[2]}" == "update" ]; then if [ "${COMP_WORDS[2]}" == "update" ]; then
retlist="--password --php --php73 --mysql --wp --wpsubdir --wpsubdomain -le --letsencrypt --dns --dns=dns_cf --dns=dns_dgon" retlist="--password --php72 --php73 --php74 --mysql --wp --wpsubdir --wpsubdomain -le --letsencrypt --dns --dns=dns_cf --dns=dns_dgon"
else else
retlist="" retlist=""
fi fi
@@ -267,11 +267,11 @@ _wo_complete()
-- $cur) ) -- $cur) )
;; ;;
"--web" | "--admin" | "--nginx" | "--php" | "--php73" | "--mysql" | "--wpcli" | "--phpmyadmin" | "--adminer" | "--utils" | "--fail2ban" | "--ufw" | "--redis | --phpredisadmin | --netdata") "--web" | "--admin" | "--nginx" | "--php" | "--php73" | "--php74" | "--mysql" | "--wpcli" | "--phpmyadmin" | "--adminer" | "--utils" | "--fail2ban" | "--ufw" | "--redis" | "--phpredisadmin" | "--netdata" | "--sendmail" | "--composer" | "--proftpd" | "--cheat" | "--nanorc" | "--clamav")
if [[ "${COMP_WORDS[2]}" == "install" || "${COMP_WORDS[2]}" == "purge" || "${COMP_WORDS[2]}" == "remove" ]]; then if [[ "${COMP_WORDS[2]}" == "install" || "${COMP_WORDS[2]}" == "purge" || "${COMP_WORDS[2]}" == "remove" ]]; then
retlist="--web --admin --security --nginx --php --php73 --mysql --wpcli --phpmyadmin --adminer --utils --redis --fail2ban --ufw --phpredisadmin --netdata --force" retlist="--web --admin --security --nginx --php --php73 --php74 --mysql --wpcli --phpmyadmin --adminer --utils --redis --fail2ban --ufw --phpredisadmin --netdata --force"
elif [[ "${COMP_WORDS[2]}" == "start" || "${COMP_WORDS[2]}" == "reload" || "${COMP_WORDS[2]}" == "restart" || "${COMP_WORDS[2]}" == "stop" ]]; then elif [[ "${COMP_WORDS[2]}" == "start" || "${COMP_WORDS[2]}" == "reload" || "${COMP_WORDS[2]}" == "restart" || "${COMP_WORDS[2]}" == "stop" ]]; then
retlist="--nginx --php --php73 --mysql --redis --netdata --fail2ban --ufw" retlist="--nginx --php --php73 --php74 --mysql --redis --netdata --fail2ban --ufw"
elif [[ "${COMP_WORDS[1]}" == "debug" ]]; then elif [[ "${COMP_WORDS[1]}" == "debug" ]]; then
retlist="--start --nginx --php --php73 --fpm --fpm7 --mysql -i --interactive -stop --import-slow-log --import-slow-log-interval= -" retlist="--start --nginx --php --php73 --fpm --fpm7 --mysql -i --interactive -stop --import-slow-log --import-slow-log-interval= -"
if [[ $prev == '--mysql' ]]; then if [[ $prev == '--mysql' ]]; then
@@ -326,8 +326,8 @@ _wo_complete()
-W "$(echo $ret)" \ -W "$(echo $ret)" \
-- $cur) ) -- $cur) )
;; ;;
"--auth" | "--port" | "--ip") "--auth" | "--port" | "--ip" | "--ssh" | "--sshport")
retlist="--auth --port --ip" retlist="--auth --port --ip --ssh --sshport"
ret="${retlist[@]/$prev}" ret="${retlist[@]/$prev}"
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \
-W "$(echo $ret)" \ -W "$(echo $ret)" \
@@ -358,7 +358,7 @@ _wo_complete()
case "$mprev" in case "$mprev" in
"--user" | "--email" | "--pass") "--user" | "--email" | "--pass")
if [ "${COMP_WORDS[2]}" == "create" ]; then if [ "${COMP_WORDS[2]}" == "create" ]; then
retlist="--user --pass --email --html --php --php73 --mysql --wp --wpsubdir --wpsubdomain --wpfc --wpsc --wpredis --wprocket --wpce -le -le=wildcard --letsencrypt --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon" retlist="--user --pass --email --html --php --php73 --php74 --mysql --wp --wpsubdir --wpsubdomain --wpfc --wpsc --wpredis --wprocket --wpce -le -le=wildcard --letsencrypt --letsencrypt=wildcard --dns --dns=dns_cf --dns=dns_dgon"
fi fi
ret="${retlist[@]/$prev}" ret="${retlist[@]/$prev}"
COMPREPLY=( $(compgen \ COMPREPLY=( $(compgen \

View File

@@ -18,7 +18,7 @@
# template_dir = /var/lib/wo/templates/ # template_dir = /var/lib/wo/templates/
[log.logging] [log.colorlog]
### Where the log file lives (no log file by default) ### Where the log file lives (no log file by default)
file = /var/log/wo/wordops.log file = /var/log/wo/wordops.log
@@ -38,6 +38,10 @@ max_bytes = 1000000
### The maximun number of log files to maintain when rotating ### The maximun number of log files to maintain when rotating
max_files = 7 max_files = 7
colorize_file_log = true
colorize_console_log = true
[stack] [stack]
### IP address that will be used in Nginx configurations while installing ### IP address that will be used in Nginx configurations while installing

54
install
View File

@@ -9,7 +9,7 @@
# ------------------------------------------------------------------------- # -------------------------------------------------------------------------
# wget -qO wo wops.cc && sudo bash wo # wget -qO wo wops.cc && sudo bash wo
# ------------------------------------------------------------------------- # -------------------------------------------------------------------------
# Version 3.10.3 - 2019-11-11 # Version 3.11.0 - 2019-12-03
# ------------------------------------------------------------------------- # -------------------------------------------------------------------------
# CONTENTS # CONTENTS
@@ -23,25 +23,25 @@
# 1 - Set the CLI output colors # 1 - Set the CLI output colors
### ###
TPUT_RESET=$(tput sgr0) CSI='\033['
TPUT_FAIL=$(tput setaf 1) TPUT_RESET="${CSI}0m"
TPUT_INFO=$(tput setaf 7) TPUT_FAIL="${CSI}1;31m"
TPUT_ECHO=$(tput setaf 4) TPUT_ECHO="${CSI}1;36m"
TPUT_OK=$(tput setaf 2) TPUT_OK="${CSI}1;32m"
wo_lib_echo() { wo_lib_echo() {
echo "${TPUT_ECHO}${*}${TPUT_RESET}" echo -e "${TPUT_ECHO}${*}${TPUT_RESET}"
} }
wo_lib_echo_info() { wo_lib_echo_info() {
echo "${TPUT_INFO}${*}${TPUT_RESET}" echo -e "$*"
} }
wo_lib_echo_fail() { wo_lib_echo_fail() {
echo "${TPUT_FAIL}${*}${TPUT_RESET}" echo -e "${TPUT_FAIL}${*}${TPUT_RESET}"
} }
### ###
@@ -49,7 +49,7 @@ wo_lib_echo_fail() {
### ###
wo_lib_error() { wo_lib_error() {
echo "[ $(date) ] ${TPUT_FAIL}${*}${TPUT_RESET}" echo -e "[ $(date) ] ${TPUT_FAIL}${*}${TPUT_RESET}"
exit "$2" exit "$2"
} }
@@ -169,7 +169,8 @@ wo_check_distro() {
else else
check_wo_linux_distro=$(lsb_release -sc | grep -E "xenial|bionic|disco|jessie|stretch|buster") check_wo_linux_distro=$(lsb_release -sc | grep -E "xenial|bionic|disco|jessie|stretch|buster")
if [ -z "$check_wo_linux_distro" ]; then if [ -z "$check_wo_linux_distro" ]; then
wo_lib_echo_fail "WordOps (wo) only supports Ubuntu 16.04/18.04/19.04 LTS, Debian 9.x/10.x and Raspbian 9.x/10x" wo_lib_echo_fail "WordOps (wo) only supports Ubuntu 16.04/18.04/19.04 LTS, Debian 9.x/10.x and Raspbian 9.x/10x.\n
You can bypass this warning by adding the flag --force to the install command"
exit 100 exit 100
fi fi
fi fi
@@ -426,8 +427,10 @@ wo_install_acme_sh() {
wo_install() { wo_install() {
cd /usr/local/lib/python3.*/dist-packages || exit 1 cd /usr/local/lib/python3.*/dist-packages || exit 1
if [ "$wo_branch" = "master" ]; then if [ "$wo_branch" = "master" ]; then
python3 -m pip uninstall wo -y
python3 -m pip install --upgrade wordops python3 -m pip install --upgrade wordops
else else
python3 -m pip uninstall wo -y
python3 -m pip install -U "git+git://github.com/WordOps/WordOps.git@$wo_branch#egg=wordops" python3 -m pip install -U "git+git://github.com/WordOps/WordOps.git@$wo_branch#egg=wordops"
fi fi
cp -rf /usr/local/lib/python3.*/dist-packages/usr/* /usr/ cp -rf /usr/local/lib/python3.*/dist-packages/usr/* /usr/
@@ -594,8 +597,7 @@ wo_domain_suffix() {
} }
wo_clean() { wo_clean() {
echo "pass" rm -rf /usr/local/lib/python3.*/dist-packages/{wo-*.egg,cement-*.egg,wordops-*.egg}
} }
wo_uninstall() { wo_uninstall() {
@@ -623,6 +625,14 @@ wo_clean_repo() {
fi fi
} }
wo_woconf() {
if [ -f /etc/wo/wo.conf ]; then
if grep -q "log.logging" /etc/wo/wo.conf; then
sed -i "s/log.logging/log.colorlog/g" /etc/wo/wo.conf
fi
fi
}
wo_init() { wo_init() {
### ###
@@ -631,12 +641,12 @@ wo_init() {
if [ -z "$wo_travis" ]; then if [ -z "$wo_travis" ]; then
# import easyengine opensusebuildservice gpg key to avoid issues with packages update # import easyengine opensusebuildservice gpg key to avoid issues with packages update
apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3050ac3cd2ae6f03 > /dev/null 2>&1 apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 3050ac3cd2ae6f03 >/dev/null 2>&1
apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 0xF1656F24C74CD1D8 > /dev/null 2>&1 apt-key adv --keyserver hkp://keyserver.ubuntu.com:80 --recv-keys 0xF1656F24C74CD1D8 >/dev/null 2>&1
# fix digitalocean mariadb repository issue # fix digitalocean mariadb repository issue
sed -i 's/sfo1.mirrors.digitalocean.com\/mariadb/mariadb.mirrors.ovh.net\/MariaDB/' /etc/apt/sources.list.d/*.list > /dev/null 2>&1 sed -i 's/sfo1.mirrors.digitalocean.com\/mariadb/mariadb.mirrors.ovh.net\/MariaDB/' /etc/apt/sources.list.d/*.list >/dev/null 2>&1
if [ -f /etc/apt/preferences.d/MariaDB.pref ]; then if [ -f /etc/apt/preferences.d/MariaDB.pref ]; then
sed -i 's/sfo1.mirrors.digitalocean.com/mariadb.mirrors.ovh.net/' /etc/apt/preferences.d/MariaDB.pref > /dev/null 2>&1 sed -i 's/sfo1.mirrors.digitalocean.com/mariadb.mirrors.ovh.net/' /etc/apt/preferences.d/MariaDB.pref >/dev/null 2>&1
fi fi
if ! { if ! {
apt-get update --allow-releaseinfo-change -qq >/dev/null 2>&1 apt-get update --allow-releaseinfo-change -qq >/dev/null 2>&1
@@ -696,8 +706,10 @@ else
# 1 - WO already installed # 1 - WO already installed
if [ -x /usr/local/bin/wo ]; then if [ -x /usr/local/bin/wo ]; then
_run wo_clean _run wo_clean
_run wo_woconf
# 2 - Migration from EEv3 # 2 - Migration from EEv3
elif [ -x /usr/local/bin/ee ]; then else
if [ -x /usr/local/bin/ee ]; then
if [ -z "$wo_force_install" ]; then if [ -z "$wo_force_install" ]; then
echo -e "Migrate from EasyEngine to WordOps (y/n): " && read -r WO_ANSWER echo -e "Migrate from EasyEngine to WordOps (y/n): " && read -r WO_ANSWER
if [ "$WO_ANSWER" != "y" ] && [ "$WO_ANSWER" != "Y" ]; then if [ "$WO_ANSWER" != "y" ] && [ "$WO_ANSWER" != "Y" ]; then
@@ -707,6 +719,8 @@ else
_run wo_backup_ee "Backing-up EE install" _run wo_backup_ee "Backing-up EE install"
_run wo_remove_ee_cron "Removing EasyEngine cronjob" _run wo_remove_ee_cron "Removing EasyEngine cronjob"
fi fi
fi
_run wo_install_dep "Installing wo dependencies" _run wo_install_dep "Installing wo dependencies"
_run wo_timesync _run wo_timesync
# skip steps if travis # skip steps if travis
@@ -737,10 +751,10 @@ else
elif [ "$wo_upgrade" = "1" ]; then elif [ "$wo_upgrade" = "1" ]; then
wo_lib_echo "WordOps (wo) upgrade to $wo_version_new was succesfull!" wo_lib_echo "WordOps (wo) upgrade to $wo_version_new was succesfull!"
echo echo
wo_lib_echo "To upgrade WordOps web stacks use the command:" wo_lib_echo "To upgrade WordOps web stacks, you can use the command:"
wo_lib_echo_info "wo stack upgrade" wo_lib_echo_info "wo stack upgrade"
echo echo
wo_lib_echo "To update all other packages use the command:" wo_lib_echo "To update all other packages, you can use the command:"
wo_lib_echo_info "wo maintenance" wo_lib_echo_info "wo maintenance"
else else
wo_lib_echo "WordOps (wo) installed successfully" wo_lib_echo "WordOps (wo) installed successfully"

View File

@@ -7,3 +7,5 @@ sh>=1.12.14
SQLAlchemy>=1.3.8 SQLAlchemy>=1.3.8
requests>=2.22.0 requests>=2.22.0
distro>=1.4.0 distro>=1.4.0
argcomplete>=1.10.0
colorlog>=4.0.2

View File

@@ -15,7 +15,7 @@ where=tests/
license-file = LICENSE license-file = LICENSE
[flake8] [flake8]
ignore = F405,W504,S322,S404,S603,s607,s602 ignore = F405,W504,S322,S404,S603,s607,s602,C901
exclude = exclude =
# No need to traverse our git directory # No need to traverse our git directory
.git, .git,

View File

@@ -27,7 +27,7 @@ if os.geteuid() == 0:
os.makedirs('/var/lib/wo/tmp/') os.makedirs('/var/lib/wo/tmp/')
setup(name='wordops', setup(name='wordops',
version='3.10.3', version='3.11.0',
description='An essential toolset that eases server administration', description='An essential toolset that eases server administration',
long_description=LONG, long_description=LONG,
long_description_content_type='text/markdown', long_description_content_type='text/markdown',
@@ -40,11 +40,17 @@ setup(name='wordops',
"Natural Language :: English", "Natural Language :: English",
"Topic :: System :: Systems Administration", "Topic :: System :: Systems Administration",
], ],
keywords='', keywords='nginx automation wordpress deployment CLI',
author='WordOps', author='WordOps',
author_email='contact@wordops.io', author_email='contact@wordops.io',
url='https://github.com/WordOps/WordOps', url='https://github.com/WordOps/WordOps',
license='MIT', license='MIT',
project_urls={
'Documentation': 'https://docs.wordops.net',
'Forum': 'https://community.wordops.net',
'Source': 'https://github.com/WordOps/WordOps',
'Tracker': 'https://github.com/WordOps/WordOps/issues',
},
packages=find_packages(exclude=['ez_setup', 'examples', 'tests', packages=find_packages(exclude=['ez_setup', 'examples', 'tests',
'templates']), 'templates']),
include_package_data=True, include_package_data=True,
@@ -64,6 +70,8 @@ setup(name='wordops',
'SQLAlchemy >= 1.3.8', 'SQLAlchemy >= 1.3.8',
'requests >= 2.22.0', 'requests >= 2.22.0',
'distro >= 1.4.0', 'distro >= 1.4.0',
'argcomplete >= 1.10.0',
'colorlog >= 4.0.2',
], ],
extras_require={ # Optional extras_require={ # Optional
'testing': ['nose', 'coverage'], 'testing': ['nose', 'coverage'],

View File

@@ -2,11 +2,7 @@ from wo.utils import test
from wo.cli.main import WOTestApp from wo.cli.main import WOTestApp
class CliTestCaseStack(test.WOTestCase): class CliTestCaseStackInstall(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_install_nginx(self): def test_wo_cli_stack_install_nginx(self):
with WOTestApp(argv=['stack', 'install', '--nginx']) as app: with WOTestApp(argv=['stack', 'install', '--nginx']) as app:

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseStackStop(test.WOTestCase): class CliTestCaseStackStop(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_services_stop_nginx(self): def test_wo_cli_stack_services_stop_nginx(self):
with WOTestApp(argv=['stack', 'stop', '--nginx']) as app: with WOTestApp(argv=['stack', 'stop', '--nginx']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseStackStart(test.WOTestCase): class CliTestCaseStackStart(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_services_start_nginx(self): def test_wo_cli_stack_services_start_nginx(self):
with WOTestApp(argv=['stack', 'start', '--nginx']) as app: with WOTestApp(argv=['stack', 'start', '--nginx']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseStackRestart(test.WOTestCase): class CliTestCaseStackRestart(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_services_restart_nginx(self): def test_wo_cli_stack_services_restart_nginx(self):
with WOTestApp(argv=['stack', 'restart', '--nginx']) as app: with WOTestApp(argv=['stack', 'restart', '--nginx']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseStackStatus(test.WOTestCase): class CliTestCaseStackStatus(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_services_status_nginx(self): def test_wo_cli_stack_services_status_nginx(self):
with WOTestApp(argv=['stack', 'status', '--nginx']) as app: with WOTestApp(argv=['stack', 'status', '--nginx']) as app:
app.run() app.run()

View File

@@ -4,47 +4,53 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteCreate(test.WOTestCase): class CliTestCaseSiteCreate(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_create_html(self): def test_wo_cli_site_create_html(self):
with WOTestApp(argv=['site', 'create', 'example1.com', with WOTestApp(argv=['site', 'create', 'html.com',
'--html']) as app: '--html']) as app:
app.config.set('wo', '', True) app.config.set('wo', '', True)
app.run() app.run()
def test_wo_cli_site_create_php(self): def test_wo_cli_site_create_php(self):
with WOTestApp(argv=['site', 'create', 'example2.com', with WOTestApp(argv=['site', 'create', 'php.com',
'--php']) as app: '--php']) as app:
app.run() app.run()
def test_wo_cli_site_create_mysql(self): def test_wo_cli_site_create_mysql(self):
with WOTestApp(argv=['site', 'create', 'example3.com', with WOTestApp(argv=['site', 'create', 'mysql.com',
'--mysql']) as app: '--mysql']) as app:
app.run() app.run()
def test_wo_cli_site_create_wp(self): def test_wo_cli_site_create_wp(self):
with WOTestApp(argv=['site', 'create', 'example4.com', with WOTestApp(argv=['site', 'create', 'wp.com',
'--wp']) as app: '--wp']) as app:
app.run() app.run()
def test_wo_cli_site_create_wpsubdir(self): def test_wo_cli_site_create_wpsubdir(self):
with WOTestApp(argv=['site', 'create', 'example5.com', with WOTestApp(argv=['site', 'create', 'wpsubdir.com',
'--wpsubdir']) as app: '--wpsubdir']) as app:
app.run() app.run()
def test_wo_cli_site_create_wpsubdomain(self): def test_wo_cli_site_create_wpsubdomain(self):
with WOTestApp(argv=['site', 'create', 'example6.com', with WOTestApp(argv=['site', 'create', 'wpsubdomain.com',
'--wpsubdomain']) as app: '--wpsubdomain']) as app:
app.run() app.run()
def test_wo_cli_site_create_wpfc(self): def test_wo_cli_site_create_wpfc(self):
with WOTestApp(argv=['site', 'create', 'example8.com', with WOTestApp(argv=['site', 'create', 'wpfc.com',
'--wpfc']) as app: '--wpfc']) as app:
app.run() app.run()
def test_wo_cli_site_create_wpsc(self): def test_wo_cli_site_create_wpsc(self):
with WOTestApp(argv=['site', 'create', 'example9.com', with WOTestApp(argv=['site', 'create', 'wpsc.com',
'--wpsc']) as app: '--wpsc']) as app:
app.run() app.run()
def test_wo_cli_site_create_wpce(self):
with WOTestApp(argv=['site', 'create', 'wpce.com',
'--wpce']) as app:
app.run()
def test_wo_cli_site_create_wprocket(self):
with WOTestApp(argv=['site', 'create', 'wprocket.com',
'--wprocket']) as app:
app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteDisable(test.WOTestCase): class CliTestCaseSiteDisable(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_disable(self): def test_wo_cli_site_disable(self):
with WOTestApp(argv=['site', 'disable', 'example2.com']) as app: with WOTestApp(argv=['site', 'disable', 'html.com']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteEnable(test.WOTestCase): class CliTestCaseSiteEnable(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_enable(self): def test_wo_cli_site_enable(self):
with WOTestApp(argv=['site', 'enable', 'example2.com']) as app: with WOTestApp(argv=['site', 'enable', 'html.com']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteInfo(test.WOTestCase): class CliTestCaseSiteInfo(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_info(self): def test_wo_cli_site_info(self):
with WOTestApp(argv=['site', 'info', 'example1.com']) as app: with WOTestApp(argv=['site', 'info', 'html.com']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteList(test.WOTestCase): class CliTestCaseSiteList(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_list_enable(self): def test_wo_cli_site_list_enable(self):
with WOTestApp(argv=['site', 'list', '--enabled']) as app: with WOTestApp(argv=['site', 'list', '--enabled']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteShow(test.WOTestCase): class CliTestCaseSiteShow(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_show_edit(self): def test_wo_cli_show_edit(self):
with WOTestApp(argv=['site', 'show', 'example1.com']) as app: with WOTestApp(argv=['site', 'show', 'html.com']) as app:
app.run() app.run()

View File

@@ -4,46 +4,42 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteUpdate(test.WOTestCase): class CliTestCaseSiteUpdate(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_update_html(self): def test_wo_cli_site_update_html(self):
with WOTestApp(argv=['site', 'update', 'example2.com', with WOTestApp(argv=['site', 'update', 'php.com',
'--html']) as app: '--html']) as app:
app.run() app.run()
def test_wo_cli_site_update_php(self): def test_wo_cli_site_update_php(self):
with WOTestApp(argv=['site', 'update', 'example1.com', with WOTestApp(argv=['site', 'update', 'html.com',
'--php']) as app: '--php']) as app:
app.run() app.run()
def test_wo_cli_site_update_mysql(self): def test_wo_cli_site_update_mysql(self):
with WOTestApp(argv=['site', 'update', 'example1.com', with WOTestApp(argv=['site', 'update', 'mysql.com',
'--html']) as app: '--html']) as app:
app.run() app.run()
def test_wo_cli_site_update_wp(self): def test_wo_cli_site_update_wp(self):
with WOTestApp(argv=['site', 'update', 'example5.com', with WOTestApp(argv=['site', 'update', 'mysql.com',
'--wp']) as app: '--wp']) as app:
app.run() app.run()
def test_wo_cli_site_update_wpsubdir(self): def test_wo_cli_site_update_wpsubdir(self):
with WOTestApp(argv=['site', 'update', 'example4.com', with WOTestApp(argv=['site', 'update', 'wp.com',
'--wpsubdir']) as app: '--wpsubdir']) as app:
app.run() app.run()
def test_wo_cli_site_update_wpsubdomain(self): def test_wo_cli_site_update_wpsubdomain(self):
with WOTestApp(argv=['site', 'update', 'example7.com', with WOTestApp(argv=['site', 'update', 'wpsubdir.com',
'--wpsubdomain']) as app: '--wpsubdomain']) as app:
app.run() app.run()
def test_wo_cli_site_update_wpfc(self): def test_wo_cli_site_update_wpfc(self):
with WOTestApp(argv=['site', 'update', 'example9.com', with WOTestApp(argv=['site', 'update', 'wpsc.com',
'--wpfc']) as app: '--wpfc']) as app:
app.run() app.run()
def test_wo_cli_site_update_wpsc(self): def test_wo_cli_site_update_wpsc(self):
with WOTestApp(argv=['site', 'update', 'example6.com', with WOTestApp(argv=['site', 'update', 'wpfc.com',
'--wpsc']) as app: '--wpsc']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseClean(test.WOTestCase): class CliTestCaseClean(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_clean(self): def test_wo_cli_clean(self):
with WOTestApp(argv=['clean']) as app: with WOTestApp(argv=['clean']) as app:
app.run() app.run()

View File

@@ -1,66 +0,0 @@
from wo.utils import test
from wo.cli.main import WOTestApp
class CliTestCaseDebug(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_debug_stop(self):
with WOTestApp(argv=['debug', '--stop']) as app:
app.run()
def test_wo_cli_debug_start(self):
with WOTestApp(argv=['debug', '--start']) as app:
app.run()
def test_wo_cli_debug_php(self):
with WOTestApp(argv=['debug', '--php']) as app:
app.run()
def test_wo_cli_debug_nginx(self):
with WOTestApp(argv=['debug', '--nginx']) as app:
app.run()
def test_wo_cli_debug_rewrite(self):
with WOTestApp(argv=['debug', '--rewrite']) as app:
app.run()
def test_wo_cli_debug_fpm(self):
with WOTestApp(argv=['debug', '--fpm']) as app:
app.run()
def test_wo_cli_debug_mysql(self):
with WOTestApp(argv=['debug', '--mysql']) as app:
app.run()
def test_wo_cli_debug_import_slow_log_interval(self):
with WOTestApp(argv=['debug', '--mysql',
'--import-slow-log-interval']) as app:
app.run()
def test_wo_cli_debug_site_name_mysql(self):
with WOTestApp(argv=['debug', 'example3.com', '--mysql']) as app:
app.run()
def test_wo_cli_debug_site_name_wp(self):
with WOTestApp(argv=['debug', 'example4.com', '--wp']) as app:
app.run()
def test_wo_cli_debug_site_name_nginx(self):
with WOTestApp(argv=['debug', 'example4.com', '--nginx']) as app:
app.run()
def test_wo_cli_debug_site_name_start(self):
with WOTestApp(argv=['debug', 'example1.com', '--start']) as app:
app.run()
def test_wo_cli_debug_site_name_stop(self):
with WOTestApp(argv=['debug', 'example1.com', '--stop']) as app:
app.run()
def test_wo_cli_debug_site_name_rewrite(self):
with WOTestApp(argv=['debug', 'example1.com', '--rewrite']) as app:
app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseInfo(test.WOTestCase): class CliTestCaseInfo(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_info_mysql(self): def test_wo_cli_info_mysql(self):
with WOTestApp(argv=['info', '--mysql']) as app: with WOTestApp(argv=['info', '--mysql']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseSecure(test.WOTestCase): class CliTestCaseSecure(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_secure_auth(self): def test_wo_cli_secure_auth(self):
with WOTestApp(argv=['secure', '--auth', 'abc', 'superpass']) as app: with WOTestApp(argv=['secure', '--auth', 'abc', 'superpass']) as app:
app.run() app.run()

View File

@@ -4,26 +4,22 @@ from wo.cli.main import WOTestApp
class CliTestCaseSiteDelete(test.WOTestCase): class CliTestCaseSiteDelete(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_site_detele(self): def test_wo_cli_site_detele(self):
with WOTestApp(argv=['site', 'delete', 'example1.com', with WOTestApp(argv=['site', 'delete', 'html.com',
'--no-prompt']) as app: '--force']) as app:
app.run() app.run()
def test_wo_cli_site_detele_all(self): def test_wo_cli_site_detele_all(self):
with WOTestApp(argv=['site', 'delete', 'example2.com', with WOTestApp(argv=['site', 'delete', 'wp.com',
'--all', '--no-prompt']) as app: '--all', '--force']) as app:
app.run() app.run()
def test_wo_cli_site_detele_db(self): def test_wo_cli_site_detele_db(self):
with WOTestApp(argv=['site', 'delete', 'example3.com', with WOTestApp(argv=['site', 'delete', 'mysql.com',
'--db', '--no-prompt']) as app: '--db', '--force']) as app:
app.run() app.run()
def test_wo_cli_site_detele_files(self): def test_wo_cli_site_detele_files(self):
with WOTestApp(argv=['site', 'delete', 'example4.com', with WOTestApp(argv=['site', 'delete', 'php.com',
'--files', '--no-prompt']) as app: '--files', '--force']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseStackRemove(test.WOTestCase): class CliTestCaseStackRemove(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_remove_admin(self): def test_wo_cli_stack_remove_admin(self):
with WOTestApp(argv=['stack', 'remove', '--admin', '--force']) as app: with WOTestApp(argv=['stack', 'remove', '--admin', '--force']) as app:
app.run() app.run()

View File

@@ -4,10 +4,6 @@ from wo.cli.main import WOTestApp
class CliTestCaseStackPurge(test.WOTestCase): class CliTestCaseStackPurge(test.WOTestCase):
def test_wo_cli(self):
with WOTestApp as app:
app.run()
def test_wo_cli_stack_purge_web(self): def test_wo_cli_stack_purge_web(self):
with WOTestApp( with WOTestApp(
argv=['stack', 'purge', '--web', '--force']) as app: argv=['stack', 'purge', '--web', '--force']) as app:

View File

@@ -16,7 +16,7 @@ export LC_ALL='C.UTF-8'
if [ -z "$1" ]; then if [ -z "$1" ]; then
{ {
apt-get -qq purge mysql* graphviz* redis* apt-get -qq purge mysql* graphviz* redis* php73-* php-*
apt-get install -qq git python3-setuptools python3-dev python3-apt ccze tree apt-get install -qq git python3-setuptools python3-dev python3-apt ccze tree
sudo apt-get -qq autoremove --purge sudo apt-get -qq autoremove --purge
} > /dev/null 2>&1 } > /dev/null 2>&1
@@ -30,7 +30,7 @@ exit_script() {
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
echo -e ' stack install ' echo -e ' stack install '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
stack_list='nginx php php73 mysql redis fail2ban clamav proftpd netdata phpmyadmin composer dashboard extplorer adminer redis phpredisadmin mysqltuner utils ufw ngxblocker cheat nanorc' stack_list='nginx php php73 php74 mysql redis fail2ban clamav proftpd netdata phpmyadmin composer dashboard extplorer adminer redis phpredisadmin mysqltuner utils ufw ngxblocker cheat nanorc'
for stack in $stack_list; do for stack in $stack_list; do
echo -ne " Installing $stack [..]\r" echo -ne " Installing $stack [..]\r"
if { if {
@@ -49,7 +49,7 @@ done
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
echo -e ' Simple site create ' echo -e ' Simple site create '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
site_types='html php php73 mysql wp wpfc wpsc wpredis wpce wprocket wpsubdomain wpsubdir ngxblocker' site_types='html php php73 php74 mysql wp wpfc wpsc wpredis wpce wprocket wpsubdomain wpsubdir ngxblocker'
for site in $site_types; do for site in $site_types; do
echo -ne " Creating $site [..]\r" echo -ne " Creating $site [..]\r"
if { if {
@@ -64,10 +64,16 @@ for site in $site_types; do
fi fi
done done
echo
echo -e "${CGREEN}#############################################${CEND}"
echo
wo site info wp.net
echo
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo site update --php73 ' echo -e ' wo site update --php73 '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
other_site_types='html mysql wp wpfc wpsc wpredis wpce wprocket wpsubdomain wpsubdir ngxblocker' other_site_types='html mysql php php74 wp wpfc wpsc wpredis wpce wprocket wpsubdomain wpsubdir ngxblocker'
for site in $other_site_types; do for site in $other_site_types; do
echo -ne " Updating site to $site php73 [..]\r" echo -ne " Updating site to $site php73 [..]\r"
if { if {
@@ -82,7 +88,57 @@ for site in $other_site_types; do
fi fi
done done
echo
echo -e "${CGREEN}#############################################${CEND}"
echo
wo site info wp.net
echo
echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo site update --php74 '
echo -e "${CGREEN}#############################################${CEND}"
other_site_types='html mysql wp php php73 wpfc wpsc wpredis wpce wprocket wpsubdomain wpsubdir ngxblocker'
for site in $other_site_types; do
echo -ne " Updating site to $site php74 [..]\r"
if {
wo site update ${site}.net --php74
} >>/var/log/wo/test.log; then
echo -ne " Updating site to $site php74 [${CGREEN}OK${CEND}]\\r"
echo -ne '\n'
else
echo -e " Updating site to $site php74 [${CRED}FAIL${CEND}]"
echo -ne '\n'
exit_script
fi
done
echo
echo -e "${CGREEN}#############################################${CEND}"
echo
wo site info wp.net
echo
echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo site update --php72 '
echo -e "${CGREEN}#############################################${CEND}"
other_site_types='html mysql php php73 php74 wp wpfc wpsc wpredis wpce wprocket wpsubdomain wpsubdir ngxblocker'
for site in $other_site_types; do
echo -ne " Updating site to $site php72 [..]\r"
if {
wo site update ${site}.net --php72
} >>/var/log/wo/test.log; then
echo -ne " Updating site to $site php72 [${CGREEN}OK${CEND}]\\r"
echo -ne '\n'
else
echo -e " Updating site to $site php72 [${CRED}FAIL${CEND}]"
echo -ne '\n'
exit_script
fi
done
echo
echo -e "${CGREEN}#############################################${CEND}"
echo
wo site info wp.net
echo
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo site update WP ' echo -e ' wo site update WP '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
@@ -147,7 +203,7 @@ if [ -z "$1" ]; then
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo stack upgrade ' echo -e ' wo stack upgrade '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
stack_upgrade='nginx php php73 mysql redis netdata dashboard phpmyadmin composer ngxblocker' stack_upgrade='nginx php php72 php73 php74 mysql redis netdata dashboard phpmyadmin composer ngxblocker mysqltuner'
for stack in $stack_upgrade; do for stack in $stack_upgrade; do
echo -ne " Upgrading $stack [..]\r" echo -ne " Upgrading $stack [..]\r"
if { if {
@@ -232,7 +288,7 @@ echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo site info ' echo -e ' wo site info '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
wo site info wp.net wo site info wpfc.net
echo echo
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
@@ -240,10 +296,29 @@ echo -e ' wo info '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
wo info wo info
echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo site delete '
echo -e "${CGREEN}#############################################${CEND}"
sites=$(wo site list 2>&1)
for site in $sites; do
echo -ne " deleting $site [..]\r"
if {
wo site delete $site --force
} >>/var/log/wo/test.log; then
echo -ne " deleting $site [${CGREEN}OK${CEND}]\\r"
echo -ne '\n'
else
echo -e " deleting $site [${CRED}FAIL${CEND}]"
echo -ne '\n'
exit_script
fi
done
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
echo -e ' wo stack purge ' echo -e ' wo stack purge '
echo -e "${CGREEN}#############################################${CEND}" echo -e "${CGREEN}#############################################${CEND}"
stack_purge='nginx php php73 mysql redis fail2ban clamav proftpd netdata phpmyadmin composer dashboard extplorer adminer redis ufw ngxblocker cheat nanorc' stack_purge='nginx php php73 php74 mysql redis fail2ban clamav proftpd netdata phpmyadmin composer dashboard extplorer adminer redis ufw ngxblocker cheat nanorc'
for stack in $stack_purge; do for stack in $stack_purge; do
echo -ne " purging $stack [..]\r" echo -ne " purging $stack [..]\r"
if { if {

View File

@@ -9,14 +9,6 @@ from cement.utils.misc import init_defaults
from wo.core import exc from wo.core import exc
# this has to happen after you import sys, but before you import anything
# from Cement "source: https://github.com/datafolklabs/cement/issues/290"
if '--debug' in sys.argv:
sys.argv.remove('--debug')
TOGGLE_DEBUG = True
else:
TOGGLE_DEBUG = False
# Application default. Should update config/wo.conf to reflect any # Application default. Should update config/wo.conf to reflect any
# changes, or additions here. # changes, or additions here.
defaults = init_defaults('wo') defaults = init_defaults('wo')
@@ -65,7 +57,7 @@ class WOApp(CementApp):
# Internal templates (ship with application code) # Internal templates (ship with application code)
template_module = 'wo.cli.templates' template_module = 'wo.cli.templates'
extensions = ['mustache'] extensions = ['mustache', 'argcomplete', 'colorlog']
hooks = [ hooks = [
("post_render", encode_output) ("post_render", encode_output)
@@ -73,10 +65,9 @@ class WOApp(CementApp):
output_handler = 'mustache' output_handler = 'mustache'
log_handler = 'colorlog'
arg_handler = WOArgHandler arg_handler = WOArgHandler
debug = TOGGLE_DEBUG
exit_on_close = True exit_on_close = True
@@ -125,13 +116,10 @@ def main():
print('FrameworkError > %s' % e) print('FrameworkError > %s' % e)
app.exit_code = 1 app.exit_code = 1
finally: finally:
# Print an exception (if it occurred) and --debug was passed # Maybe we want to see a full-stack trace for the above
# exceptions, but only if --debug was passed?
if app.debug: if app.debug:
import sys
import traceback import traceback
exc_type, exc_value, exc_traceback = sys.exc_info()
if exc_traceback is not None:
traceback.print_exc() traceback.print_exc()

View File

@@ -32,6 +32,9 @@ class WOInfoController(CementBaseController):
(['--php73'], (['--php73'],
dict(help='Get PHP 7.3 configuration information', dict(help='Get PHP 7.3 configuration information',
action='store_true')), action='store_true')),
(['--php74'],
dict(help='Get PHP 7.4 configuration information',
action='store_true')),
(['--nginx'], (['--nginx'],
dict(help='Get Nginx configuration information', dict(help='Get Nginx configuration information',
action='store_true')), action='store_true')),
@@ -238,6 +241,93 @@ class WOInfoController(CementBaseController):
debug_xdebug_profiler_enable_trigger=debug_xdebug) debug_xdebug_profiler_enable_trigger=debug_xdebug)
self.app.render((data), 'info_php.mustache') self.app.render((data), 'info_php.mustache')
@expose(hide=True)
def info_php74(self):
"""Display PHP information"""
version = os.popen("/usr/bin/php7.4 -v 2>/dev/null | "
"head -n1 | cut -d' ' -f2 |"
" cut -d'+' -f1 | tr -d '\n'").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')
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'
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'
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) @expose(hide=True)
def info_mysql(self): def info_mysql(self):
"""Display MySQL information""" """Display MySQL information"""
@@ -275,38 +365,48 @@ class WOInfoController(CementBaseController):
@expose(hide=True) @expose(hide=True)
def default(self): def default(self):
"""default function for info""" """default function for info"""
if (not self.app.pargs.nginx and not self.app.pargs.php and pargs = self.app.pargs
not self.app.pargs.mysql and not self.app.pargs.php73): if (not pargs.nginx and not pargs.php and
self.app.pargs.nginx = True not pargs.mysql and not pargs.php73 and
self.app.pargs.php = True not pargs.php74):
self.app.pargs.mysql = True pargs.nginx = True
pargs.php = True
pargs.mysql = True
if WOAptGet.is_installed(self, 'php7.3-fpm'): if WOAptGet.is_installed(self, 'php7.3-fpm'):
self.app.pargs.php73 = True pargs.php73 = True
if WOAptGet.is_installed(self, 'php7.4-fpm'):
pargs.php74 = True
if self.app.pargs.nginx: if pargs.nginx:
if ((not WOAptGet.is_installed(self, 'nginx-custom')) and if ((not WOAptGet.is_installed(self, 'nginx-custom')) and
(not os.path.exists('/usr/bin/nginx'))): (not os.path.exists('/usr/bin/nginx'))):
Log.error(self, "Nginx is not installed") Log.info(self, "Nginx is not installed")
else: else:
self.info_nginx() self.info_nginx()
if self.app.pargs.php: if pargs.php:
if WOAptGet.is_installed(self, 'php7.2-fpm'): if WOAptGet.is_installed(self, 'php7.2-fpm'):
self.info_php() self.info_php()
else: else:
Log.error(self, "PHP 7.2 is not installed") Log.info(self, "PHP 7.2 is not installed")
if self.app.pargs.php73: if pargs.php73:
if WOAptGet.is_installed(self, 'php7.3-fpm'): if WOAptGet.is_installed(self, 'php7.3-fpm'):
self.info_php73() self.info_php73()
else: else:
Log.error(self, "PHP 7.3 is not installed") Log.info(self, "PHP 7.3 is not installed")
if self.app.pargs.mysql: if pargs.php74:
if WOAptGet.is_installed(self, 'php7.4-fpm'):
self.info_php74()
else:
Log.info(self, "PHP 7.4 is not installed")
if pargs.mysql:
if WOShellExec.cmd_exec(self, "/usr/bin/mysqladmin ping"): if WOShellExec.cmd_exec(self, "/usr/bin/mysqladmin ping"):
self.info_mysql() self.info_mysql()
else: else:
Log.error(self, "MySQL is not installed") Log.info(self, "MySQL is not installed")
def load(app): def load(app):

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,551 @@
import os
from cement.core.controller import CementBaseController, expose
from wo.cli.plugins.site_functions import *
from wo.cli.plugins.sitedb import (addNewSite, deleteSiteInfo,
updateSiteInfo)
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
class WOSiteCreateController(CementBaseController):
class Meta:
label = 'create'
stacked_on = 'site'
stacked_type = 'nested'
description = ('this commands set up configuration and installs '
'required files as options are provided')
arguments = [
(['site_name'],
dict(help='domain name for the site to be created.',
nargs='?')),
(['--html'],
dict(help="create html site", action='store_true')),
(['--php'],
dict(help="create php 7.2 site", action='store_true')),
(['--php72'],
dict(help="create php 7.2 site", action='store_true')),
(['--php73'],
dict(help="create php 7.3 site", action='store_true')),
(['--php74'],
dict(help="create php 7.4 site", action='store_true')),
(['--mysql'],
dict(help="create mysql site", action='store_true')),
(['--wp'],
dict(help="create WordPress single site",
action='store_true')),
(['--wpsubdir'],
dict(help="create WordPress multisite with subdirectory setup",
action='store_true')),
(['--wpsubdomain'],
dict(help="create WordPress multisite with subdomain setup",
action='store_true')),
(['--wpfc'],
dict(help="create WordPress single/multi site with "
"Nginx fastcgi_cache",
action='store_true')),
(['--wpsc'],
dict(help="create WordPress single/multi site with wpsc cache",
action='store_true')),
(['--wprocket'],
dict(help="create WordPress single/multi site with WP-Rocket",
action='store_true')),
(['--wpce'],
dict(help="create WordPress single/multi site with Cache-Enabler",
action='store_true')),
(['--wpredis'],
dict(help="create WordPress single/multi site "
"with redis cache",
action='store_true')),
(['-le', '--letsencrypt'],
dict(help="configure letsencrypt ssl for the site",
action='store' or 'store_const',
choices=('on', 'subdomain', 'wildcard'),
const='on', nargs='?')),
(['--force'],
dict(help="force Let's Encrypt certificate issuance",
action='store_true')),
(['--dns'],
dict(help="choose dns provider api for letsencrypt",
action='store' or 'store_const',
const='dns_cf', nargs='?')),
(['--dnsalias'],
dict(help="set domain used for acme dns alias validation",
action='store', nargs='?')),
(['--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'],
dict(help="provide email address for WordPress site")),
(['--pass'],
dict(help="provide password for WordPress user",
dest='wppass')),
(['--proxy'],
dict(help="create proxy for site", nargs='+')),
(['--vhostonly'], dict(help="only create vhost and database "
"without installing WordPress",
action='store_true')),
]
@expose(hide=True)
def default(self):
pargs = self.app.pargs
# self.app.render((data), 'default.mustache')
# Check domain name validation
data = dict()
host, port = None, None
try:
stype, cache = detSitePar(vars(pargs))
except RuntimeError as e:
Log.debug(self, str(e))
Log.error(self, "Please provide valid options to creating site")
if stype is None and pargs.proxy:
stype, cache = 'proxy', ''
proxyinfo = pargs.proxy[0].strip()
if not proxyinfo:
Log.error(self, "Please provide proxy server host information")
proxyinfo = proxyinfo.split(':')
host = proxyinfo[0].strip()
port = '80' if len(proxyinfo) < 2 else proxyinfo[1].strip()
elif stype is None and not pargs.proxy:
stype, cache = 'html', 'basic'
elif stype and pargs.proxy:
Log.error(self, "proxy should not be used with other site types")
if not pargs.site_name:
try:
while not pargs.site_name:
# preprocessing before finalize site name
pargs.site_name = (input('Enter site name : ')
.strip())
except IOError as e:
Log.debug(self, str(e))
Log.error(self, "Unable to input site name, Please try again!")
pargs.site_name = pargs.site_name.strip()
wo_domain = WODomain.validate(self, pargs.site_name)
wo_www_domain = "www.{0}".format(wo_domain)
(wo_domain_type, wo_root_domain) = WODomain.getlevel(
self, wo_domain)
if not wo_domain.strip():
Log.error(self, "Invalid domain name, "
"Provide valid domain name")
wo_site_webroot = WOVar.wo_webroot + wo_domain
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))
if stype == 'proxy':
data = dict(
site_name=wo_domain, www_domain=wo_www_domain,
static=True, basic=False, wp=False,
wpfc=False, wpsc=False, wprocket=False, wpce=False,
multisite=False, wpsubdir=False, webroot=wo_site_webroot)
data['proxy'] = True
data['host'] = host
data['port'] = port
data['basic'] = True
if pargs.php72 or pargs.php73 or pargs.php74:
data = dict(
site_name=wo_domain, www_domain=wo_www_domain,
static=False, basic=False,
wp=False, wpfc=False, wpsc=False, wprocket=False,
wpce=False, multisite=False,
wpsubdir=False, webroot=wo_site_webroot)
data['basic'] = True
if stype in ['html', 'php']:
data = dict(
site_name=wo_domain, www_domain=wo_www_domain,
static=True, basic=False, wp=False,
wpfc=False, wpsc=False, wprocket=False, wpce=False,
multisite=False, wpsubdir=False, webroot=wo_site_webroot)
if stype == 'php':
data['static'] = False
data['basic'] = True
elif stype in ['mysql', 'wp', 'wpsubdir', 'wpsubdomain']:
data = dict(
site_name=wo_domain, www_domain=wo_www_domain,
static=False, basic=True, wp=False, wpfc=False,
wpsc=False, wpredis=False, wprocket=False, wpce=False,
multisite=False, wpsubdir=False, webroot=wo_site_webroot,
wo_db_name='', wo_db_user='', wo_db_pass='',
wo_db_host='')
if stype in ['wp', 'wpsubdir', 'wpsubdomain']:
data['wp'] = True
data['basic'] = False
data[cache] = True
data['wp-user'] = pargs.user
data['wp-email'] = pargs.email
data['wp-pass'] = pargs.wppass
if stype in ['wpsubdir', 'wpsubdomain']:
data['multisite'] = True
if stype == 'wpsubdir':
data['wpsubdir'] = True
else:
pass
if data and pargs.php73:
data['php73'] = True
data['php74'] = False
data['php72'] = False
data['wo_php'] = 'php73'
elif data and pargs.php74:
data['php72'] = False
data['php74'] = True
data['php73'] = False
data['wo_php'] = 'php74'
else:
data['php74'] = False
data['php72'] = True
data['php73'] = False
data['wo_php'] = 'php72'
if ((not pargs.wpfc) and (not pargs.wpsc) and
(not pargs.wprocket) and
(not pargs.wpce) and
(not pargs.wpredis)):
data['basic'] = True
if (cache == 'wpredis'):
cache = 'wpredis'
data['wpredis'] = True
data['basic'] = False
pargs.wpredis = True
# Check rerequired packages are installed or not
wo_auth = site_package_check(self, stype)
try:
pre_run_checks(self)
except SiteError as e:
Log.debug(self, str(e))
Log.error(self, "NGINX configuration check failed.")
try:
try:
# setup NGINX 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 +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain,
webroot=data['webroot'])
Log.debug(self, str(e))
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
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'):
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, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
if wo_auth and len(wo_auth):
for msg in wo_auth:
Log.info(self, Log.ENDC + msg, log=False)
Log.info(self, "Successfully created site"
" http://{0}".format(wo_domain))
return
if data['php73']:
php_version = "7.3"
elif data['php74']:
php_version = "7.4"
else:
php_version = "7.2"
addNewSite(self, wo_domain, stype, cache, wo_site_webroot,
php_version=php_version)
# Setup database for MySQL site
if 'wo_db_name' in data.keys() and not data['wp']:
try:
data = setupdatabase(self, data)
# Add database information for site into database
updateSiteInfo(self, wo_domain, db_name=data['wo_db_name'],
db_user=data['wo_db_user'],
db_password=data['wo_db_pass'],
db_host=data['wo_db_host'])
except SiteError as e:
# call cleanup actions on failure
Log.debug(self, str(e))
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain,
webroot=data['webroot'],
dbname=data['wo_db_name'],
dbuser=data['wo_db_user'],
dbhost=data['wo_db_host'])
deleteSiteInfo(self, wo_domain)
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
try:
wodbconfig = open("{0}/wo-config.php"
.format(wo_site_webroot),
encoding='utf-8', mode='w')
wodbconfig.write("<?php \ndefine('DB_NAME', '{0}');"
"\ndefine('DB_USER', '{1}'); "
"\ndefine('DB_PASSWORD', '{2}');"
"\ndefine('DB_HOST', '{3}');\n?>"
.format(data['wo_db_name'],
data['wo_db_user'],
data['wo_db_pass'],
data['wo_db_host']))
wodbconfig.close()
stype = 'mysql'
except IOError as e:
Log.debug(self, str(e))
Log.debug(self, "Error occured while generating "
"wo-config.php")
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain,
webroot=data['webroot'],
dbname=data['wo_db_name'],
dbuser=data['wo_db_user'],
dbhost=data['wo_db_host'])
deleteSiteInfo(self, wo_domain)
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
# Setup WordPress if Wordpress site
if data['wp']:
vhostonly = bool(pargs.vhostonly)
try:
wo_wp_creds = setupwordpress(self, data, vhostonly)
# Add database information for site into database
updateSiteInfo(self, wo_domain,
db_name=data['wo_db_name'],
db_user=data['wo_db_user'],
db_password=data['wo_db_pass'],
db_host=data['wo_db_host'])
except SiteError as e:
# call cleanup actions on failure
Log.debug(self, str(e))
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain,
webroot=data['webroot'],
dbname=data['wo_db_name'],
dbuser=data['wo_db_user'],
dbhost=data['wo_mysql_grant_host'])
deleteSiteInfo(self, wo_domain)
Log.error(self, "Check the log for details: "
"`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'):
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain,
webroot=data['webroot'])
if 'wo_db_name' in data.keys():
doCleanupAction(self, domain=wo_domain,
dbname=data['wo_db_name'],
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.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` "
"and please try again")
WOGit.add(self, ["/etc/nginx"],
msg="{0} created with {1} {2}"
.format(wo_www_domain, stype, cache))
# Setup Permissions for webroot
try:
setwebrootpermissions(self, data['webroot'])
except SiteError as e:
Log.debug(self, str(e))
Log.info(self, Log.FAIL +
"There was a serious error encountered...")
Log.info(self, Log.FAIL + "Cleaning up afterwards...")
doCleanupAction(self, domain=wo_domain,
webroot=data['webroot'])
if 'wo_db_name' in data.keys():
print("Inside db cleanup")
doCleanupAction(self, domain=wo_domain,
dbname=data['wo_db_name'],
dbuser=data['wo_db_user'],
dbhost=data['wo_mysql_grant_host'])
deleteSiteInfo(self, wo_domain)
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` and "
"please try again")
if wo_auth and len(wo_auth):
for msg in wo_auth:
Log.info(self, Log.ENDC + msg, log=False)
if data['wp'] and (not pargs.vhostonly):
Log.info(self, Log.ENDC + "WordPress admin user :"
" {0}".format(wo_wp_creds['wp_user']), log=False)
Log.info(self, Log.ENDC + "WordPress admin password : {0}"
.format(wo_wp_creds['wp_pass']), log=False)
display_cache_settings(self, data)
Log.info(self, "Successfully created site"
" http://{0}".format(wo_domain))
except SiteError:
Log.error(self, "Check the log for details: "
"`tail /var/log/wo/wordops.log` and please try again")
if pargs.letsencrypt:
acme_domains = []
data['letsencrypt'] = True
letsencrypt = True
Log.debug(self, "Going to issue Let's Encrypt certificate")
acmedata = dict(
acme_domains, dns=False, acme_dns='dns_cf',
dnsalias=False, acme_alias='', keylength='')
if self.app.config.has_section('letsencrypt'):
acmedata['keylength'] = self.app.config.get(
'letsencrypt', 'keylength')
else:
acmedata['keylength'] = 'ec-384'
if pargs.dns:
Log.debug(self, "DNS validation enabled")
acmedata['dns'] = True
if not pargs.dns == 'dns_cf':
Log.debug(self, "DNS API : {0}".format(pargs.dns))
acmedata['acme_dns'] = pargs.dns
if pargs.dnsalias:
Log.debug(self, "DNS Alias enabled")
acmedata['dnsalias'] = True
acmedata['acme_alias'] = pargs.dnsalias
# detect subdomain and set subdomain variable
if pargs.letsencrypt == "subdomain":
Log.warn(
self, 'Flag --letsencrypt=subdomain is '
'deprecated and not required anymore.')
acme_subdomain = True
acme_wildcard = False
elif pargs.letsencrypt == "wildcard":
acme_wildcard = True
acme_subdomain = False
acmedata['dns'] = True
else:
if ((wo_domain_type == 'subdomain')):
Log.debug(self, "Domain type = {0}"
.format(wo_domain_type))
acme_subdomain = True
else:
acme_subdomain = False
acme_wildcard = False
if acme_subdomain is True:
Log.info(self, "Certificate type : subdomain")
acme_domains = acme_domains + ['{0}'.format(wo_domain)]
elif acme_wildcard is True:
Log.info(self, "Certificate type : wildcard")
acme_domains = acme_domains + ['{0}'.format(wo_domain),
'*.{0}'.format(wo_domain)]
else:
Log.info(self, "Certificate type : domain")
acme_domains = acme_domains + ['{0}'.format(wo_domain),
'www.{0}'.format(wo_domain)]
if WOAcme.cert_check(self, wo_domain):
SSL.archivedcertificatehandle(self, wo_domain, acme_domains)
else:
if acme_subdomain is True:
# check if a wildcard cert for the root domain exist
Log.debug(self, "checkWildcardExist on *.{0}"
.format(wo_root_domain))
if SSL.checkwildcardexist(self, wo_root_domain):
Log.info(self, "Using existing Wildcard SSL "
"certificate from {0} to secure {1}"
.format(wo_root_domain, wo_domain))
Log.debug(self, "symlink wildcard "
"cert between {0} & {1}"
.format(wo_domain, wo_root_domain))
# copy the cert from the root domain
copyWildcardCert(self, wo_domain, wo_root_domain)
else:
# check DNS records before issuing cert
if not acmedata['dns'] is True:
if not pargs.force:
if not WOAcme.check_dns(self, acme_domains):
Log.error(self,
"Aborting SSL "
"certificate issuance")
Log.debug(self, "Setup Cert with acme.sh for {0}"
.format(wo_domain))
if WOAcme.setupletsencrypt(
self, acme_domains, acmedata):
WOAcme.deploycert(self, wo_domain)
else:
if not acmedata['dns'] is True:
if not pargs.force:
if not WOAcme.check_dns(self, acme_domains):
Log.error(self,
"Aborting SSL certificate issuance")
if WOAcme.setupletsencrypt(
self, acme_domains, acmedata):
WOAcme.deploycert(self, wo_domain)
if pargs.hsts:
SSL.setuphsts(self, wo_domain)
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")
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)],
msg="Adding letsencrypts config of site: {0}"
.format(wo_domain))
updateSiteInfo(self, wo_domain, ssl=letsencrypt)

View File

@@ -38,7 +38,7 @@ class SiteError(Exception):
def pre_run_checks(self): def pre_run_checks(self):
# Check nginx configuration # Check nginx configuration
Log.wait(self, "Running pre-update checks") Log.wait(self, "Running pre-run checks")
try: try:
Log.debug(self, "checking NGINX configuration ...") Log.debug(self, "checking NGINX configuration ...")
fnull = open('/dev/null', 'w') fnull = open('/dev/null', 'w')
@@ -78,12 +78,8 @@ def setupdomain(self, data):
wo_site_nginx_conf = open('/etc/nginx/sites-available/{0}' wo_site_nginx_conf = open('/etc/nginx/sites-available/{0}'
.format(wo_domain_name), encoding='utf-8', .format(wo_domain_name), encoding='utf-8',
mode='w') mode='w')
if not data['php73']:
self.app.render((data), 'virtualconf.mustache', self.app.render((data), 'virtualconf.mustache',
out=wo_site_nginx_conf) out=wo_site_nginx_conf)
else:
self.app.render((data), 'virtualconf-php7.mustache',
out=wo_site_nginx_conf)
wo_site_nginx_conf.close() wo_site_nginx_conf.close()
except IOError as e: except IOError as e:
Log.debug(self, str(e)) Log.debug(self, str(e))
@@ -148,7 +144,9 @@ def setupdatabase(self, data):
wo_random_pass = (''.join(random.sample(string.ascii_uppercase + wo_random_pass = (''.join(random.sample(string.ascii_uppercase +
string.ascii_lowercase + string.ascii_lowercase +
string.digits, 24))) string.digits, 24)))
wo_replace_dot = wo_domain_name.replace('.', '') wo_replace_dash = wo_domain_name.replace('-', '_')
wo_replace_dot = wo_replace_dash.replace('.', '_')
wo_replace_underscore = wo_replace_dot.replace('_', '')
if self.app.config.has_section('mysql'): if self.app.config.has_section('mysql'):
prompt_dbname = self.app.config.get('mysql', 'db-name') prompt_dbname = self.app.config.get('mysql', 'db-name')
prompt_dbuser = self.app.config.get('mysql', 'db-user') prompt_dbuser = self.app.config.get('mysql', 'db-user')
@@ -170,8 +168,7 @@ def setupdatabase(self, data):
raise SiteError("Unable to input database name") raise SiteError("Unable to input database name")
if not wo_db_name: if not wo_db_name:
wo_db_name = wo_replace_dot wo_db_name = (wo_replace_dot[0:32] + '_' + generate_8_random())
wo_db_name = (wo_db_name[0:16] + generate_random())
if prompt_dbuser == 'True' or prompt_dbuser == 'true': if prompt_dbuser == 'True' or prompt_dbuser == 'true':
try: try:
@@ -184,8 +181,7 @@ def setupdatabase(self, data):
raise SiteError("Unable to input database credentials") raise SiteError("Unable to input database credentials")
if not wo_db_username: if not wo_db_username:
wo_db_username = wo_replace_dot wo_db_username = (wo_replace_underscore[0:12] + generate_random())
wo_db_username = (wo_db_name[0:12] + generate_random())
if not wo_db_password: if not wo_db_password:
wo_db_password = wo_random_pass wo_db_password = wo_random_pass
@@ -195,7 +191,7 @@ def setupdatabase(self, data):
try: try:
if WOMysql.check_db_exists(self, wo_db_name): if WOMysql.check_db_exists(self, wo_db_name):
Log.debug(self, "Database already exists, Updating DB_NAME .. ") Log.debug(self, "Database already exists, Updating DB_NAME .. ")
wo_db_name = (wo_db_name[0:16] + generate_random()) wo_db_name = (wo_db_name[0:32] + '_' + generate_8_random())
wo_db_username = (wo_db_name[0:12] + generate_random()) wo_db_username = (wo_db_name[0:12] + generate_random())
except MySQLConnectionError: except MySQLConnectionError:
raise SiteError("MySQL Connectivity problem occured") raise SiteError("MySQL Connectivity problem occured")
@@ -388,7 +384,7 @@ def setupwordpress(self, data, vhostonly=False):
['MEDIA_TRASH', 'true'], ['MEDIA_TRASH', 'true'],
['EMPTY_TRASH_DAYS', '15'], ['EMPTY_TRASH_DAYS', '15'],
['WP_AUTO_UPDATE_CORE', 'minor']] ['WP_AUTO_UPDATE_CORE', 'minor']]
Log.wait(self, "Configuring WordPress")
for wp_conf in wp_conf_variables: for wp_conf in wp_conf_variables:
wp_var = wp_conf[0] wp_var = wp_conf[0]
wp_val = wp_conf[1] wp_val = wp_conf[1]
@@ -403,8 +399,10 @@ def setupwordpress(self, data, vhostonly=False):
wp_raw='--raw' wp_raw='--raw'
if var_raw is True else '')) if var_raw is True else ''))
except CommandExecutionError as e: except CommandExecutionError as e:
Log.failed(self, "Configuring WordPress")
Log.debug(self, str(e)) Log.debug(self, str(e))
Log.error(self, 'Unable to define wp-config.php variables') Log.error(self, 'Unable to define wp-config.php variables')
Log.valide(self, "Configuring WordPress")
# WOFileUtils.mvfile(self, os.getcwd()+'/wp-config.php', # WOFileUtils.mvfile(self, os.getcwd()+'/wp-config.php',
# os.path.abspath(os.path.join(os.getcwd(), os.pardir))) # os.path.abspath(os.path.join(os.getcwd(), os.pardir)))
@@ -455,7 +453,7 @@ def setupwordpress(self, data, vhostonly=False):
raise SiteError("input WordPress user email failed") raise SiteError("input WordPress user email failed")
Log.debug(self, "Setting up WordPress tables") Log.debug(self, "Setting up WordPress tables")
Log.wait(self, "Installing WordPress")
if not data['multisite']: if not data['multisite']:
Log.debug(self, "Creating tables for WordPress Single site") Log.debug(self, "Creating tables for WordPress Single site")
Log.debug( Log.debug(
@@ -478,6 +476,7 @@ def setupwordpress(self, data, vhostonly=False):
log=False): log=False):
pass pass
else: else:
Log.failed(self, "Installing WordPress")
raise SiteError( raise SiteError(
"setup WordPress tables failed for single site") "setup WordPress tables failed for single site")
except CommandExecutionError: except CommandExecutionError:
@@ -511,11 +510,12 @@ def setupwordpress(self, data, vhostonly=False):
log=False): log=False):
pass pass
else: else:
Log.failed(self, "Installing WordPress")
raise SiteError( raise SiteError(
"setup WordPress tables failed for wp multi site") "setup WordPress tables failed for wp multi site")
except CommandExecutionError: except CommandExecutionError:
raise SiteError("setup WordPress tables failed for wp multi site") raise SiteError("setup WordPress tables failed for wp multi site")
Log.valide(self, "Installing WordPress")
Log.debug(self, "Updating WordPress permalink") Log.debug(self, "Updating WordPress permalink")
try: try:
WOShellExec.cmd_exec(self, " {0} --allow-root " WOShellExec.cmd_exec(self, " {0} --allow-root "
@@ -774,8 +774,9 @@ def sitebackup(self, data):
WOFileUtils.copyfile(self, '/etc/nginx/sites-available/{0}' WOFileUtils.copyfile(self, '/etc/nginx/sites-available/{0}'
.format(data['site_name']), backup_path) .format(data['site_name']), backup_path)
if data['currsitetype'] in ['html', 'php', 'proxy', 'mysql']: if data['currsitetype'] in ['html', 'php', 'php72', 'php74',
if data['php73'] is True and not data['wp']: 'php73', 'proxy', 'mysql']:
if not data['wp']:
Log.info(self, "Backing up Webroot \t\t", end='') Log.info(self, "Backing up Webroot \t\t", end='')
WOFileUtils.copyfiles(self, wo_site_webroot + WOFileUtils.copyfiles(self, wo_site_webroot +
'/htdocs', backup_path + '/htdocs') '/htdocs', backup_path + '/htdocs')
@@ -832,8 +833,9 @@ def site_package_check(self, stype):
packages = [] packages = []
stack = WOStackController() stack = WOStackController()
stack.app = self.app stack.app = self.app
if stype in ['html', 'proxy', 'php', 'mysql', 'wp', 'wpsubdir', pargs = self.app.pargs
'wpsubdomain', 'php73']: if stype in ['html', 'proxy', 'php', 'php72', 'mysql', 'wp', 'wpsubdir',
'wpsubdomain', 'php73', 'php74']:
Log.debug(self, "Setting apt_packages variable for Nginx") Log.debug(self, "Setting apt_packages variable for Nginx")
# Check if server has nginx-custom package # Check if server has nginx-custom package
@@ -846,7 +848,7 @@ def site_package_check(self, stype):
Log.info(self, "NGINX PLUS Detected ...") Log.info(self, "NGINX PLUS Detected ...")
apt = ["nginx-plus"] + WOVar.wo_nginx apt = ["nginx-plus"] + WOVar.wo_nginx
# apt_packages = apt_packages + WOVar.wo_nginx # apt_packages = apt_packages + WOVar.wo_nginx
stack.post_pref(self, apt, packages) post_pref(self, apt, packages)
elif WOAptGet.is_installed(self, 'nginx'): elif WOAptGet.is_installed(self, 'nginx'):
Log.info(self, "WordOps detected a previously" Log.info(self, "WordOps detected a previously"
"installed Nginx package. " "installed Nginx package. "
@@ -869,69 +871,68 @@ def site_package_check(self, stype):
wo_nginx.write('fastcgi_param \tSCRIPT_FILENAME ' wo_nginx.write('fastcgi_param \tSCRIPT_FILENAME '
'\t$request_filename;\n') '\t$request_filename;\n')
if self.app.pargs.php and self.app.pargs.php73: if pargs.php and pargs.php73:
Log.error( Log.error(
self, "Error: two different PHP versions cannot be " self, "Error: two different PHP versions cannot be "
"combined within the same WordOps site") "combined within the same WordOps site")
if not self.app.pargs.php73 and stype in ['php', 'mysql', 'wp', 'wpsubdir', if pargs.php and pargs.php74:
'wpsubdomain']: Log.error(
Log.debug(self, "Setting apt_packages variable for PHP 7.2") self, "Error: two different PHP versions cannot be "
if not WOAptGet.is_installed(self, 'php7.2-fpm'): "combined within the same WordOps site")
if not WOAptGet.is_installed(self, 'php7.3-fpm'):
apt_packages = apt_packages + WOVar.wo_php + \
WOVar.wo_php_extra
else:
apt_packages = apt_packages + WOVar.wo_php
if self.app.pargs.php73 and stype in ['mysql', 'wp', if pargs.php73 and pargs.php74:
Log.error(
self, "Error: two different PHP versions cannot be "
"combined within the same WordOps site")
if ((not pargs.php73) and (not pargs.php74) and
stype in ['php', 'php72', 'mysql', 'wp', 'wpsubdir',
'wpsubdomain']):
Log.debug(self, "Setting apt_packages variable for PHP 7.2")
if not (WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php72
if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
if pargs.php73 and stype in ['php73', 'mysql', 'wp',
'wpsubdir', 'wpsubdomain']: 'wpsubdir', 'wpsubdomain']:
Log.debug(self, "Setting apt_packages variable for PHP 7.3") Log.debug(self, "Setting apt_packages variable for PHP 7.3")
if not WOAptGet.is_installed(self, 'php7.3-fpm'): if not WOAptGet.is_installed(self, 'php7.3-fpm'):
if not WOAptGet.is_installed(self, 'php7.2-fpm'):
apt_packages = apt_packages + WOVar.wo_php + \
WOVar.wo_php73 + WOVar.wo_php_extra
else:
apt_packages = apt_packages + WOVar.wo_php73 apt_packages = apt_packages + WOVar.wo_php73
if not (WOAptGet.is_installed(self, 'php7.2-fpm') or
WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
if pargs.php74 and stype in ['php74', 'mysql', 'wp',
'wpsubdir', 'wpsubdomain']:
Log.debug(self, "Setting apt_packages variable for PHP 7.4")
if not WOAptGet.is_installed(self, 'php7.4-fpm'):
apt_packages = apt_packages + WOVar.wo_php74
if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
if stype in ['mysql', 'wp', 'wpsubdir', 'wpsubdomain']: if stype in ['mysql', 'wp', 'wpsubdir', 'wpsubdomain']:
Log.debug(self, "Setting apt_packages variable for MySQL") Log.debug(self, "Setting apt_packages variable for MySQL")
if not WOShellExec.cmd_exec(self, "/usr/bin/mysqladmin ping"): if not WOShellExec.cmd_exec(self, "/usr/bin/mysqladmin ping"):
if not WOVar.wo_distro == 'raspbian': apt_packages = apt_packages + WOVar.wo_mysql
if (not WOVar.wo_platform_codename == 'jessie'):
wo_mysql = ["mariadb-server", "percona-toolkit",
"python3-mysqldb", "mariadb-backup"]
else:
wo_mysql = ["mariadb-server", "percona-toolkit",
"python3-mysql.connector"]
else:
wo_mysql = ["mariadb-server", "percona-toolkit",
"python3-mysqldb"]
apt_packages = apt_packages + wo_mysql
if stype in ['wp', 'wpsubdir', 'wpsubdomain']: if stype in ['wp', 'wpsubdir', 'wpsubdomain']:
Log.debug(self, "Setting packages variable for WP-CLI") Log.debug(self, "Setting packages variable for WP-CLI")
if not WOShellExec.cmd_exec(self, "command -v wp"): if not WOAptGet.is_exec(self, "wp"):
packages = packages + [["https://github.com/wp-cli/wp-cli/" packages = packages + [["https://github.com/wp-cli/wp-cli/"
"releases/download/v{0}/" "releases/download/v{0}/"
"wp-cli-{0}.phar" "wp-cli-{0}.phar"
.format(WOVar.wo_wp_cli), .format(WOVar.wo_wp_cli),
"/usr/local/bin/wp", "WP-CLI"]] "/usr/local/bin/wp", "WP-CLI"]]
if self.app.pargs.wpredis: if pargs.wpredis:
Log.debug(self, "Setting apt_packages variable for redis") Log.debug(self, "Setting apt_packages variable for redis")
if not WOAptGet.is_installed(self, 'redis-server'): if not WOAptGet.is_installed(self, 'redis-server'):
apt_packages = apt_packages + ["redis-server"] apt_packages = apt_packages + WOVar.wo_redis
if self.app.pargs.php73: if pargs.ngxblocker:
Log.debug(self, "Setting apt_packages variable for PHP 7.3")
if not WOAptGet.is_installed(self, 'php7.3-fpm'):
if not WOAptGet.is_installed(self, 'php7.2-fpm'):
apt_packages = apt_packages + WOVar.wo_php + \
WOVar.wo_php73 + WOVar.wo_php_extra
else:
apt_packages = apt_packages + WOVar.wo_php73
if self.app.pargs.ngxblocker:
if not os.path.isdir('/etc/nginx/bots.d'): if not os.path.isdir('/etc/nginx/bots.d'):
Log.debug(self, "Setting packages variable for ngxblocker") Log.debug(self, "Setting packages variable for ngxblocker")
packages = packages + \ packages = packages + \
@@ -1093,7 +1094,8 @@ def detSitePar(opts):
cachelist = list() cachelist = list()
for key, val in opts.items(): for key, val in opts.items():
if val and key in ['html', 'php', 'mysql', 'wp', if val and key in ['html', 'php', 'mysql', 'wp',
'wpsubdir', 'wpsubdomain', 'php73']: 'wpsubdir', 'wpsubdomain', 'php72',
'php73', 'php74']:
typelist.append(key) typelist.append(key)
elif val and key in ['wpfc', 'wpsc', 'wpredis', 'wprocket', 'wpce']: elif val and key in ['wpfc', 'wpsc', 'wpredis', 'wprocket', 'wpce']:
cachelist.append(key) cachelist.append(key)
@@ -1109,24 +1111,48 @@ def detSitePar(opts):
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('php72', 'mysql', 'html') for x in typelist]:
sitetype = 'mysql'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('php73', 'mysql', 'html') for x in typelist]: elif False not in [x in ('php73', 'mysql', 'html') for x in typelist]:
sitetype = 'mysql' sitetype = 'mysql'
if not cachelist: if not cachelist:
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('php74', '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]: elif False not in [x in ('php', 'mysql') for x in typelist]:
sitetype = 'mysql' sitetype = 'mysql'
if not cachelist: if not cachelist:
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('php72', 'mysql') for x in typelist]:
sitetype = 'mysql'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('php73', 'mysql') for x in typelist]: elif False not in [x in ('php73', 'mysql') for x in typelist]:
sitetype = 'mysql' sitetype = 'mysql'
if not cachelist: if not cachelist:
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('php74', '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]: elif False not in [x in ('html', 'mysql') for x in typelist]:
sitetype = 'mysql' sitetype = 'mysql'
if not cachelist: if not cachelist:
@@ -1139,12 +1165,6 @@ def detSitePar(opts):
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('php73', 'html') for x in typelist]:
sitetype = 'php73'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wp', 'wpsubdir') for x in typelist]: elif False not in [x in ('wp', 'wpsubdir') for x in typelist]:
sitetype = 'wpsubdir' sitetype = 'wpsubdir'
if not cachelist: if not cachelist:
@@ -1157,33 +1177,75 @@ def detSitePar(opts):
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('wp', 'php72') for x in typelist]:
sitetype = 'wp'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wp', 'php73') for x in typelist]: elif False not in [x in ('wp', 'php73') for x in typelist]:
sitetype = 'wp' sitetype = 'wp'
if not cachelist: if not cachelist:
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('wp', 'php74') for x in typelist]:
sitetype = 'wp'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdir', 'php72') for x in typelist]:
sitetype = 'wpsubdir'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdir', 'php73') for x in typelist]: elif False not in [x in ('wpsubdir', 'php73') for x in typelist]:
sitetype = 'wpsubdir' sitetype = 'wpsubdir'
if not cachelist: if not cachelist:
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('wpsubdir', 'php74') for x in typelist]:
sitetype = 'wpsubdir'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdomain', 'php72') for x in typelist]:
sitetype = 'wpsubdomain'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
elif False not in [x in ('wpsubdomain', 'php73') for x in typelist]: elif False not in [x in ('wpsubdomain', 'php73') for x in typelist]:
sitetype = 'wpsubdomain' sitetype = 'wpsubdomain'
if not cachelist: if not cachelist:
cachetype = 'basic' cachetype = 'basic'
else: else:
cachetype = cachelist[0] cachetype = cachelist[0]
elif False not in [x in ('wpsubdomain', 'php74') for x in typelist]:
sitetype = 'wpsubdomain'
if not cachelist:
cachetype = 'basic'
else:
cachetype = cachelist[0]
else: else:
raise RuntimeError("could not determine site and cache type") raise RuntimeError("could not determine site and cache type")
else: else:
if not typelist and not cachelist: if not typelist and not cachelist:
sitetype = None sitetype = None
cachetype = None cachetype = None
elif (not typelist or "php72" in typelist) and cachelist:
sitetype = 'wp'
cachetype = cachelist[0]
elif (not typelist or "php73" in typelist) and cachelist: elif (not typelist or "php73" in typelist) and cachelist:
sitetype = 'wp' sitetype = 'wp'
cachetype = cachelist[0] cachetype = cachelist[0]
elif (not typelist or "php74" in typelist) and cachelist:
sitetype = 'wp'
cachetype = cachelist[0]
elif typelist and (not cachelist): elif typelist and (not cachelist):
sitetype = typelist[0] sitetype = typelist[0]
cachetype = 'basic' cachetype = 'basic'
@@ -1208,6 +1270,13 @@ def generate_random():
return wo_random10 return wo_random10
def generate_8_random():
wo_random8 = (''.join(random.sample(string.ascii_uppercase +
string.ascii_lowercase +
string.digits, 8)))
return wo_random8
def deleteDB(self, dbname, dbuser, dbhost, exit=True): def deleteDB(self, dbname, dbuser, dbhost, exit=True):
try: try:
# Check if Database exists # Check if Database exists
@@ -1382,170 +1451,6 @@ def renewLetsEncrypt(self, wo_domain_name):
# redirect= False to disable https redirection # redirect= False to disable https redirection
def httpsRedirect(self, wo_domain_name, redirect=True, wildcard=False):
if redirect:
if os.path.isfile("/etc/nginx/conf.d/force-ssl-{0}.conf.disabled"
.format(wo_domain_name)):
WOFileUtils.mvfile(self,
"/etc/nginx/conf.d/force-ssl-{0}.conf.disabled"
.format(wo_domain_name),
"/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name))
else:
Log.wait(self, "Adding HTTPS redirection")
if wildcard:
try:
sslconf = open("/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name),
encoding='utf-8', mode='w')
sslconf.write("server {\n"
"\tlisten 80;\n" +
"\tlisten [::]:80;\n" +
"\tserver_name *.{0} {0};\n"
.format(wo_domain_name) +
"\treturn 301 https://$host"
"$request_uri;\n}")
sslconf.close()
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))
else:
try:
sslconf = open("/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name),
encoding='utf-8', mode='w')
sslconf.write("server {\n"
"\tlisten 80;\n" +
"\tlisten [::]:80;\n" +
"\tserver_name www.{0} {0};\n"
.format(wo_domain_name) +
"\treturn 301 https://$host"
"$request_uri;\n}")
sslconf.close()
except IOError as e:
Log.failed(self, "Adding HTTPS redirection")
Log.debug(self, str(e))
Log.debug(self, "Error occured while generating "
"/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name))
else:
Log.valide(self, "Adding HTTPS redirection")
# Nginx Configation into GIT
WOGit.add(self,
["/etc/nginx"], msg="Adding /etc/nginx/conf.d/"
"force-ssl-{0}.conf".format(wo_domain_name))
else:
if os.path.isfile("/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name)):
WOFileUtils.mvfile(self, "/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name),
"/etc/nginx/conf.d/force-ssl-{0}.conf.disabled"
.format(wo_domain_name))
Log.info(self, "Disabled HTTPS Force Redirection for Site "
" http://{0}".format(wo_domain_name))
def archivedCertificateHandle(self, domain):
Log.warn(
self, "You already have an existing certificate "
"for the domain requested.\n"
"(ref: {0}/"
"{1}_ecc/{1}.conf)".format(WOVar.wo_ssl_archive, domain) +
"\nPlease select an option from below?"
"\n\t1: Reinstall existing certificate"
"\n\t2: Issue a new certificate to replace "
"the current one (limit ~5 per 7 days)"
"")
check_prompt = input(
"\nType the appropriate number [1-2] or any other key to cancel: ")
if not os.path.isfile("{0}/{1}/fullchain.pem"
.format(WOVar.wo_ssl_live, domain)):
Log.error(
self, "{0}/{1}/fullchain.pem file is missing."
.format(WOVar.wo_ssl_live, domain))
if check_prompt == "1":
Log.info(self, "Reinstalling SSL cert with acme.sh")
ssl = WOAcme.deploycert(self, domain)
if ssl:
try:
if not os.path.isfile("/var/www/{0}/conf/nginx/ssl.conf"
.format(domain)):
Log.info(
self, "Adding /var/www/{0}/conf/nginx/ssl.conf"
.format(domain))
sslconf = open("/var/www/{0}/conf/nginx/ssl.conf"
.format(domain),
encoding='utf-8', mode='w')
sslconf.write("listen 443 ssl http2;\n"
"listen [::]:443 ssl http2;\n"
"ssl_certificate "
"{0}/{1}/fullchain.pem;\n"
"ssl_certificate_key {0}/{1}/key.pem;\n"
"ssl_trusted_certificate {0}/{1}/ca.pem;\n"
"ssl_stapling_verify on;\n"
.format(WOVar.wo_ssl_live, domain))
sslconf.close()
except IOError as e:
Log.debug(self, str(e))
Log.debug(self, "Error occured while generating "
"ssl.conf")
elif (check_prompt == "2"):
Log.info(self, "Issuing SSL cert with acme.sh")
ssl = WOShellExec.cmd_exec(self, "/etc/letsencrypt/acme.sh "
"--config-home "
"'/etc/letsencrypt/config' "
"--renew -d {0} --ecc "
"--force"
.format(domain))
if ssl:
try:
WOShellExec.cmd_exec(self, "mkdir -p {0}/{1} && "
"/etc/letsencrypt/acme.sh "
"--config-home "
"'/etc/letsencrypt/config' "
"--install-cert -d {1} --ecc "
"--cert-file {0}/{1}/cert.pem "
"--key-file {0}/{1}/key.pem "
"--fullchain-file "
"{0}/{1}/fullchain.pem "
"ssl_trusted_certificate "
"{0}/{1}/ca.pem;\n"
"--reloadcmd "
"\"nginx -t && service nginx restart\" "
.format(WOVar.wo_ssl_live, domain))
except IOError as e:
Log.debug(self, str(e))
Log.debug(self, "Error occured while installing "
"the certificate")
else:
Log.error(self, "Operation cancelled by user.")
if os.path.isfile("{0}/conf/nginx/ssl.conf"
.format(domain)):
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))
return ssl
def setuprocketchat(self): def setuprocketchat(self):
if ((not WOVar.wo_platform_codename == 'bionic') and if ((not WOVar.wo_platform_codename == 'bionic') and
(not WOVar.wo_platform_codename == 'xenial')): (not WOVar.wo_platform_codename == 'xenial')):
@@ -1557,6 +1462,7 @@ def setuprocketchat(self):
WOAptGet.install(self, ["snapd"]) WOAptGet.install(self, ["snapd"])
if WOShellExec.cmd_exec(self, "snap install rocketchat-server"): if WOShellExec.cmd_exec(self, "snap install rocketchat-server"):
return True return True
return False
def setupngxblocker(self, domain, block=True): def setupngxblocker(self, domain, block=True):

File diff suppressed because it is too large Load Diff

View File

@@ -41,8 +41,12 @@ class WOStackController(CementBaseController):
dict(help='Install Nginx stack', action='store_true')), dict(help='Install Nginx stack', action='store_true')),
(['--php'], (['--php'],
dict(help='Install PHP 7.2 stack', action='store_true')), dict(help='Install PHP 7.2 stack', action='store_true')),
(['--php72'],
dict(help='Install PHP 7.2 stack', action='store_true')),
(['--php73'], (['--php73'],
dict(help='Install PHP 7.3 stack', action='store_true')), dict(help='Install PHP 7.3 stack', action='store_true')),
(['--php74'],
dict(help='Install PHP 7.4 stack', action='store_true')),
(['--mysql'], (['--mysql'],
dict(help='Install MySQL stack', action='store_true')), dict(help='Install MySQL stack', action='store_true')),
(['--mysqlclient'], (['--mysqlclient'],
@@ -105,40 +109,40 @@ class WOStackController(CementBaseController):
def install(self, packages=[], apt_packages=[], disp_msg=True): def install(self, packages=[], apt_packages=[], disp_msg=True):
"""Start installation of packages""" """Start installation of packages"""
self.msg = [] self.msg = []
empty_packages = []
wo_webroot = "/var/www/"
pargs = self.app.pargs pargs = self.app.pargs
try: try:
# Default action for stack installation # Default action for stack installation
if ((not pargs.web) and (not pargs.admin) and if not (pargs.web or pargs.admin or pargs.nginx or
(not pargs.nginx) and (not pargs.php) and pargs.php or pargs.php72 or pargs.php73 or pargs.php74 or
(not pargs.mysql) and (not pargs.wpcli) and pargs.mysql or pargs.wpcli or pargs.phpmyadmin or
(not pargs.phpmyadmin) and (not pargs.composer) and pargs.composer or pargs.netdata or pargs.composer or
(not pargs.netdata) and (not pargs.dashboard) and pargs.dashboard or pargs.fail2ban or pargs.security or
(not pargs.fail2ban) and (not pargs.security) and pargs.mysqlclient or pargs.mysqltuner or
(not pargs.mysqlclient) and (not pargs.mysqltuner) and pargs.admin or pargs.adminer or
(not pargs.adminer) and (not pargs.utils) and pargs.utils or pargs.redis or
(not pargs.redis) and (not pargs.proftpd) and pargs.proftpd or pargs.extplorer or
(not pargs.extplorer) and (not pargs.clamav) and pargs.clamav or pargs.cheat or pargs.nanorc or
(not pargs.cheat) and (not pargs.nanorc) and pargs.ufw or pargs.ngxblocker or
(not pargs.ufw) and (not pargs.ngxblocker) and pargs.phpredisadmin or pargs.sendmail or pargs.all):
(not pargs.phpredisadmin) and (not pargs.sendmail) and
(not pargs.php73) and (not pargs.all)):
pargs.web = True pargs.web = True
pargs.admin = True pargs.admin = True
pargs.fail2ban = True pargs.fail2ban = True
if pargs.php:
pargs.php72 = True
if pargs.all: if pargs.all:
pargs.web = True pargs.web = True
pargs.admin = True pargs.admin = True
pargs.php73 = True pargs.php73 = True
pargs.php74 = True
pargs.redis = True pargs.redis = True
pargs.proftpd = True pargs.proftpd = True
if pargs.web: if pargs.web:
pargs.nginx = True pargs.nginx = True
pargs.php = True pargs.php72 = True
pargs.mysql = True pargs.mysql = True
pargs.wpcli = True pargs.wpcli = True
pargs.sendmail = True pargs.sendmail = True
@@ -163,23 +167,8 @@ class WOStackController(CementBaseController):
# Nginx # Nginx
if pargs.nginx: if pargs.nginx:
Log.debug(self, "Setting apt_packages variable for Nginx") Log.debug(self, "Setting apt_packages variable for Nginx")
if not (WOAptGet.is_installed(self, 'nginx-custom')): if not WOAptGet.is_exec(self, 'nginx'):
if not (WOAptGet.is_installed(self, 'nginx-plus') or
WOAptGet.is_installed(self, 'nginx')):
if not os.path.isfile('/usr/sbin/nginx'):
apt_packages = apt_packages + WOVar.wo_nginx apt_packages = apt_packages + WOVar.wo_nginx
else:
if WOAptGet.is_installed(self, 'nginx-plus'):
Log.info(self, "NGINX PLUS Detected ...")
apt = ["nginx-plus"] + WOVar.wo_nginx
post_pref(self, apt, empty_packages)
elif WOAptGet.is_installed(self, 'nginx'):
Log.info(self, "WordOps detected an already "
"installed nginx package."
"It may or may not have "
"required modules.\n")
apt = ["nginx"] + WOVar.wo_nginx
post_pref(self, apt, empty_packages)
else: else:
Log.debug(self, "Nginx already installed") Log.debug(self, "Nginx already installed")
@@ -192,11 +181,13 @@ class WOStackController(CementBaseController):
Log.info(self, "Redis already installed") Log.info(self, "Redis already installed")
# PHP 7.2 # PHP 7.2
if pargs.php: if pargs.php72:
Log.debug(self, "Setting apt_packages variable for PHP 7.2") Log.debug(self, "Setting apt_packages variable for PHP 7.2")
if not (WOAptGet.is_installed(self, 'php7.2-fpm')): if not (WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = (apt_packages + WOVar.wo_php + apt_packages = apt_packages + WOVar.wo_php72
WOVar.wo_php_extra) if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else: else:
Log.debug(self, "PHP 7.2 already installed") Log.debug(self, "PHP 7.2 already installed")
Log.info(self, "PHP 7.2 already installed") Log.info(self, "PHP 7.2 already installed")
@@ -205,13 +196,26 @@ class WOStackController(CementBaseController):
if pargs.php73: if pargs.php73:
Log.debug(self, "Setting apt_packages variable for PHP 7.3") Log.debug(self, "Setting apt_packages variable for PHP 7.3")
if not WOAptGet.is_installed(self, 'php7.3-fpm'): if not WOAptGet.is_installed(self, 'php7.3-fpm'):
apt_packages = (apt_packages + WOVar.wo_php + apt_packages = apt_packages + WOVar.wo_php73
WOVar.wo_php73 + if not (WOAptGet.is_installed(self, 'php7.2-fpm') or
WOVar.wo_php_extra) WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else: else:
Log.debug(self, "PHP 7.3 already installed") Log.debug(self, "PHP 7.3 already installed")
Log.info(self, "PHP 7.3 already installed") Log.info(self, "PHP 7.3 already installed")
# PHP 7.4
if pargs.php74:
Log.debug(self, "Setting apt_packages variable for PHP 7.4")
if not WOAptGet.is_installed(self, 'php7.4-fpm'):
apt_packages = apt_packages + WOVar.wo_php74
if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else:
Log.debug(self, "PHP 7.4 already installed")
Log.info(self, "PHP 7.4 already installed")
# MariaDB 10.3 # MariaDB 10.3
if pargs.mysql: if pargs.mysql:
pargs.mysqltuner = True pargs.mysqltuner = True
@@ -235,8 +239,7 @@ class WOStackController(CementBaseController):
# WP-CLI # WP-CLI
if pargs.wpcli: if pargs.wpcli:
Log.debug(self, "Setting packages variable for WP-CLI") Log.debug(self, "Setting packages variable for WP-CLI")
if ((not os.path.isfile("/usr/local/bin/wp")) and if not WOAptGet.is_exec(self, 'wp'):
(not os.path.isfile("/usr/bin/wp"))):
packages = packages + [["https://github.com/wp-cli/wp-cli/" packages = packages + [["https://github.com/wp-cli/wp-cli/"
"releases/download/v{0}/" "releases/download/v{0}/"
"wp-cli-{0}.phar" "wp-cli-{0}.phar"
@@ -328,9 +331,9 @@ class WOStackController(CementBaseController):
# Composer # Composer
if pargs.composer: if pargs.composer:
if not WOShellExec.cmd_exec(self, 'php -v'): if not WOAptGet.is_exec(self, 'php'):
pargs.php = True pargs.php = True
if not os.path.isfile('/usr/local/bin/composer'): if not WOAptGet.is_exec(self, 'composer'):
Log.debug(self, "Setting packages variable for Composer ") Log.debug(self, "Setting packages variable for Composer ")
packages = packages + [["https://getcomposer.org/" packages = packages + [["https://getcomposer.org/"
"installer", "installer",
@@ -344,7 +347,7 @@ class WOStackController(CementBaseController):
if pargs.adminer: if pargs.adminer:
if not os.path.isfile("{0}22222/htdocs/db/" if not os.path.isfile("{0}22222/htdocs/db/"
"adminer/index.php" "adminer/index.php"
.format(wo_webroot)): .format(WOVar.wo_webroot)):
Log.debug(self, "Setting packages variable for Adminer ") Log.debug(self, "Setting packages variable for Adminer ")
packages = packages + [[ packages = packages + [[
"https://github.com/vrana/adminer/" "https://github.com/vrana/adminer/"
@@ -434,6 +437,8 @@ class WOStackController(CementBaseController):
# ultimate ngx_blocker # ultimate ngx_blocker
if pargs.ngxblocker: if pargs.ngxblocker:
if not WOAptGet.is_exec(self, 'nginx'):
pargs.nginx = True
if not os.path.isdir('/etc/nginx/bots.d'): if not os.path.isdir('/etc/nginx/bots.d'):
Log.debug(self, "Setting packages variable for ngxblocker") Log.debug(self, "Setting packages variable for ngxblocker")
packages = packages + \ packages = packages + \
@@ -468,6 +473,12 @@ class WOStackController(CementBaseController):
# UTILS # UTILS
if pargs.utils: if pargs.utils:
if not WOShellExec.cmd_exec(self, 'mysqladmin ping'):
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')):
pargs.php = True
Log.debug(self, "Setting packages variable for utils") Log.debug(self, "Setting packages variable for utils")
packages = packages + [[ packages = packages + [[
"https://raw.githubusercontent.com" "https://raw.githubusercontent.com"
@@ -524,9 +535,7 @@ class WOStackController(CementBaseController):
Log.wait(self, "Installing APT packages ") Log.wait(self, "Installing APT packages ")
WOAptGet.install(self, apt_packages) WOAptGet.install(self, apt_packages)
Log.valide(self, "Installing APT packages ") Log.valide(self, "Installing APT packages ")
Log.wait(self, "Configuring APT packages ")
post_pref(self, apt_packages, []) post_pref(self, apt_packages, [])
Log.valide(self, "Configuring APT packages ")
if (packages): if (packages):
Log.debug(self, "Downloading following: {0}".format(packages)) Log.debug(self, "Downloading following: {0}".format(packages))
WODownload.download(self, packages) WODownload.download(self, packages)
@@ -563,13 +572,18 @@ class WOStackController(CementBaseController):
(not pargs.cheat) and (not pargs.nanorc) and (not pargs.cheat) and (not pargs.nanorc) and
(not pargs.ufw) and (not pargs.ngxblocker) and (not pargs.ufw) and (not pargs.ngxblocker) and
(not pargs.phpredisadmin) and (not pargs.sendmail) and (not pargs.phpredisadmin) and (not pargs.sendmail) and
(not pargs.php73) and (not pargs.all)): (not pargs.php73) and (not pargs.php74) and
(not pargs.php72) and (not pargs.all)):
self.app.args.print_help() self.app.args.print_help()
if pargs.php:
pargs.php72 = True
if pargs.all: if pargs.all:
pargs.web = True pargs.web = True
pargs.admin = True pargs.admin = True
pargs.php73 = True pargs.php73 = True
pargs.php74 = True
pargs.fail2ban = True pargs.fail2ban = True
pargs.proftpd = True pargs.proftpd = True
pargs.utils = True pargs.utils = True
@@ -580,7 +594,7 @@ class WOStackController(CementBaseController):
if pargs.web: if pargs.web:
pargs.nginx = True pargs.nginx = True
pargs.php = True pargs.php72 = True
pargs.mysql = True pargs.mysql = True
pargs.wpcli = True pargs.wpcli = True
pargs.sendmail = True pargs.sendmail = True
@@ -605,24 +619,40 @@ class WOStackController(CementBaseController):
apt_packages = apt_packages + WOVar.wo_nginx apt_packages = apt_packages + WOVar.wo_nginx
# PHP 7.2 # PHP 7.2
if pargs.php: if pargs.php72:
Log.debug(self, "Removing apt_packages variable of PHP") Log.debug(self, "Setting apt_packages variable for PHP 7.2")
if WOAptGet.is_installed(self, 'php7.2-fpm'): if (WOAptGet.is_installed(self, 'php7.2-fpm')):
if not WOAptGet.is_installed(self, 'php7.3-fpm'): apt_packages = apt_packages + WOVar.wo_php72
apt_packages = apt_packages + WOVar.wo_php + \ if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOVar.wo_php_extra WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else: else:
apt_packages = apt_packages + WOVar.wo_php Log.debug(self, "PHP 7.2 is not installed")
Log.info(self, "PHP 7.2 is not installed")
# PHP7.3 # PHP 7.3
if pargs.php73: if pargs.php73:
Log.debug(self, "Removing apt_packages variable of PHP 7.3") Log.debug(self, "Setting apt_packages variable for PHP 7.3")
if WOAptGet.is_installed(self, 'php7.3-fpm'): if WOAptGet.is_installed(self, 'php7.3-fpm'):
if not (WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php73 + \
WOVar.wo_php_extra
else:
apt_packages = apt_packages + WOVar.wo_php73 apt_packages = apt_packages + WOVar.wo_php73
if not (WOAptGet.is_installed(self, 'php7.2-fpm') or
WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else:
Log.debug(self, "PHP 7.3 is not installed")
Log.info(self, "PHP 7.3 is not installed")
# PHP 7.4
if pargs.php74:
Log.debug(self, "Setting apt_packages variable for PHP 7.4")
if WOAptGet.is_installed(self, 'php7.4-fpm'):
apt_packages = apt_packages + WOVar.wo_php74
if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else:
Log.debug(self, "PHP 7.4 is not installed")
Log.info(self, "PHP 7.4 is not installed")
# REDIS # REDIS
if pargs.redis: if pargs.redis:
@@ -634,9 +664,7 @@ class WOStackController(CementBaseController):
if pargs.mysql: if pargs.mysql:
if WOAptGet.is_installed(self, 'mariadb-server'): if WOAptGet.is_installed(self, 'mariadb-server'):
Log.debug(self, "Removing apt_packages variable of MySQL") Log.debug(self, "Removing apt_packages variable of MySQL")
apt_packages = apt_packages + ['mariadb-server', apt_packages = apt_packages + WOVar.wo_mysql
'mysql-common',
'mariadb-client']
# mysqlclient # mysqlclient
if pargs.mysqlclient: if pargs.mysqlclient:
@@ -849,13 +877,18 @@ class WOStackController(CementBaseController):
(not pargs.cheat) and (not pargs.nanorc) and (not pargs.cheat) and (not pargs.nanorc) and
(not pargs.ufw) and (not pargs.ngxblocker) and (not pargs.ufw) and (not pargs.ngxblocker) and
(not pargs.phpredisadmin) and (not pargs.sendmail) and (not pargs.phpredisadmin) and (not pargs.sendmail) and
(not pargs.php73) and (not pargs.all)): (not pargs.php73) and (not pargs.php74) and
(not pargs.php72) and (not pargs.all)):
self.app.args.print_help() self.app.args.print_help()
if pargs.php:
pargs.php72 = True
if pargs.all: if pargs.all:
pargs.web = True pargs.web = True
pargs.admin = True pargs.admin = True
pargs.php73 = True pargs.php73 = True
pargs.php74 = True
pargs.fail2ban = True pargs.fail2ban = True
pargs.proftpd = True pargs.proftpd = True
pargs.utils = True pargs.utils = True
@@ -864,7 +897,7 @@ class WOStackController(CementBaseController):
if pargs.web: if pargs.web:
pargs.nginx = True pargs.nginx = True
pargs.php = True pargs.php72 = True
pargs.mysql = True pargs.mysql = True
pargs.wpcli = True pargs.wpcli = True
pargs.sendmail = True pargs.sendmail = True
@@ -875,6 +908,7 @@ class WOStackController(CementBaseController):
pargs.netdata = True pargs.netdata = True
pargs.mysqltuner = True pargs.mysqltuner = True
pargs.cheat = True pargs.cheat = True
packages = packages + ['/var/www/22222/htdocs']
if pargs.security: if pargs.security:
pargs.fail2ban = True pargs.fail2ban = True
@@ -890,25 +924,41 @@ class WOStackController(CementBaseController):
else: else:
Log.info(self, "Nginx is not installed") Log.info(self, "Nginx is not installed")
# PHP # PHP 7.2
if pargs.php: if pargs.php72:
Log.debug(self, "Add PHP to apt_packages list") Log.debug(self, "Setting apt_packages variable for PHP 7.2")
if WOAptGet.is_installed(self, 'php7.2-fpm'): if (WOAptGet.is_installed(self, 'php7.2-fpm')):
if not (WOAptGet.is_installed(self, 'php7.3-fpm')): apt_packages = apt_packages + WOVar.wo_php72
apt_packages = apt_packages + WOVar.wo_php + \ if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOVar.wo_php_extra WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else: else:
apt_packages = apt_packages + WOVar.wo_php Log.debug(self, "PHP 7.2 is not installed")
Log.info(self, "PHP 7.2 is not installed")
# PHP 7.3 # PHP 7.3
if pargs.php73: if pargs.php73:
Log.debug(self, "Removing apt_packages variable of PHP 7.3") Log.debug(self, "Setting apt_packages variable for PHP 7.3")
if WOAptGet.is_installed(self, 'php7.3-fpm'): if WOAptGet.is_installed(self, 'php7.3-fpm'):
if not (WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php73 + \
WOVar.wo_php_extra
else:
apt_packages = apt_packages + WOVar.wo_php73 apt_packages = apt_packages + WOVar.wo_php73
if not (WOAptGet.is_installed(self, 'php7.2-fpm') or
WOAptGet.is_installed(self, 'php7.4-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else:
Log.debug(self, "PHP 7.3 is not installed")
Log.info(self, "PHP 7.3 is not installed")
# PHP 7.4
if pargs.php74:
Log.debug(self, "Setting apt_packages variable for PHP 7.4")
if WOAptGet.is_installed(self, 'php7.4-fpm'):
apt_packages = apt_packages + WOVar.wo_php74
if not (WOAptGet.is_installed(self, 'php7.3-fpm') or
WOAptGet.is_installed(self, 'php7.2-fpm')):
apt_packages = apt_packages + WOVar.wo_php_extra
else:
Log.debug(self, "PHP 7.4 is not installed")
Log.info(self, "PHP 7.4 is not installed")
# REDIS # REDIS
if pargs.redis: if pargs.redis:

View File

@@ -20,6 +20,7 @@ from wo.core.shellexec import CommandExecutionError, WOShellExec
from wo.core.sslutils import SSL from wo.core.sslutils import SSL
from wo.core.template import WOTemplate from wo.core.template import WOTemplate
from wo.core.variables import WOVar from wo.core.variables import WOVar
from wo.core.stackconf import WOConf
def pre_pref(self, apt_packages): def pre_pref(self, apt_packages):
@@ -112,8 +113,8 @@ def pre_pref(self, apt_packages):
WORepo.add_key(self, WOVar.wo_nginx_key) WORepo.add_key(self, WOVar.wo_nginx_key)
# add php repository # add php repository
if (set(WOVar.wo_php73).issubset(set(apt_packages)) or if (('php7.3-fpm' in apt_packages) or
set(WOVar.wo_php).issubset(set(apt_packages))): ('php7.2-fpm' in apt_packages) or ('php7.4-fpm' in apt_packages)):
if (WOVar.wo_distro == 'ubuntu'): if (WOVar.wo_distro == 'ubuntu'):
Log.debug(self, 'Adding ppa for PHP') Log.debug(self, 'Adding ppa for PHP')
if not os.path.isfile( if not os.path.isfile(
@@ -182,13 +183,13 @@ def post_pref(self, apt_packages, packages, upgrade=False):
ngxcom = '/etc/nginx/common' ngxcom = '/etc/nginx/common'
ngxroot = '/var/www/' ngxroot = '/var/www/'
WOGit.add(self, ["/etc/nginx"], msg="Adding Nginx into Git") WOGit.add(self, ["/etc/nginx"], msg="Adding Nginx into Git")
data = dict(tls13=True) data = dict(tls13=True, release=WOVar.wo_version)
WOTemplate.deploy(self, WOTemplate.deploy(self,
'/etc/nginx/nginx.conf', '/etc/nginx/nginx.conf',
'nginx-core.mustache', data) 'nginx-core.mustache', data)
if not os.path.isfile('{0}/gzip.conf.disabled'.format(ngxcnf)): if not os.path.isfile('{0}/gzip.conf.disabled'.format(ngxcnf)):
data = dict() data = dict(release=WOVar.wo_version)
WOTemplate.deploy(self, '{0}/gzip.conf'.format(ngxcnf), WOTemplate.deploy(self, '{0}/gzip.conf'.format(ngxcnf),
'gzip.mustache', data) 'gzip.mustache', data)
@@ -210,17 +211,19 @@ def post_pref(self, apt_packages, packages, upgrade=False):
'\t$request_filename;\n') '\t$request_filename;\n')
try: try:
data = dict(php="9000", debug="9001", data = dict(php="9000", debug="9001",
php7="9070", debug7="9170") php7="9070", debug7="9170",
release=WOVar.wo_version)
WOTemplate.deploy( WOTemplate.deploy(
self, '{0}/upstream.conf'.format(ngxcnf), self, '{0}/upstream.conf'.format(ngxcnf),
'upstream.mustache', data, overwrite=True) 'upstream.mustache', data, overwrite=True)
data = dict(phpconf=( data = dict(phpconf=(
bool(WOAptGet.is_installed(self, 'php7.2-fpm')))) bool(WOAptGet.is_installed(self, 'php7.2-fpm'))),
release=WOVar.wo_version)
WOTemplate.deploy( WOTemplate.deploy(
self, '{0}/stub_status.conf'.format(ngxcnf), self, '{0}/stub_status.conf'.format(ngxcnf),
'stub_status.mustache', data) 'stub_status.mustache', data)
data = dict() data = dict(release=WOVar.wo_version)
WOTemplate.deploy( WOTemplate.deploy(
self, '{0}/webp.conf'.format(ngxcnf), self, '{0}/webp.conf'.format(ngxcnf),
'webp.mustache', data, overwrite=False) 'webp.mustache', data, overwrite=False)
@@ -243,7 +246,7 @@ def post_pref(self, apt_packages, packages, upgrade=False):
os.makedirs('/etc/nginx/common') os.makedirs('/etc/nginx/common')
try: try:
data = dict() data = dict(release=WOVar.wo_version)
# Common Configuration # Common Configuration
WOTemplate.deploy(self, WOTemplate.deploy(self,
@@ -255,89 +258,52 @@ def post_pref(self, apt_packages, packages, upgrade=False):
'{0}/wpsubdir.conf' '{0}/wpsubdir.conf'
.format(ngxcom), .format(ngxcom),
'wpsubdir.mustache', data) 'wpsubdir.mustache', data)
data = dict(upstream="php72")
# PHP 7.2 conf wo_php_version = ["php72", "php73", "php74"]
for wo_php in wo_php_version:
data = dict(upstream="{0}".format(wo_php),
release=WOVar.wo_version)
WOTemplate.deploy(self, WOTemplate.deploy(self,
'{0}/php72.conf' '{0}/{1}.conf'
.format(ngxcom), .format(ngxcom, wo_php),
'php.mustache', data) 'php.mustache', data)
WOTemplate.deploy(self, WOTemplate.deploy(
'{0}/redis-php72.conf' self, '{0}/redis-{1}.conf'.format(ngxcom, wo_php),
.format(ngxcom),
'redis.mustache', data) 'redis.mustache', data)
WOTemplate.deploy(self, WOTemplate.deploy(
'{0}/wpcommon-php72.conf' self, '{0}/wpcommon-{1}.conf'.format(ngxcom, wo_php),
.format(ngxcom),
'wpcommon.mustache', data) 'wpcommon.mustache', data)
WOTemplate.deploy(self, WOTemplate.deploy(
'{0}/wpfc-php72.conf' self, '{0}/wpfc-{1}.conf'.format(ngxcom, wo_php),
.format(ngxcom),
'wpfc.mustache', data) 'wpfc.mustache', data)
WOTemplate.deploy(self,
'{0}/wpsc-php72.conf' WOTemplate.deploy(
.format(ngxcom), self, '{0}/wpsc-{1}.conf'.format(ngxcom, wo_php),
'wpsc.mustache', data) 'wpsc.mustache', data)
WOTemplate.deploy(self, WOTemplate.deploy(
'{0}/wprocket-php72.conf' self, '{0}/wprocket-{1}.conf'.format(ngxcom, wo_php),
.format(ngxcom),
'wprocket.mustache', data) 'wprocket.mustache', data)
WOTemplate.deploy(self, WOTemplate.deploy(
'{0}/wpce-php72.conf' self, '{0}/wpce-{1}.conf'.format(ngxcom, wo_php),
.format(ngxcom),
'wpce.mustache', data) 'wpce.mustache', data)
# PHP 7.3 conf
data = dict(upstream="php73")
WOTemplate.deploy(self,
'{0}/php73.conf'
.format(ngxcom),
'php.mustache', data)
WOTemplate.deploy(self,
'{0}/redis-php73.conf'
.format(ngxcom),
'redis.mustache', data)
WOTemplate.deploy(self,
'{0}/wpcommon-php73.conf'
.format(ngxcom),
'wpcommon.mustache', data)
WOTemplate.deploy(self,
'{0}/wpfc-php73.conf'
.format(ngxcom),
'wpfc.mustache', data)
WOTemplate.deploy(self,
'{0}/wpsc-php73.conf'
.format(ngxcom),
'wpsc.mustache', data)
WOTemplate.deploy(self,
'{0}/wprocket-php73.conf'
.format(ngxcom),
'wprocket.mustache', data)
WOTemplate.deploy(self,
'{0}/wpce-php73.conf'
.format(ngxcom),
'wpce.mustache', data)
except CommandExecutionError as e: except CommandExecutionError as e:
Log.debug(self, "{0}".format(e)) Log.debug(self, "{0}".format(e))
with open("/etc/nginx/common/release", with open("/etc/nginx/common/release",
"w") as release_file: "w", encoding='utf-8') as release_file:
release_file.write("v{0}" release_file.write("v{0}"
.format(WOVar.wo_version)) .format(WOVar.wo_version))
release_file.close() release_file.close()
# Following files should not be overwrited # Following files should not be overwrited
data = dict(webroot=ngxroot) data = dict(webroot=ngxroot, release=WOVar.wo_version)
WOTemplate.deploy(self, WOTemplate.deploy(self,
'{0}/acl.conf' '{0}/acl.conf'
.format(ngxcom), .format(ngxcom),
@@ -383,7 +349,7 @@ def post_pref(self, apt_packages, packages, upgrade=False):
os.makedirs('/etc/nginx/sites-enabled') os.makedirs('/etc/nginx/sites-enabled')
# 22222 port settings # 22222 port settings
data = dict(webroot=ngxroot) data = dict(webroot=ngxroot, release=WOVar.wo_version)
WOTemplate.deploy( WOTemplate.deploy(
self, self,
'/etc/nginx/sites-available/22222', '/etc/nginx/sites-available/22222',
@@ -488,7 +454,7 @@ def post_pref(self, apt_packages, packages, upgrade=False):
WOVar.wo_fqdn)]) WOVar.wo_fqdn)])
if not os.path.isfile("/opt/cf-update.sh"): if not os.path.isfile("/opt/cf-update.sh"):
data = dict() data = dict(release=WOVar.wo_version)
WOTemplate.deploy(self, '/opt/cf-update.sh', WOTemplate.deploy(self, '/opt/cf-update.sh',
'cf-update.mustache', 'cf-update.mustache',
data, overwrite=False) data, overwrite=False)
@@ -528,10 +494,11 @@ def post_pref(self, apt_packages, packages, upgrade=False):
WOShellExec.cmd_exec(self, 'systemctl daemon-reload') WOShellExec.cmd_exec(self, 'systemctl daemon-reload')
WOService.restart_service(self, 'nginx') WOService.restart_service(self, 'nginx')
if set(WOVar.wo_php).issubset(set(apt_packages)): if set(WOVar.wo_php72).issubset(set(apt_packages)):
WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git") WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git")
Log.info(self, "Configuring php7.2-fpm") Log.info(self, "Configuring php7.2-fpm")
ngxroot = '/var/www/' ngxroot = '/var/www/'
# Create log directories # Create log directories
if not os.path.exists('/var/log/php/7.2/'): if not os.path.exists('/var/log/php/7.2/'):
Log.debug(self, 'Creating directory /var/log/php/7.2/') Log.debug(self, 'Creating directory /var/log/php/7.2/')
@@ -800,6 +767,153 @@ def post_pref(self, apt_packages, packages, upgrade=False):
else: else:
WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git") WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git")
# PHP7.4 configuration
# php7.4 configuration
if set(WOVar.wo_php74).issubset(set(apt_packages)):
WOGit.add(self, ["/etc/php"], msg="Adding PHP into Git")
Log.info(self, "Configuring php7.4-fpm")
ngxroot = '/var/www/'
# Create log directories
if not os.path.exists('/var/log/php/7.4/'):
Log.debug(self, 'Creating directory /var/log/php/7.4/')
os.makedirs('/var/log/php/7.4/')
if not os.path.isfile('/etc/php/7.4/fpm/php.ini.orig'):
WOFileUtils.copyfile(self, '/etc/php/7.4/fpm/php.ini',
'/etc/php/7.4/fpm/php.ini.orig')
# Parse etc/php/7.4/fpm/php.ini
config = configparser.ConfigParser()
Log.debug(self, "configuring php file /etc/php/7.4/"
"fpm/php.ini")
config.read('/etc/php/7.4/fpm/php.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('/etc/php/7.4/fpm/php.ini',
encoding='utf-8', mode='w') as configfile:
Log.debug(self, "Writting php configuration into "
"/etc/php/7.4/fpm/php.ini")
config.write(configfile)
# Render php-fpm pool template for php7.4
data = dict(pid="/run/php/php7.4-fpm.pid",
error_log="/var/log/php7.4-fpm.log",
include="/etc/php/7.4/fpm/pool.d/*.conf")
WOTemplate.deploy(
self, '/etc/php/7.4/fpm/php-fpm.conf',
'php-fpm.mustache', data)
data = dict(pool='www-php74', listen='php74-fpm.sock',
user='www-data',
group='www-data', listenuser='root',
listengroup='www-data', openbasedir=True)
WOTemplate.deploy(self, '/etc/php/7.4/fpm/pool.d/www.conf',
'php-pool.mustache', data)
data = dict(pool='www-two-php74', listen='php74-two-fpm.sock',
user='www-data',
group='www-data', listenuser='root',
listengroup='www-data', openbasedir=True)
WOTemplate.deploy(self, '/etc/php/7.4/fpm/pool.d/www-two.conf',
'php-pool.mustache', data)
# Generate /etc/php/7.4/fpm/pool.d/debug.conf
WOFileUtils.copyfile(self, "/etc/php/7.4/fpm/pool.d/www.conf",
"/etc/php/7.4/fpm/pool.d/debug.conf")
WOFileUtils.searchreplace(self, "/etc/php/7.4/fpm/pool.d/"
"debug.conf", "[www-php74]", "[debug]")
config = configparser.ConfigParser()
config.read('/etc/php/7.4/fpm/pool.d/debug.conf')
config['debug']['listen'] = '127.0.0.1:9174'
config['debug']['rlimit_core'] = 'unlimited'
config['debug']['slowlog'] = '/var/log/php/7.4/slow.log'
config['debug']['request_slowlog_timeout'] = '10s'
with open('/etc/php/7.4/fpm/pool.d/debug.conf',
encoding='utf-8', mode='w') as confifile:
Log.debug(self, "writting PHP 7.4 configuration into "
"/etc/php/7.4/fpm/pool.d/debug.conf")
config.write(confifile)
with open("/etc/php/7.4/fpm/pool.d/debug.conf",
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/7.4/mods-available/xdebug.ini"):
WOFileUtils.searchreplace(
self, "/etc/php/7.4/mods-available/"
"xdebug.ini",
"zend_extension", ";zend_extension")
# PHP and Debug pull configuration
if not os.path.exists('{0}22222/htdocs/fpm/status/'
.format(ngxroot)):
Log.debug(self, 'Creating directory '
'{0}22222/htdocs/fpm/status/ '
.format(ngxroot))
os.makedirs('{0}22222/htdocs/fpm/status/'
.format(ngxroot))
open('{0}22222/htdocs/fpm/status/debug74'
.format(ngxroot),
encoding='utf-8', mode='a').close()
open('{0}22222/htdocs/fpm/status/php74'
.format(ngxroot),
encoding='utf-8', mode='a').close()
# Write info.php
if not os.path.exists('{0}22222/htdocs/php/'
.format(ngxroot)):
Log.debug(self, 'Creating directory '
'{0}22222/htdocs/php/ '
.format(ngxroot))
os.makedirs('{0}22222/htdocs/php'
.format(ngxroot))
WOFileUtils.textwrite(
self, "{0}22222/htdocs/php/info.php"
.format(ngxroot), "<?php\nphpinfo();\n?>")
WOFileUtils.chown(self, "{0}22222/htdocs"
.format(ngxroot),
'www-data',
'www-data', recursive=True)
# check service restart or rollback configuration
if not WOService.restart_service(self, 'php7.4-fpm'):
WOGit.rollback(self, ["/etc/php"], msg="Rollback PHP")
else:
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', 'php74'):
data = dict(php="9000", debug="9001",
php7="9070", debug7="9170",
release=WOVar.wo_version)
WOTemplate.deploy(
self, '/etc/nginx/conf.d/upstream.conf',
'upstream.mustache', data, True)
WOConf.nginxcommon(self)
# create mysql config if it doesn't exist # create mysql config if it doesn't exist
if "mariadb-server" in apt_packages: if "mariadb-server" in apt_packages:
WOGit.add(self, ["/etc/mysql"], msg="Adding MySQL into Git") WOGit.add(self, ["/etc/mysql"], msg="Adding MySQL into Git")
@@ -812,6 +926,23 @@ def post_pref(self, apt_packages, packages, upgrade=False):
config_file.write(config) config_file.write(config)
config_file.close() config_file.close()
else: else:
if "PASSWORD" not in WOShellExec.cmd_exec_stdout(
self, 'mysql -e "use mysql; show grants;"'):
try:
if not os.path.exists('/etc/mysql/conf.d/my.cnf'):
Log.error(self, 'my.cnf not found')
config = configparser.ConfigParser()
config.read('/etc/mysql/conf.d/my.cnf')
chars = config['client']['password']
WOShellExec.cmd_exec(
self, "mysql -e \"use mysql; "
"GRANT ALL PRIVILEGES on "
"*.* TO 'root'@'127.0.0.1' IDENTIFIED by "
"'{0}' WITH GRANT OPTION\"".format(chars))
WOShellExec.cmd_exec(
self, 'mysql -e "flush privileges;"')
except CommandExecutionError:
Log.error(self, "Unable to set MySQL password")
Log.info(self, "Tuning MariaDB configuration") Log.info(self, "Tuning MariaDB configuration")
if not os.path.isfile("/etc/mysql/my.cnf.default-pkg"): if not os.path.isfile("/etc/mysql/my.cnf.default-pkg"):
WOFileUtils.copyfile(self, "/etc/mysql/my.cnf", WOFileUtils.copyfile(self, "/etc/mysql/my.cnf",
@@ -867,11 +998,12 @@ def post_pref(self, apt_packages, packages, upgrade=False):
# create fail2ban configuration files # create fail2ban configuration files
if set(WOVar.wo_fail2ban).issubset(set(apt_packages)): if set(WOVar.wo_fail2ban).issubset(set(apt_packages)):
WOService.restart_service(self, 'fail2ban')
WOGit.add(self, ["/etc/fail2ban"], WOGit.add(self, ["/etc/fail2ban"],
msg="Adding Fail2ban into Git") msg="Adding Fail2ban into Git")
if not os.path.isfile("/etc/fail2ban/jail.d/custom.conf"): if not os.path.isfile("/etc/fail2ban/jail.d/custom.conf"):
Log.info(self, "Configuring Fail2Ban") Log.info(self, "Configuring Fail2Ban")
data = dict() data = dict(release=WOVar.wo_version)
WOTemplate.deploy( WOTemplate.deploy(
self, self,
'/etc/fail2ban/jail.d/custom.conf', '/etc/fail2ban/jail.d/custom.conf',
@@ -1463,7 +1595,7 @@ def pre_stack(self):
if wo_check is False: if wo_check is False:
# wo sysctl tweaks # wo sysctl tweaks
# check system type # check system type
wo_arch = bool(os.uname()[4] == 'x86_x64') wo_arch = bool((os.uname()[4]) == 'x86_64')
if os.path.isfile('/proc/1/environ'): if os.path.isfile('/proc/1/environ'):
# detect lxc containers # detect lxc containers
wo_lxc = WOFileUtils.grepcheck( wo_lxc = WOFileUtils.grepcheck(

View File

@@ -4,6 +4,7 @@ from cement.core.controller import CementBaseController, expose
from wo.core.logging import Log from wo.core.logging import Log
from wo.core.services import WOService from wo.core.services import WOService
from wo.core.variables import WOVar from wo.core.variables import WOVar
from wo.core.fileutils import WOFileUtils
class WOStackStatusController(CementBaseController): class WOStackStatusController(CementBaseController):
@@ -20,17 +21,21 @@ class WOStackStatusController(CementBaseController):
wo_system = "/lib/systemd/system/" wo_system = "/lib/systemd/system/"
pargs = self.app.pargs pargs = self.app.pargs
if not (pargs.nginx or pargs.php or if not (pargs.nginx or pargs.php or
pargs.php72 or
pargs.php73 or pargs.php73 or
pargs.php74 or
pargs.mysql or pargs.mysql or
pargs.redis or pargs.redis or
pargs.fail2ban or pargs.fail2ban or
pargs.proftpd or pargs.proftpd or
pargs.netdata): pargs.netdata or
pargs.ufw):
pargs.nginx = True pargs.nginx = True
pargs.php = True pargs.php = True
pargs.mysql = True pargs.mysql = True
pargs.fail2ban = True pargs.fail2ban = True
pargs.netdata = True pargs.netdata = True
pargs.ufw = True
if pargs.nginx: if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'): if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
@@ -47,6 +52,16 @@ class WOStackStatusController(CementBaseController):
services = services + ['php7.3-fpm'] services = services + ['php7.3-fpm']
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.php72:
if os.path.exists('{0}'.format(wo_system) + 'php7.2-fpm.service'):
services = services + ['php7.2-fpm']
else:
Log.info(self, "PHP7.2-FPM is not installed")
if pargs.php73: if pargs.php73:
if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'): if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'):
@@ -54,6 +69,12 @@ class WOStackStatusController(CementBaseController):
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if pargs.php74:
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.mysql: if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or if ((WOVar.wo_mysql_host == "localhost") or
(WOVar.wo_mysql_host == "127.0.0.1")): (WOVar.wo_mysql_host == "127.0.0.1")):
@@ -103,7 +124,8 @@ class WOStackStatusController(CementBaseController):
wo_system = "/lib/systemd/system/" wo_system = "/lib/systemd/system/"
pargs = self.app.pargs pargs = self.app.pargs
if not (pargs.nginx or pargs.php or if not (pargs.nginx or pargs.php or
pargs.php73 or pargs.php72 or pargs.php73 or
pargs.php74 or
pargs.mysql or pargs.mysql or
pargs.fail2ban or pargs.fail2ban or
pargs.netdata or pargs.netdata or
@@ -128,6 +150,16 @@ class WOStackStatusController(CementBaseController):
services = services + ['php7.3-fpm'] services = services + ['php7.3-fpm']
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.php72:
if os.path.exists('{0}'.format(wo_system) + 'php7.2-fpm.service'):
services = services + ['php7.2-fpm']
else:
Log.info(self, "PHP7.2-FPM is not installed")
if pargs.php73: if pargs.php73:
if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'): if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'):
@@ -135,6 +167,12 @@ class WOStackStatusController(CementBaseController):
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if pargs.php74:
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.mysql: if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or if ((WOVar.wo_mysql_host == "localhost") or
(WOVar.wo_mysql_host == "127.0.0.1")): (WOVar.wo_mysql_host == "127.0.0.1")):
@@ -184,7 +222,8 @@ class WOStackStatusController(CementBaseController):
wo_system = "/lib/systemd/system/" wo_system = "/lib/systemd/system/"
pargs = self.app.pargs pargs = self.app.pargs
if not (pargs.nginx or pargs.php or if not (pargs.nginx or pargs.php or
pargs.php73 or pargs.php72 or pargs.php73 or
pargs.php74 or
pargs.mysql or pargs.mysql or
pargs.netdata or pargs.netdata or
pargs.proftpd or pargs.proftpd or
@@ -210,6 +249,16 @@ class WOStackStatusController(CementBaseController):
services = services + ['php7.3-fpm'] services = services + ['php7.3-fpm']
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.php72:
if os.path.exists('{0}'.format(wo_system) + 'php7.2-fpm.service'):
services = services + ['php7.2-fpm']
else:
Log.info(self, "PHP7.2-FPM is not installed")
if pargs.php73: if pargs.php73:
if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'): if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'):
@@ -217,6 +266,12 @@ class WOStackStatusController(CementBaseController):
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if pargs.php74:
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.mysql: if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or if ((WOVar.wo_mysql_host == "localhost") or
(WOVar.wo_mysql_host == "127.0.0.1")): (WOVar.wo_mysql_host == "127.0.0.1")):
@@ -266,7 +321,9 @@ class WOStackStatusController(CementBaseController):
wo_system = "/lib/systemd/system/" wo_system = "/lib/systemd/system/"
pargs = self.app.pargs pargs = self.app.pargs
if not (pargs.nginx or pargs.php or if not (pargs.nginx or pargs.php or
pargs.php72 or
pargs.php73 or pargs.php73 or
pargs.php74 or
pargs.mysql or pargs.mysql or
pargs.netdata or pargs.netdata or
pargs.proftpd or pargs.proftpd or
@@ -277,6 +334,7 @@ class WOStackStatusController(CementBaseController):
pargs.mysql = True pargs.mysql = True
pargs.fail2ban = True pargs.fail2ban = True
pargs.netdata = True pargs.netdata = True
pargs.ufw = True
if pargs.nginx: if pargs.nginx:
if os.path.exists('{0}'.format(wo_system) + 'nginx.service'): if os.path.exists('{0}'.format(wo_system) + 'nginx.service'):
@@ -293,6 +351,16 @@ class WOStackStatusController(CementBaseController):
services = services + ['php7.3-fpm'] services = services + ['php7.3-fpm']
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.php72:
if os.path.exists('{0}'.format(wo_system) + 'php7.2-fpm.service'):
services = services + ['php7.2-fpm']
else:
Log.info(self, "PHP7.2-FPM is not installed")
if pargs.php73: if pargs.php73:
if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'): if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'):
@@ -300,6 +368,12 @@ class WOStackStatusController(CementBaseController):
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if pargs.php74:
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.mysql: if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or if ((WOVar.wo_mysql_host == "localhost") or
(WOVar.wo_mysql_host == "127.0.0.1")): (WOVar.wo_mysql_host == "127.0.0.1")):
@@ -338,6 +412,17 @@ class WOStackStatusController(CementBaseController):
else: else:
Log.info(self, "Netdata is not installed") Log.info(self, "Netdata is not installed")
# UFW
if pargs.ufw:
if os.path.exists('/usr/sbin/ufw'):
if WOFileUtils.grepcheck(
self, '/etc/ufw/ufw.conf', 'ENABLED=yes'):
Log.info(self, "UFW Firewall is enabled")
else:
Log.info(self, "UFW Firewall is disabled")
else:
Log.info(self, "UFW is not installed")
for service in services: for service in services:
if WOService.get_service_status(self, service): if WOService.get_service_status(self, service):
Log.info(self, "{0:10}: {1}".format(service, "Running")) Log.info(self, "{0:10}: {1}".format(service, "Running"))
@@ -349,7 +434,8 @@ class WOStackStatusController(CementBaseController):
wo_system = "/lib/systemd/system/" wo_system = "/lib/systemd/system/"
pargs = self.app.pargs pargs = self.app.pargs
if not (pargs.nginx or pargs.php or if not (pargs.nginx or pargs.php or
pargs.php73 or pargs.php72 or pargs.php73 or
pargs.php74 or
pargs.mysql or pargs.mysql or
pargs.netdata or pargs.netdata or
pargs.proftpd or pargs.proftpd or
@@ -375,6 +461,16 @@ class WOStackStatusController(CementBaseController):
services = services + ['php7.3-fpm'] services = services + ['php7.3-fpm']
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.php72:
if os.path.exists('{0}'.format(wo_system) + 'php7.2-fpm.service'):
services = services + ['php7.2-fpm']
else:
Log.info(self, "PHP7.2-FPM is not installed")
if pargs.php73: if pargs.php73:
if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'): if os.path.exists('{0}'.format(wo_system) + 'php7.3-fpm.service'):
@@ -382,6 +478,12 @@ class WOStackStatusController(CementBaseController):
else: else:
Log.info(self, "PHP7.3-FPM is not installed") Log.info(self, "PHP7.3-FPM is not installed")
if pargs.php74:
if os.path.exists('{0}'.format(wo_system) + 'php7.4-fpm.service'):
services = services + ['php7.4-fpm']
else:
Log.info(self, "PHP7.4-FPM is not installed")
if pargs.mysql: if pargs.mysql:
if ((WOVar.wo_mysql_host == "localhost") or if ((WOVar.wo_mysql_host == "localhost") or
(WOVar.wo_mysql_host == "127.0.0.1")): (WOVar.wo_mysql_host == "127.0.0.1")):

View File

@@ -30,8 +30,12 @@ class WOStackUpgradeController(CementBaseController):
dict(help='Upgrade Nginx stack', action='store_true')), dict(help='Upgrade Nginx stack', action='store_true')),
(['--php'], (['--php'],
dict(help='Upgrade PHP 7.2 stack', action='store_true')), dict(help='Upgrade PHP 7.2 stack', action='store_true')),
(['--php72'],
dict(help='Upgrade PHP 7.2 stack', action='store_true')),
(['--php73'], (['--php73'],
dict(help='Upgrade PHP 7.3 stack', action='store_true')), dict(help='Upgrade PHP 7.3 stack', action='store_true')),
(['--php74'],
dict(help='Upgrade PHP 7.4 stack', action='store_true')),
(['--mysql'], (['--mysql'],
dict(help='Upgrade MySQL stack', action='store_true')), dict(help='Upgrade MySQL stack', action='store_true')),
(['--wpcli'], (['--wpcli'],
@@ -44,8 +48,12 @@ class WOStackUpgradeController(CementBaseController):
dict(help='Upgrade WordOps Dashboard', action='store_true')), dict(help='Upgrade WordOps Dashboard', action='store_true')),
(['--composer'], (['--composer'],
dict(help='Upgrade Composer', action='store_true')), dict(help='Upgrade Composer', action='store_true')),
(['--mysqltuner'],
dict(help='Upgrade Composer', action='store_true')),
(['--phpmyadmin'], (['--phpmyadmin'],
dict(help='Upgrade phpMyAdmin', action='store_true')), dict(help='Upgrade phpMyAdmin', action='store_true')),
(['--adminer'],
dict(help='Upgrade Adminer', action='store_true')),
(['--ngxblocker'], (['--ngxblocker'],
dict(help='Upgrade phpMyAdmin', action='store_true')), dict(help='Upgrade phpMyAdmin', action='store_true')),
(['--no-prompt'], (['--no-prompt'],
@@ -63,27 +71,33 @@ class WOStackUpgradeController(CementBaseController):
packages = [] packages = []
self.msg = [] self.msg = []
pargs = self.app.pargs pargs = self.app.pargs
if ((not pargs.web) and (not pargs.nginx) and if ((not pargs.web) and (not pargs.nginx) and
(not pargs.php) and (not pargs.php73) and (not pargs.php) and
(not pargs.php72) and (not pargs.php73) and
(not pargs.php74) and
(not pargs.mysql) and (not pargs.ngxblocker) and (not pargs.mysql) and (not pargs.ngxblocker) and
(not pargs.all) and (not pargs.wpcli) and (not pargs.all) and (not pargs.wpcli) and
(not pargs.netdata) and (not pargs.composer) and (not pargs.netdata) and (not pargs.composer) and
(not pargs.phpmyadmin) and (not pargs.dashboard) and (not pargs.phpmyadmin) and (not pargs.adminer) and
(not pargs.dashboard) and (not pargs.mysqltuner) and
(not pargs.redis)): (not pargs.redis)):
pargs.web = True pargs.web = True
pargs.admin = True pargs.admin = True
if pargs.php:
pargs.php72 = True
if pargs.all: if pargs.all:
pargs.web = True pargs.web = True
pargs.admin = True pargs.admin = True
pargs.redis = True pargs.redis = True
pargs.php73 = True
pargs.ngxblocker = True pargs.ngxblocker = True
if pargs.web: if pargs.web:
pargs.nginx = True pargs.nginx = True
pargs.php = True pargs.php72 = True
pargs.php73 = True
pargs.php74 = True
pargs.mysql = True pargs.mysql = True
pargs.wpcli = True pargs.wpcli = True
@@ -93,6 +107,8 @@ class WOStackUpgradeController(CementBaseController):
pargs.dashboard = True pargs.dashboard = True
pargs.phpmyadmin = True pargs.phpmyadmin = True
pargs.wpcli = True pargs.wpcli = True
pargs.adminer = True
pargs.mysqltuner = True
# nginx # nginx
if pargs.nginx: if pargs.nginx:
@@ -106,34 +122,32 @@ class WOStackUpgradeController(CementBaseController):
Log.info(self, "Nginx Stable is not already installed") Log.info(self, "Nginx Stable is not already installed")
# php 7.2 # php 7.2
if pargs.php: if pargs.php72:
if WOAptGet.is_installed(self, 'php7.2-fpm'): if WOAptGet.is_installed(self, 'php7.2-fpm'):
apt_packages = apt_packages + WOVar.wo_php + \ apt_packages = apt_packages + WOVar.wo_php72 + \
WOVar.wo_php_extra WOVar.wo_php_extra
else:
Log.info(self, "PHP 7.2 is not installed")
# php 7.3 # php 7.3
if pargs.php73: if pargs.php73:
if WOAptGet.is_installed(self, 'php7.3-fpm'): if WOAptGet.is_installed(self, 'php7.3-fpm'):
apt_packages = apt_packages + WOVar.wo_php73 + \ apt_packages = apt_packages + WOVar.wo_php73 + \
WOVar.wo_php_extra WOVar.wo_php_extra
else:
Log.info(self, "PHP 7.3 is not installed") # php 7.4
if pargs.php74:
if WOAptGet.is_installed(self, 'php7.4-fpm'):
apt_packages = apt_packages + WOVar.wo_php74 + \
WOVar.wo_php_extra
# mysql # mysql
if pargs.mysql: if pargs.mysql:
if WOShellExec.cmd_exec(self, 'mysqladmin ping'): if WOShellExec.cmd_exec(self, 'mysqladmin ping'):
apt_packages = apt_packages + ['mariadb-server'] apt_packages = apt_packages + ['mariadb-server']
else:
Log.info(self, "MariaDB is not installed")
# redis # redis
if pargs.redis: if pargs.redis:
if WOAptGet.is_installed(self, 'redis-server'): if WOAptGet.is_installed(self, 'redis-server'):
apt_packages = apt_packages + ['redis-server'] apt_packages = apt_packages + ['redis-server']
else:
Log.info(self, "Redis is not installed")
# wp-cli # wp-cli
if pargs.wpcli: if pargs.wpcli:
@@ -188,6 +202,32 @@ class WOStackUpgradeController(CementBaseController):
else: else:
Log.info(self, "phpMyAdmin isn't installed") Log.info(self, "phpMyAdmin isn't installed")
# adminer
if pargs.adminer:
if os.path.isfile("{0}22222/htdocs/db/"
"adminer/index.php"
.format(WOVar.wo_webroot)):
Log.debug(self, "Setting packages variable for Adminer ")
packages = packages + [[
"https://github.com/vrana/adminer/"
"releases/download/v{0}"
"/adminer-{0}.php"
.format(WOVar.wo_adminer),
"{0}22222/"
"htdocs/db/adminer/index.php"
.format(WOVar.wo_webroot),
"Adminer"],
["https://raw.githubusercontent.com"
"/vrana/adminer/master/designs/"
"pepa-linha/adminer.css",
"{0}22222/"
"htdocs/db/adminer/adminer.css"
.format(WOVar.wo_webroot),
"Adminer theme"]]
else:
Log.debug(self, "Adminer isn't installed")
Log.info(self, "Adminer isn't installed")
# composer # composer
if pargs.composer: if pargs.composer:
if os.path.isfile('/usr/local/bin/composer'): if os.path.isfile('/usr/local/bin/composer'):
@@ -198,6 +238,18 @@ class WOStackUpgradeController(CementBaseController):
else: else:
Log.info(self, "Composer isn't installed") Log.info(self, "Composer isn't installed")
# mysqltuner
if pargs.mysqltuner:
if WOAptGet.is_exec(self, 'mysqltuner'):
Log.debug(self, "Setting packages variable "
"for MySQLTuner ")
packages = packages + [["https://raw."
"githubusercontent.com/"
"major/MySQLTuner-perl"
"/master/mysqltuner.pl",
"/usr/bin/mysqltuner",
"MySQLTuner"]]
# ngxblocker # ngxblocker
if pargs.ngxblocker: if pargs.ngxblocker:
if os.path.exists('/usr/local/sbin/install-ngxblocker'): if os.path.exists('/usr/local/sbin/install-ngxblocker'):
@@ -217,6 +269,8 @@ class WOStackUpgradeController(CementBaseController):
if (apt_packages): if (apt_packages):
if (("php7.2-fpm" not in apt_packages) and if (("php7.2-fpm" not in apt_packages) and
("php7.3-fpm" not in apt_packages) and ("php7.3-fpm" not in apt_packages) and
("php7.4-fpm" not in apt_packages) and
("redis-server" not in apt_packages) and
("nginx-custom" not in apt_packages) and ("nginx-custom" not in apt_packages) and
("mariadb-server" not in apt_packages)): ("mariadb-server" not in apt_packages)):
pass pass
@@ -243,6 +297,9 @@ class WOStackUpgradeController(CementBaseController):
if "php7.3-fpm" in apt_packages: if "php7.3-fpm" in apt_packages:
WOAptGet.remove(self, ['php7.3-fpm'], WOAptGet.remove(self, ['php7.3-fpm'],
auto=False, purge=True) auto=False, purge=True)
if "php7.4-fpm" in apt_packages:
WOAptGet.remove(self, ['php7.4-fpm'],
auto=False, purge=True)
# check if nginx upgrade is blocked # check if nginx upgrade is blocked
if os.path.isfile( if os.path.isfile(
'/etc/apt/preferences.d/nginx-block'): '/etc/apt/preferences.d/nginx-block'):
@@ -257,16 +314,16 @@ class WOStackUpgradeController(CementBaseController):
# Post Actions after package updates # Post Actions after package updates
if (packages): if (packages):
if pargs.wpcli: if WOAptGet.is_selected(self, 'WP-CLI', packages):
WOFileUtils.rm(self, '/usr/local/bin/wp') WOFileUtils.rm(self, '/usr/local/bin/wp')
if pargs.netdata: if WOAptGet.is_selected(self, 'Netdata', packages):
WOFileUtils.rm(self, '/var/lib/wo/tmp/kickstart.sh') WOFileUtils.rm(self, '/var/lib/wo/tmp/kickstart.sh')
if pargs.ngxblocker: if WOAptGet.is_selected(self, 'ngxblocker', packages):
WOFileUtils.rm(self, '/usr/local/sbin/update-ngxblocker') WOFileUtils.rm(self, '/usr/local/sbin/update-ngxblocker')
if pargs.dashboard: if WOAptGet.is_selected(self, 'WordOps Dashboard', packages):
if os.path.isfile('/var/www/22222/htdocs/index.php'): if os.path.isfile('/var/www/22222/htdocs/index.php'):
WOFileUtils.rm(self, '/var/www/22222/htdocs/index.php') WOFileUtils.rm(self, '/var/www/22222/htdocs/index.php')
if os.path.isfile('/var/www/22222/htdocs/index.html'): if os.path.isfile('/var/www/22222/htdocs/index.html'):
@@ -276,18 +333,22 @@ class WOStackUpgradeController(CementBaseController):
Log.debug(self, "Downloading following: {0}".format(packages)) Log.debug(self, "Downloading following: {0}".format(packages))
WODownload.download(self, packages) WODownload.download(self, packages)
if pargs.wpcli: if WOAptGet.is_selected(self, 'WP-CLI', packages):
WOFileUtils.chmod(self, "/usr/local/bin/wp", 0o775) WOFileUtils.chmod(self, "/usr/local/bin/wp", 0o775)
if pargs.ngxblocker: if WOAptGet.is_selected(self, 'ngxblocker', packages):
WOFileUtils.chmod( WOFileUtils.chmod(
self, '/usr/local/sbin/update-ngxblocker', 0o700) self, '/usr/local/sbin/update-ngxblocker', 0o775)
WOShellExec.cmd_exec( WOShellExec.cmd_exec(
self, '/usr/local/sbin/update-ngxblocker -nq' 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'):
WOFileUtils.rm(self, '/usr/local/bin/mysqltuner')
# Netdata # Netdata
if pargs.netdata: if WOAptGet.is_selected(self, 'Netdata', packages):
Log.wait(self, "Upgrading Netdata") Log.wait(self, "Upgrading Netdata")
# detect static binaries install # detect static binaries install
if os.path.isdir('/opt/netdata'): if os.path.isdir('/opt/netdata'):
@@ -313,7 +374,7 @@ class WOStackUpgradeController(CementBaseController):
self, "bash /var/lib/wo/tmp/kickstart.sh") self, "bash /var/lib/wo/tmp/kickstart.sh")
Log.valide(self, "Upgrading Netdata") Log.valide(self, "Upgrading Netdata")
if pargs.dashboard: if WOAptGet.is_selected(self, 'WordOps Dashboard', packages):
post_pref( post_pref(
self, [], [["https://github.com/WordOps" self, [], [["https://github.com/WordOps"
"/wordops-dashboard/" "/wordops-dashboard/"
@@ -323,7 +384,7 @@ class WOStackUpgradeController(CementBaseController):
"/var/lib/wo/tmp/wo-dashboard.tar.gz", "/var/lib/wo/tmp/wo-dashboard.tar.gz",
"WordOps Dashboard"]]) "WordOps Dashboard"]])
if pargs.composer: if WOAptGet.is_selected(self, 'Composer', packages):
Log.wait(self, "Upgrading Composer") Log.wait(self, "Upgrading Composer")
if WOShellExec.cmd_exec( if WOShellExec.cmd_exec(
self, '/usr/bin/php -v'): self, '/usr/bin/php -v'):
@@ -336,7 +397,7 @@ class WOStackUpgradeController(CementBaseController):
WOFileUtils.chmod(self, "/usr/local/bin/composer", 0o775) WOFileUtils.chmod(self, "/usr/local/bin/composer", 0o775)
Log.valide(self, "Upgrading Composer ") Log.valide(self, "Upgrading Composer ")
if pargs.phpmyadmin: if WOAptGet.is_selected(self, 'PHPMyAdmin', packages):
Log.wait(self, "Upgrading phpMyAdmin") Log.wait(self, "Upgrading phpMyAdmin")
WOExtract.extract(self, '/var/lib/wo/tmp/pma.tar.gz', WOExtract.extract(self, '/var/lib/wo/tmp/pma.tar.gz',
'/var/lib/wo/tmp/') '/var/lib/wo/tmp/')
@@ -359,5 +420,10 @@ class WOStackUpgradeController(CementBaseController):
'www-data', 'www-data',
'www-data', recursive=True) 'www-data', recursive=True)
Log.valide(self, "Upgrading phpMyAdmin") Log.valide(self, "Upgrading phpMyAdmin")
if os.path.exists('{0}22222/htdocs'.format(WOVar.wo_webroot)):
WOFileUtils.chown(self, "{0}22222/htdocs"
.format(WOVar.wo_webroot),
'www-data',
'www-data', recursive=True)
Log.info(self, "Successfully updated packages") Log.info(self, "Successfully updated packages")

View File

@@ -1,4 +1,5 @@
import glob import glob
import os
from cement.core.controller import CementBaseController, expose from cement.core.controller import CementBaseController, expose
@@ -39,6 +40,13 @@ class WOSyncController(CementBaseController):
# Read config files # Read config files
configfiles = glob.glob(wo_site_webroot + '/*-config.php') configfiles = glob.glob(wo_site_webroot + '/*-config.php')
if (os.path.exists(
'{0}/ee-config.php'.format(wo_site_webroot)) and
os.path.exists(
'{0}/wo-config.php'.format(wo_site_webroot))):
configfiles = glob.glob(
wo_site_webroot + 'wo-config.php')
# search for wp-config.php inside htdocs/ # search for wp-config.php inside htdocs/
if not configfiles: if not configfiles:
Log.debug(self, "Config files not found in {0}/ " Log.debug(self, "Config files not found in {0}/ "

View File

@@ -1,4 +1,4 @@
# WordOps admin NGINX CONFIGURATION - WO v3.9.7 # WordOps admin NGINX CONFIGURATION - WordOps {{release}}
server { server {

View File

@@ -6,19 +6,21 @@ enabled = true
[nginx-http-auth] [nginx-http-auth]
enabled = true enabled = true
logpath = /var/log/nginx/*error*.log
[nginx-botsearch] [nginx-botsearch]
enabled = true enabled = true
logpath = /var/log/nginx/*access*.log
[wo-wordpress] [wo-wordpress]
enabled = true enabled = true
filter = wo-wordpress filter = wo-wordpress
action = iptables-multiport[name="wo-wordpress", port="http,https"] action = iptables-multiport[name="wo-wordpress", port="http,https"]
logpath = /var/log/nginx/*access.log logpath = /var/log/nginx/*access*.log
maxretry = 5 maxretry = 5
[nginx-forbidden] [nginx-forbidden]
enabled = true enabled = true
filter = nginx-forbidden filter = nginx-forbidden
action = iptables-multiport[name="wo-wordpress", port="http,https"] action = iptables-multiport[name="nginx-forbidden", port="http,https"]
logpath = /var/log/nginx/*error*.log logpath = /var/log/nginx/*error*.log

View File

@@ -6,6 +6,7 @@
gzip_disable "msie6"; gzip_disable "msie6";
gzip_vary on; gzip_vary on;
gzip_static on;
gzip_proxied any; gzip_proxied any;
gzip_comp_level 6; gzip_comp_level 6;
gzip_buffers 16 8k; gzip_buffers 16 8k;

View File

@@ -1,4 +1,4 @@
# NGINX CONFIGURATION FOR COMMON LOCATION - WO v3.9.7 # NGINX CONFIGURATION FOR COMMON LOCATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# Basic locations files # Basic locations files
location = /favicon.ico { location = /favicon.ico {
@@ -41,7 +41,7 @@ location ~* "/(^$|readme|license|example|README|LEGALNOTICE|INSTALLATION|CHANGE
deny all; deny all;
} }
# Deny backup extensions & log files and return 403 forbidden # Deny backup extensions & log files and return 403 forbidden
location ~* "\.(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)$" { location ~* "\.(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)$" {
deny all; deny all;
} }
location ~* "/(=|\$&|_mm|(wp-)?config\.|cgi-|etc/passwd|muieblack)" { location ~* "/(=|\$&|_mm|(wp-)?config\.|cgi-|etc/passwd|muieblack)" {

View File

@@ -1,4 +1,4 @@
# NGINX CONFIGURATION FOR FASTCGI_CACHE EXCEPTION - WO v3.9.8 # NGINX CONFIGURATION FOR FASTCGI_CACHE EXCEPTION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# do not cache xhtml request # do not cache xhtml request

View File

@@ -16,7 +16,7 @@ events {
http { http {
## ##
# WordOps Settings # WordOps Settings - WordOps {{release}}
## ##
keepalive_timeout 8; keepalive_timeout 8;
@@ -51,17 +51,18 @@ http {
# SSL Settings # SSL Settings
## ##
# Enable 0-RTT support for TLS 1.3
proxy_set_header Early-Data $ssl_early_data;
ssl_early_data on;
ssl_session_timeout 1d; ssl_session_timeout 1d;
ssl_session_cache shared:SSL:50m; ssl_session_cache shared:SSL:50m;
ssl_session_tickets off; ssl_session_tickets off;
ssl_prefer_server_ciphers on; ssl_prefer_server_ciphers on;
ssl_early_data on; ssl_ciphers 'TLS13+AESGCM+AES256:TLS13+AESGCM+AES128:TLS13+CHACHA20:EECDH+AESGCM:EECDH+CHACHA20';
{{#tls13}}ssl_ciphers 'TLS13+AESGCM+AES256:TLS13+AESGCM+AES128:TLS13+CHACHA20:EECDH+AESGCM:EECDH+CHACHA20'; ssl_protocols TLSv1.2 TLSv1.3;
ssl_protocols TLSv1.2 TLSv1.3;{{/tls13}}
ssl_ecdh_curve X25519:P-521:P-384:P-256; ssl_ecdh_curve X25519:P-521:P-384:P-256;
{{^tls13}}# Previous TLS v1.2 configuration
ssl_protocols TLSv1.2;
ssl_ciphers EECDH+CHACHA20:EECDH+AESGCM:EECDH+AES;{{/tls13}}
# Common security headers # Common security headers
more_set_headers "X-Frame-Options : SAMEORIGIN"; more_set_headers "X-Frame-Options : SAMEORIGIN";

View File

@@ -1,4 +1,4 @@
# PHP NGINX CONFIGURATION - WO v3.9.7 # PHP NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
location / { location / {
try_files $uri $uri/ /index.php$is_args$args; try_files $uri $uri/ /index.php$is_args$args;

View File

@@ -0,0 +1,10 @@
#!/usr/bin/env bash
# WordOps script to download public suffix list from Github
# check if curl is available
if ! { command -v curl; }; then
apt-get update && apt-get install curl -qq > /dev/null 2>&1
fi
# download the list
rm -f /var/lib/wo/public_suffix_list.dat
curl -sL -m 30 --retry 3 -k https://raw.githubusercontent.com/publicsuffix/list/master/public_suffix_list.dat | sed '/^\/\//d' | sed '/^$/d' | sed 's/^\s+//g' > /var/lib/wo/public_suffix_list.dat

View File

@@ -1,4 +1,4 @@
# Redis NGINX CONFIGURATION - WO v3.9.7 # Redis NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# $skip_cache variable set in /etc/nginx/conf.d/map-wp.conf # $skip_cache variable set in /etc/nginx/conf.d/map-wp.conf

View File

@@ -2,13 +2,17 @@ Information about {{domain}}:
Nginx configuration {{type}} {{enable}} Nginx configuration {{type}} {{enable}}
{{#php_version}}PHP Version {{php_version}}{{/php_version}} {{#php_version}}PHP Version {{php_version}}{{/php_version}}
{{#ssl}}SSL {{ssl}}{{/ssl}}
{{#sslprovider}}SSL PROVIDER {{sslprovider}}{{/sslprovider}} {{#ssl}}SSL {{ssl}}{{/ssl}}{{#sslprovider}}
{{#sslexpiry}}SSL EXPIRY DATE {{sslexpiry}}{{/sslexpiry}} SSL PROVIDER {{sslprovider}}{{/sslprovider}}{{#sslexpiry}}
SSL EXPIRY DATE {{sslexpiry}}{{/sslexpiry}}
access_log {{accesslog}} access_log {{accesslog}}
error_log {{errorlog}} error_log {{errorlog}}
{{#webroot}}Webroot {{webroot}}{{/webroot}} {{#webroot}}Webroot {{webroot}}{{/webroot}}
{{#dbname}}DB_NAME {{dbname}}{{/dbname}}
{{#dbname}}
DB_NAME {{dbname}}{{/dbname}}
{{#dbname}}DB_USER {{dbuser}}{{/dbname}} {{#dbname}}DB_USER {{dbuser}}{{/dbname}}
{{#dbname}}DB_PASS {{dbpass}}{{/dbname}} {{#dbname}}DB_PASS {{dbpass}}{{/dbname}}
{{#tablepref}}table_prefix {{tableprefix}}{{/tablepref}} {{#tablepref}}table_prefix {{tableprefix}}{{/tablepref}}

View File

@@ -1,4 +1,4 @@
# NGINX Tweaks - WO v3.9.8 # NGINX Tweaks - WordOps {{release}}
directio 4m; directio 4m;
directio_alignment 512; directio_alignment 512;
http2_max_field_size 16k; http2_max_field_size 16k;

View File

@@ -1,4 +1,4 @@
# NGINX UPSTREAM CONFIGURATION - WO v3.9.8 # NGINX UPSTREAM CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
#------------------------------- #-------------------------------
# PHP 5.6 # PHP 5.6
@@ -41,8 +41,8 @@ upstream php72 {
# PHP 7.2 debug # PHP 7.2 debug
upstream debug72 { upstream debug72 {
# Debug Pool # Debug Pool
server 127.0.0.1:9172; server 127.0.0.1:9172;
} }
#------------------------------- #-------------------------------
@@ -61,10 +61,30 @@ upstream php73 {
# PHP 7.3 debug # PHP 7.3 debug
upstream debug73 { upstream debug73 {
# Debug Pool # Debug Pool
server 127.0.0.1:9173; server 127.0.0.1:9173;
} }
#-------------------------------
# PHP 7.4
#-------------------------------
# PHP 7.4 upstream with load-balancing on two unix sockets
upstream php74 {
least_conn;
server unix:/var/run/php/php74-fpm.sock;
server unix:/var/run/php/php74-two-fpm.sock;
keepalive 5;
}
# PHP 7.4 debug
upstream debug74 {
# Debug Pool
server 127.0.0.1:9174;
}
#------------------------------- #-------------------------------
# Netdata # Netdata
#------------------------------- #-------------------------------

View File

@@ -1,58 +0,0 @@
server {
{{#multisite}}
# Uncomment the following line for domain mapping
# listen 80 default_server;
{{/multisite}}
server_name {{site_name}} {{#multisite}}*{{/multisite}}{{^multisite}}www{{/multisite}}.{{site_name}};
{{#multisite}}
# Uncomment the following line for domain mapping
#server_name_in_redirect off;
{{/multisite}}
access_log /var/log/nginx/{{site_name}}.access.log {{^wpredis}}{{^static}}rt_cache{{/static}}{{/wpredis}}{{#wpredis}}rt_cache_redis{{/wpredis}};
error_log /var/log/nginx/{{site_name}}.error.log;
{{#proxy}}
add_header X-Proxy-Cache $upstream_cache_status;
location / {
proxy_pass http://{{host}}:{{port}};
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
# Security settings for better privacy
# Deny hidden files
location ~ /\.(?!well-known\/) {
deny all;
}
# letsencrypt validation
location /.well-known/acme-challenge/ {
alias /var/www/html/.well-known/acme-challenge/;
allow all;
}
{{/proxy}}
{{^proxy}}
root {{webroot}}/htdocs;
index {{^static}}index.php{{/static}} index.html index.htm;
{{#static}}
location / {
try_files $uri $uri/ =404;
}
{{/static}}
{{^static}}include {{#basic}}common/php73.conf;{{/basic}}{{#wpfc}}common/wpfc-php73.conf;{{/wpfc}} {{#wpsc}}common/wpsc-php73.conf;{{/wpsc}}{{#wpredis}}common/redis-php73.conf;{{/wpredis}}{{#wprocket}}common/wprocket-php73.conf;{{/wprocket}}{{#wpce}}common/wpce-php73.conf;{{/wpce}}
{{#wpsubdir}}include common/wpsubdir.conf;{{/wpsubdir}}{{/static}}
{{#wp}}include common/wpcommon-php73.conf;{{/wp}}
include common/locations-wo.conf;{{/proxy}}
include {{webroot}}/conf/nginx/*.conf;
}

View File

@@ -49,9 +49,9 @@ server {
} }
{{/static}} {{/static}}
{{^static}}include {{#basic}}common/php72.conf;{{/basic}}{{#wpfc}}common/wpfc-php72.conf;{{/wpfc}}{{#wpsc}}common/wpsc-php72.conf;{{/wpsc}}{{#wpredis}}common/redis-php72.conf;{{/wpredis}}{{#wprocket}}common/wprocket-php72.conf;{{/wprocket}}{{#wpce}}common/wpce-php72.conf;{{/wpce}} {{^static}}include {{#basic}}common/{{wo_php}}.conf;{{/basic}}{{#wpfc}}common/wpfc-{{wo_php}}.conf;{{/wpfc}}{{#wpsc}}common/wpsc-{{wo_php}}.conf;{{/wpsc}}{{#wpredis}}common/redis-{{wo_php}}.conf;{{/wpredis}}{{#wprocket}}common/wprocket-{{wo_php}}.conf;{{/wprocket}}{{#wpce}}common/wpce-{{wo_php}}.conf;{{/wpce}}
{{#wpsubdir}}include common/wpsubdir.conf;{{/wpsubdir}}{{/static}} {{#wpsubdir}}include common/wpsubdir.conf;{{/wpsubdir}}{{/static}}
{{#wp}}include common/wpcommon-php72.conf;{{/wp}} {{#wp}}include common/wpcommon-{{wo_php}}.conf;{{/wp}}
include common/locations-wo.conf;{{/proxy}} include common/locations-wo.conf;{{/proxy}}
include {{webroot}}/conf/nginx/*.conf; include {{webroot}}/conf/nginx/*.conf;

View File

@@ -1,7 +1,39 @@
# WEBP NGINX CONFIGURATION - WO v3.9.7 # WEBP NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
map $http_accept $webp_suffix { map $http_accept $webp_suffix_valid {
default ""; default 1;
"~*webp" ".webp"; "~*webp" 0;
}
map $realip_remote_addr $webp_suffix_cf {
default 0;
103.21.244.0/22 1;
103.22.200.0/22 1;
103.31.4.0/22 1;
104.16.0.0/12 1;
108.162.192.0/18 1;
131.0.72.0/22 1;
141.101.64.0/18 1;
162.158.0.0/15 1;
172.64.0.0/13 1;
173.245.48.0/20 1;
188.114.96.0/20 1;
190.93.240.0/20 1;
197.234.240.0/22 1;
198.41.128.0/17 1;
199.27.128.0/21 1;
2400:cb00::/32 1;
2405:8100::/32 1;
2405:b500::/32 1;
2606:4700::/32 1;
2803:f800::/32 1;
2a06:98c0::/29 1;
2c0f:f248::/32 1;
}
map $webp_suffix_cf$webp_suffix_valid $webp_suffix {
default "";
00 ".webp";
} }

View File

@@ -26,15 +26,16 @@ fi
if [ -n "$CURRENT_RELEASE" ] && [ -n "$LATEST_RELEASE" ]; then if [ -n "$CURRENT_RELEASE" ] && [ -n "$LATEST_RELEASE" ]; then
if [ "$CURRENT_RELEASE" != "$LATEST_RELEASE" ]; then if [ "$CURRENT_RELEASE" != "$LATEST_RELEASE" ]; then
# display message with motd-news on Ubuntu # display message with motd-news on Ubuntu
echo '*** A new WordOps release is available ***' > "$NEWS" 2> "$ERR" echo '*** A new WordOps release is available ***' >"$NEWS" 2>"$ERR"
echo echo
# At most, 10 lines of text, remove control characters, print at most 80 characters per line # At most, 10 lines of text, remove control characters, print at most 80 characters per line
safe_print "$NEWS" safe_print "$NEWS"
# Try to update the cache # Try to update the cache
safe_print "$NEWS" 2> /dev/null > $CACHE || true safe_print "$NEWS" 2>/dev/null >$CACHE || true
else else
# clean news # clean news
echo '' > "$NEWS" 2> "$ERR" echo '' >"$NEWS" 2>"$ERR"
safe_print "$NEWS" 2> /dev/null > $CACHE || true safe_print "$NEWS" 2>/dev/null >$CACHE || true
fi
fi fi

View File

@@ -1,4 +1,4 @@
# WPCE NGINX CONFIGURATION - WO v3.9.8 # WPCE NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# $cache_uri variable set in /etc/nginx/conf.d/map-wp.conf # $cache_uri variable set in /etc/nginx/conf.d/map-wp.conf
# Use cached or actual file if they exists, Otherwise pass request to WordPress # Use cached or actual file if they exists, Otherwise pass request to WordPress
@@ -10,7 +10,7 @@ location ~ \.php$ {
include fastcgi_params; include fastcgi_params;
fastcgi_pass {{upstream}}; fastcgi_pass {{upstream}};
} }
location ~ /wp-content/cache/cache-enabler/.*html$ { location ~ /wp-content/cache/cache-enabler/*\.html$ {
etag on; etag on;
add_header Vary "Accept-Encoding, Cookie"; add_header Vary "Accept-Encoding, Cookie";
access_log off; access_log off;

View File

@@ -1,4 +1,4 @@
# WordPress COMMON SETTINGS - WO v3.9.7 # WordPress COMMON SETTINGS - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# Limit access to avoid brute force attack # Limit access to avoid brute force attack
location = /wp-login.php { location = /wp-login.php {
@@ -12,7 +12,7 @@ location = /wp-cron.php {
include fastcgi_params; include fastcgi_params;
fastcgi_pass {{upstream}}; fastcgi_pass {{upstream}};
} }
# Prevent Dos attacks with xmlrpc.php # Prevent DoS attacks with xmlrpc.php
location = /xmlrpc.php { location = /xmlrpc.php {
limit_req zone=two burst=1 nodelay; limit_req zone=two burst=1 nodelay;
include fastcgi_params; include fastcgi_params;
@@ -41,7 +41,7 @@ location /wp-content/uploads {
location ~ \.(png|jpe?g)$ { location ~ \.(png|jpe?g)$ {
add_header Vary "Accept-Encoding"; add_header Vary "Accept-Encoding";
more_set_headers 'Access-Control-Allow-Origin : *'; more_set_headers 'Access-Control-Allow-Origin : *';
add_header Cache-Control "public, no-transform"; more_set_headers "Cache-Control : public, no-transform";
access_log off; access_log off;
log_not_found off; log_not_found off;
expires max; expires max;
@@ -57,7 +57,7 @@ location /wp-content/plugins/ewww-image-optimizer/images {
location ~ \.(png|jpe?g)$ { location ~ \.(png|jpe?g)$ {
add_header Vary "Accept-Encoding"; add_header Vary "Accept-Encoding";
more_set_headers 'Access-Control-Allow-Origin : *'; more_set_headers 'Access-Control-Allow-Origin : *';
add_header Cache-Control "public, no-transform"; more_set_headers "Cache-Control : public, no-transform";
access_log off; access_log off;
log_not_found off; log_not_found off;
expires max; expires max;

View File

@@ -1,4 +1,4 @@
# WPFC NGINX CONFIGURATION - WO v3.9.7 # WPFC NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# $skip_cache variable set in /etc/nginx/conf.d/map-wp.conf # $skip_cache variable set in /etc/nginx/conf.d/map-wp.conf

View File

@@ -1,4 +1,4 @@
# WPROCKET NGINX CONFIGURATION - WO v3.9.8 # WPROCKET NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# $cache_uri variable set in /etc/nginx/conf.d/map-wp.conf # $cache_uri variable set in /etc/nginx/conf.d/map-wp.conf
# Use cached or actual file if they exists, Otherwise pass request to WordPress # Use cached or actual file if they exists, Otherwise pass request to WordPress
@@ -10,8 +10,9 @@ location ~ \.php$ {
include fastcgi_params; include fastcgi_params;
fastcgi_pass {{upstream}}; fastcgi_pass {{upstream}};
} }
location ~ /wp-content/cache/wp-rocket/.*html$ { location ~ /wp-content/cache/wp-rocket/*\.html$ {
etag on; etag on;
gzip_static on;
add_header Vary "Accept-Encoding, Cookie"; add_header Vary "Accept-Encoding, Cookie";
access_log off; access_log off;
log_not_found off; log_not_found off;

View File

@@ -1,4 +1,4 @@
# WPSC NGINX CONFIGURATION - WO v3.9.7 # WPSC NGINX CONFIGURATION - WordOps {{release}}
# DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE # DO NOT MODIFY, ALL CHANGES WILL BE LOST AFTER AN WordOps (wo) UPDATE
# $cache_uri variable set in /etc/nginx/conf.d/map-wp.conf # $cache_uri variable set in /etc/nginx/conf.d/map-wp.conf

View File

@@ -16,8 +16,41 @@ class WOAcme:
wo_acme_exec = ("/etc/letsencrypt/acme.sh --config-home " wo_acme_exec = ("/etc/letsencrypt/acme.sh --config-home "
"'/etc/letsencrypt/config'") "'/etc/letsencrypt/config'")
def check_acme(self):
"""
Check if acme.sh is properly installed,
and install it if required
"""
if not os.path.exists('/etc/letsencrypt/acme.sh'):
if os.path.exists('/opt/acme.sh'):
WOFileUtils.rm(self, '/opt/acme.sh')
WOGit.clone(
self, 'https://github.com/Neilpang/acme.sh.git',
'/opt/acme.sh', branch='master')
WOFileUtils.mkdir(self, '/etc/letsencrypt/config')
WOFileUtils.mkdir(self, '/etc/letsencrypt/renewal')
WOFileUtils.mkdir(self, '/etc/letsencrypt/live')
try:
WOFileUtils.chdir(self, '/opt/acme.sh')
WOShellExec.cmd_exec(
self, './acme.sh --install --home /etc/letsencrypt'
'--config-home /etc/letsencrypt/config'
'--cert-home /etc/letsencrypt/renewal'
)
WOShellExec.cmd_exec(
self, "{0} --upgrade --auto-upgrade"
.format(WOAcme.wo_acme_exec)
)
except CommandExecutionError as e:
Log.debug(self, str(e))
Log.error(self, "acme.sh installation failed")
if not os.path.exists('/etc/letsencrypt/acme.sh'):
Log.error(self, 'acme.sh ')
def export_cert(self): def export_cert(self):
"""Export acme.sh csv certificate list""" """Export acme.sh csv certificate list"""
# check acme.sh is installed
WOAcme.check_acme(self)
if not WOShellExec.cmd_exec( if not WOShellExec.cmd_exec(
self, "{0} ".format(WOAcme.wo_acme_exec) + self, "{0} ".format(WOAcme.wo_acme_exec) +
"--list --listraw > /var/lib/wo/cert.csv"): "--list --listraw > /var/lib/wo/cert.csv"):
@@ -26,6 +59,9 @@ class WOAcme:
def setupletsencrypt(self, acme_domains, acmedata): def setupletsencrypt(self, acme_domains, acmedata):
"""Issue SSL certificates with acme.sh""" """Issue SSL certificates with acme.sh"""
# check acme.sh is installed
WOAcme.check_acme(self)
# define variables
all_domains = '\' -d \''.join(acme_domains) all_domains = '\' -d \''.join(acme_domains)
wo_acme_dns = acmedata['acme_dns'] wo_acme_dns = acmedata['acme_dns']
keylenght = acmedata['keylength'] keylenght = acmedata['keylength']
@@ -74,6 +110,8 @@ class WOAcme:
def deploycert(self, wo_domain_name): def deploycert(self, wo_domain_name):
"""Deploy Let's Encrypt certificates with acme.sh""" """Deploy Let's Encrypt certificates with acme.sh"""
# check acme.sh is installed
WOAcme.check_acme(self)
if not os.path.isfile('/etc/letsencrypt/renewal/{0}_ecc/fullchain.cer' if not os.path.isfile('/etc/letsencrypt/renewal/{0}_ecc/fullchain.cer'
.format(wo_domain_name)): .format(wo_domain_name)):
Log.error(self, 'Certificate not found. Deployment canceled') Log.error(self, 'Certificate not found. Deployment canceled')
@@ -135,6 +173,8 @@ class WOAcme:
def renew(self, domain): def renew(self, domain):
"""Renew letsencrypt certificate with acme.sh""" """Renew letsencrypt certificate with acme.sh"""
# check acme.sh is installed
WOAcme.check_acme(self)
try: try:
WOShellExec.cmd_exec( WOShellExec.cmd_exec(
self, "{0} ".format(WOAcme.wo_acme_exec) + self, "{0} ".format(WOAcme.wo_acme_exec) +
@@ -158,7 +198,10 @@ class WOAcme:
response = requests.get(url, headers=headers).json() response = requests.get(url, headers=headers).json()
domain_ip = response["Answer"][0]['data'] domain_ip = response["Answer"][0]['data']
except requests.RequestException: except requests.RequestException:
Log.error(self, 'Resolving domain IP failed') Log.error(
self, 'Resolving domain IP failed.\n'
'The domain {0} do not exist or a DNS record is missing'
.format(domain))
if(not domain_ip == server_ip): if(not domain_ip == server_ip):
Log.warn( Log.warn(
self, "{0}".format(domain) + self, "{0}".format(domain) +
@@ -202,6 +245,8 @@ class WOAcme:
.format(WOVar.wo_ssl_live, domain), .format(WOVar.wo_ssl_live, domain),
'/etc/letsencrypt/shared/{0}.conf'.format(domain)] '/etc/letsencrypt/shared/{0}.conf'.format(domain)]
wo_domain = domain wo_domain = domain
# check acme.sh is installed
WOAcme.check_acme(self)
if WOAcme.cert_check(self, wo_domain): if WOAcme.cert_check(self, wo_domain):
Log.info(self, "Removing Acme configuration") Log.info(self, "Removing Acme configuration")
Log.debug(self, "Removing Acme configuration") Log.debug(self, "Removing Acme configuration")

View File

@@ -1,6 +1,7 @@
"""WordOps package installation using apt-get module.""" """WordOps package installation using apt-get module."""
import subprocess import subprocess
import sys import sys
import os
from sh import ErrorReturnCode, apt_get from sh import ErrorReturnCode, apt_get
@@ -222,6 +223,29 @@ class WOAptGet():
# apt_cache.close() # apt_cache.close()
return False return False
def is_exec(self, package_name):
"""
Check if package is available by looking
for an executable or a systemd service related
to this package
"""
exec_path = ["/bin", "/usr/bin", "/usr/local/bin",
"/usr/sbin", "/usr/local/sbin"]
for path in exec_path:
if os.path.exists('{0}/{1}'.format(path, package_name)):
return True
return False
def is_selected(self, package_name, packages_list):
"""
Check if package is selected for install/removal/purge
in packages_list
"""
for package in packages_list:
if package_name == package[2]:
return True
return False
def download_only(self, package_name, repo_url=None, repo_key=None): def download_only(self, package_name, repo_url=None, repo_key=None):
""" """
Similar to `apt-get install --download-only PACKAGE_NAME` Similar to `apt-get install --download-only PACKAGE_NAME`

View File

@@ -252,10 +252,7 @@ class WOFileUtils():
Check if file exist on given path Check if file exist on given path
""" """
try: try:
if os.path.exists(path): return bool(os.path.exists(path))
return (True)
else:
return (False)
except OSError as e: except OSError as e:
Log.debug(self, "{0}".format(e.strerror)) Log.debug(self, "{0}".format(e.strerror))
Log.error(self, "Unable to check path {0}".format(path)) Log.error(self, "Unable to check path {0}".format(path))
@@ -369,3 +366,22 @@ class WOFileUtils():
except IOError as e: except IOError as e:
Log.debug(self, "{0}".format(e)) Log.debug(self, "{0}".format(e))
Log.error(self, "Unable to append content in {0}".format(path)) Log.error(self, "Unable to append content in {0}".format(path))
def enabledisable(self, path, enable=True):
"""Switch conf from .conf.disabled to .conf or vice-versa"""
if enable:
Log.debug(self, "Check if disabled file exist")
if os.path.exists('{0}.disabled'.format(path)):
Log.debug(self, "Moving .disabled file")
shutil.move('{0}.disabled'.format(path), path)
return True
else:
return False
else:
Log.debug(self, "Check if .conf file exist")
if os.path.exists(path):
Log.debug(self, "Moving .conf file")
shutil.move(path, '{0}.disabled'.format(path))
return True
else:
return False

View File

@@ -18,25 +18,24 @@ class WOGit:
""" """
for path in paths: for path in paths:
global git global git
git = git.bake("--git-dir={0}/.git".format(path), wogit = git.bake("-C", "{0}".format(path))
"--work-tree={0}".format(path))
if os.path.isdir(path): if os.path.isdir(path):
if not os.path.isdir(path + "/.git"): if not os.path.isdir(path + "/.git"):
try: try:
Log.debug(self, "WOGit: git init at {0}" Log.debug(self, "WOGit: git init at {0}"
.format(path)) .format(path))
git.init(path) wogit.init(path)
except ErrorReturnCode as e: except ErrorReturnCode as e:
Log.debug(self, "{0}".format(e)) Log.debug(self, "{0}".format(e))
Log.error(self, "Unable to git init at {0}" Log.error(self, "Unable to git init at {0}"
.format(path)) .format(path))
status = git.status("-s") status = wogit.status("-s")
if len(status.splitlines()) > 0: if len(status.splitlines()) > 0:
try: try:
Log.debug(self, "WOGit: git commit at {0}" Log.debug(self, "WOGit: git commit at {0}"
.format(path)) .format(path))
git.add("--all") wogit.add("--all")
git.commit("-am {0}".format(msg)) wogit.commit("-am {0}".format(msg))
except ErrorReturnCode as e: except ErrorReturnCode as e:
Log.debug(self, "{0}".format(e)) Log.debug(self, "{0}".format(e))
Log.error(self, "Unable to git commit at {0} " Log.error(self, "Unable to git commit at {0} "
@@ -49,9 +48,8 @@ class WOGit:
Checks status of file, If its tracked or untracked. Checks status of file, If its tracked or untracked.
""" """
global git global git
git = git.bake("--git-dir={0}/.git".format(repo), wogit = git.bake("-C", "{0}".format(repo))
"--work-tree={0}".format(repo)) status = wogit.status("-s", "{0}".format(filepath))
status = git.status("-s", "{0}".format(filepath))
if len(status.splitlines()) > 0: if len(status.splitlines()) > 0:
return True return True
else: else:
@@ -64,8 +62,7 @@ class WOGit:
""" """
for path in paths: for path in paths:
global git global git
git = git.bake("--git-dir={0}/.git".format(path), wogit = git.bake("-C", "{0}".format(path))
"--work-tree={0}".format(path))
if os.path.isdir(path): if os.path.isdir(path):
if not os.path.isdir(path + "/.git"): if not os.path.isdir(path + "/.git"):
Log.error( Log.error(
@@ -75,7 +72,7 @@ class WOGit:
Log.debug( Log.debug(
self, "WOGit: git stash --include-untracked at {0}" self, "WOGit: git stash --include-untracked at {0}"
.format(path)) .format(path))
git.stash("push", "--include-untracked", "-m {0}" wogit.stash("push", "--include-untracked", "-m {0}"
.format(msg)) .format(msg))
except ErrorReturnCode as e: except ErrorReturnCode as e:
Log.debug(self, "{0}".format(e)) Log.debug(self, "{0}".format(e))

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

@@ -0,0 +1,19 @@
"""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

View File

@@ -20,15 +20,17 @@ class WOService():
# Check Nginx configuration before executing command # Check Nginx configuration before executing command
sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE, sub = subprocess.Popen('nginx -t', stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True) stderr=subprocess.PIPE, shell=True)
output, error_output = sub.communicate() output = sub.communicate()
if 'emerg' not in str(error_output): if 'emerg' not in str(output):
Log.valide(self, "Testing Nginx configuration ") Log.valide(self, "Testing Nginx configuration ")
Log.wait(self, "Starting Nginx ") Log.wait(self, "Starting Nginx")
service_cmd = ('service {0} start'.format(service_name)) service_cmd = ('service {0} start'.format(service_name))
retcode = subprocess.getstatusoutput(service_cmd) retcode = subprocess.getstatusoutput(service_cmd)
if retcode[0] == 0: if retcode[0] == 0:
Log.valide(self, "Starting Nginx ") Log.valide(self, "Starting Nginx ")
return True return True
else:
Log.failed(self, "Starting Nginx")
else: else:
Log.failed(self, "Testing Nginx configuration ") Log.failed(self, "Testing Nginx configuration ")
return False return False
@@ -129,11 +131,11 @@ class WOService():
output, error_output = sub.communicate() output, error_output = sub.communicate()
if 'emerg' not in str(error_output): if 'emerg' not in str(error_output):
Log.valide(self, "Testing Nginx configuration ") Log.valide(self, "Testing Nginx configuration ")
Log.wait(self, "Reloading Nginx ") Log.wait(self, "Reloading Nginx")
service_cmd = ('service {0} reload'.format(service_name)) service_cmd = ('service {0} reload'.format(service_name))
retcode = subprocess.getstatusoutput(service_cmd) retcode = subprocess.getstatusoutput(service_cmd)
if retcode[0] == 0: if retcode[0] == 0:
Log.valide(self, "Reloading Nginx ") Log.valide(self, "Reloading Nginx")
return True return True
else: else:
Log.failed(self, "Testing Nginx configuration ") Log.failed(self, "Testing Nginx configuration ")
@@ -160,10 +162,11 @@ class WOService():
def get_service_status(self, service_name): def get_service_status(self, service_name):
try: try:
is_exist = subprocess.getstatusoutput('which {0}' is_exist = subprocess.getstatusoutput('command -v {0}'
.format(service_name)) .format(service_name))
if is_exist[0] == 0 or service_name in ['php7.2-fpm', if is_exist[0] == 0 or service_name in ['php7.2-fpm',
'php7.3-fpm']: 'php7.3-fpm',
'php7.4-fpm']:
retcode = subprocess.getstatusoutput('service {0} status' retcode = subprocess.getstatusoutput('service {0} status'
.format(service_name)) .format(service_name))
if retcode[0] == 0: if retcode[0] == 0:

View File

@@ -37,27 +37,6 @@ class WOShellExec():
Log.debug(self, str(e)) Log.debug(self, str(e))
raise CommandExecutionError raise CommandExecutionError
def cmd_exist(self, command):
"""Check if a command exist with command -v"""
try:
Log.debug(self, "Testing command: {0}".format(command))
testing_command = ("command -v {0}".format(command))
with subprocess.Popen([testing_command], stdout=subprocess.PIPE,
stderr=subprocess.PIPE, shell=True) as proc:
(cmd_stdout_bytes, cmd_stderr_bytes) = proc.communicate()
(cmd_stdout, cmd_stderr) = (
cmd_stdout_bytes.decode('utf-8', "replace"),
cmd_stderr_bytes.decode('utf-8', "replace"))
Log.debug(self, "Command Output: {0}, \nCommand Error: {1}"
.format(cmd_stdout, cmd_stderr))
return bool(proc.returncode == 0)
except OSError as e:
Log.debug(self, str(e))
raise CommandExecutionError
except Exception as e:
Log.debug(self, str(e))
raise CommandExecutionError
def invoke_editor(self, filepath, errormsg=''): def invoke_editor(self, filepath, errormsg=''):
""" """
Open files using sensible editor Open files using sensible editor

View File

@@ -6,26 +6,39 @@ from wo.core.fileutils import WOFileUtils
from wo.core.logging import Log from wo.core.logging import Log
from wo.core.shellexec import WOShellExec from wo.core.shellexec import WOShellExec
from wo.core.variables import WOVar from wo.core.variables import WOVar
from wo.core.acme import WOAcme
class SSL: class SSL:
def getexpirationdays(self, domain, returnonerror=False): def getexpirationdays(self, domain, returnonerror=False):
# check if exist # check if exist
if not os.path.isfile('/etc/letsencrypt/live/{0}/cert.pem' if not os.path.exists('/etc/letsencrypt/live/{0}/cert.pem'
.format(domain)): .format(domain)):
Log.debug(self, "cert not found for {0}".format(domain))
split_domain = domain.split('.')
root_domain = ('.').join(split_domain[1:])
Log.debug(self, "trying with {0}".format(root_domain))
if os.path.exists('/etc/letsencrypt/live/{0}/cert.pem'
.format(root_domain)):
domain = root_domain
else:
Log.error(self, 'File Not Found: ' Log.error(self, 'File Not Found: '
'/etc/letsencrypt/live/{0}/cert.pem' '/etc/letsencrypt/live/{0}/cert.pem'
.format(domain), False) .format(domain), False)
if returnonerror: Log.error(
return -1 self, "Check the WordOps log for more details "
Log.error(self, "Check the WordOps log for more details " "`tail /var/log/wo/wordops.log` "
"`tail /var/log/wo/wordops.log` and please try again...") "and please try again...")
Log.debug(
self,
"Getting expiration of /etc/letsencrypt/live/{0}/cert.pem"
.format(domain))
current_date = WOShellExec.cmd_exec_stdout(self, "date -d \"now\" +%s") current_date = WOShellExec.cmd_exec_stdout(self, "date -d \"now\" +%s")
expiration_date = WOShellExec.cmd_exec_stdout( expiration_date = WOShellExec.cmd_exec_stdout(
self, "date -d \"" self, "date -d \"$(openssl x509 -in /etc/letsencrypt/live/"
"$(openssl x509 -in /etc/letsencrypt/live/"
"{0}/cert.pem -text -noout | grep \"Not After\" " "{0}/cert.pem -text -noout | grep \"Not After\" "
"| cut -c 25-)\" +%s" "| cut -c 25-)\" +%s"
.format(domain)) .format(domain))
@@ -39,23 +52,27 @@ class SSL:
def getexpirationdate(self, domain): def getexpirationdate(self, domain):
# check if exist # check if exist
if os.path.islink('/var/www/{0}/conf/nginx/ssl.conf'):
split_domain = domain.split('.')
domain = ('.').join(split_domain[1:])
if not os.path.isfile('/etc/letsencrypt/live/{0}/cert.pem' if not os.path.isfile('/etc/letsencrypt/live/{0}/cert.pem'
.format(domain)): .format(domain)):
Log.error(self, 'File Not Found: /etc/letsencrypt/' if os.path.exists('/var/www/{0}/conf/nginx/ssl.conf'):
split_domain = domain.split('.')
check_domain = ('.').join(split_domain[1:])
else:
Log.error(
self, 'File Not Found: /etc/letsencrypt/'
'live/{0}/cert.pem' 'live/{0}/cert.pem'
.format(domain), False) .format(domain), False)
Log.error(self, "Check the WordOps log for more details " Log.error(
self, "Check the WordOps log for more details "
"`tail /var/log/wo/wordops.log` and please try again...") "`tail /var/log/wo/wordops.log` and please try again...")
else:
check_domain = domain
expiration_date = WOShellExec.cmd_exec_stdout( return WOShellExec.cmd_exec_stdout(
self, "date -d \"$(/usr/bin/openssl x509 -in " self, "date -d \"$(/usr/bin/openssl x509 -in "
"/etc/letsencrypt/live/{0}/cert.pem -text -noout | grep " "/etc/letsencrypt/live/{0}/cert.pem -text -noout | grep "
"\"Not After\" | cut -c 25-)\" " "\"Not After\" | cut -c 25-)\" "
.format(domain)) .format(check_domain))
return expiration_date
def siteurlhttps(self, domain): def siteurlhttps(self, domain):
wo_site_webroot = ('/var/www/{0}'.format(domain)) wo_site_webroot = ('/var/www/{0}'.format(domain))
@@ -93,8 +110,8 @@ class SSL:
Log.valide(self, "Updating site url with https") Log.valide(self, "Updating site url with https")
# check if a wildcard exist to secure a new subdomain # check if a wildcard exist to secure a new subdomain
def checkwildcardexist(self, wo_domain_name): def checkwildcardexist(self, wo_domain_name):
"""Check if a wildcard certificate exist for a domain"""
wo_acme_exec = ("/etc/letsencrypt/acme.sh --config-home " wo_acme_exec = ("/etc/letsencrypt/acme.sh --config-home "
"'/etc/letsencrypt/config'") "'/etc/letsencrypt/config'")
@@ -110,17 +127,20 @@ class SSL:
reader = csv.reader(certfile, 'acmeconf') reader = csv.reader(certfile, 'acmeconf')
wo_wildcard_domain = ("*.{0}".format(wo_domain_name)) wo_wildcard_domain = ("*.{0}".format(wo_domain_name))
for row in reader: for row in reader:
if wo_wildcard_domain in row[2]: if wo_wildcard_domain == row[2]:
if not row[2] == "": if not row[3] == "":
iswildcard = True return True
break
else:
iswildcard = False
certfile.close() certfile.close()
return False
return iswildcard def setuphsts(self, wo_domain_name, enable=True):
"""Enable or disable htsts for a site"""
def setuphsts(self, wo_domain_name): if enable:
if WOFileUtils.enabledisable(
self, '/var/www/{0}/conf/nginx/hsts.conf'
):
return 0
else:
Log.info( Log.info(
self, "Adding /var/www/{0}/conf/nginx/hsts.conf" self, "Adding /var/www/{0}/conf/nginx/hsts.conf"
.format(wo_domain_name)) .format(wo_domain_name))
@@ -135,6 +155,16 @@ class SSL:
"preload\";") "preload\";")
hstsconf.close() hstsconf.close()
return 0 return 0
else:
if WOFileUtils.enabledisable(
self, '/var/www/{0}/conf/nginx/hsts.conf',
enable=False
):
Log.info(self, "HSTS disabled")
return 0
else:
Log.info(self, "HSTS is not enabled")
return 0
def selfsignedcert(self, proftpd=False, backend=False): def selfsignedcert(self, proftpd=False, backend=False):
"""issue a self-signed certificate""" """issue a self-signed certificate"""
@@ -197,3 +227,100 @@ class SSL:
"/etc/proftpd/ssl/proftpd.crt") "/etc/proftpd/ssl/proftpd.crt")
# remove self-signed tmp directory # remove self-signed tmp directory
WOFileUtils.rm(self, selfs_tmp) 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)
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):
Log.valide(self, "Adding HTTPS redirection")
return 0
else:
try:
sslconf = open(
"/etc/nginx/conf.d/force-ssl-{0}.conf"
.format(wo_domain_name),
encoding='utf-8', mode='w')
sslconf.write(
"server {\n"
"\tlisten 80;\n" +
"\tlisten [::]:80;\n" +
"\tserver_name {0};\n"
.format(wo_acme_domains) +
"\treturn 301 https://$host"
"$request_uri;\n}")
sslconf.close()
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
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)
)
return 0
def archivedcertificatehandle(self, domain, acme_domains):
Log.warn(
self, "You already have an existing certificate "
"for the domain requested.\n"
"(ref: {0}/"
"{1}_ecc/{1}.conf)".format(WOVar.wo_ssl_archive, domain) +
"\nPlease select an option from below?"
"\n\t1: Reinstall existing certificate"
"\n\t2: Issue a new certificate to replace "
"the current one (limit ~5 per 7 days)"
"")
check_prompt = input(
"\nType the appropriate number [1-2] or any other key to cancel: ")
if not os.path.isfile("{0}/{1}/fullchain.pem"
.format(WOVar.wo_ssl_live, domain)):
Log.debug(
self, "{0}/{1}/fullchain.pem file is missing."
.format(WOVar.wo_ssl_live, domain))
check_prompt = "2"
if check_prompt == "1":
Log.info(self, "Reinstalling SSL cert with acme.sh")
ssl = WOAcme.deploycert(self, domain)
if ssl:
SSL.httpsredirect(self, domain, acme_domains)
elif (check_prompt == "2"):
Log.info(self, "Issuing new SSL cert with acme.sh")
ssl = WOShellExec.cmd_exec(
self, "/etc/letsencrypt/acme.sh "
"--config-home '/etc/letsencrypt/config' "
"--renew -d {0} --ecc --force"
.format(domain))
if ssl:
WOAcme.deploycert(self, domain)
else:
Log.error(self, "Operation cancelled by user.")
if os.path.isfile("{0}/conf/nginx/ssl.conf"
.format(domain)):
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))
return ssl

50
wo/core/stackconf.py Normal file
View File

@@ -0,0 +1,50 @@
import os
from wo.core.logging import Log
from wo.core.template import WOTemplate
from wo.core.variables import WOVar
class WOConf():
"""wo stack configuration utilities"""
def __init__():
pass
def nginxcommon(self):
"""nginx common configuration deployment"""
wo_php_version = ["php72", "php73", "php74"]
ngxcom = '/etc/nginx/common'
for wo_php in wo_php_version:
if not os.path.exists(ngxcom):
os.mkdir(ngxcom)
Log.debug(self, 'deploying templates for {0}'.format(wo_php))
data = dict(upstream="{0}".format(wo_php),
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)

View File

@@ -14,11 +14,11 @@ class WOVar():
"""Intialization of core variables""" """Intialization of core variables"""
# WordOps version # WordOps version
wo_version = "3.10.3" wo_version = "3.11.0"
# WordOps packages versions # WordOps packages versions
wo_wp_cli = "2.3.0" wo_wp_cli = "2.4.0"
wo_adminer = "4.7.3" wo_adminer = "4.7.5"
wo_phpmyadmin = "4.9.1" wo_phpmyadmin = "4.9.2"
wo_extplorer = "2.1.13" wo_extplorer = "2.1.13"
wo_dashboard = "1.2" wo_dashboard = "1.2"
@@ -133,16 +133,23 @@ class WOVar():
wo_nginx = ["nginx-custom", "nginx-wo"] wo_nginx = ["nginx-custom", "nginx-wo"]
wo_nginx_key = '188C9FB063F0247A' wo_nginx_key = '188C9FB063F0247A'
wo_php = ["php7.2-fpm", "php7.2-curl", "php7.2-gd", "php7.2-imap", wo_module = ["fpm", "curl", "gd", "imap",
"php7.2-readline", "php7.2-common", "php7.2-recode", "readline", "common",
"php7.2-cli", "php7.2-mbstring", "php7.2-intl", "cli", "mbstring", "intl",
"php7.2-bcmath", "php7.2-mysql", "php7.2-opcache", "bcmath", "mysql", "opcache",
"php7.2-zip", "php7.2-xml", "php7.2-soap"] "zip", "xml", "soap"]
wo_php73 = ["php7.3-fpm", "php7.3-curl", "php7.3-gd", "php7.3-imap", wo_php72 = []
"php7.3-readline", "php7.3-common", "php7.3-recode", for module in wo_module:
"php7.3-cli", "php7.3-mbstring", "php7.3-intl", wo_php72 = wo_php72 + ["php7.2-{0}".format(module),
"php7.3-bcmath", "php7.3-mysql", "php7.3-opcache", "php7.2-recode"]
"php7.3-zip", "php7.3-xml", "php7.3-soap"] wo_php73 = []
for module in wo_module:
wo_php73 = wo_php73 + ["php7.3-{0}".format(module),
"php7.3-recode"]
wo_php74 = []
for module in wo_module:
wo_php74 = wo_php74 + ["php7.4-{0}".format(module)]
wo_php_extra = ["php-memcached", "php-imagick", wo_php_extra = ["php-memcached", "php-imagick",
"graphviz", "php-xdebug", "php-msgpack", "php-redis"] "graphviz", "php-xdebug", "php-msgpack", "php-redis"]

17
wo/core/wpcli.py Normal file
View File

@@ -0,0 +1,17 @@
"""WordPress utilities for WordOps"""
from wo.core.logging import Log
from wo.core.shellexec import WOShellExec
from wo.core.variables import WOVar
class WOWp:
"""WordPress utilities for WordOps"""
def wpcli(self, command):
"""WP-CLI wrapper"""
try:
WOShellExec.cmd_exec(
self, '{0} --allow-root '.format(WOVar.wo_wpcli_path) +
'{0}'.format(command))
except Exception:
Log.error(self, "WP-CLI command failed")