---
name: wordpress-plugin-updates-and-site-health
description: "Every Monday: pending plugin, theme and core updates per WordPress site, plugins with known vulnerabilities, and Site Health tests that fail. Use when the user asks for this, or when it runs on a schedule."
---

# WordPress plugin updates and site health check

Every Monday: pending plugin, theme and core updates per WordPress site, plugins with known vulnerabilities, and Site Health tests that fail.

An agency with twenty client sites, or a company with a marketing site and two microsites, has the same Monday chore: log in to each dashboard, look at the update count, and hope nothing on the list has a security advisory. The site that gets skipped is the one with the outdated forms plugin.

The agent checks each site through WP-CLI or the REST API, lists what needs updating, looks up installed plugin versions against a vulnerability database, and runs the Site Health background tests. It reports; it does not update anything, since updates on client sites deserve a person and a backup.

## Two ways to get the data

Use the API or MCP route when you have an MCP server, a CLI or an API token for the app. Otherwise, if you can drive a browser the user is signed in to (Claude in Chrome, a Playwright or Chrome DevTools MCP server), use the browser route. Say which one you used.

## Route A: API or MCP server

### What you need

- SSH access with WP-CLI on each server, or an administrator account per site with an application password (Users > Profile > Application Passwords).
- A vulnerability data API key, such as a free WPScan API token, in `WPSCAN_API_TOKEN`.

If something is missing, say what and stop; do not invent numbers.

### Steps

1. **List plugins, themes and core** (WordPress): With WP-CLI over SSH: `wp plugin list --fields=name,status,version,update,update_version --format=json`, the same for `wp theme list`, and `wp core check-update --format=json`. Run against each site, for example with aliases (`wp @client-a ...`).
2. **Or use the REST API** (WordPress): Without SSH, `GET /wp-json/wp/v2/plugins` with an administrator's application password returns `plugin`, `status` and `version` but not update availability; compare each `version` with `https://api.wordpress.org/plugins/info/1.2/?action=plugin_information&request[slug]=<slug>`.
3. **Check for known vulnerabilities**: For each plugin, query a vulnerability database such as the WPScan API (`GET https://wpscan.com/api/v3/plugins/<slug>` with `Authorization: Token token=<key>`) and flag the plugin when the installed version is below a vulnerability's `fixed_in`. Cache results by slug and version to stay within the daily quota.
4. **Run Site Health tests** (WordPress): Call the background tests as an administrator: `GET /wp-json/wp-site-health/v1/tests/background-updates`, `loopback-requests`, `https-status`, `dotorg-communication` and `page-cache`. Keep results whose `status` is `critical` or `recommended`, with their `label`.
5. **Report per site**: Vulnerable plugins first, with the fixed version. Then pending updates per site (inactive plugins marked, since they should often be deleted), core status, and failing Site Health tests.

## Route B: the browser

### What you need

- Signed in to each site's wp-admin as an Administrator; the person completes any 2FA plugin prompt first. One browser profile per client login works best.

If something is missing, say what and stop; do not invent numbers.

### Steps

Start at https://example.com/wp-admin/update-core.php. The user is signed in already; never type passwords or codes, and ask if a sign-in page appears.

1. **Open Updates on each site**: Replace `example.com` with each site in your list and open **Dashboard** > **Updates**. The page shows the WordPress core status at the top, then the **Plugins** and **Themes** sections with the installed and new version of everything that has an update.
2. **Mark inactive plugins**: Open **Plugins** > **Installed Plugins** and click the **Update Available** filter. Rows without a blue background are inactive; note those, since an inactive plugin with pending updates is usually one to delete rather than update.
3. **Check Site Health**: Open **Tools** > **Site Health**, **Status** tab. Read the items under **Critical issues** and **Recommended improvements** with their titles; the loopback, HTTPS, background updates and page cache tests live here.
4. **Look up vulnerabilities**: For each plugin with an update, open `https://wpscan.com/plugins/<slug>` (the slug is the folder name shown under **View details** on the Plugins page) and check whether a listed vulnerability affects the installed version and which version fixed it. Sites with Jetpack Protect or a similar scanner show the same under its menu.
5. **Report per site**: Vulnerable plugins first with the fixed version, then pending plugin, theme and core updates per site with inactive ones marked, then Site Health items. Click nothing that says Update.

