Como hacer un Buscador con Ajax

En este post ahora trataré de explicar como crear un buscador utlizando AJAX:

Mucho de esto, fue código que implementé hace mucho tiempo, y aunque existen mejores o mas sencillas formas de hacerlo utilizando algun framework, trataré de explicar la forma en que trabajé cuando me inicié en esto de AJAX

Antes de continuar, aquí pueden ver el resultado final o descargar el ejemplo completo:

Antes de iniciar, describiré brevemente los archivos con los cuales consiste el buscador:

  • /buscador.php Este archivo es la estructura de todo el buscador.
  • /busqueda.php Este archivo es lo mismo que buscador.php con la diferencia de que le quitamos todo, menos lo que está entre el div resultados: <HTML>...<div id="resultados">...</div></BODY></HTML>. Esto con la finalidad de llamar este archivo para obtener las búsquedas y mostrarlas con AJAX sin recargar todo el sitio nuevamente.
  • /buscador.js Aquí están incluídos las funciones básicas para el funcionamiento del buscador.
  • /buscador.css Le da una bonita apariencia el buscador.
  • /include/funciones.php Aquí sólo guardamos: sql_quote para el filtrado de las consultas que se necesiten ejecutar.
  • /include/pagination.class.php Aquí descripción
  • /config.php Aquí la configuración básica para el funcionamiento del buscador. Host, usuario, password, base de datos.

Ahora, trataré de describir a detalle la finalidad de cada archivo:


