Integra la API de Vision en Dialogflow

1. Antes de comenzar

En este codelab, integrarás la API de Vision con Dialogflow para proporcionar respuestas enriquecidas y dinámicas basadas en aprendizaje automático a las entradas de imágenes proporcionadas por el usuario. Crearás una app de chatbot que tome una imagen como entrada, la procese en la API de Vision y le muestre un punto de referencia identificado al usuario. Por ejemplo, si el usuario sube una imagen del Taj Mahal, el chatbot mostrará el Taj Mahal como respuesta.

Esto es útil porque puedes analizar los elementos de la imagen y tomar medidas en función de la información obtenida. También puedes crear un sistema de procesamiento de reembolsos para ayudar a los usuarios a subir recibos, extraer la fecha de compra en el recibo y procesar el reembolso si la fecha es apropiada.

Observa el siguiente diálogo de muestra:

Usuario: Hola

Chatbot: ¡Hola! Puedes subir una foto para explorar puntos de referencia.

Usuario: Sube una imagen con el Taj Mahal.

Chatbot: Se está procesando el archivo. Estos son los resultados: Taj Mahal, Taj Mahal Garden, Taj Mahal.

15a4243e453415ca.png

Requisitos previos

Antes de continuar, debes completar los siguientes codelabs:

  1. Crea un programador de citas con Dialogflow
  2. Integra un chatbot de Dialogflow con Actions on Google.
  3. Comprende las entidades en Dialogflow
  4. Compila un cliente de Django de frontend para una app de Dialogflow

También debes comprender los conceptos y constructos básicos de Dialogflow, que puedes deducir en los siguientes videos de la ruta de aprendizaje Compila un chatbot con Dialogflow:

Qué aprenderás

  • Cómo crear un agente de Dialogflow
  • Cómo actualizar un agente de Dialogflow para subir archivos
  • Cómo configurar la conexión de la API de Vision con la entrega de Dialogflow
  • Cómo configurar y ejecutar una app de frontend de Django para Dialogflow
  • Cómo implementar la app de frontend de Django en Google Cloud en App Engine
  • Cómo probar la app de Dialogflow desde un frontend personalizado

Qué compilarás

  • Crea un agente de Dialogflow
  • Implementa un frontend de Django para subir un archivo
  • Implementar la entrega de Dialogflow para invocar la API de Vision en la imagen subida

Requisitos

  • Conocimientos básicos de Python
  • Conocimientos básicos de Dialogflow
  • Conocimientos básicos sobre la API de Vision

2. Descripción general de la arquitectura

Crearás una nueva experiencia de conversación con un frontend de Django personalizado y la extenderás para integrarla con la API de Vision. Compilarás el frontend con el marco de trabajo de Django, lo ejecutarás y probarás de forma local y, luego, lo implementarás en App Engine. El frontend se verá de la siguiente manera:

5b07e09dc4b84646.png

El flujo de solicitud funcionará de la siguiente manera, como se muestra en la siguiente imagen:

  1. El usuario enviará una solicitud a través del frontend.
  2. Eso activará una llamada a la API detectIntent de Dialogflow para asignar la declaración del usuario al intent correcto.
  3. Una vez que se detecte el intent del punto de referencia de exploración, la entrega de Dialogflow enviará una solicitud a la API de Vision, recibirá una respuesta y se la enviará al usuario.

153725eb50e008d4.png

Así se verá la arquitectura general.

a2fcea32222a9cb4.png

3. ¿Qué es la API de Vision?

La API de Vision es un modelo de AA previamente entrenado que obtiene información de imágenes. Puede obtener varias estadísticas, como etiquetado de imágenes, detección de rostros y puntos de referencia, reconocimiento óptico de caracteres y etiquetado de contenido explícito. Para obtener más información, consulta Vision AI.

