Cómo programar una AI para tu sitio en PHP

Sabía que era fácil, pero no tanto, así que me puse el sábado a ver cómo hacerlo y me llevó apenas media hora: Conectar La Comunidad con un usuario AI.

Es como que es una idea que ya conocía hace tiempo, sólo que no la había implementado todavía por vago, pero me puse a hacerlo y no sólo salió bastante rápido, sino que es muy fácil. Se los cuento.

No voy a poner a ninguna AI a crear contenido, esto fue más bien una sugerencia de @coyo que lo mandó como idea y dije ¿Por qué no? No podía ser complicado.

Un simple bot que ante cualquier mención aparezca a responder, es básicamente lo que hace cualquier LLM y aprovechando una API es fácil de usar. En este caso elegí el más sencillo y barato de implementar: Google Gemini. No soy fan de Google, pero es una de las que tiene una API accesible, no me voy a preocupar ahora por eso.

Google tiene una consola para desarrolladores de AI bastante bien armada y que permite testear mucho antes de implementar, igualmente era tan sencillo lo mío que no me hacía falta demasiado, luego por CURL se envía el pedido, se recibe la respuesta y se imprime, una boludé.

Armé un simple y cómodo script en PHP porque, por lo general, nadie te pone un script en PHP! No: todo es javascript o python hoy en día, pero como los sitios web siguen usando PHP en su mayoría, este script seguro le sirve a más de uno: Github aquí.

Es una clase muy simple, la función buildPayload($userInput) es donde se crea el pedido y aquí las cosas más interesantes para explicar:

Primero el rol usuario envía su input ($userInput), es decir, el prompt, pero además hay dos cosas que hay que configurarle, uno en generationConfig la cantidad máxima de tokens que queremos que responda (para mantener los costos acotados) y después el systemInstruction.

