Sensor de Temperatura y humedad¶
La vedad es que hice esto sin mucho esfuerzo y resulto ser la mejor opción para probar algo IOT rápido.
El objetivo de esta prueba es intentar saturar la base de datos de mucho información, durante los últimos 3 días se ha recopilado 34468 datos en la base de datos, no hay una estructura en concreto, todo mensaje que llega se guarda y ya.
Hardware usado¶
ESP32 S3¶

Usé este modulo porque la verdad es el único que tenia a la mano, es demasiado la verdad, pero cumple su función por ahora.
DHT11¶

Bueno, este modulo lo compre porque me pareció muy común, ¿ y pasa cuando algo es muy común? exacto!! hay muchos ejemplos y librerías y código ya hecho en un sin fin de aplicaciones.
Firmware¶
No investigue mucho sobre el modulo temperatura y humedad solo busque DHT11 idf en google y conseguí una librería que ya hace todo.
La librería es de Michele Biondi y su ultimo commit es de hace 7 años, lo que tal vez pueda necesitar alguna mejora, no lo se.
El código en el cual me base para hacer esto es el ejemplo de TCP del protocolo Mqtt. Hice algunos cambios para que se adaptara a lo que se necesita.
Explicaré un poco como funciona. * Conexión al WIFI de forma dura, es decir con el archivo sdkconfig
en este, colocamos las SSID del Wifi.
- Configuración del broker, solo necesitamos colocar la url del broker.
Información
Puedes usar el broker kuska para hacer pruebas, aunque no garantizo este funcionando al momento que leas esto.
Si eres un poco avanzado te podrás dar cuenta que no existe nada de seguridad en el transporte de la información, esto es con fin técnico didáctico, no para desplegar un proyecto en producción, luego será el momento para eso.
Manejador de eventos MQTT¶
Esta es la parte que modifique para que solo funcionara para enviar datos de temperatura y humedad, y bueno activar un relé, pero eso ignorenlo por ahora.
static void mqtt_event_handler(void *handler_args, esp_event_base_t base, int32_t event_id, void *event_data)
{
ESP_LOGD(TAG, "Event dispatched from event loop base=%s, event_id=%" PRIi32 "", base, event_id);
esp_mqtt_event_handle_t event = event_data;
client = event->client;
switch ((esp_mqtt_event_id_t)event_id)
{
case MQTT_EVENT_CONNECTED:
ESP_LOGI(TAG, "MQTT_EVENT_CONNECTED");
esp_mqtt_client_subscribe(client, "control/rele", 0); // Suscribirse al topic rele
break;
case MQTT_EVENT_DISCONNECTED:
ESP_LOGI(TAG, "MQTT_EVENT_DISCONNECTED");
break;
case MQTT_EVENT_DATA:
ESP_LOGI(TAG, "Mensaje recibido en %.*s: %.*s",
event->topic_len, event->topic,
event->data_len, event->data);
// Comprobar si el mensaje es "0" o "1"
if (strncmp(event->data, "1", event->data_len) == 0)
{
gpio_set_level(RELAY_PIN, 1); // Activa el relé
ESP_LOGI(TAG, "Relé ACTIVADO");
}
else if (strncmp(event->data, "0", event->data_len) == 0)
{
gpio_set_level(RELAY_PIN, 0); // Desactiva el relé
ESP_LOGI(TAG, "Relé DESACTIVADO");
}
break;
case MQTT_EVENT_ERROR:
ESP_LOGI(TAG, "MQTT_EVENT_ERROR");
if (event->error_handle->error_type == MQTT_ERROR_TYPE_TCP_TRANSPORT)
{
log_error_if_nonzero("reported from esp-tls", event->error_handle->esp_tls_last_esp_err);
log_error_if_nonzero("reported from tls stack", event->error_handle->esp_tls_stack_err);
log_error_if_nonzero("captured as transport's socket errno", event->error_handle->esp_transport_sock_errno);
ESP_LOGI(TAG, "Last errno string (%s)", strerror(event->error_handle->esp_transport_sock_errno));
}
break;
default:
ESP_LOGI(TAG, "Other event id:%d", event->event_id);
break;
}
}
Esta función lo que hace es capturar los eventos MQTT, lo mas loco es que no es necesario un bucle infinito o estar consultando, no, sólito funciona. osea, ocurre un evento y switch filtra de acuerdo al evento y función de esto se puede hacer una acción.
Casos¶
MQTT_EVENT_CONNECTED¶
cuando se conecta al broker se subscribe el topic control/rele
MQTT_EVENT_DISCONNECTED¶
Cuando se desconecta dice por la terminal "MQTT_EVENT_DISCONNECTED" (si, es tal cual el ejemplo) en este caso se puede hacer mas cosas, de acuerdo a lo critico que puede ser el sensor, podría sonar una alarma o algo así, o cambiar un LED de color.
MQTT_EVENT_DATA¶
Este caso lo deje, aunque no se usa en esta aplicación, lo deje porque es algo que usare mas adelante, este evento recibe la información del broker al que esta subscrito, en este caso "control/rele" si el mensaje es 0 apaga el relé y si es uno lo enciende. ¿simple no?
MQTT_EVENT_ERROR:¶
Bueno, esto solo indica un error en el protocolo MQTT de llegar a existir.
Creo que explique todo esto y no aplica para este caso :'(
Envió de datos al broker¶
Esta es la parte que realmente importa, aunque la anterior también sera importante para después.
void adc_task(void *pvParameters)
{
char temperatura[50];
char humedad[50];
int temp;
int hum;
while (1)
{
// Leer temperatura
temp = DHT11_read().temperature;
if (temp > 0){
snprintf(temperatura, sizeof(temperatura), "%d", temp);
esp_mqtt_client_publish(client, "sensor/temperatura", temperatura, 0, 0, 0);
vTaskDelay(pdMS_TO_TICKS(1000));
}
// Leer humedad
hum = DHT11_read().humidity;
if (hum > 0)
{
snprintf(humedad, sizeof(humedad), "%d", hum);
esp_mqtt_client_publish(client, "sensor/humedad", humedad, 0, 0, 0);
}
// Esperar 30 segundos
vTaskDelay(pdMS_TO_TICKS(15000));
}
}
Ojo
Esta tarea debería tener otro nombre, pero como les dije, fue algo rápido, luego hice corrigiendo mi código espaguetis. En vez de llamarse adc_task debería llamarse Temp_hum_task
Esta tarea en un hilo del ESP32, la cual esta leyendo continuamente la temperatura y la humedad la publican en el topic "sensor/humedad" y "sensor/temperatura" bueno, lo hace cada 15 segundos, mientras tanto el hilo principal escuchas los eventos el MQTT y todas esas cosas.
La funcion DHT11_read() viene de la Liberia de Michele Biondi, para usar este Liberia coloque dht11.h
y dht11.c
en el mismo nivel que app_main.c y luego la incluí en el programa principal.
.. y eso fue todo, para finalizar coloque el llamado a la clase en dentro de la función app_main() xTaskCreate(adc_task, "adc_task", 4096, NULL, 5, NULL);
hay mas cosas, pero para mas detalles mira el código en el repositorio.
Firmware temperatura y Humedad
Carcasa¶
Bueno para finalizar hice una cajita muy simple en FreeCad y coloque el sensor en la cocina de mi casa para ver como esta la cosa por alla.