BetterShield
Appearance

Server compatibility: what BetterShield needs from your host

10 min read

The WordPress and PHP versions, PHP extensions, HTTPS, web server and scheduled tasks BetterShield needs, and a checklist to hand your host.

BetterShield runs on ordinary WordPress hosting. A few features depend on the server, and where one cannot work, its screen says why instead of claiming a protection the site does not have. This page lists what each feature needs, with a checklist for your host at the end.

Requirements

WhatNeeds
BetterShieldWordPress 6.7 or newer and PHP 8.0 or newer. Tested up to WordPress 7.1.
Assistants (the MCP server), agent abilities and BetterShield HubThe WordPress Abilities API. WordPress 6.9 and newer include it; on 6.7 and 6.8, BetterShield loads its own copy.
AI explanationsWordPress 7.0 or newer, with an AI provider connected under Settings › Connectors.
Recording every ability call on Activity › AgentsWordPress 7.1 or newer.

On PHP older than 8.0, BetterShield does not run and the dashboard says: “BetterShield needs PHP 8.0 or newer. This site runs PHP [version], so the plugin is not running. Nothing else on the site is affected.”

If an Agents screen says Requires WordPress 6.9., or the Hub card says Connecting needs WordPress 6.9 or later., BetterShield’s own copy of the Abilities API is missing. Reinstall BetterShield from WordPress.org, or update WordPress.

PHP extensions

ExtensionWhat it is forWithout it
OpenSSLChecking a passkey’s signature, and reading when the site’s certificate expires.Passkeys stay off, with “This server is missing the OpenSSL extension, which is needed to check a passkey signature.” The certificate check cannot read the date.
SodiumPasskeys of the Ed25519 type.Devices are offered the other passkey types only.
ZipPacking the kept copies of replaced files into one archive when you delete the plugin with that choice.WordPress’s own zip writer is used instead.

The daily check of your domain’s SPF, DMARC and CAA records needs PHP’s DNS lookups, and the low disk space warning needs PHP to report free space. Where a host disables either, that check cannot run, and a check that could not run is never reported as passed.

HTTPS

FeatureNeedsOtherwise
PasskeysHTTPS, or localhostSwitched off: “Passkeys need HTTPS.”
Ask for a sign-in puzzle after wrong passwordsHTTPS, or localhost“Needs HTTPS. Your site isn’t using HTTPS yet, so this is off.” Sign-ins on plain HTTP skip the check.
Strict HTTPS (HSTS)A site address that is already HTTPSNot offered. A certificate close to expiry is flagged before you apply it.
An assistant connecting by addresshttpsConnection health shows Served over https as no.

Apache, LiteSpeed, nginx and IIS

Two fixes work by writing .htaccess rules: Uploads code block (in the uploads folder) and Private file protection (in the site’s root). BetterShield reads the server type from what the server tells PHP.

ServerReads .htaccessThose two fixes
ApacheYesAvailable.
LiteSpeedIts paid edition reads these rules; the free OpenLiteSpeed reads only rewrite rules, and the two report themselves the same wayAvailable, with “The rules will be written, but whether they are enforced could not be confirmed from here.”
OpenLiteSpeed (when it names itself)Only rewrite rulesNot available here: “This site runs on OpenLiteSpeed, which reads only rewrite rules from .htaccess files and skips the kind this fix writes, so it cannot work here.”
nginx, IISNoNot available here: “This site runs on nginx, which does not read .htaccess files, so this fix cannot work here.”
Not identifiedCannot tellApplied, with “This server did not identify itself as one that reads .htaccess files. The rules will be written, but whether they are enforced could not be confirmed from here.”

On nginx, IIS or OpenLiteSpeed, your host can add the same rules to the server configuration. Every other fix needs no server rules: Folder listing protection places blank index files instead, and works on every server. The Publish a security contact setting on Settings › General works everywhere too, because WordPress serves the file rather than writing it.

When BetterShield puts a changed file back, it keeps the replaced copy in wp-content/uploads/bettershield-quarantine/ and seals that folder with an .htaccess rule. On nginx, IIS or OpenLiteSpeed the rule does nothing, and the finding Files in quarantine can still be opened from the web (Medium) asks you to deny the folder in your server configuration. Nothing on your site loads from it.

If the site address and WordPress address point somewhere other than where the files are (an alias, or a rewrite in front of the whole site), the sensitive files fix refuses with “This plugin could not work out which .htaccess file governs your site, so nothing was written.”

wp-config.php is never edited

BetterShield never writes to wp-config.php.

  • File editor lock works through WordPress’s permissions. If wp-config.php already turns the editor off, the fix says so.
  • Sign everyone out on demand mixes a secret of its own into the keys WordPress uses, and leaves the keys in wp-config.php as they are.
  • Findings about wp-config.php itself, such as Your site’s security keys are missing or weak or Error messages are visible to visitors, are changes you make.

Proxies, CDNs and load balancers

