From 479cbe3a513f1f932ed25ebf55605aebe56fcfbc Mon Sep 17 00:00:00 2001 From: baudneo Date: Mon, 21 Feb 2022 23:17:12 -0700 Subject: [PATCH] Modsecurity is working! --- docker/Dockerfile | 7 +++- .../rootfs/etc/cont-init.d/97_modsecurity.sh | 39 +++++++++++++++++++ .../etc/cont-init.d/98_logging-options.sh | 16 ++++---- .../99_crowdsec-openresty-bouncer.sh | 7 +++- docker/rootfs/etc/logrotate.d/modsecurity | 15 +++++++ docker/rootfs/etc/nginx/conf.d/default.conf | 7 ++++ .../rootfs/etc/nginx/conf.d/production.conf | 2 + scripts/buildx | 6 +-- scripts/frontend-build | 2 +- 9 files changed, 86 insertions(+), 15 deletions(-) create mode 100755 docker/rootfs/etc/cont-init.d/97_modsecurity.sh create mode 100644 docker/rootfs/etc/logrotate.d/modsecurity diff --git a/docker/Dockerfile b/docker/Dockerfile index b75a2980..70335633 100644 --- a/docker/Dockerfile +++ b/docker/Dockerfile @@ -3,7 +3,7 @@ # This file assumes that the frontend has been built using ./scripts/frontend-build -FROM nginxproxymanager/nginx-full:certbot-node +FROM baudneo/nginx-full:certbot-node ARG TARGETPLATFORM ARG BUILD_VERSION @@ -17,7 +17,10 @@ ENV SUPPRESS_NO_CONFIG_WARNING=1 \ NPM_BUILD_VERSION="${BUILD_VERSION}" \ NPM_BUILD_COMMIT="${BUILD_COMMIT}" \ NPM_BUILD_DATE="${BUILD_DATE}" \ - OPENRESTY_DEBUG="0" + OPENRESTY_DEBUG="0" \ + MODSEC_CREATE="0" \ + MODSEC_ENABLE="0" \ + MODSEC_ADMIN_PANEL="0" RUN echo "fs.file-max = 65535" > /etc/sysctl.conf \ && apt-get update \ diff --git a/docker/rootfs/etc/cont-init.d/97_modsecurity.sh b/docker/rootfs/etc/cont-init.d/97_modsecurity.sh new file mode 100755 index 00000000..007afd26 --- /dev/null +++ b/docker/rootfs/etc/cont-init.d/97_modsecurity.sh @@ -0,0 +1,39 @@ +#!/usr/bin/with-contenv bash +# shellcheck shell=bash + +set -e # Exit immediately if a command exits with a non-zero status. +set -u # Treat unset variables as an error. + +log() { + echo "[cont-init.d] $(basename "$0"): $*" +} + +mkdir -p /data/modsec/ruleset +ln -s /data/modsec/ /etc/nginx + +[ ! -f /data/modsec/main.conf ] && MODSEC_CREATE="1" + +if [ "${MODSEC_CREATE}" == "1" ] || [ "${MODSEC_CREATE}" -eq 1 ]; then + log "Setting up modsecurity persistent data" + cp /usr/local/modsecurity/templates/main.conf /data/modsec/main.conf + cp /usr/local/modsecurity/templates/modsecurity.conf /data/modsec/modsecurity.conf + cp /usr/local/modsecurity/templates/unicode.mapping /data/modsec/unicode.mapping + cp -r /usr/local/modsecurity/templates/* /data/modsec/ + cp -r /usr/local/modsecurity/templates/ruleset/* /data/modsec/ruleset/ + mv /data/modsec/ruleset/crs-setup.conf.example /data/modsec/ruleset/crs-setup.conf +fi + +# Enable modsecurity in the server block of :80 and :443 +# Can disable this (default) and add the modsec directives in each location block +if [ "${MODSEC_ENABLE}" == "1" ] || [ "${MODSEC_ENABLE}" -eq 1 ]; then + log "Enabling modsecurity in server block of port 80 and 443" + sed-patch "s|#|modsecurity on;|g" /etc/nginx/conf.d/default.conf + sed-patch "s|#|modsecurity_rules_file /etc/nginx/modsec/main.conf;|g" /etc/nginx/conf.d/default.conf +fi +# Enabled modsecurity in the server block of :81 (admin dashboard) +if [ "${MODSEC_ADMIN_PANEL}" == "1" ] || [ "${MODSEC_ADMIN_PANEL}" -eq 1 ]; then + log "Enabling modsecurity in server block of admin dashboard port 81" + sed-patch "s|#|modsecurity on;|g" /etc/nginx/conf.d/production.conf + sed-patch "s|#|modsecurity_rules_file /etc/nginx/modsec/main.conf;|g" /etc/nginx/conf.d/production.conf + +fi \ No newline at end of file diff --git a/docker/rootfs/etc/cont-init.d/98_logging-options.sh b/docker/rootfs/etc/cont-init.d/98_logging-options.sh index 78b3b28e..3c873394 100755 --- a/docker/rootfs/etc/cont-init.d/98_logging-options.sh +++ b/docker/rootfs/etc/cont-init.d/98_logging-options.sh @@ -4,26 +4,26 @@ set -e # Exit immediately if a command exits with a non-zero status. set -u # Treat unset variables as an error. +log() { + echo "[cont-init.d] $(basename "$0"): $*" +} + # Redirect admin panel logs from /dev/null to log files if enabled if [[ ${ADMIN_PANEL_LOG} == "1" ]] || [[ ${ADMIN_PANEL_LOG} -eq 1 ]]; then - echo "Enabling admin dashboard logging" - echo "ADMIN_PANEL_LOG = $ADMIN_PANEL_LOG" + log "Enabling admin dashboard logging" sed-patch 's||/data/logs/admin-panel_access.log standard|' /etc/nginx/conf.d/production.conf sed-patch 's||/data/logs/admin-panel_error.log warn|' /etc/nginx/conf.d/production.conf else - echo "Leaving admin dashboard logging off (default behavior)" - echo "ADMIN_PANEL_LOG = $ADMIN_PANEL_LOG" + log "Leaving admin dashboard logging off (default behavior)" sed-patch 's||/dev/null|' /etc/nginx/conf.d/production.conf sed-patch 's||/dev/null|' /etc/nginx/conf.d/production.conf fi if [[ ${OPENRESTY_DEBUG} == "1" ]] || [[ ${OPENRESTY_DEBUG} -eq 1 ]]; then - echo "Changing OpenResty ERROR (fallback_error.log) logging to level: DEBUG" - echo "OPENRESTY_DEBUG = $OPENRESTY_DEBUG" + log "Changing OpenResty ERROR (fallback_error.log) logging to level: DEBUG" sed-patch 's||debug|' /etc/nginx/nginx.conf else - echo "Leaving OpenResty ERROR (fallback_error.log) logging at level: WARN (default behavior)" - echo "OPENRESTY_DEBUG = $OPENRESTY_DEBUG" + log "Leaving OpenResty ERROR (fallback_error.log) logging at level: WARN (default behavior)" sed-patch 's||warn|' /etc/nginx/nginx.conf fi diff --git a/docker/rootfs/etc/cont-init.d/99_crowdsec-openresty-bouncer.sh b/docker/rootfs/etc/cont-init.d/99_crowdsec-openresty-bouncer.sh index 1b7e7fe5..f961c01b 100755 --- a/docker/rootfs/etc/cont-init.d/99_crowdsec-openresty-bouncer.sh +++ b/docker/rootfs/etc/cont-init.d/99_crowdsec-openresty-bouncer.sh @@ -9,9 +9,14 @@ log() { } if [ "${CROWDSEC_BOUNCER}" == "1" ] || [ "${CROWDSEC_BOUNCER}" -eq 1 ]; then + log "Enabling CrowdSec Bouncer" mkdir -p /data/crowdsec #Install Crowdsec Bouncer Config. - [ -f /data/crowdsec/crowdsec-openresty-bouncer.conf ] || cp /crowdsec/crowdsec-openresty-bouncer.conf /data/crowdsec/crowdsec-openresty-bouncer.conf + if [ -f /data/crowdsec/crowdsec-openresty-bouncer.conf ]; then + cp /crowdsec/crowdsec-openresty-bouncer.conf /data/crowdsec/crowdsec-openresty-bouncer.conf + log "Crowdsec Bouncer Config copied to /data/crowdsec/crowdsec-openresty-bouncer.conf" + fi + mkdir -p /etc/nginx/lualib/plugins/crowdsec/ cp /crowdsec/lua/* /etc/nginx/lualib/plugins/crowdsec/ cp /crowdsec/crowdsec_openresty.conf /etc/nginx/conf.d/ diff --git a/docker/rootfs/etc/logrotate.d/modsecurity b/docker/rootfs/etc/logrotate.d/modsecurity new file mode 100644 index 00000000..550eedee --- /dev/null +++ b/docker/rootfs/etc/logrotate.d/modsecurity @@ -0,0 +1,15 @@ +/data/logs/modsec_audit.log { + create 0644 root root + daily + rotate 14 + missingok + notifempty + compress + maxsize 500M + minsize 500M + sharedscripts + postrotate + /bin/kill -USR1 `cat /run/nginx.pid 2>/dev/null` 2>/dev/null || true + endscript +} + diff --git a/docker/rootfs/etc/nginx/conf.d/default.conf b/docker/rootfs/etc/nginx/conf.d/default.conf index 37d316db..80d2b16f 100644 --- a/docker/rootfs/etc/nginx/conf.d/default.conf +++ b/docker/rootfs/etc/nginx/conf.d/default.conf @@ -3,6 +3,9 @@ server { listen 80; listen [::]:80; + # + # + set $forward_scheme "http"; set $server "127.0.0.1"; set $port "80"; @@ -25,6 +28,10 @@ server { listen 443 ssl; listen [::]:443 ssl; + # + # + + set $forward_scheme "https"; set $server "127.0.0.1"; set $port "443"; diff --git a/docker/rootfs/etc/nginx/conf.d/production.conf b/docker/rootfs/etc/nginx/conf.d/production.conf index 49db676c..84bb720c 100644 --- a/docker/rootfs/etc/nginx/conf.d/production.conf +++ b/docker/rootfs/etc/nginx/conf.d/production.conf @@ -8,6 +8,8 @@ server { # Replaced with /dev/null by default unless ADMIN_PANEL_LOG is set to '1' access_log ; error_log ; + # + # location /api { return 302 /api/; diff --git a/scripts/buildx b/scripts/buildx index 4da6c167..985e9dac 100755 --- a/scripts/buildx +++ b/scripts/buildx @@ -3,7 +3,7 @@ DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" . "$DIR/.common.sh" -echo -e "${BLUE}❯ ${CYAN}Building docker multiarch: ${YELLOW}${*}${RESET}" +echo -e "${BLUE}❯ ${CYAN}Building docker multi-arch: ${YELLOW}${*}${RESET}" DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" cd "${DIR}/.." || exit 1 @@ -27,10 +27,10 @@ docker buildx build \ --progress plain \ --pull \ -f docker/Dockerfile \ - $@ \ + "$@" \ . rc=$? docker buildx rm "${BUILDX_NAME:-npm}" -echo -e "${BLUE}❯ ${GREEN}Multiarch build Complete${RESET}" +echo -e "${BLUE}❯ ${GREEN}Multi-arch build Complete${RESET}" exit $rc diff --git a/scripts/frontend-build b/scripts/frontend-build index 0e12cf06..55b5245f 100755 --- a/scripts/frontend-build +++ b/scripts/frontend-build @@ -3,7 +3,7 @@ DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)" . "$DIR/.common.sh" -DOCKER_IMAGE=nginxproxymanager/nginx-full:certbot-node +DOCKER_IMAGE=baudneo/nginx-full:certbot-node # Ensure docker exists if hash docker 2>/dev/null; then