feat(F-156): completed feature

This commit is contained in:
chattie
2026-08-22 06:21:35 +02:00
parent 3b74fc10d2
commit 7a8595bebb
11 changed files with 181 additions and 12 deletions

View File

@@ -0,0 +1,50 @@
# F-156 — Implementer evidence
## Problema
Las modificaciones de páginas CMS, por ejemplo `/about`, no se reflejaban en el frontend porque esas rutas se podían servir como contenido estático/cacheado y `fetchPage()` no desactivaba explícitamente la caché de Next `fetch`.
## Cambios
- `project/frontend/src/lib/api.ts`
- `fetchPage(slug)` ahora usa `{ cache: 'no-store' }`.
- `project/frontend/src/app/about/page.tsx`
- `export const dynamic = 'force-dynamic'`.
- `project/frontend/src/app/contact/page.tsx`
- `export const dynamic = 'force-dynamic'`.
- `project/frontend/src/app/shipping/page.tsx`
- `export const dynamic = 'force-dynamic'`.
## Verificación runtime
Prueba real sobre `/about`:
1. Se añadió temporalmente marcador `F156-CMS-1787344784` al body CMS en DB.
2. `curl http://192.168.18.93:3003/about` mostró el marcador sin rebuild.
3. Se restauró el body original.
4. `curl http://192.168.18.93:3003/about` dejó de mostrar el marcador.
Resultado:
```text
reflected:F156-CMS-1787344784 ✅
restored:F156-CMS-1787344784 ✅
```
Frontend reiniciado con build final y `/about` responde:
```text
Cache-Control: private, no-cache, no-store, max-age=0, must-revalidate
```
## Checks
```text
frontend npm run build ✅
frontend npx tsc --noEmit ✅
frontend eslint archivos tocados ✅
frontend prettier archivos tocados ✅
monolith prod status ✅ backend/admin/frontend/storefront 200
verify.sh ✅
git diff --check ✅
```

View File

@@ -0,0 +1,20 @@
{
"feature_id": "F-156",
"agent": "leader",
"verdict": "APPROVED",
"summary": "F-156 closed: CMS content-managed pages (/about, /contact, /shipping) no longer serve stale cache. fetchPage uses no-store and pages are force-dynamic; static fallback and RBAC are intact. Runtime verified live; all gates approved.",
"checks": [
"reviewer.json APPROVED",
"security.json APPROVED",
"qa.json APPROVED",
"frontend build OK",
"frontend npx tsc --noEmit OK",
"frontend eslint OK on touched files",
"frontend prettier OK on touched files",
"runtime /about returns 200 with Cache-Control: no-store",
"verify.sh OK"
],
"commit_message": "feat(F-156): completed feature",
"next_step": "Resume pending tickets per work/current.md ordering: F-152 email notifications",
"closed_at": "2026-08-22T04:21:30Z"
}

View File

@@ -0,0 +1,18 @@
{
"feature_id": "F-156",
"agent": "qa",
"stage": "qa_gate",
"verdict": "APPROVED",
"summary": "CMS pages /about, /contact and /shipping now render under demand with no-store fetch and force-dynamic. Static fallback preserved. Runtime content reflected without rebuild and verify.sh green.",
"checks": [
{"item": "CMS pages force-dynamic", "ok": true, "evidence": "about/contact/shipping export const dynamic = 'force-dynamic'; build lists them as ƒ (dynamic)"},
{"item": "fetchPage disables cache", "ok": true, "evidence": "project/frontend/src/lib/api.ts uses fetch(..., { cache: 'no-store' })"},
{"item": "Runtime no-store header", "ok": true, "evidence": "curl -sI http://192.168.18.93:3003/about → Cache-Control: private, no-cache, no-store, max-age=0, must-revalidate"},
{"item": "Content visible without rebuild", "ok": true, "evidence": "implementer marked /about reflected+restored a temporary CMS body marker through a live DB edit without rebuild"},
{"item": "Static fallback intact", "ok": true, "evidence": "catch(() => null) and FALLBACK_HTML still in about/page.tsx; non-CMS body still served"},
{"item": "Regression: verify.sh", "ok": true, "evidence": "./scripts/verify.sh green"},
{"item": "Regression: build/typecheck/lint/prettier", "ok": true, "evidence": "frontend npm run build, npx tsc --noEmit, eslint, prettier on touched files all green"}
],
"issues": [],
"notes": "No public route or admin CMS endpoint changed; RBAC/security surface untouched."
}

