This is an old revision of the document!
−Table of Contents
fail2ban examples
Port 80 ban
Create new jail file in /etc/fail2ban/jail.d/test.local
[bottest] enabled = true maxretry = 4 findtime = 60s bantime = 60s action = iptables[name=bloKKKED, port=http] logpath = %(nginx_access_log)s
This will create a bottest
jail and will use a filter defined in /etc/fail2ban/filter.d/bottest.local. Example of regex matching nginx log:
[Definition] failregex = client=<HOST> .* ignoreregex = datepattern = {^LN-BEG}
<HOST> is mandatory and has to match the IP address. Adapt regex to your logging format and lines you need to match.
action is defined already in /etc/fail2ban/action.d/iptables.conf, and logpath is defined in /etc/fail2ban/paths-common.conf
Restart fail2ban:
systemctl restart fail2ban.service
This will now ban http request for 60 seconds from any client if it tries to access the site on port 80 more than 4 times within 60s. It will create a new iptables chain named f2b-bloKKKED. Truncated iptables -nvL
output:
Chain INPUT (policy ACCEPT 0 packets, 0 bytes) pkts bytes target prot opt in out source destination 73 66036 f2b-bloKKKED tcp -- * * 0.0.0.0/0 0.0.0.0/0 tcp dpt:80 ... Chain f2b-bloKKKED (1 references) pkts bytes target prot opt in out source destination 4 5864 REJECT all -- * * 10.21.21.1 0.0.0.0/0 reject-with icmp-port-unreachable 35 17374 RETURN all -- * * 0.0.0.0/0 0.0.0.0/0
If you are using shorewall the above chain will be deleted on shorewall restart. Consider using the shorewall action instead of iptables then.
Use fail2ban-regex
to check if its matching the regex. Here is an example of match
$ fail2ban-regex /var/log/nginx/access.log bottest.local Running tests ============= Use failregex filter file : bottest, basedir: /etc/fail2ban Use datepattern : {^LN-BEG} : Default Detectors Use log file : /var/log/nginx/access.log Use encoding : UTF-8 Results ======= Failregex: 42 total |- #) [# of hits] regular expression | 1) [42] client=<HOST> .* `- Ignoreregex: 0 total Date template hits: |- [# of hits] date format | [42] {^LN-BEG}Day(?P<_sep>[-/])MON(?P=_sep)ExYear[ :]?24hour:Minute:Second(?:\.Microseconds)?(?: Zone offset)? `- Lines: 42 lines, 0 ignored, 42 matched, 0 missed [processed in 0.00 sec]
nginx access.log
"08/Nov/2022:15:36:30 +0100" client=10.21.21.1 method=GET request="GET / HTTP/1.1" request_length=1414 status=304 bytes_sent=180 body_bytes_sent=0 referer=- user_agent=Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:106.0) Gecko/20100101 Firefox/106.0 upstream_addr=- upstream_status=- request_time=0.000 upstream_response_time=- upstream_connect_time=- upstream_header_time=- upstream_cache_status=- "08/Nov/2022:15:37:35 +0100" client=10.21.21.1 method=GET request="GET / HTTP/1.1" request_length=1414 status=304 bytes_sent=180 body_bytes_sent=0 referer=- user_agent=Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:106.0) Gecko/20100101 Firefox/106.0 upstream_addr=- upstream_status=- request_time=0.000 upstream_response_time=- upstream_connect_time=- upstream_header_time=- upstream_cache_status=-
Troubleshooting
You can check the logfile of fail2ban in /var/log/fail2ban.log. To get a detailed log ouput restart the fail2ban with this command
fail2ban-client --loglevel DEBUG start
then check the log file again.
Timezone issue
If you have a warning similar to
2022-12-27 11:11:57,573 fail2ban.filter [17192]: WARNING [bottest] Simulate NOW in operation since found time has too large deviation None ~ 1672135917.573329 +/- 60 2022-12-27 11:11:57,573 fail2ban.filter [17192]: WARNING [bottest] Please check jail has possibly a timezone issue. Line with odd timestamp: 10.21.21.1 - - [27/Dec/2022:11:11:57 +0100] "GET / HTTP/1.1" 304 0 "-" "Mozilla/5.0 (X11; Ubuntu; Linux x86_64; rv:108.0) Gecko/20100101 Firefox/108.0"
check your filter's dateformat line it could be incorrectly matching the log lines.
Tested on
- fail2ban 0.11.2
- Debian 11 Bullseye