4. Crea un agente de Dialogflow

  1. Ve a la consola de Dialogflow.
  2. Accede. Si eres un usuario nuevo, usa tu correo electrónico para registrarte.
  3. Acepta los Términos y Condiciones y estarás en la consola.
  4. Haz clic en d9e90c93fc779808.png, desplázate hasta la parte inferior y haz clic en Crear agente nuevo. 3b3f9677e2a26d93.png
  5. Ingresa “VisionAPI” como Agent name.
  6. Haz clic en Crear.

Dialogflow crea los dos intents predeterminados siguientes como parte del agente:

  1. El intent de bienvenida predeterminado saluda a tus usuarios.
  2. El intent de resguardo predeterminado capta todas las preguntas que tu bot no entiende.

En este punto, tienes un bot funcional que saluda a los usuarios, pero debes actualizarlo para que sepan que pueden subir una imagen y explorar puntos de referencia.

Actualiza el intent de bienvenida predeterminado para notificar al usuario que debe subir la imagen

  1. Haz clic en Default Welcome Intent.
  2. Navega a Respuestas > Predeterminada > Respuesta de texto o SSML y, luego, ingresa "Hi! Puedes subir una imagen para explorar puntos de referencia".

f9cd9ba6917a7aa9.png

Crear entidad

  1. Haz clic en Entidades.

432fff294b666c93.png

  1. Haz clic en Crear entidad, asígnale el nombre “nombredearchivo”. y haz clic en Guardar.

602d001d684485de.png

Crea un intent nuevo

  1. Haz clic en Intents > Crear intent.
  2. Ingresar "Explorar la imagen subida" como el nombre del intent.
  3. Haz clic en Frases de entrenamiento > Agrega frases de entrenamiento y escribe "el archivo es demo.jpg". y "el archivo es taj.jpeg" como expresiones de usuario con @filename como entidad.

dd54ebda59c6b896.png

  1. Haz clic en Respuestas > Agregar respuesta > Predeterminada > Respuesta de texto o SSML. Ingresa “Archivo de evaluación” y haz clic en Agregar respuestas.
  2. Haz clic en Entrega > Habilita la entrega y activa la opción Habilitar llamadas de webhook para este intent.

b32b7ac054fcc938.png

5. Configura la entrega para integrarla a la API de Vision

  1. Haz clic en Fulfillment (Entrega).
  2. Habilita el Editor intercalado.

c8574c6ef899393f.png

  1. Actualiza index.js con el siguiente código y actualiza YOUR-BUCKET-NAME con el nombre de tu bucket de Cloud Storage.
'use strict';

const functions = require('firebase-functions');
const {google} = require('googleapis');
const {WebhookClient} = require('dialogflow-fulfillment');
const vision = require('@google-cloud/vision');
  /**
   * TODO(developer): Uncomment the following lines before running the sample.
   */
const bucketName = 'YOUR-BUCKET-NAME';
const timeZone = 'America/Los_Angeles';
const timeZoneOffset = '-07:00';

exports.dialogflowFirebaseFulfillment = functions.https.onRequest((request, response) => {
  const agent = new WebhookClient({ request, response });
  console.log("Parameters", agent.parameters);

  function applyML(agent){
    const filename = agent.parameters.filename;
    console.log("filename is: ", filename);

    // call vision API to detect text
    return callVisionApi(agent, bucketName, filename).then(result => {
                      console.log(`result is ${result}`);
                      agent.add(`file is being processed, here are the results:  ${result}`);
            //agent.add(`file is being processed ${result}`);
        }).catch((error)=> {
            agent.add(`error occurred at apply ml function`  + error);
        });
  }

  let intentMap = new Map();
  intentMap.set('Explore uploaded image', applyML);
  agent.handleRequest(intentMap);
});


