

Las traducciones son generadas a través de traducción automática. En caso de conflicto entre la traducción y la version original de inglés, prevalecerá la version en inglés.

# Demostraciones de coreMQTT
<a name="mqtt-demo"></a>

**importante**  <a name="deprecation-message-demo"></a>
Esta demostración está alojada en el repositorio de Amazon-FreeRTOS, que está en desuso. Recomendamos [empezar por aquí](freertos-getting-started-modular.md) al crear un nuevo proyecto. Si ya tiene un proyecto FreeRTOS existente basado en el repositorio Amazon FreeRTOS, ahora obsoleto, consulte [Guía de migración del repositorio Github de Amazon-FreeRTOS](github-repo-migration.md).

Estas demostraciones pueden ayudarle a saber cómo utilizar la biblioteca coreMQTT.

**Topics**
+ [Demostración de la autenticación mutua de coreMQTT](mqtt-demo-ma.md)
+ [Demostración de conexión compartida del agente coreMQTT](mqtt-demo-cs.md)

# Demostración de la autenticación mutua de coreMQTT
<a name="mqtt-demo-ma"></a>

**importante**  <a name="deprecation-message-demo"></a>
Esta demostración está alojada en el repositorio de Amazon-FreeRTOS, que está en desuso. Recomendamos [empezar por aquí](freertos-getting-started-modular.md) al crear un nuevo proyecto. Si ya tiene un proyecto FreeRTOS existente basado en el repositorio Amazon FreeRTOS, ahora obsoleto, consulte [Guía de migración del repositorio Github de Amazon-FreeRTOS](github-repo-migration.md).

## Introducción
<a name="mqtt-demo-ma-introduction"></a>

