plant_watering/ ├── status/ │ ├── esp32/connected # ESP32 connection status (retained) │ ├── esp32/ip # ESP32 IP address (retained) │ ├── esp32/uptime # System uptime in seconds │ ├── esp32/version # Firmware version (retained) │ ├── esp32/rssi # WiFi signal strength │ ├── esp32/free_heap # Free memory for diagnostics │ └── esp32/restart_reason # Last restart reason (retained) ├── pump/1/ │ ├── command # Commands: ON/OFF/PULSE │ ├── status # Current status (retained) │ ├── runtime # Last run duration in seconds │ ├── total_runtime # Total runtime counter in seconds │ ├── last_activated # Timestamp of last activation │ └── flow_rate # If flow sensor added later ├── pump/2/ │ ├── command # Commands: ON/OFF/PULSE │ ├── status # Current status (retained) │ ├── runtime # Last run duration in seconds │ ├── total_runtime # Total runtime counter in seconds │ ├── last_activated # Timestamp of last activation │ └── flow_rate # If flow sensor added later ├── sensor/1/ │ ├── moisture # Current moisture reading (0-4095) │ ├── moisture_percent # Moisture as percentage │ ├── last_watered # Timestamp of last watering │ ├── temperature # Soil temperature if sensor supports │ └── calibration/ │ ├── dry_value # Calibration point for dry │ └── wet_value # Calibration point for wet ├── sensor/2/ │ ├── moisture # Current moisture reading (0-4095) │ ├── moisture_percent # Moisture as percentage │ ├── last_watered # Timestamp of last watering │ ├── temperature # Soil temperature if sensor supports │ └── calibration/ │ ├── dry_value # Calibration point for dry │ └── wet_value # Calibration point for wet ├── settings/ │ ├── pump/1/ │ │ ├── moisture_threshold # Trigger threshold (0-100%) │ │ ├── water_duration # Watering duration in seconds │ │ ├── min_interval # Minimum hours between watering │ │ ├── max_duration # Safety maximum runtime │ │ └── enabled # Enable/disable pump │ ├── pump/2/ │ │ ├── moisture_threshold # Trigger threshold (0-100%) │ │ ├── water_duration # Watering duration in seconds │ │ ├── min_interval # Minimum hours between watering │ │ ├── max_duration # Safety maximum runtime │ │ └── enabled # Enable/disable pump │ └── system/ │ ├── report_interval # How often to publish sensor data │ ├── timezone # For scheduling features │ └── auto_mode # Global auto-watering enable ├── alerts/ │ ├── low_moisture/1 # Zone 1 moisture too low │ ├── low_moisture/2 # Zone 2 moisture too low │ ├── pump_error/1 # Pump 1 malfunction │ ├── pump_error/2 # Pump 2 malfunction │ ├── sensor_error/1 # Sensor 1 reading issues │ ├── sensor_error/2 # Sensor 2 reading issues │ └── water_tank_low # If tank sensor added └── commands/ ├── calibrate/sensor/1 # Trigger calibration mode ├── calibrate/sensor/2 # Trigger calibration mode ├── restart # Restart ESP32 ├── factory_reset # Clear all settings └── ota/url # Trigger OTA from URL Additional considerations: Timestamps: Use ISO 8601 format (e.g., "2024-01-15T14:30:00Z") for consistency Retained messages: Mark critical status messages as retained (as you've done) QoS levels: QoS 0 for frequent sensor readings QoS 1 for commands and state changes QoS 2 for critical alerts (if needed) JSON payloads: Consider using JSON for complex data: // plant_watering/status/esp32/info { "version": "2.0.0", "uptime": 3600, "free_heap": 45632, "rssi": -65, "ip": "192.168.1.42" } Home Assistant Discovery: Add discovery topics if planning HA integration: homeassistant/sensor/plant_watering_moisture_1/config homeassistant/switch/plant_watering_pump_1/config