Sign-in lockouts need to tell visitors apart. Cloudflare is recognized from its published address ranges and needs no Addresses of your CDN or proxy entry, but press Yes, this site is behind Cloudflare when the screen asks: until then, a lockout counts Cloudflare’s address and the visitor’s together. Name any other reverse proxy or load balancer under Addresses of your CDN or proxy and have it send X-Forwarded-For. Until you do, a proxy on a private address makes lockouts stand down (the finding Failed sign-ins are not being counted, so password guessing is not stopped says so), and a proxy on a public address is counted as one visitor, so a lockout would shut out everyone behind it. With Cloudflare in front of a load balancer on a private address, name the load balancer, and Cloudflare is recognized behind it. The public form limits record those visitors but never close a form to them. See Proxies and Cloudflare.

HTTPS that ends at a proxy

When a proxy or load balancer handles the encryption without telling WordPress, WordPress sees plain HTTP even though the site’s address is HTTPS, and the HSTS header, which is only sent on requests WordPress sees as encrypted, never goes out. Strict HTTPS (HSTS) warns that “applying this changes nothing” until wp-config.php sets the HTTPS server variable for those requests. Passkeys go by the site’s address, so they are still offered.

Page caches and the sign-in page

A cached sign-in page hands every visitor a copy built for someone else, which can refuse a correct password. The finding Your sign-in page is being cached (Medium) checks for this daily. Exclude the sign-in address from your cache plugin, your host’s cache and your CDN. If you move the sign-in address while WP Rocket, W3 Total Cache, WP Super Cache or LiteSpeed Cache is active, the fix reminds you to exclude the new address too.

Server firewall

On a server that runs Fail2Ban, Send lockouts to the server’s firewall, on the Server firewall card on Protection › Login & Access, writes one line to the server’s auth log each time sign-in or a form pauses a connection, so the firewall can block that network before it reaches WordPress. The line names the network (IPv4 /24, IPv6 /64), never an address or a username, and a network that holds an address on your allowed list writes no line. A sample Fail2Ban filter and jail ship in the plugin’s fail2ban folder; only a jail written for this line reads it. A host can turn it on for every site with the bettershield_host_ban_line filter, and the card then says it is set by your host. Where PHP’s system log functions are turned off, it is unavailable. On multisite it is set from the main site. See Server firewall.

Replaced session storage

If another plugin has replaced how WordPress stores sessions, Sessions per account on Login & Access is unavailable: “Not available on this site: something has replaced how WordPress stores sessions, and a limit cannot be applied to them.” Signing an account out of everything still works.

Scheduled tasks (WP-Cron)

BetterShield’s background work runs on WordPress’s scheduled tasks: hourly (the hardening monitor, incidents, file check steps, unusual-activity notes), daily (the audit, the log seal, the certificate, domain and sign-in page checks, housekeeping) and weekly (looking for files a stranger could download). Anything that asks your own server a question runs from the schedule only, never inside a visitor’s page view.

WordPress runs scheduled tasks when page loads trigger them, so a quiet site can miss them. When a task is badly overdue, BetterShield runs it, or asks the site to run it, the next time an administrator opens the dashboard. If whole cycles are still missed, the finding BetterShield’s background jobs have stopped running (Medium) appears. The fix is on the host: a system cron that runs wp-cron.php, or wp cron event run --due-now, every few minutes. We recommend one on every site you look after.

With the Hub link on, sending security events to BetterShield Hub is scheduled work too, every five minutes. See Connect to BetterShield Hub.

Multisite

Network activation sets up every site, and a site created later is set up the same way. Each site keeps its own settings, counts and findings. Private file protection is applied from the main site, because every site shares one .htaccess, and sign-in key rotation is done from the network dashboard. See Multisite networks.

A checklist for your host

  • PHP 8.0 or newer, with OpenSSL and Sodium enabled.
  • HTTPS on the site’s address. If encryption ends at a proxy or load balancer, wp-config.php sets HTTPS for the requests it forwards.
  • A proxy or load balancer in front of the site sends X-Forwarded-For, and you have its address range to add under Addresses of your CDN or proxy.
  • The sign-in page, and any custom sign-in address, excluded from page caching and CDN caching.
  • A system cron running WordPress’s scheduled tasks every few minutes.
  • If the server runs Fail2Ban and you want paused networks blocked at the firewall: a jail that reads BetterShield’s auth log line (a sample filter and jail ship in the plugin’s fail2ban folder).
  • Outbound HTTPS to WordPress.org, for the file check. See What BetterShield contacts.
  • The site may make requests to its own address.
  • WordPress can send email, for alerts and the recovery link.
  • The database account may create tables, which BetterShield does on activation and updates.
  • WordPress can write to the uploads folder and, on Apache or LiteSpeed, the site’s .htaccess.
  • On nginx, IIS or OpenLiteSpeed: the rules for the two .htaccess fixes in the server configuration, and web access denied to wp-content/uploads/bettershield-quarantine/.

Close the open doors today

Install the free plugin. The first audit runs when you activate it, and all but one of the fixes wait for your choice.

Requires WordPress 6.7 or newer and PHP 8.0 or newer.

Get BetterShield