https://a.storyblok.com/f/270183/1368x665/541410e5f5/monitoring-application-health_24.png

Supervisión del estado de las Applications con Java y Messages API de Vonage

Publicado el February 21, 2023

Tiempo de lectura: 7 minutos

Introducción

La generación y el envío de informes sobre el estado de los actuadores es un proceso importante que puede ayudar a garantizar el buen funcionamiento de una aplicación.

Spring Boot es un marco popular para crear aplicaciones Java que proporciona un conjunto de herramientas para supervisar y gestionar una aplicación. Una de sus características es el Actuator, que proporciona un conjunto de puntos finales para supervisar el estado de una aplicación. Estos puntos finales se pueden utilizar para recuperar información sobre el rendimiento de la aplicación, como el uso de la memoria, el uso de la CPU y los tiempos de respuesta.

Mediante el uso de Messages API de Vonage, podemos enviar informes de salud de la aplicación a través de textos y, en caso de cualquier problema de salud crítico, podemos enviar mensajes alternativos como alerta adicional a un número de teléfono designado. En este artículo, hablaremos sobre cómo configurar Spring Boot para generar informes de salud para una aplicación y las API Voice, SMS y Messages de Vonage para entregarlos.

Spring Boot

Spring Boot es un marco de trabajo basado en Java que se utiliza para crear aplicaciones autónomas de nivel de producción fáciles de crear y ejecutar. Está construido sobre Spring Framework y utiliza sus módulos para proporcionar una amplia gama de funcionalidades a los desarrolladores. Siga este artículo de artículo para configurar un proyecto en Spring Boot.

Para habilitar Actuator en su aplicación Spring Boot, debe añadir la dependencia inicial Spring Boot Actuator a su proyecto y configurarla en el archivo application.properties de su proyecto, como se muestra a continuación.

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-actuator</artifactId>
</dependency>

Añada también las siguientes propiedades en su archivo application.properties:

management.endpoints.web.exposure.include=*
management.endpoints.web.base-path=/actuator

Otras dependencias son lombok y web. Actuator proporciona un conjunto completo de características para ayudarle a supervisar y gestionar su aplicación Spring Boot, y es una herramienta esencial para cualquier aplicación Spring Boot lista para producción.

Actuador Spring Boot

El Actuador ofrece una serie de funciones útiles, como:

  • Comprobación de la salud: Actuator proporciona un punto final de comprobación de salud. Este punto final devuelve un objeto JSON que contiene información sobre el estado de la aplicación, como si se está ejecutando o no, y si todas sus dependencias están disponibles.

  • Métricas: Actuator proporciona un punto final para recuperar métricas, como el número de solicitudes, el número de errores y el tiempo de respuesta.

  • Registro: Actuator proporciona un punto final para recuperar archivos de registro, que pueden ser útiles para solucionar problemas.

  • Configuración: Actuator proporciona un punto final para comprender cómo está configurada la aplicación y para solucionar problemas.

  • Volcado de hilos: Actuator proporciona un punto final para solucionar problemas relacionados con el volcado de hilos.

  • Audit: Actuator proporciona un punto final para realizar un seguimiento de las acciones de los usuarios, como el número de solicitudes que han realizado.

  • Rastreo HTTP: Actuator proporciona un punto final para recuperar una traza de todas las solicitudes y respuestas HTTP, que puede ser útil para solucionar problemas relacionados con la capa HTTP de la aplicación.

Mensajes API de Vonage

Messages API de Vonage es un conjunto de servicios web RESTful que permiten a los desarrolladores enviar y recibir mensajes, como SMS y MMS, así como servicios de mensajes enriquecidos como WhatsApp, Viber y Facebook Messenger. La API está diseñada para ser simple de usar y fácil de integrar con otros sistemas y servicios.

Primeros pasos con Vonage

Para comenzar a trabajar con las API de Vonage, deberás registrarte para obtener una cuenta de Vonage y luego crear una aplicación dentro de esa cuenta. A la aplicación se le asignará una clave de API y un secreto, que usarás para autenticar tus solicitudes a la API.

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.

Generación y envío de informes sobre la salud de las aplicaciones - La aplicación