Warning: include(/home/misalgor/public_html//../wp-content/uploads/buscador/source/buscador.php) [function.include]: failed to open stream: No such file or directory in /home/misalgor/public_html/app/controllers/index_controller.php(32) : runtime-created function(1) : eval()'d code on line 2

Warning: include() [function.include]: Failed opening '/home/misalgor/public_html//../wp-content/uploads/buscador/source/buscador.php' for inclusion (include_path='.:/usr/lib/php:/usr/local/lib/php') in /home/misalgor/public_html/app/controllers/index_controller.php(32) : runtime-created function(1) : eval()'d code on line 2

Warning: include(/home/misalgor/public_html//../wp-content/uploads/buscador/source/busqueda.php) [function.include]: failed to open stream: No such file or directory in /home/misalgor/public_html/app/controllers/index_controller.php(32) : runtime-created function(1) : eval()'d code on line 2

Warning: include() [function.include]: Failed opening '/home/misalgor/public_html//../wp-content/uploads/buscador/source/busqueda.php' for inclusion (include_path='.:/usr/lib/php:/usr/local/lib/php') in /home/misalgor/public_html/app/controllers/index_controller.php(32) : runtime-created function(1) : eval()'d code on line 2

Warning: include(/home/misalgor/public_html//../wp-content/uploads/buscador/source/buscador_js.php) [function.include]: failed to open stream: No such file or directory in /home/misalgor/public_html/app/controllers/index_controller.php(32) : runtime-created function(1) : eval()'d code on line 2

Warning: include() [function.include]: Failed opening '/home/misalgor/public_html//../wp-content/uploads/buscador/source/buscador_js.php' for inclusion (include_path='.:/usr/lib/php:/usr/local/lib/php') in /home/misalgor/public_html/app/controllers/index_controller.php(32) : runtime-created function(1) : eval()'d code on line 2

Espero que este tutorial, les hay servidor de algo y valga la pena la desveladota que me aventé... mañana mi examen de Ecuaciones Diferenciales y no estudié nada por estar escribiendo esto =S

Y bueno, ya para terminar: cualquier comentario o sugerencia que permita reforzar o documentar un poco mas este tutorial, es bien recibido :D ...

Igual y si notan muchas inconsistencias en mi explicación o horrores ortográficos pues me echan un grito en los comentarios /puf que yo ya me voy a dormir! u_U

Comentarios

2007-10-17 03:13:12
Buscador en PHP con un poco de AJAX V 0.1 Beta
[...] actualizada tan pronto tenga el tutorial y la CSStilación de Stan en mis manos Mejor escribí otro post, para que aparescan los cambios en el [...]
2007-10-17 10:55:01
Stan
Eres un Crack!
2007-10-17 12:25:20
pecesama
El titulo en ingles quedaria mejor como How to Create an Ajax Live Search o algo similar :P
2007-10-17 15:49:09
Victor De la Rocha
@Stan: :D
@pecesama: Si, me gusta mas y ya lo cambié en el url gracias, gracias jeje
2007-10-17 18:03:00
JL
Te equivocaste, no son 1 y 2 los eventos sino 1 y 4 (el error es nadamas en la redacción, el código si está bien)
2007-10-18 07:09:50
Victor De la Rocha
Gracias JL, ya hice el cambio :)

@Stanmx: No te hagas... Que estamos anciosos esperando la CSSstilización del buscador :D
2007-10-21 03:05:44
Algunos estilos CSS para las cajas de búsqueda
[...] Mis Algoritmos Hi :) 123456 « Como hacer un Buscador con Ajax [...]
2007-11-01 17:46:01
CHICOGREENDAY
mil algoritmos como harias un buscador youporn con ajax aver si hace un tuto y calro la descarga ah por cierto este buscador no le vanta tengo problemas con el config.php aver si me explicas si chaufas
2007-11-03 10:21:05
Revilo
En la parte de la paginacion me direcciona a index.php pero este archivo no lo tengo, me podrias ayudar diciendome que lleva este archivo?
2007-11-03 16:03:54
Victor De la Rocha
@CHICOGREENDAY: :S

@Revilo: Fue un error mio, hay que cambiar index.php por buscador.php en donde está la línea que configura la paginación: Deberá ser algo así $p->target('buscador.php') (En los archivos busqueda.php y buscador.php casi al final de ámbos archivos). Si esto no soluciona el problema lo veo mas tarde por que estoy fuera de la ciudad y lejos de mi computadora personal.
2007-11-06 03:03:18
ChicaRubia
Jeje, lamento hacer pregunta de rubia, pero la parte del direccionamiento... no me anda!!! (son como las 5 de la madrugada, mola mogollon tu script, quise probarlo, pero... no anda! :S ) Intente lo de tu ultimo post, pero no se, creo q la fatiga me esta ganando!!! :P
2007-11-06 18:39:57
Victor De la Rocha
ChicaRubia disculpa que no pueda atender esto en estos momentos, pero el fin de semana reviso con calma que está mal explicado o cual es el error.

:P Comprensión, comprensión... que estoy atareadamente lleno de trabajo :S
2007-11-07 18:03:13
ChicaRubia
Sorry Vic! Jaja, no hay problema, cuando puedas, es q soy ansiosa! :P (cuando algo me gusta, voy y lo consigo, jajajaj!) Pero no t hagas problema, te re entiendo, xq yo tb estoy llena de trabajo! :S Creeme, si tuviera algo de time para betatestearlo en profundidad, lo haria! Hagamos un trato: si puedo, trato de meter mano al codigo y colaborar algo, xq en verdad esta MUY bueno este script!!! :D (y sino... pues vere de colaborar en otro script; la verdad es q no conocia tu blog, pero me volvere asidua visitante, xq esta interesante!!!)
2007-11-29 15:11:21
Intergus
Hola Victor

Me está gustando tu codigo, quiero utilizarlo pero me encuentro con algunas dudas. Estoy haciendo funcionar solo buscador.php y parace que todo va Ok, parece que no necesita a busqueda.php. Solo me da un error pero no creo que se deba a haber anulado busqueda.php

Cuando tecleo una letra que no está en lo buscado me devuelve en el DIV resultado el tipico OBJETO NO ENCONTRADO, sin embargo no hay problemas mientras vas tecleando letras que si que estan, es decir que si que arrojan resultados.

La otra duda es ¿para que el boton del submit, si no es necesario pulsarlo? ¿sería posible usarlo para enviar la consulta a otra pagina?

Esta ultima pregunta es porque sería muy util buscar en una base de datos y cuando ya tengas el resultado que buscas (por ejemplo se te haya quedado en 5 o 6 registros que coinciden con tu busqueda, le mandas a otro php la query que arroja esos 5 resultados para que haga algo con ellos, como por ejemplo pintarlos en un google map (que es mi intención), si te interesa hablamos del tema....
Saludos
2007-11-29 15:36:59
Victor De la Rocha
Hola Intergus

buscador.php es la base de esta aplicación. El muestra resultados si le envías la variable ?q= en la barra de direcciones, pero si en vez de enviar la variable, escribes en la caja de texto, esta manda llamar a busqueda.php con la variable ?q= algo así busqueda.php?q=. Así, busqueda.php trae los resultados tal cual lo haría buscador.php, pero sin volver a mostrar la caja de búsqueda y el botón enviar. Son indispensables, ámbos archivos.

Cuando tecleo una letra que no está en lo buscado me devuelve en el DIV resultado el tipico OBJETO NO ENCONTRADO, sin embargo no hay problemas mientras vas tecleando letras que si que estan, es decir que si que arrojan resultados.

No entendí muy bien eso...

El botón "submit" podría ocultarse con CSS, y aunque no sirva de mucho si tenémos javascript activado, este debería funcionar cuando "javascript no está activado" :)

Puedes comentar lo que gustes. Cuéntame más acerca de lo que quieres hacer con google map. Podría ocurrírseme algo.

2007-11-29 16:48:27
Intergus
Pues no entiendo entonces muy bien como va.... lo estudiaré un poco más.

Lo que quiero hacer es permitir que busquen todos aquellos registros que cumplan la condicion de tener en un determinado campo, la palabra que el usuario busca, cuando al usuario ya le parece buena la busqueda, enviar esa busqueda a otro php que hará esa consulta y meterá los resultados (que serán los mismos que arrojó el buscador), los meterá como marcadores en el google map. Esa parte ya la tengo funcionando, es decir puedo hacer una consulta "select * from tabla where campo like $q" y lo que arroja, lo estoy metiendo en el mapa, ya que los registros disponen de coordenadas entre otras cosas.

Pero no se como hacer para lanzar la consulta. Por eso te comentaba si se podia usar el boton del form para lanzar esa consulta a un index con la query oculta para que no aparezca en el navegador.....

No se, ¿cómo lo ves?
2007-11-29 17:13:10
Intergus
La paginación da error. Al principio sale bien pero al no mostrar los resultados de la base de datos pero si los cuenta, saca paginación (2 páginas) pero no se ven resultados pues aun no se ha tecleado nada en la caja del buscador. Pues en ese momento si se pasa de pagina, salta error de OBJETO NO ENCONTRADO
2007-11-29 17:16:40
Intergus
vale.... solucionado cambiando en busqueda.php y buscador.php, aquello de ....
$p->target("index.php............
por
$p->target("buscador.php..........

son 2 lineas en cada fichero.
2007-12-01 14:40:06
Intergus
Hola Victor

En un intento de mejora, he modificado este trozo de codigo en ambos php (buscador y busqueda)

if(isset($_GET['q']) and !eregi('^ *$',$_GET['q'])){
$q = sql_quote($_GET['q']); //para ejecutar consulta
$busqueda = htmlentities($q); //para mostrar en pantalla
 
if ($q''){
//CUENTA EL NUMERO DE PALABRAS
$trozos=explode(" ",$q);
$numero=count($trozos);
if ($numero==1) {
//SI SOLO HAY UNA PALABRA DE BUSQUEDA SE ESTABLECE UNA INSTRUCION CON LIKE
$sqlStr = "SELECT * FROM empresas WHERE pal_busca LIKE '%$q%'";
$sqlStrAux = "SELECT count(*) as total FROM empresas WHERE pal_busca LIKE '%$q%'";
} elseif ($numero&gt;1) {
//SI HAY UNA FRASE SE UTILIZA EL ALGORTIMO DE BUSQUEDA AVANZADO DE MATCH AGAINST
//busqueda de frases con mas de una palabra y un algoritmo especializado
$sqlStr = "SELECT *, MATCH ( descripcion, pal_busca ) AGAINST ( '$q' ) AS Score FROM empresas WHERE MATCH ( descripcion, pal_busca ) AGAINST ( '$q' ) ORDER BY Score DESC";
$sqlStrAux = "SELECT count(*) as total FROM empresas WHERE MATCH ( descripcion, pal_busca ) AGAINST ( '$q' )";
 
}
}
}else{
$sqlStr = "SELECT * FROM empresas WHERE pal_busca LIKE ''";
$sqlStrAux = "SELECT count(*) as total FROM empresas WHERE pal_busca LIKE ''";
}



Con ello pretendo hacer una busqueda más completa para cuando pongan mas de una palabra en la caja de busqueda, pues si en el campo hay por ejemplo "pan pasteles tartas" y en la caja de busqueda pones pan tartas ya no encontraría nada y con este otro tipo de busqueda si que lo haria, pero me da un error, relativo al mysql_assoc y es por el valor de $sqlStrAux que no le debe de llegar....

¿se te ocurre algo?
Gracias
2007-12-01 15:10:22
Victor De la Rocha
Si Intergus, esa sería una mejora en la consulta que realiza la búsqueda. No está de mas mencionar que este paso requiere crear un índice de texto completo en la tabla con la que trabajaremos referenciando a los campos con los que se realizará la búsqueda (Esta es para @Stan que está aprendiendo de estas cosas y trabajando con la CSStilización del buscador :P )

Este paso podemos verlo en la documentación de MySQL con mucho detalle: "12.7. Funciones de búsqueda de texto completo (Full-Text)".

Bueno, continuando con el problema:

Creo que en las últimas dos consultas SQL te equivocaste. Yo no pondría la búsqueda con espacios en blanco:

...}else{
$sqlStr = "SELECT * FROM empresas WHERE pal_busca LIKE ''";
$sqlStrAux = "SELECT count(*) as total FROM empresas WHERE pal_busca LIKE ''";
}

Yo lo haría así:

...}else{
$sqlStr = "SELECT * FROM empresas";
$sqlStrAux = "SELECT count(*) as total FROM empresas";
}

También veo otro errorsito, o algo que no entiendo por que lo haz hecho así:

if ($q''){
//CUENTA EL NUMERO DE PALABRAS


uff, espera, vi varios errores o cosas extrañas, así que mejor pongo como lo haría yo:

if(isset($_GET['q']) and !eregi('^ *$',$_GET['q'])){
$q = sql_quote($_GET['q']); //para ejecutar consulta
$busqueda = htmlentities($q); //para mostrar en pantalla
 
if(strpos(trim($q),' ')){
/*
* Si encuentra un espacio, entonces tenemos 2 o mas palabras, por lo que podemos utilizar MATCH(campos) AGAINST(búsqueda).
* Siempre y cuando exista un índice de texto completo (FULLTEXT) en la tabla relacionado a los campos que se pretende realizar la búsqueda.
*/

$sqlStr = "SELECT *, MATCH ( descripcion, pal_busca ) AGAINST ( '$q' ) AS Score FROM empresas WHERE MATCH ( descripcion, pal_busca ) AGAINST ( '$q' ) ORDER BY Score DESC";
$sqlStrAux = "SELECT count(*) as total FROM empresas WHERE MATCH ( descripcion, pal_busca ) AGAINST ( '$q' )";
}else{
/*
* Si no encuentra ningun espacio, entonces tenemos nada mas una palabra, por lo que utilizamos LIKE en la consulta SQL.
*/

$sqlStr = "SELECT * FROM empresas WHERE pal_busca LIKE '%$q%'";
$sqlStrAux = "SELECT count(*) as total FROM empresas WHERE pal_busca LIKE '%$q%'";
}
}else{
$sqlStr = "SELECT * FROM empresas";
$sqlStrAux = "SELECT count(*) as total FROM empresas";
}


uff, por último, no entiendo por que te muestra un error en cuanto al mysql_assoc. Tal vez tenga que ver con la tabla que usas, algún campo mal escrito o el índice de texto completo. Revísale bien ;)
2007-12-01 15:15:28
Intergus
Bueno, ahora no da error, faltaba poner como fulltext en la base de datos los 2 campos descripcion y pal_busca, pero ahora mientras tecleas la primera palabra va de lujo pero al teclear el espacio en blanco para continuar, ya no encuentra nada y aunque sigas tecleando ya no encuentra nada pero no da errores, simplemente dice que no coincide ningun registro.
...... sigo probando.....
2007-12-03 11:39:21
Intergus
Nada, no funciona bien y tiene que ser por poca cosa. No me gustaria tirar la toalla pues me ha gustado el codigo pero sin el match again funcionando, vale de poco ....

Victor, ¿no te animas?.... supongo que estarás hasta arriba pero a lo mejor es cosa de poco.
2007-12-03 15:03:20
Intergus
Por cierto, no encuentra nada con ñ, en cuanto la tecleas... se acabó.
2007-12-26 13:57:25
Abraham
Una duda... es posible en vez de hacer que pase las búsquedas (al dar clic en las diferentes páginas) por la URL que las pase por $_POST y así no cambié la URL???

:$
2008-01-10 11:40:32
link
gracias me fue de mucha ayuda, lo adapte a mis necesidades, pero super facil de usar, no me demore nada

muchas gracias la verdad
2008-01-11 01:47:21
Victor De la Rocha
@Intergus, debes de tener cuidado con el juego de caracteres. Tal vez si tomas en cuenta utf8_encode y utf8_decode puedas lograr lo que no funciona, de otra manera no podría ayudarte.

@Abraham, creo que es posible, tendrás que hacer alguna función que haga exáctamente lo mismo que hago al dar clic en el botón submit.

@link, me alegra mucho saberlo ¡Suerte con eso! ;)

