[wp-trac] [WordPress Trac] #25446: Return HTTP status code 401 upon failed login

WordPress Trac noreply at wordpress.org
Thu Jan 22 15:58:23 UTC 2015

#25446: Return HTTP status code 401 upon failed login
 Reporter:  raoulbhatia             |       Owner:
     Type:  enhancement             |      Status:  new
 Priority:  normal                  |   Milestone:  Awaiting Review
Component:  Login and Registration  |     Version:  3.6
 Severity:  normal                  |  Resolution:
 Keywords:  has-patch               |     Focuses:

Comment (by RavanH):

 Replying to [comment:17 sippis]:
 > Nope. Example Twitter, Facebook, GitHub, Google and BitBucket all
 returns 200. So I'll +1 for staying with 200 because seems that everyone
 else is doing the same, and HTTP response spec lacks decent status code
 for failed web login.
 > But what about adding op-in custom log for this purpose? I'm not so
 familiar with fail2ban, but i think that it can use custom logs.

 Yes, fail2ban (talking about the server service, not a plugin) can monitor
 custom logs. However, it would mean that a generic WordPress rule cannot
 be added to the available fal2ban preset rules. So only those that have
 their own server/VPS could add their own custimized rule and set up
 fail2ban to monitor this extra WP log. Plus, it will mean even more server
 load as fail2ban is not that friendly on CPU usage. A small price to pay
 for added security and not bad for starters but it'd be better if the
 failed login attempts would be recognizable straight in the access logs
 that are already monitored.

 Maybe an entry in the error log instead of a dedicated login log would be
 better? Not very elegant but probably less demanding on server

 Replying to [comment:7 nacin]:
 > Does *anyone* send a non-200 for a failed web login? I can't say I've
 ever noticed this in practice.

 The login flow of sites like Gmail, Facebook, Twitter etc. is the same as
 the current flow in WordPress. Accessing the admin will first do a 302
 temp redirect to a seperate login form page which then responds with 200
 ok status. Subsequent failed attempts reload that same login form page
 which responds each time with a 200 ok. And that's all according to logic.
 The form page loads and responds correctly so it '''should''' return a 200

 That is why I proposed in comment:8 to change the login flow to something
 where a 401 status can be a fitting response on a failed login. A flow
 that no longer redirects to a separate login page (login.php) but instead
 return an 'in-page' login form might work.

 A smaller adaptation of the current flow might suffice too:

 Consider an attacker submits login data to login.php he currently gets a
 200 status and knows this means a failed attempt because on success, the
 response is a 301 (with header Location: /wp-admin/)... the attacker tries
 again and again, filling the access log with status 200 responses. But
 what if one extra step is added? Let's say a submission to login.php
 '''always''' responds with a 301 (either to /wp-admin/ or the back-end
 page that was originally requested) but then depending on the login
 credentials the user gets again a 301 back to the login.php form on failed

 This would mean that a successful login would only generate two 302
 responses. And a legit user that forgot his password will likely try a
 limited amount of times before finally resorting to using the Lost
 Password form so he would create - let's say - max twenty 302 responses
 over a period of 30 to 60 seconds. While a brute force attack would fill
 the logs quickly with hundreds 301 (instead of 200 as it is now) status
 request in just a few seconds. This can then easily be recognized as brute
 force attempts by fail2ban...

 Unless, of course, '''many''' other pages on the domain respond with a
 302. In that case, the risk is blocking legit visitors or search spiders.

Ticket URL: <https://core.trac.wordpress.org/ticket/25446#comment:20>
WordPress Trac <https://core.trac.wordpress.org/>
WordPress publishing platform

More information about the wp-trac mailing list