El proyecto de demostración de autenticación mutua de coreMQTT muestra cómo establecer una conexión con un agente HTTP mediante TLS con autenticación mutua entre el cliente y el servidor. Esta demostración utiliza una implementación de interfaz de transporte basada en mbedTLS para establecer una conexión TLS autenticada por el servidor y el cliente, y muestra el flujo de trabajo de suscripción-publicación de MQTT en el nivel de [ QoS 1](http://docs.oasis-open.org/mqtt/mqtt/v3.1.1/errata01/os/mqtt-v3.1.1-errata01-os-complete.html#_Toc442180914). Se suscribe a un filtro de temas, luego publica los temas que coinciden con el filtro y espera a que el servidor reciba esos mensajes en el nivel de QoS 1. Este ciclo de publicación en el agente y recepción del mismo mensaje por parte del agente se repite indefinidamente. Los mensajes de esta demostración se envían en QoS 1, lo que garantiza al menos una entrega de acuerdo con la especificación MQTT.

**nota**  
Para configurar y ejecutar las demostraciones de FreeRTOS, siga los pasos que se indican en [Introducción a FreeRTOS](freertos-getting-started.md).

## Código fuente
<a name="mqtt-demo-ma-source-code"></a>

El archivo fuente de la demostración tiene un nombre `mqtt_demo_mutual_auth.c` y se puede encontrar en el `freertos/demos/coreMQTT/` directorio y en el [ GitHub](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c)sitio web.

## Funcionalidad
<a name="mqtt-demo-ma-functionality"></a>

La demostración crea una única tarea de aplicación que recorre un conjunto de ejemplos que muestran cómo conectarse al agente, suscribirse a un tema en el agente, publicar en un tema en el agente y, por último, desconectarse del agente. La aplicación de demostración se suscribe y publica en el mismo tema. Cada vez que la demostración publica un mensaje en el agente de MQTT, este envía el mismo mensaje a la aplicación de demostración.

Si se completa correctamente la demostración, se generará una salida similar a la de la siguiente imagen.

![\[Salida del terminal de demostración MQTT tras una finalización correcta\]](http://docs.aws.amazon.com/es_es/freertos/latest/userguide/images/coremqtt-mad-output.png)


La AWS IoT consola generará un resultado similar al de la imagen siguiente.

![\[Salida de la consola de demostración MQTT tras una finalización correcta\]](http://docs.aws.amazon.com/es_es/freertos/latest/userguide/images/coremqtt-mad-console.png)


## Reintento de la lógica con retroceso exponencial y fluctuación
<a name="mqtt-demo-ma-retry-logic"></a>

La función [ prvBackoffForReintentar](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L671-L717) muestra cómo se pueden reintentar las operaciones de red fallidas con el servidor, por ejemplo, las conexiones TLS o las solicitudes de suscripción a MQTT, con un retraso y una fluctuación exponenciales. La función calcula el período de retroceso para el siguiente reintento y realiza el retroceso si no se han agotado los reintentos. Como el cálculo del período de espera requiere la generación de un número aleatorio, la función utiliza el módulo para generar el número aleatorio. PKCS11 El uso del PKCS11 módulo permite acceder a un generador de números aleatorios verdaderos (TRNG) si la plataforma del proveedor lo admite. Le recomendamos que añada al generador de números aleatorios una fuente de entropía específica del dispositivo para reducir la probabilidad de colisiones entre los dispositivos durante los reintentos de conexión.

## Conexión al agente de MQTT
<a name="mqtt-demo-ma-connecting"></a>

La [ prvConnectToServerWithBackoffRetries](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L721-L782)función intenta establecer una conexión TLS autenticada mutuamente con el intermediario MQTT. Si la conexión falla, se vuelve a intentar tras un período de retroceso. El valor de retroceso aumenta exponencialmente hasta que se alcanza el número máximo de intentos o se alcanza el valor de período de retroceso máximo. La función `BackoffAlgorithm_GetNextBackoff` proporciona un valor de retroceso que aumenta exponencialmente y devuelve `RetryUtilsRetriesExhausted` cuando se alcanza el número máximo de intentos. La función `prvConnectToServerWithBackoffRetries` devuelve un estado de error si no se puede establecer la conexión TLS con el agente tras el número de intentos configurado.

La MQTTConnection WithBroker función [PrvCreate](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L785-L848) muestra cómo establecer una conexión MQTT con un broker MQTT con una sesión limpia. Utiliza la interfaz de transporte TLS, que está implementada en el archivo `FreeRTOS-Plus/Source/Application-Protocols/platform/freertos/transport/src/tls_freertos.c`. Tenga en cuenta que estamos configurando los segundos de permanencia activa para el agente en `xConnectInfo`.

La siguiente función muestra cómo se configuran la interfaz de transporte TLS y la función de tiempo en un contexto MQTT mediante la función `MQTT_Init`. También muestra cómo se configura un puntero de la función de devolución de llamada de eventos (`prvEventCallback`). Esta devolución de llamada se utiliza notificar los mensajes entrantes.

## Suscripción a un tema de MQTT
<a name="mqtt-demo-ma-subscribing"></a>

La MQTTSubscribe WithBackoffRetries función [prv](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L871-L969) muestra cómo suscribirse a un filtro de temas en el bróker MQTT. El ejemplo muestra cómo suscribirse a un filtro de temas, pero es posible transferir una lista de filtros de temas en la misma llamada a la API de suscripción para suscribirse a más de un filtro de temas. Además, en caso de que el agente de MQTT rechace la solicitud de suscripción, la suscripción volverá a intentarlo, con un retroceso exponencial, durante el valor establecido en `RETRY_MAX_ATTEMPTS`.

## Publicación de un tema
<a name="mqtt-demo-ma-publishing"></a>

La MQTTPublish ToTopic función [prv](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L972-L1004) muestra cómo publicar un tema en el bróker MQTT. 

## Recepción de mensajes entrantes
<a name="mqtt-demo-ma-receiving"></a>

La aplicación registra una función de devolución de llamada de eventos antes de conectarse al agente, tal y como se ha descrito anteriormente. La función `prvMQTTDemoTask` llama a la función `MQTT_ProcessLoop` para recibir los mensajes entrantes. Cuando se recibe un mensaje MQTT entrante, llama a la función de devolución de llamada del evento registrada por la aplicación. La [ prvEventCallback](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L1139-L1154)función es un ejemplo de una función de devolución de llamada de eventos de este tipo. `prvEventCallback`examina el tipo de paquete entrante y llama al gestor correspondiente. En el ejemplo siguiente, la función llama a `prvMQTTProcessIncomingPublish()` para gestionar los mensajes de publicación entrantes o a `prvMQTTProcessResponse()` para gestionar los acuses de recibo (ACK).

## Proceso de paquetes de publicación MQTT entrantes
<a name="mqtt-demo-ma-processing"></a>

La MQTTProcess IncomingPublish función [prv](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L1108-L1135) muestra cómo procesar un paquete de publicación del broker MQTT. 

## Cancelación de la suscripción a un tema
<a name="mqtt-demo-ma-unsubscribing"></a>

El último paso del flujo de trabajo consiste en cancelar la suscripción al tema para que el agente no envíe ningún mensaje publicado desde `mqttexampleTOPIC`. [Esta es la definición de la función prv. MQTTUnsubscribe FromTopic](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT/mqtt_demo_mutual_auth.c#L1007-L1043)

## Cambio de la CA raíz utilizada en la demostración
<a name="mqtt-demo-ma-root-ca"></a>

De forma predeterminada, las demostraciones de FreeRTOS utilizan el certificado Amazon Root CA 1 (clave RSA de 2048 bits) para autenticarse en el servidor. AWS IoT Core Es posible utilizar otros [ certificados CA para la autenticación del servidor](https://docs.aws.amazon.com/iot/latest/developerguide/server-authentication.html#server-authentication-certs), incluido el certificado CA raíz 3 de Amazon (clave ECC de 256 bits). Para cambiar la CA raíz de la demostración de autenticación mutua coreMQTT: 

1. Abra el archivo `freertos/vendors/vendor/boards/board/aws_demos/config_files/mqtt_demo_mutual_auth_config.h` en un editor de texto.

1. En el archivo, localice la línea siguiente.

   ```
    * #define democonfigROOT_CA_PEM    "...insert here..." 
   ```

   Elimine el comentario de esta línea y, si es necesario, muévala más allá del extremo del bloque de comentarios ` */`.

1. Copie el certificado CA que desee utilizar y péguelo en el texto `"...insert here..."`. El resultado debe ser similar al siguiente ejemplo:

   ```
   #define democonfigROOT_CA_PEM   "-----BEGIN CERTIFICATE-----\n"\
   "MIIBtjCCAVugAwIBAgITBmyf1XSXNmY/Owua2eiedgPySjAKBggqhkjOPQQDAjA5\n"\
   "MQswCQYDVQQGEwJVUzEPMA0GA1UEChMGQW1hem9uMRkwFwYDVQQDExBBbWF6b24g\n"\
   "Um9vdCBDQSAzMB4XDTE1MDUyNjAwMDAwMFoXDTQwMDUyNjAwMDAwMFowOTELMAkG\n"\
   "A1UEBhMCVVMxDzANBgNVBAoTBkFtYXpvbjEZMBcGA1UEAxMQQW1hem9uIFJvb3Qg\n"\
   "Q0EgMzBZMBMGByqGSM49AgEGCCqGSM49AwEHA0IABCmXp8ZBf8ANm+gBG1bG8lKl\n"\
   "ui2yEujSLtf6ycXYqm0fc4E7O5hrOXwzpcVOho6AF2hiRVd9RFgdszflZwjrZt6j\n"\
   "QjBAMA8GA1UdEwEB/wQFMAMBAf8wDgYDVR0PAQH/BAQDAgGGMB0GA1UdDgQWBBSr\n"\
   "ttvXBp43rDCGB5Fwx5zEGbF4wDAKBggqhkjOPQQDAgNJADBGAiEA4IWSoxe3jfkr\n"\
   "BqWTrBqYaGFy+uGh0PsceGCmQ5nFuMQCIQCcAu/xlJyzlvnrxir4tiz+OpAUFteM\n"\
   "YyRIHN8wfdVoOw==\n"\
   "-----END CERTIFICATE-----\n"
   ```

1. (Opcional) Puede cambiar la CA raíz para otras demostraciones. Repita los pasos 1 a 3 para cada archivo `freertos/vendors/vendor/boards/board/aws_demos/config_files/demo-name_config.h`.

# Demostración de conexión compartida del agente coreMQTT
<a name="mqtt-demo-cs"></a>

**importante**  <a name="deprecation-message-demo"></a>
Esta demostración está alojada en el repositorio de Amazon-FreeRTOS, que está en desuso. Recomendamos [empezar por aquí](freertos-getting-started-modular.md) al crear un nuevo proyecto. Si ya tiene un proyecto FreeRTOS existente basado en el repositorio Amazon FreeRTOS, ahora obsoleto, consulte [Guía de migración del repositorio Github de Amazon-FreeRTOS](github-repo-migration.md).

## Introducción
<a name="mqtt-demo-cs-introduction"></a>

El proyecto de demostración de conexión compartida de CoreMQTT muestra cómo utilizar una aplicación multiproceso para establecer una conexión con el broker AWS MQTT mediante TLS con autenticación mutua entre el cliente y el servidor. Esta demostración utiliza una implementación de interfaz de transporte basada en mbedTLS para establecer una conexión TLS autenticada por el servidor y el cliente, y muestra el flujo de trabajo de suscripción-publicación de MQTT en el nivel de [ QoS 1](http://docs.oasis-open.org/mqtt/mqtt/v3.1.1/errata01/os/mqtt-v3.1.1-errata01-os-complete.html#_Toc442180914). La demostración se suscribe a un filtro de temas, publica los temas que coinciden con el filtro y espera a que el servidor reciba esos mensajes en el nivel de QoS 1. Este ciclo de publicación al agente y de recepción del mismo mensaje de vuelta del agente se repite varias veces para cada tarea creada. Los mensajes de esta demostración se envían en QoS 1, lo que garantiza al menos una entrega de acuerdo con la especificación MQTT.

**nota**  
Para configurar y ejecutar las demostraciones de FreeRTOS, siga los pasos que se indican en [Introducción a FreeRTOS](freertos-getting-started.md).

Esta demostración utiliza una cola segura para subprocesos para almacenar los comandos que interactúan con la API MQTT. En esta demostración, hay dos tareas que hay que tener en cuenta.
+ Una tarea del agente MQTT (principal) procesa los comandos de la cola de comandos mientras que otras tareas los ponen en cola. Esta tarea entra en un bucle durante el cual procesa los comandos de la cola de comandos. Si se recibe un comando de terminación, esta tarea saldrá del bucle.
+ Una tarea de subpublicación de demostración crea una suscripción a un tema de MQTT, luego crea operaciones de publicación y las envía a la cola de comandos. A continuación, la tarea del agente MQTT ejecuta estas operaciones de publicación. La tarea subpublicación de demostración espera a que finalice la publicación, indicada por la ejecución de la devolución de llamada de finalización del comando y luego introduce un breve retardo antes de iniciar la siguiente publicación. Esta tarea muestra ejemplos de cómo las tareas de aplicación utilizarían la API del agente coreMQTT.

Para los mensajes de publicación entrantes, el agente de coreMQTT invoca una única función de devolución de llamada. Esta demostración también incluye un administrador de suscripciones que permite a las tareas especificar una devolución de llamada para invocar los mensajes de publicación entrantes sobre temas a los que se han suscrito. En esta demostración, la devolución de llamada de publicación entrante del agente invoca al administrador de suscripciones que distribuya las publicaciones hacia cualquier tarea que haya registrado una suscripción.

Esta demostración utiliza una conexión TLS con autenticación mutua para conectarse. AWS Si la red se desconecta inesperadamente durante la demostración, el cliente intenta volver a conectarse mediante una lógica de retroceso exponencial. Si el cliente se vuelve a conectar correctamente, pero el agente no puede reanudar la sesión anterior, el cliente volverá a suscribirse a los mismos temas que en la sesión anterior.

### Un único subproceso frente a varios subprocesos
<a name="mqtt-demo-cs-single-vs-multi"></a>

Hay dos modelos de uso de coreMQTT: subproceso único y varios subprocesos (multitarea). El modelo de subproceso único utiliza la biblioteca coreMQTT únicamente desde un subproceso y requiere que se realicen repetidas llamadas explícitas en la biblioteca MQTT. En cambio, en los casos de uso con varios subprocesos se puede ejecutar el protocolo MQTT en segundo plano dentro de una tarea de agente (o daemon), como se muestra en la demostración documentada aquí. Al ejecutar el protocolo MQTT en una tarea de agente, no es necesario gestionar explícitamente ningún estado de MQTT ni llamar a la función de la API `MQTT_ProcessLoop`. Además, si utiliza una tarea de agente, varias tareas de la aplicación pueden compartir una única conexión MQTT sin necesidad de primitivas de sincronización, como mutex. 

## Código fuente
<a name="mqtt-demo-cs-source-code"></a>

Los archivos fuente de la demostración tienen un nombre `mqtt_agent_task.c` y se pueden encontrar en el `simple_sub_pub_demo.c` directorio y en el sitio web. `freertos/demos/coreMQTT_Agent/` [GitHub](https://github.com/aws/amazon-freertos/tree/main/demos/coreMQTT_Agent/)

## Funcionalidad
<a name="mqtt-demo-cs-functionality"></a>

Esta demostración crea al menos dos tareas: una principal que procesa las solicitudes de llamadas a la API de MQTT y una cantidad configurable de subtareas que crean esas solicitudes. En esta demostración, la tarea principal crea las subtareas, llama al bucle de procesamiento y, después, se limpia. La tarea principal crea una única conexión MQTT con el agente que se comparte entre las subtareas. Las subtareas crean una suscripción a MQTT con el agente y, a continuación, publican los mensajes en ella. Cada subtarea utiliza un tema único para sus publicaciones.

## Tarea principal
<a name="mqtt-demo-cs-main-task"></a>

La tarea principal de la aplicación, [ RunCoreMQTTAgentDemo](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT_Agent/mqtt_agent_task.c#L435-L480), establece una sesión MQTT, crea las subtareas y ejecuta el bucle de procesamiento [ MQTTAgent\$1 CommandLoop](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT_Agent/mqtt_agent_task.c#L856) hasta que se recibe una orden de finalización. Si la red se desconecta inesperadamente, la demostración volverá a conectarse al agente en segundo plano y restablecerá las suscripciones con el agente. Una vez finalizado el bucle de procesamiento, se desconecta del agente.

### Comandos
<a name="mqtt-demo-cs-main-task-commands"></a>

Cuando invoca una API de agente coreMQTT, crea un comando que se envía a la cola de tareas del agente, donde se procesa en `MQTTAgent_CommandLoop()`. En el momento en que se crea el comando, se pueden transferir los parámetros opcionales de contexto y devolución de llamada de finalización. Una vez que se complete el comando correspondiente, se invocará la devolución de llamada de finalización con el contexto transferido y cualquier valor devuelto que se haya creado como resultado del comando. La firma de la devolución de llamada de finalización es la siguiente:

```
typedef void (* MQTTAgentCommandCallback_t )( void * pCmdCallbackContext,
                                              MQTTAgentReturnInfo_t * pReturnInfo );
```

[El contexto de finalización de comandos lo define el usuario; en esta demostración, es: struct. MQTTAgent CommandContext](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT_Agent/simple_sub_pub_demo.c#L105-L115)

Los comandos se consideran completados cuando:
+ Se suscribe, cancela la suscripción y publica con QoS > 0: una vez recibido el paquete de acuse de recibo correspondiente.
+ Todas las demás operaciones: una vez que se haya invocado la API de coreMQTT correspondiente.

Todas las estructuras utilizadas por el comando, incluida la información de publicación, la información de suscripción y los contextos de finalización, deben permanecer dentro del ámbito de aplicación hasta que se complete el comando. Una tarea de llamada no debe reutilizar ninguna de las estructuras de un comando antes de que se invoque la devolución de llamada de finalización. Tenga en cuenta que, dado que el agente MQTT invoca la devolución de llamada de finalización, se ejecutará en el contexto de subproceso de la tarea del agente, no con la tarea que creó el comando. Los mecanismos de comunicación entre procesos, como las notificaciones o las colas de tareas, se pueden utilizar para indicar la tarea de llamada cuando se ha completado el comando.

### Ejecución del bucle de comandos
<a name="mqtt-demo-cs-command-loop"></a>

Los comandos se procesan de forma continua en `MQTTAgent_CommandLoop()`. Si no hay ningún comando que procesar, el bucle esperará el valor máximo establecido en `MQTT_AGENT_MAX_EVENT_QUEUE_WAIT_TIME` para añadir uno a la cola y, si no se añade ningún comando, ejecutará una sola iteración de `MQTT_ProcessLoop()`. Esto garantiza que MQTT Keep-Alive esté gestionado y que todas las publicaciones entrantes se reciban incluso cuando no haya ningún comando en la cola.

La función de bucle de comandos regresará por las siguientes razones:
+ Un comando devuelve cualquier código de estado que no sea `MQTTSuccess`. El bucle de comandos devuelve el estado del error, por lo que puede decidir cómo gestionarlo. En esta demostración, se restablece la conexión TCP y se intenta volver a conectarla. Si se produce algún error, se puede volver a conectar en segundo plano sin que intervengan otras tareas que utilicen MQTT.
+ Se procesa un comando de desconexión (desde `MQTTAgent_Disconnect`). El bucle de comandos se cierra para que se pueda desconectar el TCP.
+ Se procesa un comando de terminación (desde `MQTTAgent_Terminate`). Este comando también marca como error cualquier comando que aún esté en la cola o en espera de un paquete de acuse de recibo, con un código de devolución de `MQTTRecvFailed`.

### Administrador de suscripciones
<a name="mqtt-demo-cs-subscription-manager"></a>

Como en la demostración se utilizan varios temas, un administrador de suscripciones es una forma cómoda de asociar los temas suscritos a devoluciones de llamadas o tareas únicas. El administrador de suscripciones de esta demostración es de un solo subproceso, por lo que no debe utilizarse en varias tareas al mismo tiempo. En esta demostración, solo se llama a las funciones del administrador de suscripciones desde las funciones de devolución de llamada que se transfieren al agente MQTT y se ejecutan únicamente en el contexto del subproceso de la tarea del agente.

## Tarea sencilla de suscripción y publicación
<a name="mqtt-demo-cs-sub-pub"></a>

Cada instancia de [ prvSimpleSubscribePublishTask](https://github.com/aws/amazon-freertos/blob/main/demos/coreMQTT_Agent/simple_sub_pub_demo.c#L447-L569)crea una suscripción a un tema de MQTT y crea operaciones de publicación para ese tema. Para demostrar varios tipos de publicación, las tareas con números pares utilizan QoS 0 (que se completan una vez que se envía el paquete de publicación) y las tareas impares utilizan QoS 1 (que se completan al recibir un paquete PUBACK).