¡Feliz año a todos! Ya estoy de vuelta por aquí ... uff, casi desde noviembre desaparecido. :D
2008-02-14 00:25:23
Jackfort
Cual es la base de datos?
2008-02-14 01:57:18
Victor De la Rocha
La que pienses usar.
2008-02-19 02:52:02
estibaliz2006
y si quiero poner más de un criterio de búsqueda, es decir, hacer un buscador avanzado, donde poder seleccionar los campos por los que buscar y si hay dos campos a buscar me los busque?
2008-02-19 10:15:40
Victor De la Rocha
Sólo agrega los inputs que necesites y algún momento (apoyandote de los eventos) realizas la búsqueda.

Para cualquier otro caso, sólo es cuestion de agregar los <input> que necesites y tener en cuenta que cada uno tiene eventos especiales con los cuales podrías tu determinar "en este momento realiza la búsqueda".

Para buscas en dos campos, pues modificas la consulta en base a lo que envíes mediante los _POST.

Creo que es momento de dejar en claro: Para coomprender este documento, es necesario tener cierto dominio (al menos conocimiento básico) del funcionamiento de los formularios, y entender perfectamente que es el envío de datos por _GET, _POST u otro método. http://www.w3schools.com/html/html_forms.asp
2008-02-25 13:45:20
Marcelo
AYUDA!!!!!!!


