Sign In
Access your IPWhois.net account
No account? Create one
WordPress Integration
Block blacklisted IPs from accessing wp-login.php, wp-admin, and xmlrpc.php. Stops brute-force attacks before WordPress even loads.
3 min setup MU-Plugin Cached lookups
Blacklist / Docs / WordPress
Installation

This integration uses a must-use plugin (mu-plugin) that loads automatically without activation. Create the file at wp-content/mu-plugins/ipwhois-guard.php:

wp-content/mu-plugins/ipwhois-guard.php
<?php /** * Plugin Name: IPWhois Blacklist Guard * Description: Blocks blacklisted IPs on login and admin pages * Version: 1.0 * Author: IPWhois.net */ // Check IP against IPWhois Blacklist with transient cache function ipwhois_is_blocked($ip, $min_confidence = 70) { $key = 'ipwhois_' . md5($ip); $cached = get_transient($key); if ($cached !== false) { return $cached === 'blocked'; } $response = wp_remote_get( "https://bl.ipwhois.net/api/check?ip=" . urlencode($ip), ['timeout' => 3, 'sslverify' => true] ); if (is_wp_error($response)) { // Fail open: don't block if API is unreachable set_transient($key, 'ok', 300); // Cache for 5 min on error return false; } $data = json_decode(wp_remote_retrieve_body($response), true); $blocked = !empty($data['listed']) && ($data['confidence'] ?? 0) >= $min_confidence; set_transient($key, $blocked ? 'blocked' : 'ok', HOUR_IN_SECONDS); return $blocked; } // Block on login page add_action('login_init', function() { $ip = $_SERVER['REMOTE_ADDR']; if (ipwhois_is_blocked($ip)) { status_header(403); wp_die( 'Access denied. Your IP address has been flagged for malicious activity.', 'Forbidden', ['response' => 403, 'back_link' => false] ); } }); // Block on xmlrpc.php add_action('xmlrpc_call', function() { $ip = $_SERVER['REMOTE_ADDR']; if (ipwhois_is_blocked($ip)) { status_header(403); exit('Forbidden'); } }); // Optional: block on all admin pages add_action('admin_init', function() { // Skip for AJAX requests to avoid breaking admin features if (defined('DOING_AJAX') && DOING_AJAX) return; $ip = $_SERVER['REMOTE_ADDR']; if (ipwhois_is_blocked($ip)) { wp_die('Access denied.', 'Forbidden', ['response' => 403]); } });
MU-plugins load automatically. There is no need to activate this plugin in the WordPress admin. Just upload the file and it works immediately.
Configuration

Adjust the minimum confidence threshold by editing the $min_confidence parameter:

  • 70 (default) - Blocks IPs with 70%+ confidence. Good balance of security and false positives.
  • 50 - More aggressive. May block some legitimate IPs that had minor reports.
  • 90 - Conservative. Only blocks IPs with very high confidence scores.

If your site is behind a reverse proxy (Cloudflare, load balancer), you need to use the real client IP. Add this to wp-config.php:

// Trust X-Forwarded-For from Cloudflare / proxy if (!empty($_SERVER['HTTP_X_FORWARDED_FOR'])) { $_SERVER['REMOTE_ADDR'] = explode(',', $_SERVER['HTTP_X_FORWARDED_FOR'])[0]; }
Testing

Verify the plugin is loaded:

# Check mu-plugin is detected by WP-CLI wp plugin list --status=must-use # Test the API from the server curl -s "https://bl.ipwhois.net/api/check?ip=$(curl -s ifconfig.me)"

Visit wp-login.php from a clean IP to confirm it still loads. The plugin fails open, so if the API is unreachable, access is not blocked.

Troubleshooting
  • Plugin not loading: Check the file path is exactly wp-content/mu-plugins/ipwhois-guard.php. The mu-plugins directory may not exist by default -- create it.
  • Blocking legitimate users: Lower the confidence threshold to 90 or add IP exceptions in the function.
  • Slow page loads: The API call has a 3-second timeout. Results are cached for 1 hour via WordPress transients. If the API is consistently slow, increase the cache duration.
  • Behind Cloudflare: Use the HTTP_CF_CONNECTING_IP header instead of HTTP_X_FORWARDED_FOR for the real client IP.
IPWhois Blacklist — Community-driven IP threat intelligence — ipwhois.net