{"id":7720,"date":"2021-03-12T00:08:56","date_gmt":"2021-03-11T21:08:56","guid":{"rendered":"https:\/\/kifarunix.com\/?p=7720"},"modified":"2024-03-19T19:21:07","modified_gmt":"2024-03-19T16:21:07","slug":"protect-wordpress-against-brute-force-attacks-using-fail2ban","status":"publish","type":"post","link":"https:\/\/kifarunix.com\/protect-wordpress-against-brute-force-attacks-using-fail2ban\/","title":{"rendered":"Protect WordPress Against Brute force Attacks Using Fail2ban"},"content":{"rendered":"
In this tutorial, you will learn about how to protect WordPress against brute force attacks using Fail2ban. Fail2ban<\/a> is a python based intrusion prevention tool that;<\/p>\n\n\n\n monitors log files (e.g. \/var\/log\/auth.log,\/var\/log\/apache\/access.log) and temporarily or persistently bans failure-prone addresses by updating existing firewall rules. Fail2ban allows easy specification of different actions to be taken such as to ban an IP using iptables or hostsdeny rules, or simply to send a notification email.<\/em><\/p>\n\n\n\n By default, it comes with filter expressions for various services (sshd, apache, proftpd, sasl, etc.) but configuration can be easily extended for monitoring any other text file. All filters and actions are given in the config files, thus fail2ban can be adopted to be used with a variety of files and firewalls. Following recommends are listed:<\/em><\/p>\n\n\n\n Are you using WordPress and looking for a professional WordPress website builder? Look no further since Elementor can help you create beautiful pages<\/a>.<\/p>\n\n\n\n As much as there are multiple ways of protecting WordPress logins against brute force attacks such as Restricting Access to WordPress Login Page to Specific IPs with libModSecurity<\/a>, this guide will focus on the use of Fail2ban for that purpose.<\/p>\n\n\n\n To begin with, install Fail2ban on your host system. Installation of Fail2ban varies from one Linux distribution to the other.<\/p>\n\n\n\n If you are on an Ubuntu\/Debian system, simply run the command below to install Fail2ban;<\/p>\n\n\n\n On CentOS and similar distros, run the commands below to install Fail2ban;<\/p>\n\n\n\n First off, you need to know that Fail2ban monitors log files (e.g. \/var\/log\/auth.log,\/var\/log\/apache\/access.log) and temporarily or persistently bans failure-prone addresses by updating existing firewall rules. Fail2ban allows easy specification of different actions to be taken such as to ban an IP using iptables or hostsdeny rules<\/em>…<\/p>\n\n\n\n To effectively ban or block offending IP addresses, Fail2ban uses Fail2ban has four configuration file types:<\/p>\n\n\n\n Note: It is recommended that *.conf files should remain unchanged to ease upgrades. If needed, customizations should be provided in *.local files.<\/em><\/strong><\/p>\n\n\n\n Copy the Next, edit the Some of the parameters we will adjust include;<\/p>\n\n\n\n This basically means, if there will be any suspicious activity like more than 3 failed logins within a duration of one minute, the suspicious host, except localhost and 192.168.57.33, will be banned for one hour.<\/p>\n\n\n\n Once you have defined the default options above, create a jail for wordpress. For example, paste the content below at the bottom of the jail.local file above;<\/p>\n\n\n\n You can adjust all these settings to meet your needs!!<\/strong><\/p>\n\n\n\n Most options above are self explanatory. The filter specifies the name of the filter that we will create to Save and exit the file.<\/p>\n\n\n\n Next you need to create a filter to define a regular expression that filters out the WordPress authentication logs from the specified log file.<\/p>\n\n\n\n Note that, in our case, we use the log file, For every WordPress login attempt, a So while creating our filter, we will use a regex that filters out such kind of log lines from the log file.<\/p>\n\n\n\n Multiple Fail2ban filters are located under, Create a WordPress authentication filter. Pay attention the name of the filter configuration file<\/p>\n\n\n\n That is a sample failregex for our WordPress logins.<\/p>\n\n\n\n Save and exit. You can add more filters that suits your needs.<\/p>\n\n\n\n To verify if your filter can match the pattern in the log files, use Command synopsis.<\/p>\n\n\n\n So to test our WordPress filter;<\/p>\n\n\n\n Sample output showing matched lines;<\/p>\n\n\n\n That confirms that the filter works fine.<\/p>\n\n\n\n Restart Fail2ban service. Note that is started and enabled to run on system boot upon installation.<\/p>\n\n\n\n Checking the status;<\/p>\n\n\n\n Check the enabled jails using You can simulate events of the multiple failed authentications to WordPress to check if any banning can happen.<\/p>\n\n\n\n While tailing the logs and running failed login test;<\/p>\n\n\n\n After the third failed login, my IP is blocked and get such error on browser;<\/p>\n\n\n\n To check the status of the banned IPs, use You can obtain a list of jails using Checking Iptables;<\/p>\n\n\n\n If you want to unban an IP, run the command;<\/p>\n\n\n\n Fail2ban Manual<\/a><\/p>\n\n\n\n Visualize WordPress User Activity Logs on ELK Stack<\/a><\/p>\n\n\n\n Create Scrolling Text Box on WordPress Newspaper Theme<\/a><\/p>\n\n\n\n How to fix WordPress could not establish a secure connection to WordPress.org<\/a><\/p>\n\n\n\n\n
Using Fail2ban to Protect WordPress Against Brute force Attacks<\/h2>\n\n\n\n
Installing Fail2ban<\/h3>\n\n\n\n
apt update<\/code><\/pre>\n\n\n\n
apt install fail2ban<\/code><\/pre>\n\n\n\n
dnf install epel-release<\/code><\/pre>\n\n\n\n
dnf update<\/code><\/pre>\n\n\n\n
dnf install fail2ban<\/code><\/pre>\n\n\n\n
Configure Fail2ban to Protect WordPress Authentications against Brute force attacks<\/h3>\n\n\n\n
jails<\/code><\/strong> which is basically a combination of various
filters<\/code><\/strong> and
actions<\/code><\/strong>.
Fail2ban filters<\/code><\/strong> are just but regular that matches a specific pattern in the respective log file being monitored. The can pattern can correspond to a failed login attempt, request status code, request URI or any other suspicious activity.
Fail2ban actions<\/code><\/strong> on the other hand define commands that are executed when the filter matches a specified pattern such as suspicious IP address.<\/p>\n\n\n\n
Create Fail2ban WordPress Jail<\/h4>\n\n\n\n
\n
fail2ban.conf<\/code><\/strong>: Fail2Ban global configuration (such as logging)<\/li>\n\n\n\n
filter.d\/*.conf<\/code><\/strong>: Filters specifying how to detect authentication failures<\/li>\n\n\n\n
action.d\/*.conf<\/strong><\/code>: Actions defining the commands for banning and unbanning of IP address<\/li>\n\n\n\n
jail.conf<\/strong><\/code>: Jails defining combinations of Filters with Actions.<\/li>\n<\/ul>\n\n\n\n
jail.conf<\/code> file to
jail.local<\/strong><\/code> file;<\/p>\n\n\n\n
cp \/etc\/fail2ban\/jail.{conf,local}<\/code><\/pre>\n\n\n\n
jail.local<\/strong><\/code> file and set the default parameters under the
[DEFAULT]<\/strong><\/code> section.<\/p>\n\n\n\n
vim \/etc\/fail2ban\/jail.local<\/code><\/pre>\n\n\n\n
\n
...\nignoreip = 127.0.0.1\/8 192.168.57.33\n...\nbantime = 3600\n...\nfindtime = 60\n...\nmaxretry = 3<\/code><\/pre>\n\n\n\n
...\n# WordPress Jail\n[wordpress-auths]\nenabled = true\nport = http,https\nfilter = wordpress-auth\nlogpath = \/var\/log\/apache2\/wp.access.log<\/code><\/pre>\n\n\n\n
filter<\/strong><\/code> the logs that identifies the WordPress logins logs in the log file defined by the
logpath<\/code><\/strong>.<\/p>\n\n\n\n
Create Fail2ban WordPress Login Filter<\/h4>\n\n\n\n
\/var\/log\/apache2\/wp.access.log<\/strong><\/code>.<\/p>\n\n\n\n
POST<\/code><\/strong> request is sent to
\/wp-login.php<\/code><\/strong> file with 200 status code and is written to the Web server access log. Below are the sample logs for our logins;<\/p>\n\n\n\n
tail -f \/var\/log\/apache2\/wp.access.log | grep \"POST \/wp-login.php\"<\/code><\/pre>\n\n\n\n
192.168.57.33 - - [11\/Mar\/2021:20:18:15 +0000] \"POST \/wp-login.php HTTP\/1.1\" 200 2825 \"http:\/\/kifarunix-demo.com\/wp-login.php\" \"Mozilla\/5.0 (X11; Linux x86_64; rv:78.0) Gecko\/20100101 Firefox\/78.0\"\n192.168.57.1 - - [11\/Mar\/2021:20:19:14 +0000] \"POST \/wp-login.php HTTP\/1.1\" 200 2815 \"http:\/\/kifarunix-demo.com\/wp-login.php\" \"Mozilla\/5.0 (X11; Linux x86_64) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/89.0.4389.72 Safari\/537.36\"<\/code><\/pre>\n\n\n\n
\/etc\/fail2ban\/filter.d\/<\/strong><\/code>. You can check any of them on how filters can be created.<\/p>\n\n\n\n
vim \/etc\/fail2ban\/filter.d\/wordpress-auth.conf<\/code><\/pre>\n\n\n\n
[Definition]\nfailregex = ^<HOST> .* \"POST \/wp-login.php HTTP.* 200<\/code><\/pre>\n\n\n\n
Test Fail2ban WordPress Filter<\/h4>\n\n\n\n
fail2ban-regex<\/strong><\/code> tool as follows.<\/p>\n\n\n\n
fail2ban-regex [OPTIONS] <LOG> <REGEX> [IGNOREREGEX]<\/code><\/pre>\n\n\n\n
fail2ban-regex \/var\/log\/apache2\/wp.access.log \/etc\/fail2ban\/filter.d\/wordpress-auth.conf<\/code><\/pre>\n\n\n\n
Running tests\n=============\n\nUse failregex filter file : wordpress-auth, basedir: \/etc\/fail2ban\nUse log file : \/var\/log\/apache2\/wp.access.log\nUse encoding : UTF-8\n\n\nResults\n=======\n\nFailregex: 10 total\n|- #) [# of hits] regular expression\n| 1) [10] ^<HOST> .* \"POST \/wp-login.php HTTP.* 200\n`-\n\nIgnoreregex: 0 total\n\nDate template hits:\n|- [# of hits] date format\n| [577] Day(?P<_sep>[-\/])MON(?P=_sep)ExYear[ :]?24hour:Minute:Second(?:\\.Microseconds)?(?: Zone offset)?\n`-\n\nLines: 577 lines, 0 ignored, 10 matched, 567 missed\n[processed in 0.25 sec]\n\nMissed line(s): too many to print. Use --print-all-missed to print all 567 lines<\/code><\/pre>\n\n\n\n
Running Fail2ban<\/h4>\n\n\n\n
systemctl restart fail2ban<\/code><\/pre>\n\n\n\n
systemctl status fail2ban<\/code><\/pre>\n\n\n\n
\u25cf fail2ban.service - Fail2Ban Service\n Loaded: loaded (\/lib\/systemd\/system\/fail2ban.service; enabled; vendor preset: enabled)\n Active: active (running) since Thu 2021-03-11 20:43:32 UTC; 44s ago\n Docs: man:fail2ban(1)\n Process: 5484 ExecStartPre=\/bin\/mkdir -p \/run\/fail2ban (code=exited, status=0\/SUCCESS)\n Main PID: 5486 (f2b\/server)\n Tasks: 7 (limit: 2282)\n Memory: 11.8M\n CGroup: \/system.slice\/fail2ban.service\n \u2514\u25005486 \/usr\/bin\/python3 \/usr\/bin\/fail2ban-server -xf start\n\nMar 11 20:43:32 ubuntu20 systemd[1]: Starting Fail2Ban Service...\nMar 11 20:43:32 ubuntu20 systemd[1]: Started Fail2Ban Service.\nMar 11 20:43:33 ubuntu20 fail2ban-server[5486]: Server ready<\/code><\/pre>\n\n\n\n
Check Enabled Fail2ban Jails<\/h4>\n\n\n\n
fail2ban-client status<\/strong><\/code> command.<\/p>\n\n\n\n
fail2ban-client status<\/code><\/pre>\n\n\n\n
Status\n|- Number of jail:\t2\n`- Jail list:\tsshd, wordpress-auths<\/code><\/pre>\n\n\n\n
Verifying WordPress authentication Protection<\/h3>\n\n\n\n
tail -f \/var\/log\/apache2\/wp.access.log | grep \"POST \/wp-login.php\"<\/code><\/pre>\n\n\n\n
192.168.57.1 - - [11\/Mar\/2021:20:47:59 +0000] \"POST \/wp-login.php HTTP\/1.1\" 200 2825 \"http:\/\/kifarunix-demo.com\/wp-login.php\" \"Mozilla\/5.0 (X11; Linux x86_64) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/89.0.4389.72 Safari\/537.36\"\n192.168.57.1 - - [11\/Mar\/2021:20:48:02 +0000] \"POST \/wp-login.php HTTP\/1.1\" 200 2814 \"http:\/\/kifarunix-demo.com\/wp-login.php\" \"Mozilla\/5.0 (X11; Linux x86_64) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/89.0.4389.72 Safari\/537.36\"\n192.168.57.1 - - [11\/Mar\/2021:20:48:04 +0000] \"POST \/wp-login.php HTTP\/1.1\" 200 2825 \"http:\/\/kifarunix-demo.com\/wp-login.php\" \"Mozilla\/5.0 (X11; Linux x86_64) AppleWebKit\/537.36 (KHTML, like Gecko) Chrome\/89.0.4389.72 Safari\/537.36\"<\/code><\/pre>\n\n\n\n
<\/figure><\/a><\/div>\n\n\n\n
Checking Status of Fail2ban Banned IP<\/h4>\n\n\n\n
fail2ban-client<\/strong><\/code> command;<\/p>\n\n\n\n
fail2ban-client status wordpress-auths<\/code><\/pre>\n\n\n\n
Status for the jail: wordpress-auths\n|- Filter\n| |- Currently failed:\t0\n| |- Total failed:\t3\n| `- File list:\t\/var\/log\/apache2\/wp.access.log\n`- Actions\n |- Currently banned:\t1\n |- Total banned:\t1\n `- Banned IP list:\t192.168.57.10<\/code><\/pre>\n\n\n\n
fail2ban-client status<\/strong><\/code> command.<\/p>\n\n\n\n
iptables -L -nv<\/code><\/pre>\n\n\n\n
...\nChain f2b-wordpress-auths (1 references)\n pkts bytes target prot opt in out source destination \n 21 9078 REJECT all -- * * 192.168.57.1 0.0.0.0\/0 reject-with icmp-port-unreachable\n 0 0 RETURN all -- * * 0.0.0.0\/0 0.0.0.0\/0<\/code><\/pre>\n\n\n\n
Unbanning Fail2ban Banned IP<\/h4>\n\n\n\n
fail2ban-client set <jail> unbanip <IP><\/code><\/pre>\n\n\n\n
fail2ban-client set wordpress-auths unbanip 192.168.57.1<\/code><\/pre>\n\n\n\n
Further Reading<\/h4>\n\n\n\n
Other Tutorials<\/h4>\n\n\n\n