A mi no me funciona porque no tengo los campos nesesarios ;(!!!!!!!!!!!1


Dijiste todo menos la tabla y campo de mysql!!!!


Decime dejando un comentario en mi web...http://mrb.laweb.es o por msn, marcelo11_Cho@hotmail.com



Porfa!!!!
2008-03-04 00:56:06
Alex Ludvin
Un saludo cordial a todos y gracias a ti Victor.

quisiera que pulbicases tambien el script d ela BD.
2008-03-05 07:30:35
David
El script va perfectamente, pero hay un problema bastante grande, que la paginación no es ajax. Es decir, la busqueda la hace sin hacer la renovación de la página, pero la paginación necesita refrescarla.

Hay alguna forma para que la paginación también sea utilizando ajax?
2008-03-08 00:18:06
Alex Ludvin
Como hago paraque al aparecer los links despues de la busqueda, al darle click, por ejemplo me lleve a otra pagina que tengo alojado en mi localhost
2008-03-08 00:22:26
Alex Ludvin
Quizas no me explique bien:

Yo en mi buscador tecleo "algorit" y me muestra el contenido que teno en una tabla de mi BD, ahora quisiera saber como al darle click en un link que yo elijo me lleva a otra pagina donde muestro el contenido completo de lo que yo seleccione.
2008-03-08 14:05:44
jaime
y si por ejemplo quiero hacer uina busqueda, en la cual yo le envien el nombre del campo donde va a buscar?? los nombres de los campos se pueden manaejar con un combo
2008-04-18 08:27:37
gabriel_666
siii, el gran problema de ajax es la letra ñ y Ñ y los acentos, yo tambien hice un buscador pero cuando metia palabras con ñ o Ñ no las encontraba, osea, las encotraba si tecleaba todo en minusculas pero si lo hacia con mayusculas no lo encontraba y es debido a q la ñ y Ñ se codifican de distinto modos y usando la funcion utf8_encode no lo solucionaba, tampoco pasando todo a mayuscula o minuscula con strtoupper y strtolower
todavia sigo buscando como corregir eso si alguien tiene alguna sugerencia
2008-04-19 00:50:07
Victor De la Rocha
Hola a todos! disculpen que no haya podido contestarles antes, El sitio estado siendo atacado con DDoS por algún listillo y también he tenido bastantes pendientes.

Para los que **creen** necesitar el script de la base de datos: NO se necesita un script? úsenlo con la base de datos que ustedes quieran, lo único indispensable para tenerla funcionando es que contenga registros, y si de plano no les sale,? tómenlo como reto,

Y si, el problema con este tipo de aplicaciones para los que utilizamos la eñe y los acentos es el uso de los caracteres extraños dado que internamente estas aplicaciones DEBEN casi por regla :P jeje utilizar UTF-8, disculpen que se me haya olvidado mencionar esto: Realmente no tengo un listado de que mejoras podría hacer para un 2do artículo para mejorar este buscador tan fofo.

Uff, no se por qué no apliqué la paginación en AJAX, pero trataré algún día no muy lejano de implementarlo, y tal vez compartirlo con ustedes :D

@Alex Ludvin: Disculpa que no te haya contestado antes, no me ha sido posible atender el sitio desde hace ya tiempo... Lo que tratas de decir es que quieres que prácticamente esto funcione como si estuviéramos creando un mini blog?