async function callVisionApi(agent, bucketName, fileName){
    // [START vision_text_detection_gcs]
  // Imports the Google Cloud client libraries
  // Creates a client
  
  const client = new vision.ImageAnnotatorClient();
    try {
        // Performs text detection on the gcs file
        const [result] = await client.landmarkDetection(`gs://${bucketName}/${fileName}`);
        const detections = result.landmarkAnnotations;
        var detected = [];
        detections.forEach(text => {
            console.log(text.description);
            detected.push(text.description);
        });
        return detected;
    }
    catch(error) {
        console.log('fetch failed', error);
        return [];
    }
}
  1. Pega lo siguiente en package.json para reemplazar su contenido.
{
  "name": "dialogflowFirebaseFulfillment",
  "description": "Dialogflow fulfillment for the bike shop sample",
  "version": "0.0.1",
  "private": true,
  "license": "Apache Version 2.0",
  "author": "Google Inc.",
  "engines": {
    "node": "6"
  },
  "scripts": {
    "lint": "semistandard --fix \"**/*.js\"",
    "start": "firebase deploy --only functions",
    "deploy": "firebase deploy --only functions"
  },
  "dependencies": {
    "firebase-functions": "2.0.2",
    "firebase-admin": "^5.13.1",
    "actions-on-google": "2.2.0", 
    "googleapis": "^27.0.0",
    "dialogflow-fulfillment": "^0.6.1",
    "@google-cloud/bigquery": "^1.3.0",
    "@google-cloud/storage": "^2.0.0",
    "@google-cloud/vision": "^0.25.0"
  }
}
  1. Haz clic en Guardar.

6. Descarga y ejecuta la app de frontend

  1. Clona este repositorio en tu máquina local:
https://github.com/priyankavergadia/visionapi-dialogflow.git
  1. Cambia al directorio que contiene el código. Como alternativa, puedes descargar la muestra como un archivo ZIP y extraerla.
cd visionapi-dialogflow

7. Cómo configurar tu entorno local

Cuando se implementa, la aplicación usa el proxy de Cloud SQL integrado en el entorno estándar de App Engine para comunicarse con la instancia de Cloud SQL. Sin embargo, para probar tu aplicación de manera local, debes instalar y usar una copia local del proxy de Cloud SQL en tu entorno de desarrollo. Para obtener más información, consulta Acerca del proxy de Cloud SQL.

Para realizar tareas administrativas básicas en tu instancia de Cloud SQL, puedes usar el cliente de Cloud SQL para MySQL.

Instalar el proxy de Cloud SQL

Descarga y, luego, instala el proxy de Cloud SQL con el siguiente comando. El proxy de Cloud SQL se usa para conectarse a tu instancia de Cloud SQL cuando se ejecuta de forma local.

Descarga el proxy:

curl -o cloud_sql_proxy https://dl.google.com/cloudsql/cloud_sql_proxy.darwin.amd64

Haz que el proxy sea ejecutable.

chmod +x cloud_sql_proxy

Cree una instancia de Cloud SQL

  1. Crea una instancia de Cloud SQL para MySQL de segunda generación. Ingresa el nombre "polls-instance" o uno similar. Es posible que la instancia tarde algunos minutos en estar lista. Cuando esté lista, debería aparecer en la lista de instancias.
  2. Ahora usa la herramienta de línea de comandos de gcloud para ejecutar el siguiente comando, en el que [YOUR_INSTANCE_NAME] representa el nombre de tu instancia de Cloud SQL. Toma nota del valor que se muestra para connectionName en el siguiente paso. Se muestra en el formato [PROJECT_NAME]:[REGION_NAME]:[INSTANCE_NAME].
gcloud sql instances describe [YOUR_INSTANCE_NAME]

Como alternativa, puedes hacer clic en la instancia en la consola para obtener el Nombre de la conexión con la instancia.

c11e94464bf4fcf8.png

Inicializa la instancia de Cloud SQL

Inicia el proxy de Cloud SQL con el connectionName de la sección anterior.

./cloud_sql_proxy -instances="[YOUR_INSTANCE_CONNECTION_NAME]"=tcp:3306

