Suricata + Reverse Proxy (HTTPD/Apache)

Hi,

I am having issues with suricata and httpd as a reverse proxy, i’ve noticed that it does not seem to alert anything to my supprise so I start searching and came on a feature that’s called xff.

I have tried to implement this but I am not sure what I am doing wrong.

this is the nftables rules (i’ve cleaned up other rules for illustration):

	chain input {
		type filter hook input priority 0; policy drop;
		ct state established,related accept
		iifname "lo" queue to 0
		tcp dport { 80, 443 } queue to 0
	}

I’ve also tried to put it in the prerouting with priority -100, but that does not seem to change anything.

An example of the vhost file I am using:

<VirtualHost *:80>
	ServerName example.com
	ServerSignature Off
	
	RewriteEngine on
	RewriteCond %{HTTPS} !=on
	RewriteRule .* https://%{SERVER_NAME}%{REQUEST_URI} [NE,R,L]
</VirtualHost>

<VirtualHost *:443>
	ServerName example.com
	ServerSignature Off
	
	SSLEngine On
	SSLCertificateFile /etc/letsencrypt/live/example.com/fullchain.pem
	SSLCertificateKeyFile /etc/letsencrypt/live/example.com/privkey.pem
	Include /etc/letsencrypt/options-ssl-apache.conf
	
	ProxyPreserveHost On
	ProxyRequests Off
	ProxyPass / http://172.16.1.248/
	ProxyPassReverse / http://172.16.1.248/
	
    Header always set X-Forwarded-Proto https
    Header always append X-Forwarded-For %{REMOTE_ADDR}s
    RemoteIPHeader X-Forwarded-For
	
    ErrorLog /var/log/httpd/example.com-error.log

    LogFormat "%{X-Forwarded-For}i %l %u %t \"%r\" %>s %b" combined
    CustomLog /var/log/httpd/example.com-access.log combined
</VirtualHost>

I have tried multiple things with header, X-Forwarded-For, … as you can see
I’ve also changed settings in suricata.yaml for xff on 2 places, like extra-data, overwrite, …

The above is from a vhost file on the reverse proxy itself where suricata is running, the actual server also has multiple vhost files.

I need some guidance on this one :slight_smile:

Grts,
Steven

For anyone interested in this:

I’m using a combination of nftables (with NFQUEUE) and Suricata. Initially, I encountered issues where Suricata wasn’t detecting my HTTP/HTTPS traffic.

It turned out the solution was quite simple, I discovered that the way the ruleset is configured is crucial for ensuring proper traffic inspection.

My current working configuration:

include "/etc/nftables/variables.conf"

table ip filter {
	set blocked_countries {
		type ipv4_addr
		flags interval
	}
	
	chain prerouting {
		type nat hook prerouting priority -100; policy accept;
		iifname $WAN tcp dport 18443 dnat to $QBITTORRENT:18443
		iifname $WAN tcp dport 8888 dnat to $MYSQL:3306
		ip saddr $BRABEN-OVPN-USER2 ip daddr $MYSQL tcp dport 8888 dnat to $MYSQL:3306
		queue num 0 bypass
	}
	
	chain input {
		type filter hook input priority 0; policy drop;
		tcp dport { 80, 443 } queue num 0 bypass
		tcp sport { 80, 443 } queue num 0 bypass
		ct state established,related accept
		iifname "lo" queue num 0
		ip saddr @blocked_countries drop
		ip saddr $LAN-SUBNET tcp dport 53 accept
		ip saddr $LAN-SUBNET udp dport 53 accept
		ip saddr $VPN-SUBNET tcp dport 53 accept
		ip saddr $VPN-SUBNET udp dport 53 accept
		ip saddr $COMPANY-WAN tcp dport 22 accept
		ip saddr $BRABEN-OVPN-USER1 tcp dport 22 accept
		iifname $LAN tcp dport 22 accept
		iifname $LAN udp dport 68 accept
		iifname $LAN udp sport 67 udp dport 68 accept
		udp dport 1194 accept
	}

	chain forward {
		type filter hook forward priority 10; policy drop;
		ip saddr @blocked_countries drop
		ip daddr @blocked_countries drop
	
		# queue everything to Suricata
		queue num 0 bypass
	}
	
	chain postrouting {
		type nat hook postrouting priority 0; policy accept;
		oifname $WAN ct state established,related,new masquerade
	}

	chain output {
		type filter hook output priority 0; policy accept;
		ip daddr @blocked_countries drop
#		ip protocol tcp queue num 0 bypass
		tcp dport {80, 443} queue num 0 bypass
		tcp sport {80, 443} queue num 0 bypass
	}
}

I believe this configuration has potential for improvement, but I’m still in the process of testing and learning.

Currently, the issue is resolved, as Suricata is now successfully detecting traffic to and from the reverse proxy.

If I understand correctly, when someone connects to my WAN IP or via an FQDN defined in a virtual host file, the TLS handshake is managed by the reverse proxy. After that, the traffic is sent unencrypted to the backend web server within the same network. My plan is to enable encryption for this internal traffic by generating certificates and configuring TLS between the reverse proxy and the backend servers.

Regards,
Steven