15%

Save 15% on All Hosting Services

Test your skills and get Discount on any hosting plan

Use code:

Skills
Get Started
10.10.2024

How to Enable and Disable xmlrpc.php in WordPress (And Why It Matters)

The xmlrpc.php file is a core WordPress component that exposes an XML-RPC API endpoint, allowing remote applications to authenticate and execute server-side operations — publishing posts, managing comments, triggering pingbacks, and more. Because it accepts unauthenticated POST requests by default and processes them before most security layers activate, it is one of the most frequently abused attack surfaces in any WordPress installation.

If you do not use the WordPress mobile app, Jetpack, or any third-party service that explicitly requires XML-RPC, disabling xmlrpc.php is the correct default security posture. If you do rely on those integrations, you can harden the endpoint rather than remove it entirely.

What Is xmlrpc.php and How Does It Work

XML-RPC (Extensible Markup Language Remote Procedure Call) is a protocol that encodes function calls in XML and transmits them over HTTP. WordPress has shipped a full XML-RPC server since version 3.5, implemented in the xmlrpc.php file located in the WordPress root directory.

When a remote client — a mobile app, a desktop blogging client, or an automation script — sends a POST request to https://yourdomain.com/xmlrpc.php, WordPress parses the XML payload, authenticates the credentials embedded in the request body, and executes the requested method. The entire exchange happens in a single HTTP round-trip, which is both its strength and its fundamental weakness from a security standpoint.

Core XML-RPC Methods Exposed by WordPress

  • wp.newPost / wp.editPost — create and update posts remotely
  • wp.getComments / wp.deleteComment — manage comments
  • wp.uploadFile — upload media to the server
  • pingback.ping — notify a remote site that it has been linked
  • system.multicall — batch multiple method calls into a single HTTP request

The system.multicall method is particularly dangerous. A single HTTP request can bundle hundreds of wp.getUsersBlogs calls, each testing a different password. This allows an attacker to perform thousands of authentication attempts while generating only one server log entry, bypassing rate-limiting tools that count individual requests.

Security Risks of Leaving xmlrpc.php Enabled

Brute Force Amplification via system.multicall

Traditional brute force attacks send one credential pair per HTTP request. With XML-RPC, an attacker wraps 500 login attempts inside a single system.multicall payload. A standard fail2ban rule or login-attempt counter sees one request; the attacker gets 500 guesses. This is not a theoretical risk — it is the most common XML-RPC exploit observed in the wild.

Pingback-Amplified DDoS

WordPress automatically processes incoming pingback requests through xmlrpc.php. An attacker can send a crafted pingback.ping request to thousands of WordPress sites, instructing each one to send an HTTP request to a single victim URL. The victim receives a volumetric flood of requests originating from legitimate WordPress servers, making IP-based blocking ineffective. Your server simultaneously becomes a victim (resource exhaustion) and an unwilling attack amplifier.

SSRF via Pingback

The pingback mechanism can be abused for Server-Side Request Forgery (SSRF). An attacker sends a pingback.ping request where the source URL points to an internal network resource — http://192.168.1.1/admin, for example. The WordPress server fetches that URL from inside the network perimeter, potentially exposing internal services that are not publicly routable.

Credential Exposure in Transit

XML-RPC transmits credentials in the POST body as plain text within the XML envelope. If your site does not enforce HTTPS, credentials are exposed to any network observer. Even with TLS, the credentials are embedded in every single request — there is no session token or OAuth flow to limit the exposure window.

When You Should Keep xmlrpc.php Enabled

Disable it by default, but keep it enabled if your workflow genuinely depends on any of the following:

  • WordPress mobile app (iOS/Android): The official app uses XML-RPC for all site management operations on self-hosted WordPress installations.
  • Jetpack plugin: Several Jetpack modules — including publicize, mobile push notifications, and some stats features — communicate via XML-RPC to WordPress.com servers.
  • Desktop blogging clients: MarsEdit, Windows Live Writer, and similar tools rely exclusively on the XML-RPC API.
  • Automated publishing pipelines: IFTTT, Zapier, and custom scripts that push content to WordPress often use XML-RPC when the REST API is not configured.
  • Pingbacks/trackbacks between WordPress sites: If cross-site pingback notifications are part of your editorial workflow, disabling xmlrpc.php silences them.