Reemplaza [YOUR_INSTANCE_CONNECTION_NAME] por el valor que registraste en la sección anterior. Esto establecerá una conexión entre tu computadora local y tu instancia de Cloud SQL para realizar pruebas locales. Mantén el proxy de Cloud SQL en ejecución durante todo el tiempo que realices pruebas locales en la aplicación.

A continuación, crea un nuevo usuario y base de datos de Cloud SQL.

  1. Crea una nueva base de datos con la consola de Google Cloud para tu instancia de Cloud SQL llamada polls-instance. Por ejemplo, puedes ingresar "encuestas" como el nombre. a3707ec9bc38d412.png
  2. Usa la consola de Cloud para crear un usuario nuevo de tu instancia de Cloud SQL llamado polls-instance. f4d098fca49cccff.png

Configura la base de datos

  1. Abre mysite/settings-changeme.py para edición.
  2. Cambia el nombre del archivo a setting.py.
  3. En dos lugares, reemplaza [YOUR-USERNAME] y [YOUR-PASSWORD] por el nombre de usuario y la contraseña de la base de datos que creaste en la sección anterior. Eso ayuda a configurar la conexión a la base de datos para la implementación en App Engine y las pruebas locales.
  4. En la línea ‘HOST': ‘cloudsql/ [PROJECT_NAME]:[REGION_NAME]:[INSTANCE_NAME] Reemplaza [PROJECT_NAME]:[REGION_NAME]:[INSTANCE_NAME] por el nombre de la instancia que obtuviste en la sección anterior.
  5. Ejecuta el siguiente comando y copia el valor de connectionName resultante para el siguiente paso.
gcloud sql instances describe [YOUR_INSTANCE_NAME]
  1. Reemplaza [YOUR-CONNECTION-NAME] por el valor que registraste en el paso anterior.
  2. Reemplaza [YOUR-DATABASE] por el nombre que elegiste en la sección anterior.
# [START db_setup]
if os.getenv('GAE_APPLICATION', None):
    # Running on production App Engine, so connect to Google Cloud SQL using
    # the unix socket at /cloudsql/<your-cloudsql-connection string>
    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.mysql',
            'HOST': '/cloudsql/[PROJECT_NAME]:[REGION_NAME]:[INSTANCE_NAME]',
            'USER': '[YOUR-USERNAME]',
            'PASSWORD': '[YOUR-PASSWORD]',
            'NAME': '[YOUR-DATABASE]',
        }
    }
else:
    # Running locally so connect to either a local MySQL instance or connect to
    # Cloud SQL via the proxy. To start the proxy via command line:
    #     $ cloud_sql_proxy -instances=[INSTANCE_CONNECTION_NAME]=tcp:3306
    # See https://cloud.google.com/sql/docs/mysql-connect-proxy
    DATABASES = {
        'default': {
            'ENGINE': 'django.db.backends.mysql',
            'HOST': '127.0.0.1',
            'PORT': '3306',
            'NAME': '[YOUR-DATABASE]',
            'USER': '[YOUR-USERNAME]',
            'PASSWORD': '[YOUR-PASSWORD]'
        }
    }
# [END db_setup]
  1. Cierra y guarda settings.py.

8. Configura la cuenta de servicio

  1. En la consola de Dialogflow, haz clic en 21a21c1104f5fdf3.png. En la pestaña General, navega a Proyecto de Google > ID del proyecto y haz clic en Google Cloud 7b2236f5627c37a0.png para abrir la consola de Cloud. a4cfb880b3c8e789.png
  2. Haz clic en Menú de navegación ⁕ > IAM y Administrador > Cuentas de servicio, luego, haz clic en 796e7c9e65ae751f.png junto a Integraciones de Dialogflow y haz clic en Crear clave.