En aras de la simplicidad, vamos a rastrear nuestra aplicación para los estados en los que el lado del servidor genera un código de error 5xx para las solicitudes que se le envían. Según el estándar de códigos HTTP, 5XX implica un error Internal Server Error. Esto significa esencialmente que nuestra aplicación podría estar teniendo algunos problemas que requieren atención. Usted puede extender esto para manejar diferentes códigos de respuesta y diversos códigos de respuesta, generados desde su aplicación en respuesta a peticiones hechas a ella.

Si desea guardar las respuestas de Actuator, necesitará crear un modelo y un repositorio para hacerlo. El modelo llevará campos que corresponden a pares clave-valor de la salida JSON del actuador. Esto no está cubierto en este artículo.

Aplicación de laHttpTraceRepository

Crear una clase RemoteRepository que implemente la interfaz "HttpTraceRepository". La clase utiliza las anotaciones "Getter" y "Setter" de la biblioteca "lombok", que proporcionan métodos getter y setter para los campos de la clase sin que el desarrollador tenga que escribirlos explícitamente.

La clase tiene dos métodos que deben ser implementados por la interfaz HttpTraceRepository: findAll() y add(HttpTrace trace). El método findAll() devuelve una lista vacía de objetos HttpTrace y el método add(HttpTrace trace) toma un objeto de tipo HttpTrace. Aquí es donde entra su lógica. En este caso, comprueba el código de estado de respuesta de ese objeto trace procedente de actuator y si es igual a 500, llama a los servicios para enviar mensajes SMS a través de la API de Vonage. También puedes indicarle que envíe mensajes de WhatsApp.

import lombok.Getter;
import lombok.Setter;
import org.springframework.boot.actuate.trace.http.HttpTrace;
import org.springframework.boot.actuate.trace.http.HttpTraceRepository;
import java.util.Collections;
import java.util.List;

@Getter
@Setter
public class RemoteRepository implements HttpTraceRepository {

   @Override
   public List<HttpTrace> findAll() {
       return Collections.emptyList();
   }

   @Override
   public void add(HttpTrace trace) {

       int responseStatusCode = trace.getResponse().getStatus();

       if (responseStatusCode == 500) {
           // call the services to send SMS and Messages via Vonage API
       }
   }
}

El actuadorConfiguration clase

A continuación, cree una clase de configuración para actuator. Esta clase de configuración , ActuatorConfigconfigura ciertos aspectos de la función Actuador de Spring.

  • @Configuration: Indica que esta clase contiene una o más definiciones @Bean para el Contexto de Aplicación de Spring.

  • @ConditionalOnWebApplication: Esta anotación es una característica de Spring Boot, indica que esta configuración debe aplicarse sólo si la aplicación es una aplicación web.

  • @ConditionalOnProperty(prefix = "management.trace.http", name = "enabled", matchIfMissing = true): Esta anotación comprueba la presencia de una propiedad de configuración específica, en este caso management.trace.http.enabled en la configuración de la aplicación. Si la propiedad no está presente, por defecto es true.

  • @EnableConfigurationProperties(HttpTraceProperties.class): Esta anotación indica a Spring que habilite el soporte para inyectar automáticamente propiedades de configuración desde los archivos de configuración de la aplicación en instancias de la clase especificada (HttpTraceProperties).

  • @AutoConfigureBefore(HttpTraceAutoConfiguration.class): Esta anotación indica que la clase ActuatorConfig debe procesarse antes que HttpTraceAutoConfiguration.

La clase también define un método traceRepository() anotado con @Bean y @ConditionalOnMissingBean(HttpTraceRepository.class)lo que significa que sólo se ejecutará si no se ha definido ningún otro bean de tipo HttpTraceRepository en el contexto de la aplicación. El método devuelve una nueva instancia de RemoteRepository que se espera que sea utilizada como un HttpTraceRepository.

import org.springframework.boot.actuate.trace.http.HttpTraceRepository;
import org.springframework.boot.actuate.autoconfigure.trace.http.HttpTraceProperties;
import org.springframework.boot.actuate.autoconfigure.trace.http.HttpTraceAutoConfiguration;
import org.springframework.boot.autoconfigure.AutoConfigureBefore;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.autoconfigure.condition.ConditionalOnWebApplication;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