If none of these apply, there is no operational reason to leave the endpoint open.

xmlrpc.php vs. the WordPress REST API

WordPress introduced the REST API in version 4.7 as a modern, token-based replacement for XML-RPC. Understanding the differences helps you decide whether disabling XML-RPC breaks anything critical.

Featurexmlrpc.phpWordPress REST API
AuthenticationUsername + password in every requestApplication passwords, OAuth, JWT
TransportHTTP POST onlyHTTP GET, POST, PUT, PATCH, DELETE
Payload formatXMLJSON
IntroducedWordPress 1.5 (2005)WordPress 4.7 (2016)
Brute force riskHigh (system.multicall)Lower (per-request, rate-limitable)
SSRF via pingbackYesNo
Mobile app supportYes (legacy)Yes (current)
Jetpack dependencyPartialPartial
Granular permission scopesNoYes (application passwords)
Recommended for new integrationsNoYes

If you are building a new integration or migrating an existing one, use the REST API. The authentication model is significantly more secure, and the endpoint is far easier to audit and rate-limit at the infrastructure level.

How to Disable xmlrpc.php in WordPress

Choose the method that matches your server access level and risk tolerance. Methods are ordered from lowest to highest server-level enforcement.

Method 1: Disable via Plugin (Quickest, No Server Access Required)

For shared hosting environments or sites where you prefer not to edit server configuration files, a plugin is the most accessible option.

Recommended plugins:

  • Disable XML-RPC-API — single-purpose, minimal footprint, activates instantly
  • All In One WP Security and Firewall — broader security suite with granular XML-RPC controls

Steps for Disable XML-RPC-API:

  1. Navigate to Plugins > Add New in your WordPress dashboard.
  2. Search for "Disable XML-RPC-API" and click Install Now, then Activate.
  3. No further configuration is required — the plugin hooks into xmlrpc_enabled and returns false immediately on activation.

Steps for All In One WP Security and Firewall:

  1. After activating the plugin, go to WP Security > Firewall.
  2. Locate the XML-RPC section.
  3. Enable the option to completely block XML-RPC requests.
  4. Save settings.

Limitation: Plugin-based blocking fires inside the WordPress PHP execution context. The server still boots PHP, loads WordPress, and processes the request before rejecting it. Under a heavy attack, this consumes CPU and memory. For high-traffic sites under active attack, use the .htaccess or Nginx method instead.

Method 2: Disable via .htaccess (Apache — Server-Level Block)

Blocking at the .htaccess level prevents PHP from executing at all for requests targeting xmlrpc.php. This is significantly more efficient under load.

  1. Connect to your server via FTP, SFTP, or your hosting file manager and open the .htaccess file in your WordPress root (typically public_html/.htaccess).
  2. Add the following block. Place it before the standard WordPress rewrite rules:
# Block all access to xmlrpc.php
<Files "xmlrpc.php">
    Order Deny,Allow
    Deny from all
</Files>
  1. Save the file.

To verify the block is active, run a test from your local machine:

curl -s -o /dev/null -w "%{http_code}" -X POST https://yourdomain.com/xmlrpc.php

You should receive a 403 response. A 200 or 405 means the block is not yet in effect.

Edge case — if you still need pingbacks from specific trusted IPs, you can whitelist them:

<Files "xmlrpc.php">
    Order Deny,Allow
    Deny from all
    Allow from 192.0.2.10
</Files>

Method 3: Disable via Nginx Configuration

If your server runs Nginx (common on VPS Hosting environments), .htaccess files have no effect. Add the block directly to your site's server block configuration.

# Block xmlrpc.php at the Nginx level
location = /xmlrpc.php {
    deny all;
    access_log off;
    log_not_found off;
    return 444;
}

