Cutover Joomla->WP: antiguo.feadulta.com da HTTP 500 en frontend (pedir opinion a Opus) #162

Open
opened 2026-07-08 02:41:51 +00:00 by rafa · 2 comments
Owner

Cutover Joomla→WP: antiguo.feadulta.com da HTTP 500 en frontend — pido opinión a Opus

Contexto

Cutover ejecutado 2026-07-07/08: WordPress pasa a servir www.feadulta.com (antes Joomla).
Para no perder las URLs viejas de Joomla, el sitio Joomla se mantiene vivo bajo un subdominio
nuevo, antiguo.feadulta.com, con banner + noindex (issue de referencia: checklist maestro
del cutover). Mecanismo: mv físico de directorios en el mismo filesystem del hosting (cPanel,
sin acceso root, shell restringido — ver feadulta-server-glibc-rota en memoria).

  • Joomla: /web/*/web/antiguo/* (mv, no copia).
  • WordPress: /web/wp-nuevo/*/web/* (mv).
  • Subdominio antiguo creado en cPanel apuntando a /web/antiguo.

www.feadulta.com (WordPress) quedó correcto y verificado (contenido, dominio en enlaces,
GA4, Search Console, redirección 301 de URLs viejas de Joomla → antiguo, permalinks). Ese lado
está cerrado.

El problema: antiguo.feadulta.com

Tras el mv, el frontend de Joomla en antiguo.feadulta.com devuelve HTTP 500 para
cualquier ruta de contenido real (/es/, /item/8856-venid-a-mi.html, etc.), con cero
output de error capturable por PHP
(ni excepción, ni fatal reportado por
register_shutdown_function).

En cambio:

  • /administrator/ (panel admin de Joomla) → 200 OK, carga perfectamente.
  • / a secas → 200/redirect JS a /es/ (el bootstrap básico de Joomla funciona).

Es decir: el framework Joomla arranca bien (DB, sesión, bootstrap), pero algo específico del
pipeline de renderizado del frontend (plantilla + módulos + vista del componente) revienta
el proceso sin dejar rastro.

Cambios hechos en el mv (candidatos a causa)

  1. configuration.php: $log_path y $tmp_path tenían rutas absolutas hardcodeadas
    (/usr/home/feadulta.com/web/...) — corregidas a incluir /antiguo/. $live_site=''
    (relativo, no tocado, no debería importar). Confirmado que no quedan más rutas
    /usr/home/feadulta.com/web sin /antiguo/ en ese fichero.
  2. Plantilla fe_adulta_1/index.php: yo mismo añadí código condicional por HTTP_HOST
    (banner "hemos migrado" + noindex + header X-Robots-Tag) ANTES del mv, y se probó con
    éxito vía HTTP real contra el subdominio wp-nuevo con Host header simulado (200 OK, banner
    visible) — es decir, el mismo fichero, con los mismos bytes, SÍ renderizó una página completa
    correctamente antes de mover los ficheros. Esto hace menos probable (pero no descarta del
    todo) que mi edición sea la causa directa.

Diagnóstico hecho (todo descartado como causa, salvo lo no resuelto)

  • Plugin de sistema Admin Tools (com_admintools, extension_id 10207): desactivado y
    reactivado, sin cambio de comportamiento.
  • session_handler: probado 'database' (original) y 'none' — el 500 persiste en ambos
    casos. Sesión nativa PHP (session_start() files-based) funciona bien de forma aislada.
  • Versión/extensiones PHP: 8.3.31, sapi:fpm-fcgi, session y pdo_mysql cargadas — normal.
  • memory_limit=768M, max_execution_time=240, open_basedir incluye la ruta nueva
    /usr/home/feadulta.com/ — todo cubre el path /web/antiguo sin problema.
  • Tabla de sesiones Joomla (ew4r_session, 2605 filas) intacta.
  • Caché de página de Joomla: casi vacía, nada que pudiera estar sirviendo contenido corrupto
    desde la ruta vieja.
  • Bootstrap manual de Joomla envuelto en try/catch + handlers custom de error/shutdown
    (_diag.php, ruta /): ejecuta OK, solo warnings de deprecación normales de PHP 8.3 sobre
    código Joomla 3.x viejo.
  • Mismo bootstrap pero forzando $_SERVER['REQUEST_URI'] a una ruta de artículo real antes de
    cargar el framework (_diag2.php): llega al log hasta "app-created-ok" y ahí se corta sin
    más output — ni excepción, ni fatal, ni nada en el shutdown handler.

Hipótesis principal, sin confirmar

El servidor tiene un problema de compatibilidad glibc/libpthread conocido y documentado
(feadulta-server-glibc-rota): binarios que cargan libpthread (grep, sort, scp, php -l)
segfaultan (exit 139) de forma reproducible y no relacionada con nuestro código. La ausencia
total de output de error incluso con try/catch + shutdown handler alrededor de
$app->execute() es consistente con un crash de proceso a bajo nivel (segfault) durante el
renderizado de plantilla/módulo/componente del frontend — un crash así no pasa por el manejo de
errores de PHP en absoluto.

Pero esto es una hipótesis, no una confirmación: no he conseguido localizar el log de error real
del servidor (busqué en rutas típicas de cPanel tipo domlogs, sin éxito con el shell
restringido de esta cuenta) para confirmar un segfault a nivel de sistema.

Estado actual / decisión de prioridad

Rafa decidió (2026-07-08) que antiguo.feadulta.com es de prioridad baja — es un subdominio
legado, no el sitio principal. No se sigue invirtiendo tiempo en depurarlo de forma urgente. Se
documenta aquí para retomarlo con calma, y para pedir opinión a Opus sobre la causa más probable
y el siguiente paso de diagnóstico más eficiente, dado el shell muy restringido del hosting
(cPanel jail, sin uname/which/hostname, sin acceso root, sin log de errores localizado
aún).

Pendiente de limpieza (no relacionado con el bug, pero anotado aquí)

  • Ficheros de diagnóstico temporales en /web/antiguo/: _phpcheck.php, _phpcheck2.php,
    _diag.php, _diag2.php — exponen configuración interna de PHP, borrar cuando se cierre este
    issue.
  • configuration.php: $error_reporting quedó en 'maximum' (debería volver a 'none' en
    producción) una vez se concluya el diagnóstico.
  • Subdominio wp-nuevo en cPanel: ya no se usa, pendiente de eliminar.
# Cutover Joomla→WP: antiguo.feadulta.com da HTTP 500 en frontend — pido opinión a Opus ## Contexto Cutover ejecutado 2026-07-07/08: WordPress pasa a servir `www.feadulta.com` (antes Joomla). Para no perder las URLs viejas de Joomla, el sitio Joomla se mantiene vivo bajo un subdominio nuevo, `antiguo.feadulta.com`, con banner + `noindex` (issue de referencia: checklist maestro del cutover). Mecanismo: `mv` físico de directorios en el mismo filesystem del hosting (cPanel, sin acceso root, shell restringido — ver [[feadulta-server-glibc-rota]] en memoria). - Joomla: `/web/*` → `/web/antiguo/*` (mv, no copia). - WordPress: `/web/wp-nuevo/*` → `/web/*` (mv). - Subdominio `antiguo` creado en cPanel apuntando a `/web/antiguo`. **www.feadulta.com (WordPress) quedó correcto y verificado** (contenido, dominio en enlaces, GA4, Search Console, redirección 301 de URLs viejas de Joomla → antiguo, permalinks). Ese lado está cerrado. ## El problema: antiguo.feadulta.com Tras el `mv`, el frontend de Joomla en `antiguo.feadulta.com` devuelve **HTTP 500** para cualquier ruta de contenido real (`/es/`, `/item/8856-venid-a-mi.html`, etc.), con **cero output de error capturable por PHP** (ni excepción, ni fatal reportado por `register_shutdown_function`). En cambio: - `/administrator/` (panel admin de Joomla) → **200 OK**, carga perfectamente. - `/` a secas → **200/redirect JS a /es/** (el bootstrap básico de Joomla funciona). Es decir: el framework Joomla arranca bien (DB, sesión, bootstrap), pero algo específico del **pipeline de renderizado del frontend** (plantilla + módulos + vista del componente) revienta el proceso sin dejar rastro. ## Cambios hechos en el `mv` (candidatos a causa) 1. **`configuration.php`**: `$log_path` y `$tmp_path` tenían rutas absolutas hardcodeadas (`/usr/home/feadulta.com/web/...`) — corregidas a incluir `/antiguo/`. `$live_site=''` (relativo, no tocado, no debería importar). Confirmado que no quedan más rutas `/usr/home/feadulta.com/web` sin `/antiguo/` en ese fichero. 2. **Plantilla `fe_adulta_1/index.php`**: yo mismo añadí código condicional por `HTTP_HOST` (banner "hemos migrado" + `noindex` + header `X-Robots-Tag`) ANTES del `mv`, y se probó con éxito vía HTTP real contra el subdominio `wp-nuevo` con Host header simulado (200 OK, banner visible) — es decir, el mismo fichero, con los mismos bytes, SÍ renderizó una página completa correctamente antes de mover los ficheros. Esto hace menos probable (pero no descarta del todo) que mi edición sea la causa directa. ## Diagnóstico hecho (todo descartado como causa, salvo lo no resuelto) - Plugin de sistema Admin Tools (`com_admintools`, extension_id 10207): desactivado y reactivado, sin cambio de comportamiento. - `session_handler`: probado `'database'` (original) y `'none'` — el 500 persiste en ambos casos. Sesión nativa PHP (`session_start()` files-based) funciona bien de forma aislada. - Versión/extensiones PHP: 8.3.31, `sapi:fpm-fcgi`, `session` y `pdo_mysql` cargadas — normal. - `memory_limit=768M`, `max_execution_time=240`, `open_basedir` incluye la ruta nueva `/usr/home/feadulta.com/` — todo cubre el path `/web/antiguo` sin problema. - Tabla de sesiones Joomla (`ew4r_session`, 2605 filas) intacta. - Caché de página de Joomla: casi vacía, nada que pudiera estar sirviendo contenido corrupto desde la ruta vieja. - Bootstrap manual de Joomla envuelto en try/catch + handlers custom de error/shutdown (`_diag.php`, ruta `/`): ejecuta OK, solo warnings de deprecación normales de PHP 8.3 sobre código Joomla 3.x viejo. - Mismo bootstrap pero forzando `$_SERVER['REQUEST_URI']` a una ruta de artículo real antes de cargar el framework (`_diag2.php`): llega al log hasta `"app-created-ok"` y ahí se corta sin más output — ni excepción, ni fatal, ni nada en el shutdown handler. ## Hipótesis principal, sin confirmar El servidor tiene un problema de compatibilidad glibc/libpthread conocido y documentado ([[feadulta-server-glibc-rota]]): binarios que cargan libpthread (grep, sort, scp, `php -l`) segfaultan (exit 139) de forma reproducible y no relacionada con nuestro código. La ausencia total de output de error incluso con try/catch + shutdown handler alrededor de `$app->execute()` es consistente con un **crash de proceso a bajo nivel (segfault)** durante el renderizado de plantilla/módulo/componente del frontend — un crash así no pasa por el manejo de errores de PHP en absoluto. Pero esto es una hipótesis, no una confirmación: no he conseguido localizar el log de error real del servidor (busqué en rutas típicas de cPanel tipo `domlogs`, sin éxito con el shell restringido de esta cuenta) para confirmar un segfault a nivel de sistema. ## Estado actual / decisión de prioridad Rafa decidió (2026-07-08) que **antiguo.feadulta.com es de prioridad baja** — es un subdominio legado, no el sitio principal. No se sigue invirtiendo tiempo en depurarlo de forma urgente. Se documenta aquí para retomarlo con calma, y para pedir opinión a Opus sobre la causa más probable y el siguiente paso de diagnóstico más eficiente, dado el shell muy restringido del hosting (cPanel jail, sin `uname`/`which`/`hostname`, sin acceso root, sin log de errores localizado aún). ## Pendiente de limpieza (no relacionado con el bug, pero anotado aquí) - Ficheros de diagnóstico temporales en `/web/antiguo/`: `_phpcheck.php`, `_phpcheck2.php`, `_diag.php`, `_diag2.php` — exponen configuración interna de PHP, borrar cuando se cierre este issue. - `configuration.php`: `$error_reporting` quedó en `'maximum'` (debería volver a `'none'` en producción) una vez se concluya el diagnóstico. - Subdominio `wp-nuevo` en cPanel: ya no se usa, pendiente de eliminar.
Author
Owner

Opinión (Opus) — causa probable y próximos pasos

(a) Causa más probable

Coincido con la hipótesis de crash nativo del proceso (SIGSEGV), no un fatal PHP — confianza media-alta en el tipo de fallo, media en el trigger exacto.

El razonamiento decisivo es el que ya intuisteis pero conviene explicitar: register_shutdown_function dispara ante E_ERROR, memory_limit agotado y excepciones no capturadas (que PHP convierte en fatal). Que no dispare nada — ni con try/catch + shutdown alrededor de $app->execute() — descarta prácticamente todo el universo de errores gestionados por PHP y deja el proceso muriendo por debajo del runtime: segfault o kill por señal. Es exactamente el patrón de la glibc/libpthread rota ya documentada.

Matices importantes sobre lo que NO prueba lo que funciona:

  • / a secas NO valida el render: solo emite un redirect JS a /es/. Es un render mínimo, no ejercita plantilla + módulos + vista de componente.
  • /administrator/ no ejercita el pipeline que revienta: no corre los content plugins, ni el router SEF, ni el Language Filter del frontend.
  • La prueba previa contra wp-nuevo con Host simulado tampoco es equivalente: mismo fichero, sí, pero distinto docroot, distinto pool FPM y, sobre todo, distinta ruta de ejecución (probablemente no llegó a renderizar un artículo real con todos los content-plugins). No descarta tu edición, pero tampoco la incrimina.

Sospechosos concretos del trigger, por probabilidad:

  1. PCRE2 JIT durante el procesado de content-plugins / router SEF. Joomla aplica muchísimo preg_replace sobre el cuerpo del artículo y en el enrutado. Un fallo de PCRE JIT contra glibc rota da exactamente esto: proceso muerto, cero output, HTTP 500. Y el admin// casi no tocan ese camino. Es mi favorito porque además es trivial de probar y revertir.
  2. Extensión nativa invocada solo en frontend: intl (ICU/collator del Language Filter multilingüe), mbstring, imagick/gd (render de módulos con imágenes). Cualquiera que enlace libpthread encaja con el patrón documentado.
  3. Recursión del router SEF / Language Filter → stack overflow en C → SIGSEGV. El cambio de rutas o algún desajuste post-mv podría haber metido un bucle de enrutado. También produce muerte silenciosa sin traza PHP.

(b) Próximos pasos, priorizados (ejecutables con el shell jaulado)

1. Confirmar el segfault en el log correcto (lo más rentable, no depende del shell roto).
El error real NO estará en el output de PHP; estará como señal en el log de Apache/FPM:

  • Panel cPanel → "Errors" (muestra los últimos ~300 errores de Apache). Busca literalmente exit signal Segmentation fault (11) o child pid ... signal. Ese único renglón confirma o tumba toda la hipótesis.
  • Busca un fichero error_log dentro de /web/antiguo/ (PHP lo suele volcar en el CWD del script) y en ~/public_html/error_log, ~/logs/, ~/access-logs/.
  • Si hay PHP-FPM slowlog / pool log, suele colgar de ~/logs/.

2. SEF vs. RAW (el discriminador más barato y potente).
Compara vía curl la URL SEF contra la cruda sin router:
index.php?option=com_content&view=article&id=8856&lang=es vs. /item/8856-venid-a-mi.html

  • Si la RAW renderiza y la SEF revienta → el problema está en el router SEF / Language Filter (regex/recursión → apunta a PCRE JIT o bucle).
  • Si ambas revientan → es más abajo, en el render de componente/plantilla.

3. pcre.jit=0 (confirma/descarta el sospechoso #1 en un minuto).
Crea /web/antiguo/.user.ini (FPM lo lee) con:
pcre.jit=0
y para descartar el otro JIT: opcache.jit=0. Espera el TTL del .user.ini (~300s) o toca un .php. Si el 500 desaparece → PCRE2 JIT confirmado, y tienes workaround permanente sin tocar el binario roto.

4. Bisección por BD — SÍ, en bloque, no uno a uno.
El bootstrap ya funciona, así que puedes cortar por lo sano (haz backup de cada tabla antes):

  • UPDATE ew4r_modules SET published=0; en bloque → si el 500 se va, era un módulo; reactiva en binario (mitad y mitad).
  • Desactiva en bloque los plugins de content y editors (UPDATE ew4r_extensions SET enabled=0 WHERE type='plugin' AND folder IN ('content','editors','editors-xtd');). Estos corren en el render de artículo y NO tumban el arranque. Si desaparece → content-plugin.
  • Con los system ve con más tiento, pero como el bootstrap arranca bien, puedes probar desactivar en bloque los system no esenciales (deja languagefilter y redirect para el final, y NUNCA toques el que necesite el arranque). Merece la pena el "todos de golpe" también aquí para acotar rápido.

5. Aislar plantilla vs. componente sin php -l.

  • offline=1 en config: la página offline renderiza plantilla + módulo offline pero no el componente ni los content-plugins. Si la offline sale 200 → plantilla y base OK, el crash está en el pipeline de componente/content-plugin. Discriminador de 30 segundos.
  • Cambia el template style por defecto a uno core (protostar/beez3) en ew4r_template_styles (home=1). Si con el core renderiza → el culpable es fe_adulta_1 (tu index.php o algo que carga). Si sigue 500 → no es la plantilla.

6. Instrumentar _diag2.php por fases (localiza la fase exacta del segfault).
En vez de $app->execute() de una pieza, llama y loguea (con flush/escritura a fichero entre cada una): $app->route()$app->dispatch()$app->render(). La última línea escrita antes del corte te dice si muere en enrutado, despacho o render — el equivalente a un php -l funcional para este caso, y sin depender del binario que segfaultea.

Orden sugerido

1 (log cPanel) y 2 (SEF vs raw) primero: entre ambos, ~10 min, y probablemente ya sabes si es router/SEF y si hay firma de segfault. Luego 3 (pcre.jit) para confirmar el mecanismo. 4–6 solo si 1–3 no cierran el caso. Dado que Rafa lo marcó prioridad baja, con 1+2+3 tienes el 80% del diagnóstico por muy poco esfuerzo.

## Opinión (Opus) — causa probable y próximos pasos ### (a) Causa más probable **Coincido con la hipótesis de crash nativo del proceso (SIGSEGV), no un fatal PHP** — confianza *media-alta* en el *tipo* de fallo, *media* en el *trigger exacto*. El razonamiento decisivo es el que ya intuisteis pero conviene explicitar: `register_shutdown_function` **sí** dispara ante `E_ERROR`, `memory_limit` agotado y excepciones no capturadas (que PHP convierte en fatal). Que no dispare **nada** — ni con try/catch + shutdown alrededor de `$app->execute()` — descarta prácticamente todo el universo de errores gestionados por PHP y deja el proceso muriendo por debajo del runtime: **segfault o kill por señal**. Es exactamente el patrón de la glibc/libpthread rota ya documentada. Matices importantes sobre lo que NO prueba lo que funciona: - **`/` a secas NO valida el render**: solo emite un redirect JS a `/es/`. Es un render mínimo, no ejercita plantilla + módulos + vista de componente. - **`/administrator/` no ejercita el pipeline que revienta**: no corre los *content plugins*, ni el *router SEF*, ni el *Language Filter* del frontend. - **La prueba previa contra `wp-nuevo` con Host simulado tampoco es equivalente**: mismo fichero, sí, pero distinto docroot, distinto pool FPM y, sobre todo, distinta ruta de ejecución (probablemente no llegó a renderizar un artículo real con todos los content-plugins). No descarta tu edición, pero tampoco la incrimina. **Sospechosos concretos del trigger, por probabilidad:** 1. **PCRE2 JIT** durante el procesado de content-plugins / router SEF. Joomla aplica muchísimo `preg_replace` sobre el cuerpo del artículo y en el enrutado. Un fallo de PCRE JIT contra glibc rota da *exactamente* esto: proceso muerto, cero output, HTTP 500. Y el admin/`/` casi no tocan ese camino. Es mi favorito porque además es **trivial de probar y revertir**. 2. **Extensión nativa invocada solo en frontend**: `intl` (ICU/collator del Language Filter multilingüe), `mbstring`, `imagick`/`gd` (render de módulos con imágenes). Cualquiera que enlace libpthread encaja con el patrón documentado. 3. **Recursión del router SEF / Language Filter → stack overflow en C → SIGSEGV**. El cambio de rutas o algún desajuste post-`mv` podría haber metido un bucle de enrutado. También produce muerte silenciosa sin traza PHP. ### (b) Próximos pasos, priorizados (ejecutables con el shell jaulado) **1. Confirmar el segfault en el log correcto (lo más rentable, no depende del shell roto).** El error real NO estará en el output de PHP; estará como señal en el log de Apache/FPM: - **Panel cPanel → "Errors"** (muestra los últimos ~300 errores de Apache). Busca literalmente `exit signal Segmentation fault (11)` o `child pid ... signal`. Ese único renglón confirma o tumba toda la hipótesis. - Busca un fichero **`error_log`** *dentro* de `/web/antiguo/` (PHP lo suele volcar en el CWD del script) y en `~/public_html/error_log`, `~/logs/`, `~/access-logs/`. - Si hay **PHP-FPM slowlog / pool log**, suele colgar de `~/logs/`. **2. SEF vs. RAW (el discriminador más barato y potente).** Compara vía curl la URL SEF contra la cruda sin router: `index.php?option=com_content&view=article&id=8856&lang=es` vs. `/item/8856-venid-a-mi.html` - Si la RAW renderiza y la SEF revienta → el problema está en el **router SEF / Language Filter** (regex/recursión → apunta a PCRE JIT o bucle). - Si ambas revientan → es más abajo, en el **render de componente/plantilla**. **3. `pcre.jit=0` (confirma/descarta el sospechoso #1 en un minuto).** Crea `/web/antiguo/.user.ini` (FPM lo lee) con: `pcre.jit=0` y para descartar el otro JIT: `opcache.jit=0`. Espera el TTL del `.user.ini` (~300s) o toca un `.php`. Si el 500 desaparece → PCRE2 JIT confirmado, y tienes workaround permanente sin tocar el binario roto. **4. Bisección por BD — SÍ, en bloque, no uno a uno.** El bootstrap ya funciona, así que puedes cortar por lo sano (haz backup de cada tabla antes): - `UPDATE ew4r_modules SET published=0;` en bloque → si el 500 se va, era un **módulo**; reactiva en binario (mitad y mitad). - Desactiva en bloque los plugins de **`content` y `editors`** (`UPDATE ew4r_extensions SET enabled=0 WHERE type='plugin' AND folder IN ('content','editors','editors-xtd');`). Estos corren en el render de artículo y NO tumban el arranque. Si desaparece → content-plugin. - Con los `system` ve con más tiento, pero como el bootstrap arranca bien, puedes probar desactivar en bloque los system **no esenciales** (deja `languagefilter` y `redirect` para el final, y NUNCA toques el que necesite el arranque). Merece la pena el "todos de golpe" también aquí para acotar rápido. **5. Aislar plantilla vs. componente sin `php -l`.** - `offline=1` en config: la página offline renderiza plantilla + módulo offline pero **no** el componente ni los content-plugins. Si la offline sale 200 → plantilla y base OK, el crash está en el pipeline de componente/content-plugin. Discriminador de 30 segundos. - Cambia el *template style* por defecto a uno core (`protostar`/`beez3`) en `ew4r_template_styles` (`home=1`). Si con el core renderiza → el culpable es **`fe_adulta_1`** (tu `index.php` o algo que carga). Si sigue 500 → no es la plantilla. **6. Instrumentar `_diag2.php` por fases (localiza la fase exacta del segfault).** En vez de `$app->execute()` de una pieza, llama y loguea (con `flush`/escritura a fichero entre cada una): `$app->route()` → `$app->dispatch()` → `$app->render()`. La última línea escrita antes del corte te dice si muere en **enrutado, despacho o render** — el equivalente a un `php -l` funcional para este caso, y sin depender del binario que segfaultea. ### Orden sugerido 1 (log cPanel) y 2 (SEF vs raw) primero: entre ambos, ~10 min, y probablemente ya sabes si es router/SEF y si hay firma de segfault. Luego 3 (pcre.jit) para confirmar el mecanismo. 4–6 solo si 1–3 no cierran el caso. Dado que Rafa lo marcó prioridad baja, con 1+2+3 tienes el 80% del diagnóstico por muy poco esfuerzo.
Author
Owner

RESUELTO. No era un segfault — era un bucle de mod_rewrite de Apache.

Causa real

En /errors.log (Apache), cada ruta de contenido real de antiguo.feadulta.com daba:

AH00124: Request exceeded the limit of 10 internal redirects due to probable
configuration error. ..., referer: https://antiguo.feadulta.com/es/...

El .htaccess de Joomla tenía # RewriteBase / comentado (valor por defecto de Joomla, que asume que el sitio vive en la raíz del vhost). El subdominio antiguo en este cPanel no es un vhost separado con DocumentRoot propio en /web/antiguo — es un alias de subdirectorio sobre el mismo vhost. Con la base sin ajustar, el router SEF de Joomla generaba URLs internas mal resueltas y Apache entraba en bucle intentando reescribir la ruta, abortando a los 10 saltos. Encaja con la evidencia: / y /administrator/ funcionaban (rutas físicas reales, no dependen del RewriteBase), pero cualquier ruta SEF virtual (/es/item/..., /es/temas/...) entraba en bucle.

Fix aplicado

sed -i 's|# RewriteBase /|RewriteBase /|' /web/antiguo/.htaccess (backup guardado como .htaccess.bak-pre-rewritebase).

Verificado tras el cambio: /es/, /item/8856-venid-a-mi.html (redirige 301 a la URL SEF canónica, 200), /es/temas/678-... — todas devuelven 200 ahora.

Nota sobre el diagnóstico anterior

La hipótesis del segfault (PCRE2 JIT, glibc/libpthread) que barajamos antes —incluida la de Opus— quedó descartada por esta evidencia más directa. Lección: el log de Apache (/errors.log, en la raíz accesible desde el shell restringido, no en domlogs como busqué antes) tenía la respuesta desde el principio; debí buscarlo con más prioridad antes de especular con hipótesis de bajo nivel.

Pendiente

  • Limpieza de /web/antiguo/: ficheros _phpcheck*.php, _diag*.php, y ahora también .htaccess.bak-pre-rewritebase cuando se confirme estable.
  • Revertir $error_reporting de configuration.php a 'none'.
  • Cerrar este issue tras una comprobación final.
**RESUELTO.** No era un segfault — era un bucle de `mod_rewrite` de Apache. ## Causa real En `/errors.log` (Apache), cada ruta de contenido real de antiguo.feadulta.com daba: ``` AH00124: Request exceeded the limit of 10 internal redirects due to probable configuration error. ..., referer: https://antiguo.feadulta.com/es/... ``` El `.htaccess` de Joomla tenía `# RewriteBase /` comentado (valor por defecto de Joomla, que asume que el sitio vive en la raíz del vhost). El subdominio `antiguo` en este cPanel no es un vhost separado con DocumentRoot propio en `/web/antiguo` — es un alias de subdirectorio sobre el mismo vhost. Con la base sin ajustar, el router SEF de Joomla generaba URLs internas mal resueltas y Apache entraba en bucle intentando reescribir la ruta, abortando a los 10 saltos. Encaja con la evidencia: `/` y `/administrator/` funcionaban (rutas físicas reales, no dependen del RewriteBase), pero cualquier ruta SEF virtual (`/es/item/...`, `/es/temas/...`) entraba en bucle. ## Fix aplicado `sed -i 's|# RewriteBase /|RewriteBase /|' /web/antiguo/.htaccess` (backup guardado como `.htaccess.bak-pre-rewritebase`). Verificado tras el cambio: `/es/`, `/item/8856-venid-a-mi.html` (redirige 301 a la URL SEF canónica, 200), `/es/temas/678-...` — todas devuelven 200 ahora. ## Nota sobre el diagnóstico anterior La hipótesis del segfault (PCRE2 JIT, glibc/libpthread) que barajamos antes —incluida la de Opus— quedó descartada por esta evidencia más directa. Lección: el log de Apache (`/errors.log`, en la raíz accesible desde el shell restringido, no en `domlogs` como busqué antes) tenía la respuesta desde el principio; debí buscarlo con más prioridad antes de especular con hipótesis de bajo nivel. ## Pendiente - Limpieza de `/web/antiguo/`: ficheros `_phpcheck*.php`, `_diag*.php`, y ahora también `.htaccess.bak-pre-rewritebase` cuando se confirme estable. - Revertir `$error_reporting` de `configuration.php` a `'none'`. - Cerrar este issue tras una comprobación final.
Sign in to join this conversation.
No Label
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: rafa/feadulta#162