@Configuration
@ConditionalOnWebApplication
@ConditionalOnProperty(prefix = "management.trace.http", name = "enabled", matchIfMissing = true)
@EnableConfigurationProperties(HttpTraceProperties.class)
@AutoConfigureBefore(HttpTraceAutoConfiguration.class)
public class ActuatorConfig {

	@Bean
	@ConditionalOnMissingBean(HttpTraceRepository.class)
	public RemoteRepository traceRepository() {
    	return new RemoteRepository();
	}
}

UtilidadService Clases para los servicios API de Vonage

Para cada uno de los servicios de Vonage con los que se trabajará, se creará una service clase. Esencialmente, una clase de servicio para cada uno de nuestros servicios de mensajes (SMS, WhatsApp, Viber) y un servicio de Voice.

VoiceService clase

Para usar la Voice API de Vonage para enviar un mensaje de voz, deberás usar el Java SDK de Vonage. Puedes enviar mensajes de voz a un número de teléfono usando texto a voz (TTS) o reproduciendo un archivo de audio pregrabado. A continuación, te mostramos cómo usar el Java SDK de Vonage para enviar un mensaje de voz:

Primero, debes agregar Vonage Java SDK como dependencia en tu proyecto. Puedes hacerlo agregando el siguiente código a tu archivo pom.xml si utilizas Maven:

<dependency>
 	<groupId>com.vonage</groupId>
    	<artifactId>client</artifactId>
    	<version>7.1.1</version>
</dependency>

A continuación, deberás crear una nueva clase que se encargará de enviar el mensaje de voz. En esta clase, deberás importar las clases com.vonage.client.voice.Call y com.vonage.client.VonageClient. En esta clase, deberás pasar tu ID de aplicación y clave privada para autenticar tu aplicación durante las llamadas.

String applicationId = "your-application-id";
String privateKeyPath = "path/to/private.key";

A continuación, cree una nueva instancia de la clase VonageClient e introduzca el ID de su aplicación y la ruta a su clave privada.

VonageClient client = VonageClient
.builder()
.applicationId(applicationId)
.privateKeyPath(privateKey)
.build();

Ahora, puede crear una nueva instancia de la clase Call y establecer las propiedades from, to y answer_url. La propiedad from es el número de teléfono o número virtual desde el que se envía el mensaje, la propiedad to es el número al que se envía el mensaje, y la propiedad answer_url es la URL que se solicitará cuando se conteste la llamada.

Call call = new Call();
call.setFrom(FROM_NUMBER);
call.setTo(TO_NUMBER);
call.setAnswerUrl(ANSWER_URL);

Para simplificar, crea una clase VonageClientProvider donde construyas una instancia de tu cliente de Vonage - con tus credenciales. Esto es vital para que no tengas que repetir código en otras clases.

import com.vonage.client.VonageClient;

public class VonageClientProvider {

    private static final String APPLICATION_ID = "VONAGE_APPLICATION_ID";
    private static final String PRIVATE_KEY = "VONAGE_PRIVATE_KEY_PATH";
    private static VonageClient instance;

    private VonageClientProvider() {}

    public static VonageClient getInstance() {
        if (instance == null) {
            instance = VonageClient.builder()
                    .applicationId(APPLICATION_ID)
                    .privateKeyPath(PRIVATE_KEY)
                    .build();
        }

        return instance;
    }
}

messagesService clase

Aquí tienes una clase en Java que demuestra cómo enviar un SMS, un mensaje de WhatsApp y un mensaje de Viber utilizando la API de Messages API de Vonage:

import com.vonage.client.VonageClient;
import com.vonage.client.messages.MessageResponse;
import com.vonage.client.messages.MessagesClient;
import com.vonage.client.messages.sms.SmsTextRequest;
import com.vonage.client.messages.viber.Category;
import com.vonage.client.messages.viber.ViberTextRequest;
import com.vonage.client.messages.whatsapp.WhatsappTextRequest;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;

@Service
@Slf4j
public class MessagingService {

    private static final String VONAGE_NUMBER = "YOUR_VONAGE_NUMBER_HERE";