3d72abc0c184d281.png

  1. Se descargará en tu computadora un archivo JSON que necesitarás en las siguientes secciones de configuración.

9. Configura el extremo detectIntent de Dialogflow para que se llame desde la app

  1. En la carpeta de chat, reemplaza key-sample.json por el archivo JSON de tus credenciales y asígnale el nombre key.json.
  2. En views.py, en la carpeta del chat, cambia GOOGLE_PROJECT_ID = "<YOUR_PROJECT_ID>" por el ID del proyecto.

10. Crea buckets de Cloud Storage

Crea un bucket de Cloud Storage para los objetos estáticos de frontend

  1. En la consola de Cloud, haz clic en el menú de navegación ⁕ > Almacenamiento.

87ff9469db4eb77f.png

  1. Haga clic en Crear bucket.
  2. Proporciona un nombre global único.

a15a6612e92a39d3.png

  1. Elige dónde almacenar tus datos. Elige Región y elige la ubicación que mejor se adapte a tus necesidades.
  2. Elige Estándar como la clase de almacenamiento predeterminada.

9c56abe632cf61db.png

  1. Elige Establecer permisos uniformemente a nivel del bucket (Solo política del bucket) y, luego, haz clic en Continuar para crear el bucket.

f175ac794049df04.png

  1. Una vez que se haya creado el bucket, haz clic en el menú de navegación ⁕ > Almacenamiento > Navegador y busca el bucket que creaste.

9500ee19b427158c.png

  1. Haz clic en 796e7c9e65ae751f.png junto al bucket correspondiente y, luego, en Editar permisos del bucket.

fd0a310bc3656edd.png

  1. Haz clic en Agregar miembros, luego en Nuevos miembros, ingresa “allUsers”. Luego, haz clic en Selecciona un rol > Visualizador de objetos de Storage. Eso proporciona acceso de visualización a los archivos de frontend estáticos para allUsers. Esa no es una configuración de seguridad ideal para los archivos, pero funciona con el propósito de este codelab en particular.

7519116abd56d5a3.png

Crea un bucket de Cloud Storage para las imágenes subidas por el usuario

Sigue las mismas instrucciones para crear un bucket independiente y subir imágenes de los usuarios. Configura los permisos en “allUsers” pero selecciona Creador de objetos de Storage y Visualizador de objetos de Storage como los roles.

11. Configura los buckets de Cloud Storage en la app de frontend

Configura el bucket de Cloud Storage en settings.py

  1. Abre mysite/setting.py.
  2. Ubica la variable GCS_BUCKET y reemplaza ‘<YOUR-GCS-BUCKET-NAME>. con tu bucket estático de Cloud Storage.
  3. Localiza la variable GS_MEDIA_BUCKET_NAME y reemplaza ‘<YOUR-GCS-BUCKET-NAME-MEDIA>'. por el nombre de tu bucket de Cloud Storage para las imágenes.
  4. Localiza la variable GS_STATIC_BUCKET_NAME y reemplaza ‘<YOUR-GCS-BUCKET-NAME-STATIC>'. con el nombre de tu bucket de Cloud Storage para los archivos estáticos.
  5. Guarda el archivo.
GCS_BUCKET = '<YOUR-GCS-BUCKET-NAME>'
GS_MEDIA_BUCKET_NAME = '<YOUR-GCS-BUCKET-NAME-MEDIA>'
GS_STATIC_BUCKET_NAME = '<YOUR-GCS-BUCKET-NAME-STATIC>'

Configura el bucket de Cloud Storage en home.html

  • Abre la carpeta de chat, abre templates y cambia el nombre de home-changeme.html a home.html.
  • Busca <YOUR-GCS-BUCKET-NAME-MEDIA> y reemplázalo por el nombre de tu bucket en el que te gustaría guardar el archivo subido por el usuario. Esto impide que almacenes el archivo subido por el usuario en el frontend y que conserves los recursos estáticos en el bucket de Cloud Storage. La API de Vision llama al bucket de Cloud Storage para tomar el archivo y hacer la predicción.

