Sindbad~EG File Manager

Current Path : /opt/nginxhttpd_/etc/openresty_config/
Upload File :
Current File : //opt/nginxhttpd_/etc/openresty_config/main_vhost.conf

server {
    listen 80 reuseport;

    set $rateLimitedOrigin '';

    # This directive allow the process of errors > HTTP 300
    # In our case, we'll retry the proxy_pass
    proxy_intercept_errors on;
    # This directive allow us to do mulitple fallback (chained)
    recursive_error_pages on;

    ###
    # Check the response of the JS-Challenge
    ###
    location ^~ /o2s-cgi/ {
        #lua_code_cache off;
        limit_req zone=o2sapi burst=2;
        lua_need_request_body on;
        access_by_lua_file 'conf/lua/api_entrypoint.lua';
    }

    ###
    ## Exception for LetsEncrypt
    ###
    location ~ ^/.well-known/acme-challenge/[a-zA-Z0-9_-]+$ {
        error_page 588 = @origin;
        return 588;
    }

    ###
    # One of the first Lua code executed, it will retrieve the configuration from Redis, both the Vhost configuration
    # and the configuration for the Waf. It will return a different HTTP code, that will be intercepted and passed to
    # differents @origin based on the waf configuration detected.
    # @return 588 => @origin meaning no waf & security
    # @return 589 => @defaultSecurity meaning the default o2switch rules, the customer dont have a personnalized waf
    # @return 590 => @customSecurity the customer ask for custom rules
    ###
    location / {
        #lua_code_cache off; # TODO : REMOVE ON PROD !
        # Mandatory security rules, like the abuse host. Early block.
        if ($abusehost) { return 451; }
        if ($abuseuri) { return 451; }
        if ($host ~ '^(cpanel|webmail|autoconfig|autodiscover|cpcalendars|cpcontacts|webdisk)\.') {
            error_page 588 = @origin;
            return 588;
        }
        include custom_security/999-variables-def.conf;
        access_by_lua_file 'conf/lua/waf_manager.lua';
        error_page 588 = @origin;
        error_page 589 = @defaultSecurity;
        error_page 590 = @customSecurity;
        error_page 403 451 500 501 502 503 /custom_error.html;
    }

    ###
    # Execute the custom WAF rules and return HTTP code based on the WAF decision and action.
    # @return 418 => OK, passed to the @origin.
    # @return 571 => RateLimit at 5 req/s @rateLimitedOrigin5
    # @return 572 => RateLimit at 20 req/s @rateLimitedOrigin20
    # @return 573 => RateLimit at 40 req/s @rateLimitedOrigin40
    ###
    location @customSecurity {
        #lua_code_cache off; # TODO : REMOVE ON PROD !
        include custom_security/*.inc;
        error_page 418 = @origin;
        error_page 571 = @rateLimitedOrigin5;
        error_page 572 = @rateLimitedOrigin20;
        error_page 573 = @rateLimitedOrigin40;
        error_page 403 429 /custom_error.html;
        if ($challengetype = 0) {
            error_page 418 = @origin;
            return 418;
        }
        access_by_lua_file 'conf/lua/waf_challenge.lua';
    }

    ###
    # Default security (+waf)
    ###
    location @defaultSecurity {
        #lua_code_cache off; # TODO : REMOVE ON PROD !
        include custom_security/*.inc;
        include security.inc;
        error_page 418 = @origin;
        error_page 571 = @rateLimitedOrigin5;
        error_page 572 = @rateLimitedOrigin20;
        error_page 573 = @rateLimitedOrigin40;
        error_page 403 429 /custom_error.html; 

        if ($challengetype = 0) {
            error_page 418 = @origin;
            return 418;
        }

        access_by_lua_file 'conf/lua/waf_challenge.lua';
    }

    ###
    # Rate limited @origin, 5, 20 and 40 req / s
    # We must have multiple @location because the limit_req cant be put inside a "if"
    ###
    location @rateLimitedOrigin5 {
        error_page 429 /custom_error.html;
        limit_req zone=rateLimitedOrigin5 nodelay burst=2;
        proxy_intercept_errors on; # Error handling
        error_page 502 504 508 = @forwarder.srv;
        include proxy_pass/proxypass_http_default.conf;
    }
    location @rateLimitedOrigin20 {
        error_page 429 /custom_error.html;
        limit_req zone=rateLimitedOrigin20 nodelay burst=5;
        proxy_intercept_errors on; # Error handling
        error_page 502 504 508 = @forwarder.srv;
        include proxy_pass/proxypass_http_default.conf;
    }
    location @rateLimitedOrigin40 {
        error_page 429 /custom_error.html;
        limit_req zone=rateLimitedOrigin40 nodelay burst=10;
        proxy_intercept_errors on; # Error handling
        error_page 502 504 508 = @forwarder.srv;
        include proxy_pass/proxypass_http_default.conf;
    }

    ###
    # Origin : proxy pass to the right server
    ##
    location @origin {
        limit_req zone=globalddos burst=160;
        proxy_intercept_errors on; # Error handling
        # Note : Dont catch the HTTP 503 error here, it's used by maintenance plugin and will display a "no vhost error"
        error_page 502 504 508 = @forwarder.srv;
        include microcache.inc;
        include proxy_pass/proxypass_http_default.conf;
    }

    ###
    # Forwarder server : on the ipxtender, the backup server in case of errors on origin
    ###
    location @forwarder.srv {
        proxy_intercept_errors off;
        include proxy_pass/forwarder_proxy_pass.conf;
        add_header X-Bypassed 2;
    }

    ###
    # Configuration for the custom error page
    ###
    location = /custom_error.html {
        ssi on;
        internal;
        auth_basic off;
        root /etc/nginx/openresty/error_page;
        more_set_headers 'Tiger-Protect-Security: https://faq.o2switch.fr/hebergement-mutualise/tutoriels-cpanel/tiger-protect';
        more_set_headers 'Cache-Control: private, max-age=0, no-store, no-cache, must-revalidate, post-check=0, pre-check=0';
        more_set_headers 'Expires: Thu, 01 Jan 1970 00:00:01 GMT';
        more_set_headers 'Access-Control-Allow-Origin: *';
        if ($securityRule != ''){
            more_set_headers "Blocked-By-Security-Rule: $securityRule";
        }
        #lua_code_cache off;
    }

    # Used for the Nginx status and Netdata
    location /stub_status {
        stub_status;
        # Security: Only allow access from the IP below.
        allow 127.0.0.1;
        allow 109.234.164.18;
        # Deny anyone else
        deny all;
        #lua_code_cache off;
    }
}

server {
    listen 443 ssl http2;
    ###
    # Dynamically fetch the SSL certificate.
    ###
    #lua_code_cache off; # TODO : REMOVE ON PROD !
    ssl_certificate_by_lua_file "conf/lua/ssl_certificate.lua";

    # This directive allow the process of errors > HTTP 300
    # In our case, we'll retry the proxy_pass
    proxy_intercept_errors on;
    # This directive allow us to do mulitple fallback (chained)
    recursive_error_pages on;

    ###
    # Check the response of the JS-Challenge
    ###
    location  ^~ /o2s-cgi/ {
        #lua_code_cache off;
        limit_req zone=o2sapi burst=2;
        lua_need_request_body on;
        access_by_lua_file 'conf/lua/api_entrypoint.lua';
    }

    ###
    ## Exception for LetsEncrypt
    ###
    location ~ ^/.well-known/acme-challenge/[a-zA-Z0-9_-]+$ {
        error_page 588 = @origin;
        return 588;
    }


    ###
    # One of the first Lua code executed, it will retrieve the configuration from Redis, both the Vhost configuration
    # and the configuration for the Waf. It will return a different HTTP code, that will be intercepted and passed to
    # differents @origin based on the waf configuration detected.
    # @return 588 => @origin meaning no waf & security
    # @return 589 => @defaultSecurity meaning the default o2switch rules, the customer dont have a personnalized waf
    # @return 590 => @customSecurity the customer ask for custom rules
    ###
    location / {
        #lua_code_cache off; # TODO : REMOVE ON PROD !
        # Mandatory security rules, like the abuse host. Early block.
        if ($abusehost) { return 451; }
        if ($abuseuri) { return 451; }
        if ($host ~ '^(cpanel|webmail|autoconfig|autodiscover|cpcalendars|cpcontacts|webdisk)\.') {
            error_page 588 = @origin;
            return 588;
        }
        include custom_security/999-variables-def.conf;
        access_by_lua_file 'conf/lua/waf_manager.lua';
        error_page 588 = @origin;
        error_page 589 = @defaultSecurity;
        error_page 590 = @customSecurity;
        error_page 403 451 500 501 502 503 /custom_error.html;
    }

    ###
    # Execute the custom WAF rules and return HTTP code based on the WAF decision and action.
    # @return 418 => OK, passed to the @origin.
    # @return 571 => RateLimit at 5 req/s @rateLimitedOrigin5
    # @return 572 => RateLimit at 20 req/s @rateLimitedOrigin20
    # @return 573 => RateLimit at 40 req/s @rateLimitedOrigin40
    # @return 403 => Display the error page with the detail
    ###
    location @customSecurity {
        #lua_code_cache off; # TODO : REMOVE ON PROD !
        include custom_security/*.inc;
        error_page 418 = @origin;
        error_page 571 = @rateLimitedOrigin5;
        error_page 572 = @rateLimitedOrigin20;
        error_page 573 = @rateLimitedOrigin40;
        error_page 403 429 /custom_error.html;

        if ($challengetype = 0) {
            error_page 418 = @origin;
            return 418;
        }

        access_by_lua_file 'conf/lua/waf_challenge.lua';
    }

    ###
    # Default security, when no waf customization is detected
    ###
    location @defaultSecurity {
        #lua_code_cache off; # TODO : REMOVE ON PROD !
        include security-ssl.inc;
        include custom_security/*.inc;
        error_page 418 = @origin;
        error_page 571 = @rateLimitedOrigin5;
        error_page 572 = @rateLimitedOrigin20;
        error_page 573 = @rateLimitedOrigin40;
        error_page 403 429 /custom_error.html;

        if ($challengetype = 0) {
            error_page 418 = @origin;
            return 418;
        }

        access_by_lua_file 'conf/lua/waf_challenge.lua';
    }

    ###
    # Rate limited @origin, 5, 20 and 40 req / s
    # We must have multiple @location because the limit_req cant be put inside a "if"
    ###
    location @rateLimitedOrigin5 {
        error_page 429 /custom_error.html;
        limit_req zone=rateLimitedOrigin5 nodelay burst=2;
        proxy_intercept_errors on; # Error handling
        error_page 502 504 508 = @forwarder.srv;
        include proxy_pass/proxypass_https_default.conf;
    }
    location @rateLimitedOrigin20 {
        error_page 429 /custom_error.html;
        limit_req zone=rateLimitedOrigin20 nodelay burst=5;
        proxy_intercept_errors on; # Error handling
        error_page 502 504 508 = @forwarder.srv;
        include proxy_pass/proxypass_https_default.conf;
    }
    location @rateLimitedOrigin40 {
        error_page 429 /custom_error.html;
        limit_req zone=rateLimitedOrigin40 nodelay burst=10;
        proxy_intercept_errors on; # Error handling
        error_page 502 504 508 = @forwarder.srv;
        include proxy_pass/proxypass_https_default.conf;
    }

    ###
    # Origin : proxy pass to the right server
    ##
    location @origin {
        limit_req zone=globalddos burst=160;
        proxy_intercept_errors on; # Error handling
        # Note : Dont catch the HTTP 503 error here, it's used by maintenance plugin and will display a "no vhost error"
        error_page 502 504 508 429 = @forwarder.srv;
        include microcache.inc;
        include proxy_pass/proxypass_https_default.conf;
    }

    ###
    # Forwarder server : on the ipxtender, the backup server in case of errors on origin
    ###
    location @forwarder.srv {
        proxy_intercept_errors off;
        include proxy_pass/forwarder_proxy_pass.conf;
        add_header X-Bypassed 2;
    }

    ###
    # Configuration for the custom error pagec 
    ###
    location = /custom_error.html {
        ssi on;
        internal;
        auth_basic off;
        root /etc/nginx/openresty/error_page;
        more_set_headers 'Tiger-Protect-Security: https://faq.o2switch.fr/hebergement-mutualise/tutoriels-cpanel/tiger-protect';
        more_set_headers 'Cache-Control: private, max-age=0, no-store, no-cache, must-revalidate, post-check=0, pre-check=0';
        more_set_headers 'Expires: Thu, 01 Jan 1970 00:00:01 GMT';
        more_set_headers 'Access-Control-Allow-Origin: *';
        if ($securityRule != ''){
            more_set_headers "Blocked-By-Security-Rule: $securityRule";
        }
        #lua_code_cache off;
    }
}

Sindbad File Manager Version 1.0, Coded By Sindbad EG ~ The Terrorists