La Ayuda en español no abría ningún artículo: el filtro de seguridad T9 solo aceptaba wiki/, no wiki-es/
Cuándo
Desde el 01-09-2026 hasta el fix del 14-09-2026 (v1.132.3, PR #533) — 13 días. Detectado en la ronda de mantenimiento del 13-09 y registrado como task #308 del Gestor.
Síntomas visibles
Con la sesión de usuario en español, el panel de Ayuda listaba perfectamente los 69 títulos traducidos (GET /api/help/wiki funcionaba), pero ningún artículo se podía abrir: cualquier clic devolvía “Error loading article” (GET /api/help/article respondía 403). El fallo era binario — 0 de 69 — y afectaba solo a la sesión en español; en inglés todo seguía abriendo con normalidad.
Causa raíz
Dos piezas del mismo módulo, escritas en momentos distintos, dejaron de encajar:
- El listado (
_apply_language, sesión 137) reescribe las rutas de los artículos awiki-es/crearack--*.mdcuando la sesión está en español — comportamiento correcto y ya existente desde hace meses. - El filtro de seguridad T9 (
_HELP_ARTICLE_REencore/api_help.py:38, introducido en v1.100.0 para cerrar una fuga real: un usuario autenticado podía leer documentación interna del workspace víaread_guidepasando cualquier ruta) solo aceptaba el patrónwiki/crearack--*.md. La carpeta traducidawiki-es/no estaba en la whitelist.
El resultado: el endpoint que lista artículos entregaba una ruta (wiki-es/...) que el endpoint que abre artículos rechazaba de forma sistemática. El filtro de seguridad era correcto en su objetivo — impedir la lectura de rutas fuera de la Ayuda de usuario — pero no contempló que la carpeta traducida llevaba dos meses y medio sirviendo contenido legítimo.
Ninguno de los dos lados tenía un test que uniera listado + apertura: tests/api/test_tanda9_security.py solo probaba la ruta inglesa, y tests/api/test_help.py solo probaba el listado por separado.
Fix aplicado
Commit cc37a5336d01310341ae1dcbb533e0090efcafb0 (PR #533, v1.132.3):
_HELP_ARTICLE_REpasa a^(?:src/content/)?wiki(?:-es)?/crearack--[a-z0-9-]+\.md$— aceptawiki-es/con las mismas exigencias quewiki/(prefijocrearack--, extensión.md, sin..). La doc interna del workspace sigue vetada bajo ambas carpetas.- Test de contrato “lo que listo, lo puedo abrir” (
test_help_list_then_open_contract, parametrizado en inglés y español): pide el listado, coge la primera ruta devuelta y la abre — exige 200, nunca 403. Este es el test que faltaba y que habría cazado la regresión el mismo día que nació. - Test negativo en la carpeta traducida (
test_help_article_rechaza_ruta_interna_en_carpeta_es): confirma quewiki-es/decision--*.md(doc interna bajo la carpeta ES) sigue devolviendo 403 — el fix amplía la whitelist, no la debilita.
Límite honesto: el fix está verificado por test automático; la sonda de la task #308 (comprobar los 69 artículos en ambos idiomas contra producción tras el deploy) queda pendiente y su resultado se registra en la propia tarea.
Lecciones
- Un filtro de seguridad y un rewrite de rutas son dos mitades de un contrato que hay que testear juntas, no por separado. Cada mitad por su lado pasaba sus tests; la combinación llevaba 13 días rota sin que ninguna alarma saltara — el fallo es silencioso porque un 403 no es un error de servidor, es “funcionando como se diseñó” para una ruta que el propio sistema acababa de entregar.
- Tercer incidente del mismo patrón en el puente de la Ayuda en menos de 4 meses: [[incident—20260512—cf-access-help-widget-403]] (auth), [[incident—20260823—help-es-json-error-como-articulo]] (payload de error servido como contenido) y este (whitelist incompleta). Los tres comparten la forma: dos piezas que se escribieron en sesiones distintas y que solo se validan juntas cuando alguien prueba el camino completo en español.
- Un endurecimiento de seguridad (T9, v1.100.0) necesita repasar TODOS los caminos legítimos existentes en el momento de escribirlo, no solo el caso que motivó el cierre de la fuga.
Preventivos futuros
- El test de contrato añadido (
test_help_list_then_open_contract) corre en CI para EN y ES en cada PR — cualquier futura carpeta de idioma (wiki-fr/, etc.) que no esté en la whitelist lo hará fallar antes de mergear. - Pendiente de decisión de equipo (no bloqueante de este fix): una sonda periódica contra producción que liste y abra una muestra de artículos en cada idioma habría detectado el 0/69 el mismo 01-09 en vez de 13 días después.
Véase también
- [[entity—core—service—api-help]]
- [[entity—core—endpoint—api-help-wiki]]
- [[incident—20260823—help-es-json-error-como-articulo]]
- [[incident—20260512—cf-access-help-widget-403]]
- [[crearack-tech—guides—help-widget-bridge]]
- [[feature—core—help-widget-i4]]