# Live verification matrix

The regression suite (`php tests/run-tests.php`) proves the logic is right. It cannot prove a
real site still works, because the failures that hurt us most were never logic errors - they
were a half-written file served with a `200 OK`, a cached page outliving its nonce, a script
that needed to run before another one. Those only show up on a real page load.

So: **the suite is the gate for merging, this matrix is the gate for releasing.**

## The rule

Before a version is published, run every archetype below on a real install. A blocking result
stops the release. Nothing here takes longer than a few minutes per site once the sites exist.

Keep the test sites standing between releases. Rebuilding them each time is why this kind of
check quietly stops happening.

## Archetypes

Each one exists because it is a class of site that broke, or that we know is fragile.

| # | Archetype | Minimum setup | What to do | Blocking failure |
|---|---|---|---|---|
| 1 | **Plain content site** | Any block theme, 5 posts | Load home, a post, an archive. Hard-reload in a private window. | Unstyled render, missing images, console errors |
| 2 | **Page builder** | Elementor (or Divi) | Load a builder page, front and back. Edit and save one section. | Layout collapse, editor fails to load, animations dead |
| 3 | **WooCommerce** | Woo + 3 products | Add to cart, view cart, checkout, log in. | Cart shows wrong count, checkout errors, cart shared between visitors |
| 4 | **AJAX login / custom session** | A theme or plugin using `session_start()` for login | Log in from the front end. Reload. | Logged straight back out, redirect loop, or the previous visitor's page |
| 5 | **Forms** | Gravity Forms or WPForms | Submit a form with validation and conditional logic. | Silent failure, "security check failed", conditional fields stuck |
| 6 | **LMS / membership** | LearnDash, LifterLMS or MemberPress | Open a course/protected page as a member and as a guest. | Protected content leaked to a guest, player or quiz dead |
| 7 | **Multilingual** | WPML or Polylang | Switch language twice. Load a translated page directly. | Wrong language served from cache, switcher dead |
| 8 | **Slider / popup heavy** | RevSlider or Smart Slider + Popup Maker | Load the page with the slider. Trigger the popup. | Slider blank or unstyled, popup never fires |
| 9 | **Locked-down host** | A site behind a WAF (Cloudflare/Sucuri/Wordfence) | Connect the licence, change a setting in the dashboard, wait for the poll. | Settings never arrive, connection drops |
| 10 | **Low-spec shared host** | PHP memory 128M, no OPcache | Clear all cache, then load the home page cold, twice. | Timeout, 500, or a partially styled first render |

## Every archetype, every time

Run these on **each** site above - they are the failures that have cost us the most:

1. **Cold cache, private window, hard reload.** The first uncached render is where a
   half-written CSS/JS file appears. Text-only render is blocking.
2. **View source.** Confirm the SpeedyGo signature comment is present and that no asset URL
   returns a `0`-byte body or a `404`.
3. **Console must be clean.** Any new JS error is blocking, even if the page looks fine.
4. **Network tab, filter by our cache directory.** Every `.css`/`.js` we generated must return
   `200` with a non-zero length.
5. **Log in, then reload.** A logged-in visitor must never be served a cached page.
6. **Toggle the preset** (Starter -> Extensive) and repeat step 1. Most breakages only appear at
   the aggressive end.

## Compatibility rules

Archetypes 5-8 exist to exercise `includes/compat-rules.php`. When one of those sites breaks:

1. Confirm it is ours - deactivate SpeedyGo, reload, see if it goes away.
2. Find the script that must not be touched (usually the one throwing in the console).
3. Add a rule for it. **Fleet-wide, no plugin release needed:**
   `PUT /api/admin/compat-rules` on Node, and every site picks it up on its next settings poll.
4. Add the same rule to the bundled list in `compat-rules.php` so fresh installs are protected
   before their first poll, and add a regression test naming the plugin.

A rule can only ever *add* an exclusion, so the fix cannot itself break anything - the worst
case is that a site running that plugin loses a little optimization.

## Recording the run

Keep it lightweight - a checklist per release with the version, the date, who ran it, and any
archetype that failed with what was done about it. The value is in noticing that archetype 4
has failed in three consecutive releases, which no amount of green unit tests will tell you.