    public static void sendSms(String toNumber, String text) {

        VonageClient client = VonageClientProvider.getInstance();

        MessagesClient smsClient = client.getMessagesClient();

        var message = SmsTextRequest.builder()
                .from(VONAGE_NUMBER).to(toNumber)
                .text(text)
                .build();


            MessageResponse response = smsClient.sendMessage(message);
            log.info("Message sent successfully. ID: "+response.getMessageUuid());

    }

    public static void sendWhatsApp(String toNumber, String text) {

        VonageClient client = VonageClientProvider.getInstance();

        MessagesClient whatsAppClient = client.getMessagesClient();

        var message = WhatsappTextRequest.builder()
                .from(VONAGE_NUMBER).to(toNumber)
                .text(text)
                .build();

            MessageResponse response = whatsAppClient.sendMessage(message);
            log.info("Message sent successfully. ID: "+response.getMessageUuid());
    }

sendViber() método

public static void sendViber(String toNumber, String text) {

        VonageClient client = VonageClientProvider.getInstance();

        MessagesClient viberClient = client.getMessagesClient();

        var message = ViberTextRequest.builder()
                .from(VONAGE_NUMBER).to(toNumber)
                .text(text)
                .category(Category.TRANSACTION)
                .build();

            MessageResponse response = viberClient.sendMessage(message);
            log.info("Message sent successfully. ID: " + response.getMessageUuid());
    }

MejorarRemoteRepository clase

Ya se han creado todos los servicios necesarios para enviar mensajes a través de la API de Vonage. Entra en la clase RemoteRepository y autocablea cada uno de estos servicios, de modo que, cuando se genere un "500 - Error interno del servidor", cada uno de estos servicios sea llamado y ejecutado en el orden y formato que desees. La estructura completa de la clase RemoteRepository se muestra a continuación:

import com.vonage.tracer.service.MessagingService;
import com.vonage.tracer.service.VoiceService;
import lombok.*;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.actuate.trace.http.HttpTrace;
import org.springframework.boot.actuate.trace.http.HttpTraceRepository;

import java.util.Collections;
import java.util.List;

@Getter
@Setter
@AllArgsConstructor
@NoArgsConstructor
public class RemoteRepository implements HttpTraceRepository {
    @Autowired
    private MessagingService messagingService;

    @Autowired
    private VoiceService voiceService;

    @Override
    public List<HttpTrace> findAll() {
        return Collections.emptyList();
    }

    @SneakyThrows
    @Override
    public void add(HttpTrace trace) {

        int responseStatusCode = trace.getResponse().getStatus();
        String errorMessage = "Check Server - 500 generated. Kindly check the server for an Internal Server Error";

        if (responseStatusCode == 500) {

            // call the services to send SMS, Messaging and Voice Messages via Vonage API

            MessagingService.sendSms(
                    "<sender-number-here",
                    "<recipient-number-here"
            );

            MessagingService.sendWhatsApp(
                    "<recipient-number-here", errorMessage
                    );

            MessagingService.sendViber(
                    "<recipient-number-here", errorMessage);

            voiceService.sendVoiceMessage(
                    "<recipient-here", errorMessage);

        }
    }
}

Ahora puedes crear tus controladores y cada vez que se haga una llamada a tu aplicación y resulte en un código de respuesta 500, los servicios serán llamados uno tras otro. Usted tiene la libertad de controlar cómo funciona esto, pero esto debe conseguir que en su camino a grandes cosas.

Conclusión

En este artículo, vimos cómo generar y enviar mensajes a las respectivas direcciones o ubicaciones cuando se crea un Código de Error HTTP 500 desde nuestro servidor. Con esto, puedes revisar el contenido del objeto de rastreo de Actuator y ver qué otras cosas puedes hacer con él. También puedes hacer mucho más con la API de Vonage. Consulta la documentación aquí. El código de este artículo se encuentra aquí también.

Únete a la conversación en Slack de la comunidad de Vonage o envía un mensaje en Twitter.

Compartir:

https://a.storyblok.com/f/270183/400x398/eaee70de70/tolulope-ayemobola.png
Tolulope AyemobolaAutor invitado

Tolulope es un ingeniero de software en crecimiento al que le encanta programar y escribir sobre lo que hace. Cuando no está programando, disfruta de su tiempo como disc jockey.