feat(moderation): optional Cloudflare CDN purge after removal master
Removal and the consumer's media reconcile can now purge a Cloudflare-fronted image hostname by URL, best-effort, once, after commit. With nothing configured, behaviour is unchanged apart from one Info line at boot. - Config: CLOUDFLARE_CACHE_PURGE_ZONE_ID and CLOUDFLARE_CACHE_PURGE_API_TOKEN. Both empty means purge is off; exactly one set is a boot error; both set requires the image proxy enabled with absolute http(s) base/CDN URLs. The token never appears in errors, logs or formatted config. - imageproxy purger: one URL per preset per purge base for each (owner DID, CID) pair, byte-identical to HydrateImageURL output; POST to /zones/{zone}/purge_cache in batches of at most 100 URLs with a pair's URLs kept together; failures carry a code (HTTP status, api_unsuccessful, transport) and never the token or response body. - Moderation: removeContent and the media reconcile purge every owner-scoped block they committed after commit; a purge failure is logged and never fails or rolls back the removal. Every blocked blob gets an owner-scoped block for the subject's owner, illegal-content included. - Wiring, prod env example and compose entries; testkit fake Cloudflare purge endpoint; T0/T1 contract tests; CSAM PRD notes updated. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>