
Compartir:
Javier studied Industrial Engineering back in Madrid where he's from. He is now one of our Solution Engineers, so if you get into trouble using our APIs he may be the one that gives you a hand. Out of work he loves playing football and travelling as much as he can.
Comprobación del estado del metro de Londres con la SMS API de Vonage
Tiempo de lectura: 21 minutos
Hoy vamos a construir una aplicación que nos permitirá comprobar el estado de una determinada línea del metro de Londres utilizando la API de Vonage SMS API DE VONAGE. Vamos a aprovechar la API de Transport for London (TFL API) para recuperar datos en tiempo real sobre el estado de una línea de metro elegida por el usuario. El desencadenante será un SMS entrante a nuestro número virtual. ¿Te parece un buen plan? Pues sigue este tutorial. Obtendremos el mismo estado que en su página web directamente a nuestro teléfono a través de SMS. Esto es especialmente útil si por alguna razón no tienes acceso a Internet para consultar Google Maps/Citymapper o si has superado tu asignación mensual de datos.
El flujo de trabajo de nuestra aplicación será algo parecido al siguiente diagrama:
sketch diagram of workflow
Lo sé 😌 lo más probable es que no vivas en Londres, y puedes pensar que este tutorial no es relevante para ti. Sin embargo, creo sinceramente que es un ejemplo muy ilustrativo de lo que puedes construir sobre Vonage.
Este tutorial te guiará a través de todos los pasos para crear esta aplicación desde cero. Sin embargo, si prefieres hacerte con el repositorio terminadopor favor, ¡consúltalo!
Requisitos previos
Vonage API Account
To complete this tutorial, you will need a Vonage API account. If you don’t have one already, you can sign up today and start building with free credit. Once you have an account, you can find your API Key and API Secret at the top of the Vonage API Dashboard.
This tutorial also uses a virtual phone number. To purchase one, go to Numbers > Buy Numbers and search for one that meets your needs.
Para la primera parte del tutorial, necesitaremos:
Algunos conocimientos básicos de Javascript/node.js.
Deberá utilizar ngrok para exponer tu servidor local a Internet y que Vonage pueda acceder a él. Tenemos un tutorial detallado sobre esto.
Si quieres que tu aplicación se despliegue en Heroku, también necesitarás:
A cuenta de Heroku (sólo utilizaremos el nivel gratuito).
Algunos conceptos básicos git básicos para desplegar nuestra aplicación en Heroku.
Poner en marcha nuestro proyecto
Cree una carpeta de proyecto llamada tubestatus en su máquina local y cambie a ella.
mkdir tubestatus && cd tubestatus
Vamos a crear nuestro archivo principal donde almacenaremos nuestro código. También crearemos nuestro archivo .env donde almacenaremos nuestro Vonage y credenciales así como algunas otras variables.
El siguiente paso es crear el archivo package.json archivo.
Vamos a instalar y guardar las dependencias necesarias.
Ahora tenemos que crear una aplicación de Vonage y comprar un número.
Instala la CLI de Vonage globalmente con este comando:
npm install @vonage/cli -gLuego, configura la CLI con tu clave y secreto de API de Vonage. Puedes encontrar esta información en el Panel del desarrollador.
vonage config:set --apiKey=VONAGE_API_KEY --apiSecret=VONAGE_API_SECRETVamos a ejecutar ngrok en el mismo puerto donde nuestro servidor local está escuchando (en mi caso 3000).
ngrok http 3000
Ahora, usa la CLI para crear una aplicación de Vonage y crea un webhook para tu URL de ngrok.
Usted querrá guardar esa identificación que se imprime después de Application created:. Lo necesitarás en breve.
Ahora necesitas un número para poder recibir llamadas. Puedes alquilar uno utilizando el siguiente comando (sustituyendo el código del país por tu código). Por ejemplo, si estás en EE.UU., sustituye GB por US:
Ahora vincula el número a tu aplicación:
vonage apps:link --number=VONAGE_NUMBER APP_IDPor último, rellena el archivo .env con la clave API de Vonage para apiKeyel secreto de Vonage para apiSecrety el número que acabas de comprar para from. Luego, agrega tu TFL app_id y app_key.
Empecemos por lo divertido
Como siempre, vamos a requerir todas las dependencias al principio de nuestro proyecto. Utilizaremos el express framework para construir nuestra aplicación. Vamos a usar la librería dotenv librería para que trabajemos con variables de entorno. Usaremos body-parser para que podamos analizar las solicitudes entrantes provenientes del servidor de Vonage. Para las solicitudes a la API de TFL, elegí la biblioteca request biblioteca ya que me parece bastante sencilla pero puedes utilizar cualquier otra como por ejemplo axios. Por último y más importante, 😊 requerimos la librería de Vonage para enviar el estado de la línea de vuelta al usuario.
Pega el siguiente código en tu archivo recién creado. Importamos todas las dependencias instaladas, y hemos definido una variable que contiene todos los nombres de línea aceptados proporcionados por la API TFL. No queremos enviar una petición a la API TFL si el usuario no proporciona un nombre de línea válido (explicaré en un momento por qué todos los valores están en mayúsculas). La variable llamada status contendrá cualquier estado relevante en relación al estado de dicha línea. Además, agrega las diferentes credenciales que necesitarás para utilizar las API de Vonage y TFL respectivamente. Estas se recuperarán del archivo .env archivo:
const Vonage = require('@vonage/server-sdk')
const express = require('express');
const bodyParser = require('body-parser');
const port = process.env.PORT || 3000;
const request = require('request');
const dotenv = require('dotenv');
let status = []
dotenv.config();
const lines =['CENTRAL','BAKERLOO', 'DISTRICT', 'VICTORIA', 'NORTHERN', 'CIRCULAR', 'HAMMERSMITH-CITY', 'JUBILEE', 'METROPOLITAN', 'PICCADILLY', 'WATERLOO-CITY' ];
const vonage = new Vonage({
apiKey: process.env.apiKey,
apiSecret: process.env.apiSecret
})En las siguientes líneas, estamos iniciando nuestra aplicación y definiendo algunos middleware básicos. Ten en cuenta que hemos definido el puerto 3000 para que nuestro servidor escuche, pero puedes elegir otro. Account que hay algún espacio en medio (comentado) que será rellenado con nuestra ruta para las peticiones entrantes:
const app = express();
app.use(bodyParser.json());
app.use(bodyParser.urlencoded({ extended:true}));
//We will define our route here
app.listen(port, ()=>{console.log('App listening in port ', port)});
Vamos a definir dos funciones para ordenar un poco el código. La primera función sendSms() va a tomar dos parámetros: el número de teléfono del usuario y el texto a enviar de vuelta al usuario. Vamos a reutilizar un poco el código.
function sendMessage(to, message){
vonage.message.sendSms(process.env.from, to, message, (err, responseData) => {
if (err) {
console.log(err);
} else {
if(responseData.messages[0]['status'] === "0") {
console.log("Message sent successfully.");
} else {
console.log(`Message failed with error: ${responseData.messages[0]['error-text']}`);
}
}
})
}
La segunda función checkLineStatus() recibirá dos parámetros: el nombre de la línea y el número de teléfono del usuario, ya que enviaremos un mensaje al usuario con la información solicitada.
function checkLineStatus(Line, number) {
var options = {
json: true,
url: 'https://api.tfl.gov.uk/Line/' + Line + '/status?app_id=' + app_id + '&app_key=' + app_key,
}
request(options, function (err, res, body) {
if (err) {
console.log(err)
}
else {
if (body[0].lineStatuses[0].statusSeverityDescription === 'Good Service') {
sendMessage(number, 'There is a ' + body[0].lineStatuses[0].statusSeverityDescription + ' operating on ' + body[0].name + ' line')
}
else {
for (let i = 0; i < body.length; i++) {
for (let j = 0; j < body[i].lineStatuses.length; j++) {
status.push(body[i].lineStatuses[j].reason)
}
}
sendMessage(number, status)
console.log(status)
}
}
})
}
Si el estado de la línea dada es Buen Servicio (Tenga en cuenta que la API TFL siempre devolverá esto cuando el servicio normal esté funcionando) envíe esto de vuelta al usuario. En caso contrario, es importante tener en cuenta que cuando hay una interrupción en la línea, la API de TFL proporcionará un icono reason dentro del objeto lineStatus objeto. Eso es lo que estamos empujando en nuestro array por cada interrupción ocurrida (Esperemos que ninguna por el bien de los viajeros 😂). No olvides que dentro de esta función, también estamos llamando a la función sendSms() para devolver el estado de la línea al usuario en ambos escenarios.
Por último, vamos a completar nuestra ruta de entrada para escuchar los mensajes entrantes de los usuarios. Veamos cómo se ve un mensaje entrante de Vonage.
Para lograr nuestro objetivo, vamos a necesitar almacenar dos de los parámetros anteriores; El texto enviado por el usuario (nombre de la línea) y el número del usuario. Estos serán almacenados en nuestras nuevas variables (Tube_line y Number_msisdn respectivamente) tan pronto como nuestra /inbound ruta es golpeada.
Es importante notar que estamos poniendo en mayúsculas la línea del tubo. La razón detrás de esto es que queremos comparar una Cadena especificada con otra Cadena ignorando consideraciones de caso (el usuario puede enviarnos Central, CENTRAL o central). Poniendo en mayúsculas la entrada del usuario y comparándola con nuestra matriz lines (ya en mayúsculas) podemos evitarlo. Añade el siguiente código en el espacio que tenemos reservado para nuestra ruta.
app.post('/inbound', (req, res) => {
let Tube_Line = req.body.text.toUpperCase()
let Number_msisdn = req.body.msisdn
if ((lines.indexOf(Tube_Line) > -1)) {
checkLineStatus(Tube_Line, Number_msisdn)
}
else {
sendMessage(Number_msisdn, 'Valid values are ' + lines)
}
res.status(204).send()
})
El bit (lines.indexOf(Tube_Line) > -1) nos permitirá comprobar si el valor almacenado en Tube_line coincide con alguno de los valores del lines matriz. Este método devuelve un primer índice en el que se puede encontrar el elemento dado en un array, o -1 si no está presente en un array. Sólo querremos comprobar el estado de una línea dada si la entrada coincide con alguno de los valores válidos. En caso contrario, recibiremos un bonito HTTP 404 de vuelta de la API TFL. Suponiendo que seamos lo suficientemente amables como para hacer saber al usuario que ha introducido un valor incorrecto, le devolveremos un mensaje proporcionándole los valores válidos. Esto se hace cuando el método indexOf es igual a -1 como se explicó anteriormente.
Muy bien, es hora de probar esto 🙈. Tomemos nuestro teléfono y enviemos un SMS con cualquier nombre de línea que coincida con nuestra matriz lines a tu número de Vonage. Como ejemplo, consultaré el nombre de la línea que me lleva al trabajo todos los días.
demo of app performance on phone
💃💃 Como podéis ver, poco después de enviar un mensaje a nuestro número virtual previamente configurado, estamos recibiendo un SMS con el estado de la línea solicitada. ¡Bien hecho y gracias por seguir hasta aquí!
Simulación de mensajes entrantes
Si por alguna razón no tienes la oportunidad de usar tu teléfono o no quieres enviar SMS manualmente para probar la aplicación, también te tenemos cubierto. Un mensaje entrante se representa simplemente como una petición GET o POST a tu webhook. Puedes definir qué método deseas que Vonage utilice para entregar tus mensajes entrantes en tu Configuración del panel de Vonage. Estoy usando POST para este tutorial.
Teniendo esto en cuenta, podemos simular el comportamiento de un mensaje entrante golpeando manualmente nuestro servidor local expuesto con ngrok para ver si la aplicación funciona como debería. Utilizaré POSTMAN pero siéntete libre de usar cualquier otro servicio de tu elección. Vamos a realizar una solicitud POST a nuestro webhook de entrada definiendo un cuerpo JSON sin procesar genérico (como el que Vonage enviaría para un mensaje de entrada). Sin embargo, recuerda cambiar el campo msisdn para que nuestra aplicación sepa dónde responder. Además, reemplaza el parámetro text para jugar con diferentes valores de nombre de línea, puedes escribir a propósito un valor no válido para que recibas un mensaje que contenga los valores permitidos. Mi solicitud de API se parece a esto:

