Técnicas de caché en php
En este caso mi intención era comprobar la mejora real utilizando un pequeño script PHP para generar un archivo de caché mediante código, aunque existen maneras y maneras, prometo ir analizando varias otras opciones en el transcurso de siguientes entradas.
El objetivo es crear archivos HTML “puros” a partir de scripts PHP que podrían contener: largos y complejos procesos, consultas a base de datos, etc.; pero que una vez creado el contenido no necesita la generación del mismo constantemente. Si necesitamos que el contenido sea 100% en tiempo real el caché, en este caso, no es recomendable ni útil, la intensión es “cachear” páginas con contenidos que pueden de alguna u otra manera tardar N segundos en refrescarse dicho contenido. Al generar archivos HTML estamos protegiendo el desgaste de los recursos del servidor, y obviamente optimizamos el rendimiento general: recursos más resultados, entiéndase que al consumir directamente HMLT estaríamos con: menos consultas a Base de datos, menos procesos, etc.
Pero cómo optimizar algo sin una métrica inicial?
Bueno, eso mismo es lo que tenemos que hacer, medir primeramente el tiempo de ejecución de un script sin cache, puede ser toda una página (entiéndase que nos referimos al documento individual pues, muchas personas se podrían referir erróneamente como página a un sitio) o parte del script en realidad.
Para medir utilicé el siguiente código
<?php
$comienzo= microtime(true); //al inicio del archivo
?>
Luego viene todo el código PHP, HTML, etc.
Y al final colocamos esto.
<?php
/*—————-Fin Código———————–*/
$final= microtime(true); //al final del archivo
echo «Tiempo: «. number_format($final-$comienzo,4).» segundos.»;
?>
Ahora tendremos documentado el tiempo de ejecución, debemos guardar esa información.
Seguidamente crearemos dos nuevos archivos.
top_cache.php
<?php
$comienzo= microtime(true); //al inicio del archivo
$url = $_SERVER[«SCRIPT_NAME»]; //obtenemos el nombre la url y nombres de archivo actual
$break = explode(‘/’, $url); //dividimos las uniones por / y obtenemos una matriz de datos
$file = $break[count($break) – 1]; //obtenemos el nombre real del archivo
$cachefile = ‘cached-‘.substr_replace($file ,»»,-4).’.html’; //creamos un nombre nuevo para el caché, este será HTML para optimizar recursos
$cachetime = 900; //seteamos el tiempo de duración de la caché en segundos | 900/60 = 15 minutos
// Servir desde la cache si es más actual que $cachetime
if (file_exists($cachefile) && time() – $cachetime < filemtime($cachefile)) {
echo «<!– Copia en cache generada «.date(‘H:i’, filemtime($cachefile)).» –>\n»;
include($cachefile);
$final= microtime(true); //al final del archivo
echo «<div>Nuevo tiempo: «. number_format($final-$comienzo,4).» segundos.</div>»;
exit;
}
ob_start(); // Crear buffer de salida
?>
bottom_cache.php
<?php
// Cachear el contenido del fichero
$cached = fopen($cachefile, ‘w’); //toma el nombre del archivo caché que creamos en topo_cache si no existe o si ya pasó su vida útil
fwrite($cached, ob_get_contents()); //escribe todo el contenido del archivo actual
fclose($cached);
ob_end_flush(); // Enviar el navegador
?>
Este archivo top_cache.php debo incluirlo en la primera línea de mi página a “cachear” y bottom_cache.php al final.
<?php include "top_cache.php"; ?>
Aquí va el código PHP, HTML, css, etc.
<?php include "bottom _cache.php"; ?>
En mis pruebas se notó la mejoría a un 50% pero extrañamente recién a partir de la tercera llamada a la página; otra cosa que no me funcionó es cuando existe paginación de por medio pues, esto está basado en el nombre del archivo y cuando es paginación, el nombre de la página sigue siendo la misma solo cambian los parámetros, a no ser que usemos url amigables en cuyo caso cada paginación podría ser un nombre distinto (veremos url amigables en otras entradas)