# v0.1.7

**Releasedatum:** 8 mei 2026

## Nieuwe Functies

### S3-asset-opslag

- Een nieuwe optionele instelling `ASSETS_STORAGE_MODE=s3` laat winkels uploads naar een S3-compatibele bucket sturen en vanaf een CDN serveren, in plaats van de standaard lokale map `data/files/`
- Wanneer S3-modus actief is, wordt elke geüploade afbeelding op gangbare breedtes (200/400/600/800/1200) als WebP-variant voorgegenereerd en naast het origineel opgeslagen, zodat de storefront afbeeldingen op de juiste maat kan serveren zonder conversie tijdens runtime
- Een nieuwe optionele `ASSETS_MAX_BYTES`-limiet beperkt cumulatieve bestandsopslag (in zowel lokale als S3-modus), zodat een ontspoorde uploadstroom de bucketrekening niet kan opblazen — limieten per upload (5 MB afbeelding / 50 MB video) blijven ongewijzigd
- Een eenmalig script `migrate-assets-to-s3.mjs` zit bij de Docker-image; het uitvoeren binnen een container uploadt bestaande lokale bestanden naar de bucket, herschrijft de opgeslagen URLs naar het CDN en genereert varianten voor

### CSV-exports voor Gebruikers en Bestellingen

- De Gebruikerslijst heeft een nieuwe knop **Gebruikers exporteren** die de huidige weergave als CSV downloadt
- De Bestellingenlijst heeft een nieuwe knop **Bestellingen exporteren** die de huidige weergave als CSV downloadt
- Beide endpoints zijn CSRF-beveiligd en rate-limited

### Responsieve Storefront-afbeeldingen

- Productkaarten, productpagina's, slideshow-slides, image-with-text-secties, collectietegels en andere storefront-afbeeldingen worden nu gerenderd met `srcSet` en `sizes`, uitgelijnd op voorgegenereerde WebP-breedtes (200/400/600/800/1200)
- Telefoons en tablets halen de kleinste variant die past in hun viewport in plaats van altijd het desktop-formaat te laden, wat het paginagewicht verlaagt en de Core Web Vitals op trage verbindingen verbetert

### Foutentelemetrie

- Wanneer **Platformtelemetrie** is ingeschakeld in Instellingen → Integraties, worden uitzonderingen aan de serverzijde en niet-afgehandelde clientfouten (`window.onerror`, niet-afgehandelde promise-rejections) anoniem aan het Capyshop-team gerapporteerd als `$exception`-events
- Geen persoonlijke gegevens, klantinformatie of winkeldetails worden doorgestuurd — de bestaande telemetrieschakelaar regelt de volledige pipeline, en uitschakelen stopt ook alle foutrapportage

### Page-builder-fontladen

- Slideshow-titels en -subtitels, image-with-text-titels/-subtitels/-body, en body-fonts van tekstsecties die in de page builder zijn gekozen, worden nu automatisch met de pagina geladen
- Voorheen werd alleen het winkelbrede thema-font geladen, wat betekende dat fontkeuzes van beheerders op homepage-secties stilletjes terugvielen op het standaardfont bij de eerste render

### Lokalisatie van Stripe Checkout

- Stripe Elements (het ingebedde kaartformulier) wordt nu in de door de klant geselecteerde taal gemount, zodat veldlabels, foutmeldingen en de "Betalen"-knop overeenkomen met de rest van de checkout

## Verbeteringen

- Webfonts blokkeren de rendering niet meer — de storefront rendert direct en het webfont wisselt in zodra het geladen is, wat de eerdere "leeg scherm tot Google Fonts antwoordt"-vertraging elimineert
- Build-target geüpdatet naar moderne browsers (Chrome 111+, Edge 111+, Firefox 128+, Safari 16+), zodat de bundle geen ES6-polyfills meer meeneemt die geen huidige browser nodig heeft
- Formaten van het admin-dashboard, het analytics-overzicht en de analytics-funnelgrafiek verfijnd voor duidelijkere visualisatie
- De Docker-image-releasepipeline is verplaatst naar een dedicated workflow die wordt getriggerd door GitHub Releases, gecontroleerd op een groene CI-run op `main` voor dezelfde commit — geen ad-hoc image-pushes meer

## Beveiligingsfixes

- Alle state-wijzigende API-endpoints (POST/PATCH/PUT/DELETE) valideren nu de request-`Origin` tegen `TRUSTED_ORIGINS` en wijzen mismatches af; alleen Stripe-webhooks vormen een uitzondering, omdat die zich authenticeren via signature in plaats van cookie
- De AI-assistent-proxy (`/api/admin/chat`, `/api/admin/generate-text`) en het sign-up-endpoint tellen nu elke aanroep mee in de rate limit — niet alleen de mislukte — als verdediging tegen het leegtrekken van betaalde API's en bulkmisbruik bij accountregistratie