En este caso, el parámetro to no es relevante, así que lo pongo en un valor aleatorio. Es importante añadir la cabecera Content-Type y ponerlo a application/json para que nuestra aplicación sepa cómo manejar estos datos. Como se puede ver en la parte inferior derecha, nuestra aplicación devuelve un HTTP 204 como se define en nuestro /inbound a través de res.status(204).send()
¿Y ahora qué? Despleguemos en Heroku
Heroku es una plataforma pensada para desplegar fácilmente tu aplicación Web y escalar tus servicios según tus necesidades. También ofrecen algunos complementos útiles para simplificar algunas tareas diarias. Vamos a aprovechar Heroku debido al hecho de que es bastante fácil de usar, y la documentación es grande en el sitio de Heroku. Mediante el uso de Heroku podemos evitar la molestia de alquilar y configurar nuestro servidor.
El concepto de dynos existe dentro de la plataforma de Heroku. No es más que un contenedor donde se desplegará tu aplicación. El uso de su aplicación consumirá horas dyno (sólo cuando se está ejecutando), pero no se preocupe, ya que ofrecen 550 horas gratuitas al mes out-of-the-box o 1000 horas en caso de que acepte verificar su Account proporcionando una tarjeta de crédito. Puedes ampliar o reducir fácilmente tu aplicación teniendo en cuenta la demanda de tráfico, pero esto está fuera del alcance de este tutorial.
Si nunca has desplegado una aplicación Heroku, puede valer la pena ir a través de sus documentos, o al menos leer la parte donde se explica cómo desplegar una aplicación node.js. Para determinar cómo iniciar tu aplicación, Heroku primero busca un Procfile. Este es un archivo que especifica los comandos que son ejecutados por la aplicación en el arranque. Si no hay Procfile existe para una aplicación Node.js, Heroku intentará iniciar un proceso web por defecto a través del script de inicio en tu package.json.
Modifiquemos nuestro package.jsonpara que la parte que contiene los scripts tenga incluida esta parte:
"scripts": {
"start": "node server.js"
},A continuación, vamos a crear un archivo .gitignore para asegurarnos de que las variables de entorno locales, la salida relacionada con la compilación y los módulos no se envían al repositorio git
/node_modules
npm-debug.log
.DS_Store
/*.envLa única desventaja de usar el nivel libre es que una vez que tu aplicación se queda inactiva después de 30 minutos de inactividad, puede tardar un poco en despertarse (al recibir una nueva solicitud). Desde un punto de vista pragmático, esto significa que podemos ver un leve retraso al recibir el mensaje de vuelta de Vonage si la aplicación ha estado inactiva durante un tiempo. Esto se debe a que la solicitud a la API de TFL se manejará una vez que la aplicación se reinicie nuevamente. Esto es aceptable ya que esta aplicación no es de tiempo crítico. Sin embargo, si esto no te parece suficiente, puedes pasarte al servicio pago y tener un banco de pruebas dedicado funcionando para tu aplicación.
Para determinar cómo iniciar tu aplicación, Heroku primero busca un Procfile. Si no existe un Procfile para una aplicación Node.js, Heroku intentará iniciar un proceso web por defecto a través del script de inicio en tu package.json. El comando en un tipo de proceso web debe enlazarse al número de puerto especificado en la variable de entorno PORT. Si no lo hace, el dyno no se iniciará.
Compruebe que dispone de la Heroku CLI instalado y luego ejecute los siguientes comandos dentro de la carpeta de su proyecto, uno a la vez:
En este punto, hemos creado un nuevo repositorio git, añadido todos los cambios a nuestro repositorio y enviado nuestro primer commit. Ahora vamos a crear nuestra aplicación y desplegarla en Heroku:
En estas pocas líneas, hemos creado nuestra aplicación Heroku y empujado los cambios a Heroku. Si todo ha ido como esperabas, deberías tener tu propia aplicación creada. También te proporcionarán la URL donde se puede encontrar tu app una vez desplegada. ¡Bien hecho!
Por último, tenemos que decirle a nuestra aplicación dónde encontrar las variables de entorno, ya que no hemos proporcionado ninguna .env file. Ejecute este comando para establecer las variables de configuración necesarias
Puede volver a comprobar que estas variables se han añadido correctamente echando un vistazo a la configuración de su aplicación en Panel de control de Heroku. Este es el aspecto de nuestra aplicación en el panel de control de Heroku. Si pulsamos en Revelar Config Varsveremos las variables de entorno configuradas a través de la CLI de Heroku.

En conclusión, ¡este proceso fue relativamente sencillo! Pude ponerlo en marcha en cuestión de pocos minutos, lo cual es excelente. Todo lo que queda ahora es actualizar nuestro número para que apunte a nuestro nuevo webhook, simplemente puedes replicar los pasos anteriores (cuando configuramos nuestro número a través de la API de Numbers). Como recordatorio, no olvides incluir el símbolo /inbound al final de la URL que coincide con la ruta en nuestro script.
Con suerte, si enviamos un SMS una vez que hayamos actualizado la URL del Webhook de entrada para nuestro número, esto funcionará como se espera. Este es el aspecto de un estado de interrupción. Parece que habría sido necesario reprogramar nuestro viaje si estuviéramos viajando a Heathrow a través de la District Line en el momento en que estaba probando esto.

Esto es todo por hoy, pero si quieres seguir jugando con nuestras API, puede que te resulten útiles los siguientes enlaces:
Documentación de las distintas API en el portal para desarrolladores
Serie de tutoriales para varias API de Vonage
Si nos necesitas, prueba el canal Slack de la comunidad de Vonage
Háganos saber lo que piensa tuiteando en @VonageDev