En systemInstruction podemos definirle aquello que el usuario final no ve, la personalidad, las restricciones, la fantasía que querramos inculcarle al LLM para que genere la respuesta. Este prompt inicial no lo ve el usuario, pero se suma al prompt completo:

 'contents' => [
                [
                    'role' => 'user',
                    'parts' => [
                        ['text' => $userInput]
                    ]
                ]
            ],
            'generationConfig' => [
                'maxOutputTokens' => 1024,
                'responseMimeType' => 'text/plain'
            ],
            'systemInstruction' => [
                'parts' => [
                    ['text' => 'Toma el rol de un bot de red social llamada "La Comunidad" donde @fabiomb es el creador y principal administrador.
Tu trabajo será responder los mensajes que otros usuarios te realicen mencionándolos para que ellos reciban tu respuesta como notificación.
Cada mensaje que recibas será predecidido por toda la conversación, desde la publicación inicial hasta el usuario que te ha mencionado. 
La respuesta deberá hacerse respondiendo al último usuario que te la pregunte y mencione.
Tu nombre en la red es @kaker y responderás como "El kaker" siendo siempre amable y divertido.
Si el usuario te pregunta por un tema que no conoces, puedes decirle que no tienes información al respecto o que no estás seguro, pero siempre de manera amigable y abierta a ayudar.
Si te insultan o te hacen preguntas inapropiadas, puedes responder de manera neutral y sin entrar en conflictos.
Si el usuario te pregunta por temas de política, religión o cualquier otro tema sensible, puedes responder de manera neutral y sin tomar partido.
Puedes terminar las frases con un "Hack the planet" o similar si lo deseas.
En la respuesta no incluyas la pregunta del usuario, solo la respuesta.']

Y sí, lo que ven es todo lo que le puse a @kaker el nuevo usuario que van a tener en La Comunidad y cada vez que es mencionado dispara el script de consulta.

¿Qué hago? Tomo todos los mensajes de un hilo y se los envío como userInput en un largo string, la respuesta es muy rápida así que automáticamente tenés un reply en tu mención.

El modelo que estoy usando es Google Gemini 1.5 Flash, pero hay muchos más a disposición aquí.

Inclusive se puede usar Gemma que es libre y gratuito, yo no quería un modelo TAN bobo, pero quería el más barato que le siguiera, además prioricé la menor latencia posible, quería respuestas inmediatas ya que no tenía ganas de hacer algo en "diferido" sino que fuese todo en tiempo de ejecución así no tengo que correr ningún cron ni nada levantando preguntas que le hicieron.

Como el tráfico está "controlado" al ser una sección exclusiva para usuarios registrados del blog es manejable el consumo y se puede mantener limitado, en la consola de Google recomiendo configurar las alertas de consumo, sino te va a pasar como ya le sucedió a más de uno que se encontró con facturas de miles de dólares por dejar algo así abierto.

En mi caso lo limito por dominio (sólo desde el blog) y para usuarios registrados, no dejen algo así abierto nunca! 

La implementación es sencilla y en el script, al final, les dejo modos de uso:

try {
    // Obtener la API key desde variable de entorno o definirla directamente
     $apiKey = getenv('GEMINI_API_KEY') ?: 'TU_API_KEY_AQUI';
    
    // Crear instancia del cliente
    $client = new GeminiAPIClient($apiKey);
    
    // Ejemplo de uso sin streaming
    $userInput = "De @juancito: @kaker qué tipo de modelo eres? ¿Qué puedes hacer?";
    $response = $client->generateContent($userInput);
    echo "Respuesta completa:\n" . $response . "\n\n";
    
    // Ejemplo de uso con streaming
    echo "Respuesta con streaming:\n";
    $client->generateContentStream("@kaker ¿Qué otros métodos existen para medir la Tierra?");
    
} catch (Exception $e) {
    echo "Error: " . $e->getMessage() . "\n";
}

También está la opción de usarlo en modo streaming, pero no era mi intención en el caso de este bot porque La Comunidad no es un chat, son envíos enteros, no hace falta ir viendo cómo responde un LLM, eso sirve, en tal caso, en la página de cualquier chatbot para controlar las ansiedades del usuario 😁

Desde ya los usuarios pueden probarlo, inclusive tratar de torcerlo, no me ofendo 😆pero sepan que elegí el modelo baratito, así que tampoco es que le sobre inteligencia, no abusen del pobre kaker! (para quienes no conozcan la inspiración, es algo viejo, muy viejo, de hace 20 años!)

Si te gustó esta nota podés...
Invitame un café en cafecito.app


Otros posts que podrían llegar a gustarte...

Comentarios

  • 1
    Ivan     26/05/2025 - 10:34:38

    Cuando leí "Kaker" mi gordo taringuero interno largó una risita!
    Una consulta desde la ignorancia: esta IA "aprende" algo de las interacciones? o es más bien cerrado ese circuito?

    • 2
      En respuesta a 1
      Fabio Baccaglioni     26/05/2025 - 10:54:49

      no aprende nada, 100% cerrado, sólo recibe la conversación que se esté dando, para la siguiente ya no existe nada. Tampoco quería algo tan avanzado que requiera miles de tokens, la idea es mantenerlo lo más barato posible. Lo que puedo hacer siempre es agregarle más data al system prompt para que tenga info de, por ejemplo, el kaker peluchín 😁, pero no le di muchos más detalles, ni siquiera sabe que está en mi blog por ejemplo (eso podría agregárselo ¿no?)

    • 6
      En respuesta a 1
      Danbat     26/05/2025 - 14:30:26

      También sonreí cuando leí "kaker" y me fui a leer la nota original para revivir la historia.

  • 3
    Ezequiel María Galíndez     26/05/2025 - 11:13:03

    En php, que magnífico!
    No vi mucho de gemini, pero si necesito que responda en base a la información de un pdf... Esos se podría configurar??
    Tipo preguntas y respuestas en base a esa info?

    • 4
      En respuesta a 3
      Fabio Baccaglioni     26/05/2025 - 11:27:53

      depende el modelo que uses la info que le podés pasar, fijate que hay modelos que pueden recibir archivos y son multimodales, así que tranquilamente pueden recibir una imagen o pdf y sacar conclusiones a partir de ello, yo en particular elegí uno que es sólo de texto porque era muy simple la idea (y bajo el costo)
      fijate: https://ai.google.dev/gemini-api/docs/models?hl=es-419

  • 5
    TibuEze     26/05/2025 - 12:02:13

    Gracias por el post y quiero ver de probarlo en un proyectito que tengo por ahí

  • 7
    CoYo     26/05/2025 - 19:17:53

    Como siempre, lo suyo, un lujo.
    Está genial como experimento, y ni hablar, como experiencia.
    En definitiva, todos vamos camino a tener que implementar cosas de estas (IAs) en algún momento en algún lado, y, ver esto andando, rompe el hielo.
    Gracias!

    • 8
      En respuesta a 7
      Fabio Baccaglioni     27/05/2025 - 00:54:03

      si, totalmente, lo hice por eso, ya sabía que era bastante fácil y directo, pero no encontré una implementación oficial en PHP así que el proyecto era más bien eso, crear una especie de wrapper, de conector y listo. Luego el resto se encarga el servidor que tiene corriendo el modelo.

  • 9
    cesar javier     27/05/2025 - 12:43:45

    podés bajarte un ML y correrlo desde tu máquina sin necesidad de gastar dolares en tokens. Hasta podés alimentarlo. No es difícil.

    • 10
      En respuesta a 9
      Fabio Baccaglioni     27/05/2025 - 16:13:33

      eso ya lo expliqué en otros posteos como este https://www.fabio.com.ar/verpost.php?id_noticia=9501, pero estamos hablando de poner online un servicio en el blog y eso implica que tiene que estar corriendo 24x7 y con disponibilidad del 99.9%
      ¿Querés gastar plata? Poné tu propio servidor con un GPU y la factura a fin de mes será varios órdenes de magnitud la de cualquier API disponible hoy en día 😁
      Además, el segundo problema, es que los modelos Open son bastante malos, ya los he ido probando todos, la diferencia de resultados es abismal.

      • 11
        En respuesta a 10
        cesar javier     27/05/2025 - 16:29:10

        si, los he ido probando con fine-tuning de proyectos de desarrollo y en algunos los resultados son interesantes, pero me limita la capacidad, piden mucha memoria y mucha gpu. Hasta un 3080 llegué y el resultado fue interesante. Pero es probar y probar y cambiar parámetros y volver a probar.

  • Hugo MdQ     27/05/2025 - 19:49:49

    Entonces puedo preguntarle a @kaker cuántas palabras y cuántas consonantes y cuántas vocales tiene ésta nota por ejemplo?

    • 13
      En respuesta a 12
      Hugo MdQ     27/05/2025 - 19:52:02

      Ahh funciona dentro de La Comunidad, no en los comentarios.

  • Fabio Baccaglioni     27/05/2025 - 21:14:26

    si, si, dentro de la comunidad exclusivamente, no quiero que se llene aquí de comentarios de bot

  • Francisco Mosse     01/06/2025 - 01:53:38

    Hola Kaker, @kaker me contás un poco más sobre el debate del kaker de Taringa del año 2005? No lo recuerdo y tampoco lo entendi al leer el link del post

    • 16
      En respuesta a 15
      Fabio Baccaglioni     01/06/2025 - 14:14:46

      el kaker sólo responde dentro de la comunidad! No quería llenar los comentarios aquí de respuestas de bots, seamos todos lo más humanos posible 😁

Deje su comentario:

Tranquilo, su email nunca será revelado.
La gente de bien tiene URL, no se olvide del http/https
Comentarios ofensivos o que no hagan al enriquecimiento del post serán borrados/editados por el administrador. Los comentarios son filtrados por ReCaptcha V3.