Note: Each site is a separate login, so an agency with twenty sites is better served by WP-CLI aliases. The Updates page only knows about plugins that report updates to WordPress; premium plugins with their own licensing can show as current while a newer version exists.

## The report

- **Vulnerable plugins**: site, plugin, installed version, fixed version, severity.
- **Pending updates** per site: plugins, themes and core, inactive ones marked.
- **Site Health**: critical and recommended items per site.
- One line per site on what to update first.

## Post it to Briefkin

When `BRIEFKIN_TOKEN` is set, or `~/.config/briefkin/env` exists (the installer from https://briefkin.dev/docs writes it), also send the result to the user's Briefkin board as one card. Keep the `item_key` the same on every run so the card updates in place, use a new `event_id` per run, and put today's real numbers in place of the example ones. If the request fails, say so once and carry on.

```bash
[ -n "${BRIEFKIN_TOKEN:-}" ] || . ~/.config/briefkin/env
curl -sS -X POST "${BRIEFKIN_URL:-https://briefkin.dev}/v1/events" \
  -H "authorization: Bearer $BRIEFKIN_TOKEN" \
  -H "content-type: application/json" \
  -d @- <<'JSON'
{
  "v": 1,
  "event_id": "wordpress-plugin-updates-and-site-health/<date of this run, e.g. 2026-10-16>",
  "item_key": "wordpress-plugin-updates-and-site-health",
  "project": "Acme Agency",
  "source": "WordPress plugin updates and site health check skill",
  "kind": "update",
  "title": "1 vulnerable plugin, 23 plugin and theme updates pending",
  "summary": "**client-b.com** runs **acme-forms 2.4.1**, which has a known cross-site scripting issue fixed in 2.4.3. **23** plugin and theme updates are pending across 4 sites.",
  "work_state": "blocked",
  "widget": [
    {
      "type": "Table",
      "props": {
        "columns": [
          "Site",
          "Plugins",
          "Themes",
          "Core",
          "Site Health"
        ],
        "align": [
          "left",
          "right",
          "right",
          "left",
          "left"
        ],
        "rows": [
          [
            "client-a.com",
            6,
            1,
            "Up to date",
            "Good"
          ],
          [
            "client-b.com",
            9,
            0,
            "Update available",
            "1 critical"
          ],
          [
            "client-c.com",
            3,
            1,
            "Up to date",
            "2 recommended"
          ],
          [
            "example.com",
            2,
            1,
            "Up to date",
            "Good"
          ]
        ]
      }
    },
    {
      "type": "Log",
      "props": {
        "lines": [
          {
            "text": "client-b.com: acme-forms 2.4.1 vulnerable (XSS), fixed in 2.4.3",
            "level": "error"
          },
          {
            "text": "client-b.com: Site Health critical, loopback request failed",
            "level": "warn"
          },
          {
            "text": "client-c.com: 2 inactive plugins with updates, consider removing",
            "level": "info"
          }
        ]
      }
    }
  ]
}
JSON
```

Widgets come from the Briefkin catalog (https://briefkin.dev/v1/catalog). Without a token, just give the user the report.

## Run it on a schedule

Suggested: Mondays at 9:00 (`0 9 * * 1`). From cron, with the agent signed in on that machine:

```bash
0 9 * * 1 claude -p "Run the wordpress-plugin-updates-and-site-health skill"
# Codex: codex exec, Gemini CLI: gemini -p, Copilot CLI: copilot -p, OpenCode: opencode run
```

Or use the agent's own scheduler (Claude Code routines, Codex automations, Claude or ChatGPT scheduled tasks): https://briefkin.dev/skills/wordpress-plugin-updates-and-site-health#schedule

Source: https://briefkin.dev/skills/wordpress-plugin-updates-and-site-health
