From 9bb97fc85798c7349bee80724a43d1a53d3a0a65 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ha=C5=82as=20Piotr?= Date: Wed, 6 May 2026 20:10:14 +0200 Subject: [PATCH] docs: add feature matrix comparing support across all server integrations A new docs/features.md table shows which mESI features are available, configurable, hardcoded, or unsupported in each server (Traefik, RoadRunner, Caddy/FrankenPHP, Nginx, Apache, PHP Extension, CLI, Proxy). Linked from README.md. --- README.md | 3 +++ docs/features.md | 55 ++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 58 insertions(+) create mode 100644 docs/features.md diff --git a/README.md b/README.md index db73764..90eab0c 100644 --- a/README.md +++ b/README.md @@ -17,6 +17,9 @@ - **esi:include timeout** - Timeout can be set both globally and specifically for a selected `esi:include` tag. In combination with fallback content, you can easily manage the page generation time. - **Fallback content** - Set the content to be displayed if remote content download fails. - **SSRF Protection** – Built-in protection against Server-Side Request Forgery attacks with private IP blocking and optional host whitelisting. + +See the full [Feature Matrix](docs/features.md) for a detailed breakdown of which features are supported in each server integration. + ## ESI Parser Configuration This document describes the configuration structure for the mESI parser. diff --git a/docs/features.md b/docs/features.md new file mode 100644 index 0000000..706231d --- /dev/null +++ b/docs/features.md @@ -0,0 +1,55 @@ +# mESI – Feature Matrix + +Support status of mESI features across all server integrations. + +| Feature | mESI Core | Traefik | RoadRunner | Caddy / FrankenPHP | Nginx | Apache | PHP Extension | CLI | Proxy | +|---|---|---|---|---|---|---|---|---|---| +| `` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `` (inline) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| ``, ``, ``, `` | ⚠️ | ⚠️ | ⚠️ | ⚠️ | ⚠️ | ⚠️ | ⚠️ | ⚠️ | ⚠️ | +| `src` / `alt` attributes | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `fetch-mode="fallback"` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `fetch-mode="ab"` (A/B testing) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `ab-ratio` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `fetch-mode="concurrent"` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `timeout` (per-tag) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `max-depth` (per-tag) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `onerror="continue"` | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| Fallback content (tag body) | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| `IncludeErrorMarker` | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ⚠️ | ✅ | +| Global MaxDepth | ✅ | ✅ | ❌ | ❌ | ❌ | ❌ | ✅ | ✅ | ✅ | +| Global Timeout | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | ✅ | +| SSRF (BlockPrivateIPs) | ✅ | 🔒 | 🔒 | 🔒 | ❌ | ✅ | ❌ | 🔒 | ✅ | +| AllowedHosts | ✅ | ❌ | ❌ | ❌ | ❌ | ✅ | ❌ | ❌ | ✅ | +| AllowPrivateIPsForAllowedHosts | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| MaxResponseSize | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| MaxConcurrentRequests | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| MaxWorkers | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| ParseOnHeader | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | ✅ | +| Debug mode | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | ✅ | +| Cache (in-memory) | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| Cache (Redis) | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| Cache (Memcached) | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| Custom CacheKeyFunc | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | +| Recursive ESI processing | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | ✅ | +| Shared HTTPClient | ✅ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ❌ | ✅ | + +## Legend + +| Symbol | Meaning | +|---|---| +| ✅ | Supported and configurable | +| 🔒 | Always on (hardcoded, not configurable) | +| ⚠️ | Partial support / limitations | +| ❌ | Not supported / unavailable | + +## Notes + +- **``, ``, ``, ``** – Recognized by the tokenizer (no parse errors), but their content is silently dropped from output. Full support planned. +- **Nginx** – Uses the `Parse` function from `libgomesi` which does not enable `BlockPrivateIPs` (defaults to `false`). No SSRF protection. +- **PHP Extension** – Exposes only `\mesi\parse(input, max_depth, default_url)`. No security configuration. +- **Caddy / FrankenPHP** – FrankenPHP uses the Caddy plugin, identical functionality. +- **Proxy** – Accepts full `EsiParserConfig`; all features available when provided by calling code. +- **IncludeErrorMarker (CLI)** – Can only be set programmatically (no CLI flag).