# WordPress login URL: how to find it, and how to protect it with 2FA and rate limits

> The WordPress login URL is yoursite.com/wp-login.php, and /wp-admin/ takes you there too. Here is how to find it on any install, why bots hammer it, and how to protect it with two-factor login and rate limits.

Updated 2026-09-26 · WordPress & WooCommerce · HTML version: https://getreport.app/guides/wordpress-login-security

The WordPress login URL is your site address followed by `/wp-login.php`, for example `https://example.com/wp-login.php`. Opening `https://example.com/wp-admin/` while logged out sends you to the same page. If WordPress lives in a subfolder, add the folder: `https://example.com/blog/wp-login.php`. This guide shows how to find the login on any install, how to get back in when a plugin has moved it, and then how to protect it, because the same address is the most attacked page on every WordPress site. It is part of the [WordPress security checklist](https://getreport.app/guides/wordpress-security-basics-without-a-plugin), where login security is step 2.

## Quick answer

- **Log in at** `/wp-login.php` or `/wp-admin/`. With pretty permalinks on, `/login`, `/admin` and `/dashboard` redirect there too.
- **Login moved by a plugin and forgotten?** Rename that plugin's folder over SFTP and the default address works again.
- **Turn on two-factor login (2FA)** for every administrator and editor. WordPress core has none, so this needs a plugin.
- **Limit login attempts** at the CDN or web server; a plugin is the fallback. Cover `xmlrpc.php` too.
- **Use unique generated passwords** and no user called "admin".
- **Hiding the login URL is not protection.** It cuts log noise, nothing more.

## What is my WordPress login URL?

WordPress answers on these addresses out of the box:

| Address | What it does |
| --- | --- |
| `/wp-login.php` | The login form itself |
| `/wp-admin/` | The dashboard; redirects to the login form when you are logged out |
| `/login`, `/admin`, `/dashboard` | Redirect to the login form or the dashboard, when pretty permalinks are on and no page uses that address |
| `/wp-login.php?action=lostpassword` | The "Lost your password?" form |

The short addresses come from a core function that only redirects when the request would otherwise be a 404. If you have a page with the slug `login`, the page wins and no redirect happens.

### When the address is different

- **WordPress in a subfolder.** If the site address is `example.com` but WordPress was installed in `/wp/`, the login is `example.com/wp/wp-login.php`. The WordPress Address under Settings → General shows where the core files are.
- **Multisite.** Every subsite has its own login at its own path, such as `example.com/shop/wp-login.php`; a network administrator can log in on any of them.
- **A hosted service.** On WordPress.com and some managed platforms you log in through the platform's own login page; the host's documentation has the address.
- **A security plugin moved it.** Plugins that rename the login page make `/wp-login.php` return a 404 or redirect elsewhere. The new address is in the plugin's settings.

### Locked out of a moved login page

If you cannot remember the custom address and cannot reach the settings, disable the plugin from the file system:

1. Connect with SFTP or your host's file manager.
2. Open `wp-content/plugins/` and rename the plugin's folder, for example `wps-hide-login` to `wps-hide-login-off`.
3. Open `/wp-login.php`. WordPress deactivates a plugin whose folder is missing, so the default login works again.
4. Log in, rename the folder back, reactivate the plugin and write the address down in your password manager.

With WP-CLI you can do the same in one command: `wp plugin deactivate plugin-folder-name`.

## Why bots attack the WordPress login

A WordPress site is recognisable in seconds, and every one has its login at the same address. That makes brute-force attacks cheap: scripts try common and leaked passwords against `wp-login.php`, and against `xmlrpc.php`, which accepts logins too, on millions of sites. They do not need to succeed often.

A WordPress brute force attack is dangerous in two ways. The obvious one is a guessed password. The less obvious one is load: every attempt starts PHP and checks the database, so a steady stream of guesses slows the whole site on small hosting. Two-factor login makes a guessed password worthless; rate limits remove the load.

Attackers try usernames they can discover. `/?author=1` redirecting to `/author/admin/` confirms a login name, and the REST API's users endpoint lists the slugs of users who have published posts. [The "admin" user and author archives](https://getreport.app/guides/wordpress-admin-user-and-author-archives) shows how to remove that head start.

## How to set up WordPress 2FA

Two-factor login asks for a second proof after the password, usually a six-digit code from an authenticator app on your phone. A stolen or guessed password is then not enough to log in.

WordPress core has no built-in two-factor login, so you need a plugin:

- **The Two Factor plugin** on wordpress.org is maintained by WordPress core contributors and does only this job. It supports authenticator apps (time-based one-time passwords), codes sent by email and one-time backup codes.
- **Security suites** usually include 2FA as one feature among many. If you already run one, use its 2FA rather than adding a second plugin; [what WordPress security plugins do](https://getreport.app/guides/best-wordpress-security-plugins) explains how the jobs overlap.
- **Single sign-on.** Teams that already use Google Workspace or Microsoft 365 can log in to WordPress through them with an SSO plugin, and enforce 2FA there.

Setting it up with the Two Factor plugin:

1. Install and activate it from Plugins → Add New.
2. Go to Users → Profile. Under Two-Factor Options, tick Authenticator App and scan the QR code with an app such as Google Authenticator, Microsoft Authenticator or a password manager that stores one-time codes.
3. Enter the current code to confirm, then generate backup codes and store them in your password manager.
4. Set the authenticator app as your primary method and save.
5. Repeat for every administrator and editor. Log out and in once to test before you close the session.

Prefer an authenticator app over email codes. If someone controls your mailbox, email codes protect nothing, and the password-reset link goes to the same mailbox.

> **Note:**
> Application passwords (Users → Profile → Application Passwords) are meant for apps and scripts that use the REST API. They skip the two-factor step by design. Create one per app, name it after the app and revoke it when you stop using the app.

## How to limit login attempts in WordPress

Core does not limit failed logins. Put the limit where a blocked request costs the least: in front of WordPress, not inside it.

### At the CDN

On Cloudflare, a custom WAF rule in Security → WAF → Custom rules can show a Managed Challenge on the login to everyone except your own addresses:

```text
(http.request.uri.path eq "/wp-login.php" and not ip.src in {203.0.113.10})
```

Replace the example address with your office or home IP, or leave that part out. A rate limiting rule on `POST` requests to `/wp-login.php` and `/xmlrpc.php` is the other option; the periods and thresholds available depend on your Cloudflare plan. [Rate limiting and bot protection on a small site](https://getreport.app/guides/rate-limiting-and-bot-protection-on-a-small-site) has the rule set and the traps to avoid.

### At the web server

On nginx, `limit_req` slows every client to a few login attempts per minute:

```nginx
# http block (nginx.conf): 6 login requests per minute per IP address
limit_req_zone $binary_remote_addr zone=wplogin:10m rate=6r/m;

# server block: the login location needs its own PHP handling
location = /wp-login.php {
    limit_req zone=wplogin burst=3 nodelay;
    limit_req_status 429;
    include fastcgi_params;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    fastcgi_pass unix:/run/php/php8.3-fpm.sock;   # use your PHP-FPM socket
}
```

Copy the `fastcgi_pass` line from your existing `location ~ \.php$` block so the socket matches. Behind a CDN, make sure nginx sees the visitor's real IP (the `real_ip` module), or every visitor shares the CDN's address and the limit. On Apache hosts without that access, fail2ban with a WordPress filter does a similar job from the logs.

### With a plugin

When you control neither the CDN nor the server, a small plugin that only limits login attempts is enough; it counts failures in the database and blocks an IP after a few of them. It does not remove the load, because every attempt still runs PHP. Check that it also covers XML-RPC logins, or block XML-RPC as described in [xmlrpc.php: what it is and how to disable it](https://getreport.app/guides/xmlrpc-php).

## Should you hide or rename the login URL?

Renaming `/wp-login.php` to a secret address stops the dumbest bots and makes your logs quieter. It is not a lock: the address can leak through redirects, plugin links or a browser extension, and it does nothing against a leaked password. It also causes lockouts when someone forgets the new address, as the section above shows.

Use it as noise reduction after 2FA and rate limits are in place, never instead of them. The same goes for CAPTCHA on the login form: it slows bots, but real protection is a second factor.

## Other login settings worth changing

- **Force HTTPS for the admin.** Add `define('FORCE_SSL_ADMIN', true);` to `wp-config.php` so passwords and cookies never travel over plain HTTP.
- **Log out old sessions.** Users → Profile → "Log Out Everywhere Else" ends every other session for that account, for example after using a shared computer.
- **Lock staging copies.** A public staging site has the same users and often weaker settings. Put it behind HTTP authentication.
- **Keep one account per person** and delete accounts when people leave, as in the [checklist](https://getreport.app/guides/wordpress-security-basics-without-a-plugin).

## What getReport checks

Nobody outside the site can see whether 2FA or a rate limit is switched on, and the [WordPress security scan](https://getreport.app/tools/wordpress-checker) never tries to log in. It checks what an attacker can learn before the first attempt:

> **Free tool:** [WordPress security scan and health check](https://getreport.app/tools/wordpress-checker): Free WordPress security scan and health check from the outside: outdated core, closed plugins, exposed files, blocked indexing and classic launch mistakes.

> **Check: No default admin author exposed.** /?author=1 redirects to /author/admin/, which confirms a login name called "admin" exists. Brute-force scripts try that name first.
>
> 1. Create a new administrator with a unique username, log in as it, delete "admin" and attribute its content to the new user.
> 2. Optionally disable author archives or the ?author= redirect in your security plugin.

> **Check: No public staging copy found.** A staging or dev copy that Google can index competes with the live site for its own content and often runs older, unpatched code. Anyone can find it.
>
> 1. Put the staging site behind HTTP authentication or an IP allow-list, or delete it when the launch is done.
> 2. At minimum switch on "Discourage search engines" there and add a noindex X-Robots-Tag header.

> **Check: The site is served over HTTPS.** Browsers label HTTP pages "Not secure" and Google uses HTTPS as a small ranking signal. Anyone on the network can read or alter what visitors see.
>
> 1. Get a certificate (Let's Encrypt is free) and enable HTTPS on your host.
> 2. Redirect every http:// URL to https:// with a 301.

A check for user enumeration through the REST API's users endpoint is planned. Like the other sensitive WordPress checks, it will show a plain yes or no to anyone who runs the report, and the usernames only to the site's verified owner.

## Common mistakes

- **Adding 2FA for yourself only.** Every administrator and editor is a way in. Enforce it for all of them.
- **Email as the only second factor.** A compromised mailbox gets both the reset link and the code. Use an authenticator app.
- **Rate-limiting `wp-login.php` but not `xmlrpc.php`.** Bots switch to XML-RPC. Cover both, or block XML-RPC.
- **Limiting by IP behind a CDN without real-IP setup.** Every visitor seems to come from the CDN, so one bot locks everyone out. Configure the real client IP first.
- **Renaming the login and calling it done.** A hidden login with `admin` / `Summer2024!` is still one leaked password away. 2FA first.

## Questions people ask

### How do I find my WordPress login page?

Add `/wp-login.php` to your site address, for example `https://example.com/wp-login.php`, or open `/wp-admin/`, which redirects to the login when you are logged out. If WordPress is installed in a subfolder, include the folder. If both return a 404, a security plugin has probably moved the login; the new address is in its settings, or rename its folder over SFTP to restore the default.

### Why does wp-admin redirect me back to the login page?

Usually because the login cookie is not being kept. Common causes are a site address and WordPress address that differ (www against non-www, or http against https) under Settings → General, a caching plugin or CDN caching the login page, or browser cookies being blocked. Make both addresses identical, exclude `wp-login.php` and `/wp-admin/` from every cache, and clear your cookies.

### Does WordPress have built-in two-factor authentication?

No. WordPress core has no built-in two-factor login, so self-hosted sites need a plugin. The Two Factor plugin on wordpress.org is maintained by core contributors and supports authenticator apps, email codes and backup codes; most security suites include 2FA too. Turn it on for every administrator and editor, and prefer an authenticator app over email codes.

### How many login attempts should WordPress allow?

A handful per minute from one IP address is plenty for real people. Around 5 failed attempts before a block of 10 to 20 minutes is a common starting point, applied at the CDN or web server so blocked requests never reach PHP. Make sure the limit uses the visitor's real IP behind a CDN, and apply it to `xmlrpc.php` as well.

### Does changing the WordPress login URL improve security?

Only a little. A renamed login stops the simplest bots and makes logs quieter, but the address can leak, and it does nothing against a stolen or reused password. It also locks owners out when they forget the new address. Two-factor login and a rate limit at the CDN or server protect far more; add a renamed login only on top of them.
