Intermediate 25 min

Step 6: Alerts & Production Notes

Let’s add alert rules and discuss what you’d need for production.

Add Alert Rules

We’ll add two alerts:

  1. Battery Low: When battery < 20%
  2. Temperature High: When temperature > 30°C

Alert Flow in Node-RED

1. Add Switch Node (Route by Condition)

After the Function node, add a switch node:

  • Property: metrics.batteryPct
  • Condition 1: < 20 → Output 1 (battery low)
  • Condition 2: >= 20 → Output 2 (normal)

2. Add Another Switch for Temperature

Add another switch node:

  • Property: metrics.temperatureC
  • Condition 1: > 30 → Output 1 (temp high)
  • Condition 2: <= 30 → Output 2 (normal)

3. Add Rate Limiter (Prevent Spam)

Add a delay node before alerts:

  • Action: Rate limit
  • Rate: 1 message per 60 seconds
  • This prevents alert spam if condition stays true

4. Add Alert Notification

Add a function node for alert messages:

// Create alert message
const alert = {
    deviceId: msg.deviceId,
    timestamp: msg.ts,
    type: msg.alertType, // "battery_low" or "temperature_high"
    severity: "warning",
    message: msg.alertMessage,
    metrics: msg.metrics
};

// Publish to alert topic
return {
    topic: `iot/alerts/${msg.deviceId}`,
    payload: JSON.stringify(alert)
};

5. Add MQTT Out Node

  • Connect to alert function
  • Topic: iot/alerts/{{deviceId}}
  • QoS: 1
  • Retain: false

Complete Alert Flow

Data Data Low High Alert Publish Validate Battery Check Temp Check Rate Limit Create Alert MQTT Out

Alert Function Code

Here’s the complete alert function:

// Determine alert type and message
let alertType, alertMessage;

if (msg.metrics.batteryPct < 20) {
    alertType = "battery_low";
    alertMessage = `Battery low: ${msg.metrics.batteryPct}%`;
} else if (msg.metrics.temperatureC > 30) {
    alertType = "temperature_high";
    alertMessage = `Temperature high: ${msg.metrics.temperatureC}°C`;
} else {
    return null; // No alert
}

// Create alert payload
const alert = {
    deviceId: msg.deviceId,
    timestamp: msg.ts,
    type: alertType,
    severity: "warning",
    message: alertMessage,
    metrics: msg.metrics
};

// Add alert metadata
msg.alertType = alertType;
msg.alertMessage = alertMessage;
msg.payload = JSON.stringify(alert);

return msg;

Test Alerts

  1. Battery Low: Wait for battery to drop below 20% (or modify simulator to start at 15%)
  2. Temperature High: Modify simulator to generate high temperatures

Subscribe to alerts:

mosquitto_sub -h localhost -p 1883 -t iot/alerts/+

Production Considerations

Here’s what you’d need for a real deployment:

1. Security

❌ Current (Dev Only):

  • Anonymous access allowed
  • No encryption
  • No authentication

✅ Production:

  • Username/password authentication
  • TLS/SSL encryption (port 8883)
  • Access Control Lists (ACLs) for topic permissions
  • Certificate-based authentication for devices

Example Mosquitto config:

# Require authentication
allow_anonymous false
password_file /mosquitto/config/passwd

# TLS/SSL
listener 8883
cafile /mosquitto/config/ca.crt
certfile /mosquitto/config/server.crt
keyfile /mosquitto/config/server.key

2. Quality of Service (QoS)

When to use each:

  • QoS 0: Sensor readings, non-critical data (fastest)
  • QoS 1: Commands, alerts (guaranteed delivery)
  • QoS 2: Critical state changes (exactly once, slower)

Current: We use QoS 1 for telemetry (good balance)

3. Retained Messages

Use for:

  • Device state (last known value)
  • Configuration
  • Status updates

Don’t use for:

  • High-frequency telemetry (wastes storage)
  • Commands (shouldn’t be retained)

4. Last Will and Testament

Set a “last will” message when device connects:

client.will_set(
    topic=f"iot/devices/{DEVICE_ID}/status",
    payload='{"status":"offline"}',
    qos=1,
    retain=True
)

If device disconnects unexpectedly, broker publishes this message.

5. Message Persistence

For critical data:

  • Use a database (InfluxDB, TimescaleDB)
  • Store in Node-RED context (limited)
  • Use MQTT broker persistence (limited)

6. Scalability

Current setup: Single broker, localhost

Production options:

  • MQTT Broker Clusters: Multiple brokers
  • Load Balancing: Distribute devices
  • Cloud Services: AWS IoT Core, Azure IoT Hub, Google Cloud IoT

7. Monitoring

Monitor:

  • Broker connections
  • Message throughput
  • Error rates
  • Device connectivity
  • Alert frequency

Troubleshooting

“Subscriber prints nothing”

  • Check broker is running: docker-compose ps
  • Check topic matches: Use mosquitto_sub -v to see topics
  • Check simulator is publishing: Look for “Published message” logs

“Docker ports conflict”

  • Change ports in docker-compose.yml
  • Check what’s using ports: lsof -i :1883

“Node-RED can’t connect to broker”

  • Use mosquitto as hostname (Docker network)
  • Or use localhost if Node-RED runs outside Docker
  • Check broker logs: docker-compose logs mosquitto

“JSON parse errors”

  • Verify message format matches schema
  • Check for extra characters
  • Use mosquitto_sub -v to see raw messages

“High CPU due to publish interval”

  • Increase PUBLISH_INTERVAL (e.g., 5 seconds)
  • Use QoS 0 for non-critical data
  • Reduce message size

Next Steps

Now that you have a working system, here are ideas to extend it:

1. Replace Simulator with Real Hardware

  • Use ESP32 or Raspberry Pi
  • Connect real sensors (DHT22, BME280)
  • Same MQTT code, different sensor reading

2. Store Telemetry in Database

  • Add InfluxDB to Docker Compose
  • Store all messages
  • Query historical data

3. Add REST API

  • Query latest device state
  • Get historical data
  • Trigger commands

4. Multi-Device Dashboard

  • Show multiple devices
  • Device selector dropdown
  • Aggregate statistics

5. Advanced Alerts

  • Email notifications
  • Slack integration
  • SMS alerts

Knowledge Check

Test your understanding:

Congratulations! 🎉

You’ve built a complete IoT digital twin system:

  • ✅ MQTT broker running in Docker
  • ✅ Python device simulator publishing telemetry
  • ✅ Node-RED flow processing and validating data
  • ✅ Real-time dashboard with gauges and charts
  • ✅ Alert rules for battery and temperature

You now understand:

  • How MQTT works
  • How to design topics
  • How to process IoT data
  • How to build dashboards
  • Production considerations

Wrap-up

This tutorial showed you a real IoT pattern used in production. The same concepts apply whether you’re using:

  • AWS IoT Core
  • Azure IoT Hub
  • Google Cloud IoT
  • Your own MQTT broker

The principles are the same: devices publish, brokers route, applications subscribe and process.

Keep experimenting, and happy building! 🚀