Desarrollo de Aplicaciones

Full text search con Laravel

Full Text Search nos permite buscar una cadena de texto en una aplicación web consiguiendo un conjunto de elementos que contengan ese texto.

Full text search con Laravel

¿Qué es Full Text Search?

Es común poder buscar una cadena de texto en una aplicación como, por ejemplo, en una tienda online. Debemos de ser capaces de buscar un texto y que el resultado sea un conjunto de productos que contengan ese texto en el título, en la descripción o en la especificaciones.

En Laravel para realizar esta consulta haríamos:

$productos->where('titulo', 'like', '%texto%')->orWhere('descripcion', 'like', '%texto%')

Con mysql se ejecutaría de la siguiente manera:

select * from productos where titulo like '%texto%' or descripcion like '%texto%' or...

El problema de esta búsqueda es que le estamos diciendo que 'texto' puede estar al principio, en medio o al final de cada campo que consultamos, lo que conlleva una gran carga del servidor. Estamos hablando de muchos segundos y a nadie le gusta esperar.

Esta espera se incrementa al añadir registros en la tabla que queremos, pasando de un par de segundos para unos pocos cientos de registros, a minutos cuando hablamos de millones. Esto es algo a tener en cuenta, ya que hay que valorar la posibilidad de que nuestra tienda vaya a tener solo unos pocos productos. Si es así, con este código ya cumplimos nuestro cometido y no hay necesidad de añadirle nada al servidor o tener que pagar por un servicio externo. Pero si estamos creando un proyecto que necesita un tamaño superior como, por ejemplo, una tienda que integre productos de muchos proveedores, podemos acabar hablando fácilmente de millones de productos. Aquí la búsqueda anterior pasa del par de segundos de la tienda pequeña a un par de minutos. Nadie espera 2 minutos.

Así pues, tenemos un millón de productos, queremos buscar por texto en cualquiera de sus campos y no queremos esperar. Toca cambiar nuestro sistema de búsqueda. Laravel 5.3 vino con un par de regalos bajo el brazo. Mi favorito es sin duda las Notificaciones, pero aquí no nos sirven. Seguimos buscando y vemos que otro de estos regalos es Laravel Scout, que nos podrá ayudar mejor en esta tarea.

Realizamos una petición 'composer' a nuestro Laravel/Scout, le indicamos a los productos que son "Searchables" y los importamos a Scout con:

php artisan scout:import App\Producto

Y el siguiente paso será:

Producto::search('texto')

La magia ocurre y tenemos nuestro resultado en 200ms. 

También existe la opción de conectar Scout con servicios como Algolia, un servicio de pago donde 1M de registros costaría aproximadamente 250$/mes, algo que no está al alcance de todo el mundo. Esto también sucede con los servidores. Si tu app necesita un servidor potente porque tiene mucha carga y no se puede optimizar más, debes pasar por una inversión de ese tipo.

También puedes optar por instalar tu propio servicio en alguno(s) de tus servidores, en este caso ElasticSearch.

Uses Algolia o ElasticSearch, la gracia de Scout está en que es invisible en el código, él se encarga de transformar tu 'search' al código que necesitan estos servicios. Esto permite empezar por el plan gratuito de Algolia (10k registros, mostrando su logo) a Elastic una vez que superas este límite sin tener que hacer grandes cambios en tu código.

Como la mayoría de características de Laravel simplemente funciona y él mismo se encarga de la parte más tediosa.

Comparte este artículo

Artículos Relacionados