The return 444 directive closes the TCP connection without sending an HTTP response, which is more efficient than a 403 because it prevents the attacker's client from receiving any feedback. After editing, reload Nginx:

sudo nginx -t && sudo systemctl reload nginx

Place this location block inside your server {} block, before any try_files or PHP processing directives.

Method 4: Disable via functions.php (WordPress Filter Hook)

This method uses a WordPress filter to disable XML-RPC at the application layer. It is less efficient than server-level blocking but useful when you lack direct server access and want a code-based solution without a plugin dependency.

  1. Go to Appearance > Theme Editor in your WordPress dashboard, or access the file directly via SFTP at wp-content/themes/your-theme/functions.php.
  2. Add the following to the end of the file:
// Disable XML-RPC completely
add_filter( 'xmlrpc_enabled', '__return_false' );
  1. Save the file.

Important caveat: This filter disables authenticated XML-RPC methods, but it does not block the pingback.ping method or prevent the file from being accessed. The server still processes the request up to the point where WordPress evaluates the filter. For complete protection, combine this with the .htaccess or Nginx block.

If you are using a child theme, always add custom code to the child theme's functions.php, not the parent theme. Parent theme updates will overwrite your changes.

Method 5: Selective Disable — Block Pingbacks Only

If you need XML-RPC for Jetpack or mobile publishing but want to eliminate the DDoS amplification vector, you can disable only the pingback method while keeping the rest of the API functional.

// Disable only the pingback method, keep XML-RPC otherwise functional
add_filter( 'xmlrpc_methods', function( $methods ) {
    unset( $methods['pingback.ping'] );
    unset( $methods['pingback.extensions.getPingbacks'] );
    return $methods;
} );

Add this to your child theme's functions.php or a site-specific plugin. This is the recommended configuration for sites that run Jetpack but do not need to receive pingbacks.

How to Re-Enable xmlrpc.php

Reversing any of the above methods restores XML-RPC access:

  • Plugin method: Deactivate or delete the blocking plugin from Plugins > Installed Plugins.
  • .htaccess method: Remove the <Files "xmlrpc.php"> block from .htaccess and save.
  • Nginx method: Remove the location = /xmlrpc.php block from your server configuration and reload Nginx with sudo systemctl reload nginx.
  • functions.php method: Remove the add_filter( 'xmlrpc_enabled', '__return_false' ) line and save.

After re-enabling, verify the endpoint responds correctly:

curl -s -X POST https://yourdomain.com/xmlrpc.php 
  -H "Content-Type: text/xml" 
  --data '<?xml version="1.0"?><methodCall><methodName>system.listMethods</methodName><params></params></methodCall>'

A valid XML response listing available methods confirms the endpoint is active.

Hardening xmlrpc.php Without Disabling It

If disabling is not an option, apply these mitigations to reduce the attack surface:

Enforce HTTPS: Ensure your site uses a valid TLS certificate. If you have not already, configure one through your hosting provider — SSL Certificates prevent credential interception in transit.

Rate-limit at the firewall or CDN level: Configure your WAF (Cloudflare, ModSecurity) to limit POST requests to xmlrpc.php to a maximum of 5–10 per minute per IP.

Block system.multicall specifically:

add_filter( 'xmlrpc_methods', function( $methods ) {
    unset( $methods['system.multicall'] );
    return $methods;
} );

This eliminates the brute force amplification vector while preserving all other XML-RPC functionality.