View File

@@ -0,0 +1,15 @@
{
"feature_id": "F-156",
"agent": "reviewer",
"stage": "review_gate",
"verdict": "APPROVED",
"summary": "El fix elimina la caché de las páginas CMS afectadas y mantiene fallbacks existentes. /about, /contact y /shipping se renderizan bajo demanda y fetchPage no usa caché.",
"checks": [
{"item":"CMS fetch no-store","ok":true,"evidence":"fetchPage usa fetch(..., { cache: 'no-store' })"},
{"item":"Páginas CMS dinámicas","ok":true,"evidence":"about/contact/shipping exportan dynamic='force-dynamic'; build las lista como ƒ"},
{"item":"Cambio visible sin rebuild","ok":true,"evidence":"marcador temporal en /about apareció y desapareció tras revertir DB"},
{"item":"No rompe fallback","ok":true,"evidence":"catch(() => null) y FALLBACK_HTML se mantienen"},
{"item":"Checks verdes","ok":true,"evidence":"frontend build/typecheck/lint/prettier, verify.sh, git diff --check"}
],
"issues": []
}

View File

@@ -0,0 +1,15 @@
{
"feature_id": "F-156",
"agent": "security",
"stage": "security_gate",
"verdict": "APPROVED",
"summary": "No se amplía superficie de permisos ni se cambia quién puede editar CMS. El cambio solo reduce caché de lectura pública de páginas ya publicadas.",
"checks": [
{"item":"Autorización CMS intacta","ok":true,"evidence":"No se modifican rutas admin CMS ni requireRole(admin)"},
{"item":"Solo contenido publicado público","ok":true,"evidence":"fetchPage sigue llamando /cms/pages/:slug público, que usa getPublicPageBySlug"},
{"item":"XSS no empeora respecto a comportamiento existente","ok":true,"evidence":"dangerouslySetInnerHTML ya existía; no se añaden nuevos campos ni bypass"},
{"item":"Cache no-store evita stale content","ok":true,"evidence":"Cache-Control no-store en /about runtime"}
],
"issues": [],
"notes": "Sanitización/allowlist de HTML CMS queda como hardening futuro si se requiere; este fix no introduce HTML nuevo."
}

View File

@@ -1,11 +1,33 @@
{
"feature_id": null,
"stage": "idle",
"feature_id": "F-156",
"stage": "close",
"agent": "leader",
"action": "Sin ejecución activa",
"state": "waiting",
"next_agent": "leader",
"waiting_for": "Seleccionar una feature pending y actualizar este estado",
"updated_at": "2026-08-21T20:37:03Z",
"timeline": []
"action": "Validate gates and close F-156",
"state": "running",
"next_agent": "reviewer",
"waiting_for": "review_gate",
"updated_at": "2026-08-22T04:21:17Z",
"timeline": [
{
"ts": "2026-08-21T20:43:14Z",
"agent": "implementer",
"stage": "build",
"state": "running",
"message": "Reapply CMS dynamic rendering changes"
},
{
"ts": "2026-08-22T04:19:11Z",
"agent": "qa",
"stage": "qa_gate",
"state": "running",
"message": "Run CMS dynamic rendering acceptance and regression checks"
},
{
"ts": "2026-08-22T04:21:17Z",
"agent": "leader",
"stage": "close",
"state": "running",
"message": "Validate gates and close F-156"
}
]
}