1. Introducción
El siguiente artículo explica cómo limpiar tablas de Prestashop que se suelen llenar y que contienen datos que no son vitales para el funcionamiento de la web. Con el tiempo, a medida que se llenan, pueden causar problemas de rendimiento.
El proceso se puede hacer de dos formas:
-
Automatizada, con la herramienta
crad-prestashop-mgr.pyc, que hace la limpieza, la optimización de la base de datos y además deja programada la automatización diaria de ambas (ver punto 4). - Manual, desde el gestor de #MySQL de Core-Admin, tabla a tabla (ver punto 3). Este apartado se mantiene para que quede visible exactamente qué hace el proceso automático.
| ADVERTENCIA: antes de cualquier cambio, haz una copia de seguridad: |
|---|
2. Tablas involucradas
Las siguientes tablas serán el blanco del borrado manual o automatizado para mantener fresco el Prestashop:
- ps_guest
- ps_connections
- ps_connections_page
- ps_connections_source
- ps_page_viewed
- ps_layered_filter_block
- ps_log
- ps_statssearch
- ps_pagenotfound
- ps_smarty_cache
-
ps_layered_price_index (y sus variantes numeradas:
ps_layered_price_index_2,ps_layered_price_index_3, …)
Todas ellas son tablas de estadísticas, logs, cachés o índices que Prestashop vuelve a generar por sí mismo, por lo que vaciarlas es seguro.
2.1. Cuidado con el prefijo de las tablas
ps_ es el prefijo por defecto, pero no todas las instalaciones lo usan: al instalar Prestashop se puede elegir otro (psx_, pshop_, un prefijo aleatorio, etc.). El prefijo real de cada tienda está en su fichero de configuración:
- Prestashop 1.7.x / 8.x / 9.x:
app/config/parameters.php→'database_prefix' => 'ps_', - Prestashop 1.6.x:
config/settings.inc.php→define('_DB_PREFIX_', 'ps_');
Si se trabaja a mano, hay que sustituir ps_ por el prefijo que use esa tienda. La herramienta lo lee automáticamente del fichero de configuración de la instalación, por lo que no hay que indicárselo.
2.2. Variantes de layered_price_index
El módulo de búsqueda por facetas (ps_facetedsearch) mantiene un índice de precios por tienda y por ranura de reconstrucción. Por eso, además de ps_layered_price_index, una instalación puede tener ps_layered_price_index_2, ps_layered_price_index_3, etc.
Todas ellas son índices reconstruibles y hay que limpiarlas y programarlas igual que la tabla base: si sólo se trata la base, la variante más grande se queda fuera del mantenimiento en silencio (es un caso que hemos visto con la variante ocupando varios GB mientras la tabla base estaba vacía).
La herramienta detecta y trata todas las variantes automáticamente. Sólo se consideran los sufijos numéricos, de manera que tablas como ps_layered_price_index_backup o ps_layered_price_index_old no se vacían nunca.
2.3. Tablas que NO se vacían: ps_cart_rule_combination
ps_cart_rule_combination guarda, por cada cupón/regla de carrito declarada como “restringida”, con qué otras reglas se puede combinar: una fila por cada par. Prestashop reescribe esas filas cada vez que se guarda un cupón y propaga la compatibilidad al resto, de modo que la tabla crece de forma cuadrática respecto al número de cupones restringidos y acaba siendo, con frecuencia, la tabla más grande de una tienda antigua (varios GB frente a unos pocos MB de ps_cart_rule).
Esta tabla no se debe vaciar nunca. El back-office pinta las casillas de compatibilidad leyendo precisamente esta tabla: si se trunca, todos los cupones restringidos pasan a ser no combinables y, al guardar cualquiera de ellos, ese estado se consolida (guardar no restaura la selección anterior, persiste lo que muestre el formulario).
Lo que sí se puede borrar, y es lo que hace la herramienta, son las filas que ya no pueden tener ningún efecto:
| Grupo | Significado | ¿Se borra? |
|---|---|---|
| Huérfanas | uno de los dos cupones ya no existe | Siempre (basura pura) |
| Caducadas hace tiempo | uno de los dos cupones caducó hace más de N días (180 por defecto) | Sí, política por defecto |
| Caducadas/desactivadas recientes | uno de los dos cupones está desactivado o caducó hace poco | Sólo con --include-expired
|
| Vivas | los dos cupones son utilizables | Nunca |
El grupo de “caducadas hace tiempo” ignora a propósito el flag active: un cupón desactivado con fecha de fin futura es una campaña pausada y, si se reactiva, aparecería con su lista de compatibilidades vacía. Por eso esos casos sólo se tocan pidiéndolo explícitamente.
Borrar pares caducados no tiene efecto en la tienda mientras el cupón siga caducado: CartRule::checkValidity() rechaza el cupón antes de llegar a comprobar la combinabilidad.
3. Borrado manual
Este es el proceso manual, equivalente a lo que hace la automatización, útil para revisar tabla a tabla qué se está tocando.
-
Para borrar estas tablas arranca el gestor de #MySQL. Para ello necesitas ser administrador de la máquina o tener un usuario administrador de plataforma:
-
Dentro, localizar la base de datos asociada a tu Prestashop, y en la pestaña de tablas, buscarlas para poder pinchar sobre ellas:
-
Dentro de la ficha de la tabla usar el botón de “Limpiar tabla de BD”: OJO: selecciona bien!:
Lo que hace ese botón es, simplemente, un TRUNCATE TABLE sobre la tabla seleccionada. El equivalente por consola sería:
TRUNCATE TABLE ps_guest;
TRUNCATE TABLE ps_connections;
TRUNCATE TABLE ps_connections_page;
TRUNCATE TABLE ps_connections_source;
TRUNCATE TABLE ps_page_viewed;
TRUNCATE TABLE ps_layered_filter_block;
TRUNCATE TABLE ps_log;
TRUNCATE TABLE ps_statssearch;
TRUNCATE TABLE ps_pagenotfound;
TRUNCATE TABLE ps_smarty_cache;
TRUNCATE TABLE ps_layered_price_index;
Recuerda ajustar el prefijo (punto 2.1) y añadir las variantes numeradas de ps_layered_price_index que tenga esa tienda (punto 2.2). Para saber cuáles hay:
SHOW TABLES LIKE 'ps\_layered\_price\_index%';
4. Automatizar el borrado
4.1. Desde el interfaz web
Para automatizar el borrado, simplemente completa los de configuración de hora de borrado y luego pulsa a editar. Esto creará una configuración periódica, diaria, para el borrado de la tabla:
Hay que repetirlo para cada una de las tablas del punto 2.
4.2. Con crad-prestashop-mgr.pyc (recomendado)
Todo lo anterior (limpieza, optimización y programación diaria de ambas) se puede hacer en un único comando. Es la forma recomendada porque no se olvida ninguna tabla, aplica el prefijo real de la tienda y recoge las variantes de índices:
crad-prestashop-mgr.pyc --optimize-tables example.com --dry-run
Con --dry-run sólo informa: qué tablas existen, cuáles se van a limpiar, cuáles no están presentes y qué programación se dejaría puesta, sin tocar nada. Cuando el informe sea el esperado, se aplica:
crad-prestashop-mgr.pyc --optimize-tables example.com --yes
La tienda se puede identificar por dominio, por nombre de hosting o por la ruta de la instalación.
Los pasos que ejecuta son:
-
Limpieza de todas las tablas de rendimiento que existan en esa base de datos (
TRUNCATE), incluyendo todas las variantes delayered_price_index. -
Poda de los pares muertos de
cart_rule_combination(huérfanos + caducados hace más de 180 días), volcando antes las filas borradas a una copia restaurable. Este paso sólo se activa si la tabla supera los 100 MB. - Optimización de toda la base de datos, que además reconstruye la tabla podada para que el espacio vuelva al disco.
- Programación de la limpieza diaria automática de cada tabla (por defecto a las 04:00).
- Programación de la optimización diaria automática de la base de datos (por defecto a las 05:00).
Las horas se pueden cambiar:
crad-prestashop-mgr.pyc --optimize-tables example.com --cleanup-time 03:30 --optimize-time 04:30 --yes
Es decir, una sola ejecución deja la tienda limpia y el mantenimiento diario configurado, que es lo que en el punto 4.1 habría que hacer tabla a tabla desde el interfaz.
4.3. Dónde queda configurada la automatización
La programación de los pasos 4 y 5 no es un temporizador interno: se materializa en ficheros de cron reales, que la propia herramienta muestra al final de la ejecución:
| Qué | Dónde |
|---|---|
| Limpieza diaria, un fichero por tabla | /etc/cron.d/mysql-manager-auto-cleanup-<tabla>-<basededatos>-<servidor> |
| Script que ejecuta cada uno de ellos | /var/beep/core-admin/client-agent/scripts/mysql-manager-auto-cleanup-<tabla>-<basededatos>-<servidor>.py |
| Optimización diaria de la base de datos | /etc/cron.d/mysql-manager-auto-optimize-<basededatos>-<servidor> |
Los nombres se normalizan: los espacios y los guiones bajos pasan a guiones y todo va en minúsculas. Por ejemplo, la tabla ps_guest de la base de datos tienda_portatilmovil en el servidor MySQL Default queda en:
/etc/cron.d/mysql-manager-auto-cleanup-ps-guest-tienda-portatilmovil-default
Para revisarlos todos de golpe:
cat /etc/cron.d/mysql-manager-auto-cleanup-*
cat /etc/cron.d/mysql-manager-auto-optimize-*
El script que lanza cada cron de limpieza es un pequeño fichero generado que hace un TRUNCATE TABLE de esa tabla, y el cron de optimización llama a crad-mysql-dump-all.pyc -o.
Para desactivar la automatización, hay que quitar la hora de limpieza/optimización desde el gestor de #MySQL del interfaz web: eso borra los ficheros. Si se borran a mano, la opción sigue marcada como activa en el gestor y volvería a escribirlos en la siguiente edición.
5. Optimización de tablas por borrados recurrentes
Otro aspecto a tener en cuenta a la hora optimizar la base de datos de un prestashop es que algunas tablas puede llegar a crecer mucho se almacen información que fluctúa mucho, es decir, muchos añadidos unidos a muchos borrados.
Esto pasa especialmente para tablas de índices. Son tablas con mucha información pero que no podemos borrar.
Sin embargo, en dichos casos, si exportamos la información de dichas tablas vemos que no hay una relación directamente entre el uso y el tamaño de la base de datos. El motivo es que InnoDB no devuelve al sistema de ficheros las páginas que libera un DELETE: hay que reconstruir la tabla para recuperar ese espacio.
En dichos casos, recomendamos seguir procedimiento de optimización:
El paso 3 de --optimize-tables (punto 4.2) ya hace esto sobre toda la base de datos, y deja además la optimización diaria programada.
6. Limpieza de combinaciones de cupones (cart_rule_combination)
Cuando la tienda usa muchos cupones restringidos, esta tabla suele ser la que más ocupa de toda la base de datos. Como se explica en el punto 2.3, no se puede vaciar, pero sí se pueden podar los pares que ya no sirven.
Primero, para ver la situación sin tocar nada:
crad-prestashop-mgr.pyc --clean-cart-rule-combinations example.com --dry-run
La salida desglosa los cuatro grupos (huérfanos, caducados hace tiempo, caducados recientes y vivos) con filas y MB de cada uno, además del número de cupones totales y cuántos están desactivados o caducados. Para aplicar la poda:
crad-prestashop-mgr.pyc --clean-cart-rule-combinations example.com --yes
Detalles del proceso:
-
Todo lo que se borra se vuelca antes a un fichero
.sql.gzrestaurable conzcat FICHERO | mysql BASEDEDATOS. Por defecto se escribe en/var/lib/core-admin/prestashop_manager; se puede elegir con--backup-filey saltar con--no-backup(no recomendado: estos datos no los regenera Prestashop). La ejecución se niega a empezar si el sistema de ficheros no tiene sitio para la copia. - El borrado se hace por lotes sobre rangos de
id_cart_rule_1(la primera columna de la clave primaria), para que cada sentencia vaya por índice y las transacciones queden acotadas. En tablas de decenas de millones de filas esto evita bloqueos largos. - Al terminar se reconstruye la tabla (
OPTIMIZE TABLE) para devolver el espacio al disco. Se puede saltar con--skip-optimize. - Con
--older-than Nse cambia el umbral de “caducado hace tiempo” (180 días por defecto). - Con
--include-expiredse borran también los pares de cupones simplemente desactivados o caducados hace poco. Es opcional a propósito: son campañas pausadas y, si se reactivan, habría que volver a marcar a mano su lista de compatibilidades en el back-office.
crad-prestashop-mgr.pyc --clean-cart-rule-combinations example.com --older-than 365 --yes
crad-prestashop-mgr.pyc --clean-cart-rule-combinations example.com --include-expired --yes
7. Eliminar los cupones caducados (causa del crecimiento)
Podar las combinaciones trata el síntoma. Mientras los cupones muertos sigan en ps_cart_rule, cada cupón restringido nuevo vuelve a generar pares contra ellos.
--remove-expired-cart-rules borra los cupones que caducaron hace más de --older-than días (180 por defecto), replicando exactamente lo que hace Prestashop al borrar un cupón (CartRule::delete()): cart_cart_rule, cart_rule_carrier, cart_rule_shop, cart_rule_group, cart_rule_country, cart_rule_lang, cart_rule_combination, cart_rule_product_rule_group, después cart_rule_product_rule y cart_rule_product_rule_value por dependencia, y finalmente cart_rule.
crad-prestashop-mgr.pyc --remove-expired-cart-rules example.com --dry-run
crad-prestashop-mgr.pyc --remove-expired-cart-rules example.com --older-than 365 --yes
Garantías:
-
Nunca toca un cupón que siga siendo válido, que esté simplemente pausado o que no tenga fecha de fin. El criterio es la fecha
date_topasada hace más de N días, nuncaactive = 0. -
El histórico de pedidos no se ve afectado:
ps_order_cart_ruleguarda su propia copia del nombre y el importe del cupón, que es lo que pinta el back-office en un pedido antiguo. La herramienta comprueba que exista esa columna y, si no existe, se niega a tocar los cupones referenciados por pedidos. - Todas las filas borradas de todas las tablas se vuelcan antes a una copia restaurable.
Este comando no forma parte de --optimize-tables: hacer desaparecer cupones del back-office es visible para el responsable de la tienda y debe ser una decisión consciente.
8. Revisar el estado antes de actuar
Para ver de un vistazo todos los problemas de rendimiento de una tienda (versión de PHP, opcache, modo debug, ajustes de front-office, recolectores de estadísticas, tablas que crecen sin control, cart_rule_combination, specific_price, carritos abandonados…) sin modificar nada:
crad-prestashop-mgr.pyc --check-performance example.com
El informe termina con las recomendaciones concretas, indicando qué comando de los anteriores aplicar en cada caso. Conviene lanzarlo antes y después del mantenimiento.
Un apunte importante: los recolectores de estadísticas de Prestashop (PS_STATSDATA_*) son los que vuelven a llenar las tablas del punto 2. Si no se usan esas estadísticas, desactivarlos evita el problema de raíz, y eso lo aplica:
crad-prestashop-mgr.pyc --fix-performance example.com