Restrict by IP: If you only access XML-RPC from known IP addresses (your mobile app's carrier IP range, or a static office IP), whitelist those addresses in .htaccess or Nginx and deny all others.

Monitor access logs: Regularly audit your server logs for repeated POST requests to xmlrpc.php. A spike in 200-status POST requests to this file is a reliable indicator of an ongoing brute force campaign.

On a VPS with cPanel or other managed panel environment, you can configure ModSecurity rules directly from the control panel to enforce these restrictions without manual file editing.

Choosing the Right Method: Decision Matrix

Your SituationRecommended Method
Shared hosting, no server accessPlugin (Disable XML-RPC-API)
Apache server, full file access.htaccess block
Nginx server (VPS/Dedicated)Nginx location block
Need Jetpack but not pingbacksSelective filter in functions.php
Need full XML-RPC (mobile app)Harden with rate limiting + block system.multicall
Under active brute force attackNginx `return 444` + server firewall rule
Managed WordPress on cPanel VPSModSecurity rule via cPanel WAF

For production sites hosted on Dedicated Servers, the Nginx or Apache server-level block is always preferable to a plugin-based solution because it prevents PHP execution entirely for malicious requests, eliminating the CPU overhead that plugin-based blocking incurs under sustained attack.

Practical Key-Takeaway Checklist

  • Audit whether any active plugin or service in your stack actually requires XML-RPC before disabling it — check Jetpack, mobile apps, and any publishing automation tools.
  • If no dependency exists, apply the server-level block (.htaccess or Nginx) rather than a plugin — it is more efficient and survives plugin deactivation.
  • If you must keep XML-RPC active, unconditionally remove system.multicall and pingback.ping via the xmlrpc_methods filter — these two methods account for the vast majority of XML-RPC abuse.
  • Always enforce HTTPS on any WordPress site that accepts authenticated requests, including XML-RPC.
  • After applying any block, verify with curl that the endpoint returns 403 or drops the connection — do not assume the configuration is correct without testing.
  • On Nginx-based VPS or dedicated server environments, use return 444 instead of deny all to avoid giving attackers any HTTP-level feedback.
  • Log and monitor POST requests to xmlrpc.php — a sudden spike is an early warning of a credential-stuffing or DDoS amplification campaign.
  • If you manage multiple WordPress sites, consider centralizing this configuration at the server or CDN level rather than applying per-site plugin rules.

For sites that need robust remote management without the XML-RPC risk surface, migrating integrations to the WordPress REST API with application passwords is the correct long-term path. The REST API provides per-token revocation, scoped permissions, and standard HTTP semantics that are far easier to secure and audit.

If you are setting up a new WordPress environment and want a clean, secure baseline from the start, VPS Control Panels with ModSecurity pre-configured give you server-level WAF protection without requiring manual rule authoring.

Frequently Asked Questions

Does disabling xmlrpc.php break the WordPress REST API?

No. The REST API (/wp-json/) is a completely separate endpoint with its own authentication and routing. Blocking xmlrpc.php has zero effect on REST API functionality. The two systems are architecturally independent.

Will disabling xmlrpc.php break Jetpack?

It depends on which Jetpack modules you use. Jetpack has progressively migrated features to the REST API, but some older modules — including certain publicize and notification features — still communicate via XML-RPC. Check the Jetpack debug page at Jetpack > Dashboard > Debug to see if XML-RPC connectivity is listed as a requirement before disabling it.

Is the .htaccess method or the functions.php method more secure?

The .htaccess method is significantly more secure under attack conditions. It blocks the request at the web server layer before PHP loads, consuming minimal resources. The functions.php filter fires inside WordPress's PHP execution context, meaning the server still bootstraps WordPress for every blocked request — which is expensive under a high-volume attack.

Can an attacker still exploit xmlrpc.php if I only disable it via the WordPress filter?

Partially. The xmlrpc_enabled filter prevents authenticated method calls, but the file remains publicly accessible and the server still processes incoming requests. The pingback endpoint may remain partially functional depending on WordPress version. For complete protection, pair the filter with a server-level block.

How do I check if xmlrpc.php is currently accessible on my site?

Run the following command from your local terminal, replacing the domain with your own:

curl -s -o /dev/null -w "%{http_code}" -X POST https://yourdomain.com/xmlrpc.php

A 200 response means the endpoint is open. A 403 or a connection drop (000) confirms it is blocked. You can also use the online tool at xmlrpc.eritreo.it to test pingback vulnerability specifically.

15%

Save 15% on All Hosting Services

Test your skills and get Discount on any hosting plan

Use code:

Skills
Get Started