12. Compila y ejecuta la app de manera local

Para ejecutar la app Django en tu computadora local, tendrás que configurar un entorno de desarrollo de Python, que incluye Python, pip y virtualenv. Para obtener instrucciones, consulta Configura un entorno de desarrollo de Python.

  1. Crea un entorno aislado de Python e instala las dependencias.
virtualenv env
source env/bin/activate
pip install -r requirements.txt
  1. Ejecuta las migraciones de Django para configurar tus modelos.
python3 manage.py makemigrations
python3 manage.py makemigrations polls
python3 manage.py migrate
  1. Inicia un servidor web local.
python3 manage.py runserver
  1. En tu navegador web, ve a http://localhost:8000/. Deberías ver una página web simple que se ve de la siguiente manera:

8f986b8981f80f7b.png

El servidor web de Django que se ejecuta en tu computadora proporciona las páginas de la app de ejemplo. Cuando quieras continuar, presiona Control+C (Command+C en Macintosh) para detener el servidor web local.

Usar la Consola del administrador de Django

  1. Crea un superusuario.
python3 manage.py createsuperuser
  1. Inicia un servidor web local.
python3 manage.py runserver
  1. Navega a http://localhost:8000/admin/ en tu navegador web. Para acceder al sitio del administrador, ingresa el nombre de usuario y la contraseña que creaste cuando ejecutaste createsuperuser.

13. Implementar la app en el entorno estándar de App Engine

Recopila todo el contenido estático en una carpeta con la ejecución del siguiente comando, que mueve todos los archivos estáticos de la app a la carpeta que especifica STATIC_ROOT en settings.py:

python3 manage.py collectstatic

Para subir la app, ejecuta el siguiente comando desde el directorio de la app en el que se encuentra el archivo app.yaml:

gcloud app deploy

Espera a que aparezca el mensaje que indica que se completó la actualización.

14. Prueba la app de frontend

En tu navegador web, ve a https://<your_project_id>.appspot.com.

Esta vez, un servidor web que se ejecuta en el entorno estándar de App Engine atiende la solicitud.

El comando app deploy implementa la app como se describe en app.yaml y establece la versión recién implementada como la versión predeterminada, lo que hace que entregue todo el tráfico nuevo.

15. Producción

Cuando tengas todo listo para publicar tu contenido en producción, cambia la variable DEBUG a False en mysite/settings.py.

16. Probar el chatbot

Puedes probar tu chatbot en el simulador o usar la integración web o de Google Home que creaste anteriormente.

  1. Usuario: "hi"
  2. Chatbot: “¡Hola! Puedes subir una imagen para explorar puntos de referencia".
  3. El usuario sube una imagen.

Descarga esta imagen, asígnale el nombre demo.jpg y úsala.

c3aff843c9f132e4.jpeg

  1. Chatbot: "Se está procesando el archivo. Estos son los resultados: Golden Gate Bridge,Golden Gate National Recreation Area,Golden Gate Bridge,Golden Gate Bridge,Golden Gate Bridge".

En general, debería verse de la siguiente manera:

228df9993bfc001d.png

17. Limpia

Si deseas completar otros codelabs de Dialogflow, omite esta sección y vuelve a ella más tarde.

Borra el agente de Dialogflow

  1. Haz clic en ca4337eeb5565bcb.png junto a tu agente existente.

520c1c6bb9f46ea6.png

  1. En la pestaña General, desplázate hacia abajo y haz clic en Delete This Agent.
  2. Escribe Borrar en la ventana que aparece y haz clic en Borrar.

18. Felicitaciones

Creaste un chatbot en Dialogflow y lo integraste a la API de Vision. Ya eres un desarrollador de chatbots.

Más información

Para obtener más información, consulta las muestras de código en la página de Dialogflow GitHub.