WordPress Security with WPScan: Username

WPScan is a popular black box WordPress security scanner. For anyone who is serious about WordPress security but still stuck with a list of to-do tasks, it is highly recommended to check WPScan out, and learn how to implement it into your workflow.

Two very interesting features in the list are username enumeration and brute force attack using password wordlist. While malicious attackers may use tools like this to attack a WordPress site, website owners can certainly utilize the very function to test their site security measures. WPScan can check a list of security vulnerabilities, from theme, plugins, to username & brute force attack.

I won’t spend time on explaining how to setup and use WPScan, as this kind of information can be easily found on its own site (Installation & basic instruction). In this post, I will only focus on one possible WordPress security weakness, the username. Let’s take a look how an improper user account setup could be vulnerable, and how to improve site security accordingly.

The typical user login credentials consist of a username (or user id) and password. Theoretically, if the attacker has any part of the login, the job left out is to guess the other half. This is exactly the very nature of brute force attack, try until success. In most case, it is the user password being tested out against popular password wordlist, which can be easily obtained by a simple search. Most users pay extra attention to protecting the password, not the username.The fact is, securing WordPress login username is almost as important as protecting the password.

Discover Username by Author Query

After default WordPress installation, without specific security enhancement, it is possible and fairly easy to find out a valid WordPress username, (version 4.0 is the current at time of writing), here is how:

http://url/?author=userid

This is a simple author query. Just by replacing userid with different number (starting from 1), we can get the username (not full name). To be specific, what we get is user nickname, not username yet. If a nickname is not provided at time of the user account was created, then username is used as nickname. (Unless there are special characters in username. But almost all usernames ain’t so). This value is stored in database, and can’t be replaced by simply adding / changing “Nickname” or set a new “Display name publicly as”. Unless, you change the database record either manually (e.g., via phpMyAdmin) or by 3rd-party plugin.

wordpress-username-nickname-displayname

Sad fact is, many WordPress site owners don’t pay enough attention to this, don’t know or ignore this part when create a new user account. After rushing into the dashboard, typing in only the required fields, they create a new user in just few seconds. This means, if no further security measures are in position to protect username, it will be displayed publicly.

If the queried user id is valid, return of the author query like this:

http://url/author/nickname/

Discover Username from Author Link

Author query isn’t the only way to discover a username. The author link is another place where hacker can pickup a valid username. Being used widely as a standard function by most themes, the_author_link() returns the author’s Website URL as a link and the text for the link is the author’s Profile Display name publicly as field (displayname).

The displayname is a tricky field. When creating a user, the displayname can be anything from username, to firstname, lastname or first & lastname as long as any field is provided. But don’t mess up displayname with nickname. The nickname is always taken from username unless otherwise specified.

The text returned by the_author_link() can be controlled later on by making change in user profile, the author query return result won’t be changed accordingly. Author query always return user nickname, the user_nicename field in database at time of the user being created.

There are tips can be found here or there, which recommend to:

  • Delete the first user (userid = 1), which is the first user created by WordPress installation. Or
  • Change the default user’s username from “admin” to something else, such as “mysiteadmin” or something totally different, such as “abcxyz”. Or
  • Change the admin userid to something else, such as 999. (This isn’t as easy as a database query)

Well, from what we know so far, none of these methods really work, if there isn’t a different nickname in position, or some protection against author query. Hackers can always find the username sooner or later. Using the WordPress security scanning tool WPScan is one of them.

 

Discover Username using WPScan

Upon installation, we can do a simple scan to enumerate users of a targeted WordPress site. The command is:

$ ruby wpscan.rb –url http://domain.com –enumerate u

This is to ask WPScan to get usernames from id 1 to 10. The result looks like this if usernames can be discovered.

wpscan-usernames-enumeration

Login is user_nicename field from wp_users table, which may not be nickname listed in user profile, but always match the result from author query.

In this scan, I don’t have 100% evidence to consider username of user (id=8) is “admin1” just by looking at the result. But it won’t hurt anyone who wants to carry on a brute force attack using “admin1” as one possibility username.

 

The Conclusion

Security is an ongoing battle for website owners. WordPress is one of the most widely used tools on the Internet, and also becoming the go-to target for outlaws. With the help from security scanning tools like WPScan, it is easier for website owners to implement a targeted security plan.

Security comes from good habit. To stop the possible security leak from username, we simply need to provide complete information in user profile when create a new (admin) user, a friendly nickname without giving out the real username.

In case an admin user is created without giving a nickname other than username, we can make a manual change in database using phpMyAdmin.