Complete Rebuild, with Subsystems for each component. RTOS Tasks. (help by Claude)

This commit is contained in:
2025-10-01 12:42:00 +03:00
parent 104c1d04d4
commit f696984cd1
57 changed files with 11757 additions and 2290 deletions

View File

@@ -0,0 +1,232 @@
/*
* ═══════════════════════════════════════════════════════════════════════════════════
* COMMUNICATION.HPP - Multi-Protocol Communication Manager v3.0
* ═══════════════════════════════════════════════════════════════════════════════════
*
* 📡 THE COMMUNICATION HUB OF VESPER 📡
*
* This class manages all external communication protocols including MQTT,
* WebSocket, and UDP discovery. It provides a unified interface for
* grouped command handling and status reporting across multiple protocols.
*
* 🏗️ ARCHITECTURE:
* • Multi-protocol support with unified grouped command processing
* • Multi-client WebSocket support with device type identification
* • Automatic connection management and reconnection
* • Unified response system for consistent messaging
* • Thread-safe operation with proper resource management
* • Batch command support for efficient configuration
*
* 📡 SUPPORTED PROTOCOLS:
* • MQTT: Primary control interface with auto-reconnection
* • WebSocket: Real-time multi-client web interface communication
* • UDP Discovery: Auto-discovery service for network scanning
*
* 📱 CLIENT MANAGEMENT:
* • Support for multiple WebSocket clients (master/secondary devices)
* • Client type identification and targeted messaging
* • Automatic cleanup of disconnected clients
* • Broadcast capabilities for status updates
*
* 🔄 MESSAGE ROUTING:
* • Commands accepted from both MQTT and WebSocket
* • Responses sent only to originating protocol/client
* • Status broadcasts sent to all WebSocket clients + MQTT
* • Grouped command processing for all protocols
*
* 📋 VERSION: 3.0 (Grouped commands + batch processing)
* 📅 DATE: 2025
* 👨‍💻 AUTHOR: Advanced Bell Systems
* ═══════════════════════════════════════════════════════════════════════════════════
*/
#pragma once
#include <Arduino.h>
#include <AsyncMqttClient.h>
#include <ESPAsyncWebServer.h>
#include <AsyncUDP.h>
#include <ArduinoJson.h>
#include "ResponseBuilder.hpp"
#include "../ClientManager/ClientManager.hpp"
class ConfigManager;
class OTAManager;
class Player;
class FileManager;
class Timekeeper;
class Networking;
class FirmwareValidator;
class Communication {
public:
// Message source identification for response routing
enum class MessageSource {
MQTT,
WEBSOCKET
};
struct MessageContext {
MessageSource source;
uint32_t clientId; // Only used for WebSocket messages
MessageContext(MessageSource src, uint32_t id = 0)
: source(src), clientId(id) {}
};
explicit Communication(ConfigManager& configManager,
OTAManager& otaManager,
Networking& networking,
AsyncMqttClient& mqttClient,
AsyncWebServer& server,
AsyncWebSocket& webSocket,
AsyncUDP& udp);
~Communication();
void begin();
void setPlayerReference(Player* player) { _player = player; }
void setFileManagerReference(FileManager* fm) { _fileManager = fm; }
void setTimeKeeperReference(Timekeeper* tk) { _timeKeeper = tk; }
void setFirmwareValidatorReference(FirmwareValidator* fv) { _firmwareValidator = fv; }
void setupUdpDiscovery();
// Public methods for timer callbacks
void connectToMqtt();
void subscribeMqtt();
// Status methods
bool isMqttConnected() const { return _mqttClient.connected(); }
bool hasActiveWebSocketClients() const { return _clientManager.hasClients(); }
size_t getWebSocketClientCount() const { return _clientManager.getClientCount(); }
// Response methods - unified response system
void sendResponse(const String& response, const MessageContext& context);
void sendSuccessResponse(const String& type, const String& payload, const MessageContext& context);
void sendErrorResponse(const String& type, const String& message, const MessageContext& context);
// Broadcast methods - for status updates that go to everyone
void broadcastStatus(const String& statusMessage);
void broadcastStatus(const JsonDocument& statusJson);
void broadcastToMasterClients(const String& message);
void broadcastToSecondaryClients(const String& message);
void broadcastToAllWebSocketClients(const String& message);
void broadcastToAllWebSocketClients(const JsonDocument& message);
void publishToMqtt(const String& data);
// ═══════════════════════════════════════════════════════════════════════════════
// HEALTH CHECK METHOD
// ═══════════════════════════════════════════════════════════════════════════════
/** @brief Check if Communication is in healthy state */
bool isHealthy() const;
// Bell overload notification
void sendBellOverloadNotification(const std::vector<uint8_t>& bellNumbers,
const std::vector<uint16_t>& bellLoads,
const String& severity);
// Network connection callbacks (called by Networking)
void onNetworkConnected();
void onNetworkDisconnected();
// Static instance for callbacks
static Communication* _instance;
private:
// Dependencies
ConfigManager& _configManager;
OTAManager& _otaManager;
Networking& _networking;
AsyncMqttClient& _mqttClient;
AsyncWebServer& _server;
AsyncWebSocket& _webSocket;
AsyncUDP& _udp;
Player* _player;
FileManager* _fileManager;
Timekeeper* _timeKeeper;
FirmwareValidator* _firmwareValidator;
// Client manager
ClientManager _clientManager;
// State
TimerHandle_t _mqttReconnectTimer;
// Reusable JSON documents
static StaticJsonDocument<2048> _parseDocument;
// MQTT methods
void initMqtt();
static void onMqttConnect(bool sessionPresent);
static void onMqttDisconnect(AsyncMqttClientDisconnectReason reason);
static void onMqttMessage(char* topic, char* payload, AsyncMqttClientMessageProperties properties,
size_t len, size_t index, size_t total);
static void onMqttSubscribe(uint16_t packetId, uint8_t qos);
static void onMqttUnsubscribe(uint16_t packetId);
static void onMqttPublish(uint16_t packetId);
// WebSocket methods
void initWebSocket();
static void onWebSocketEvent(AsyncWebSocket* server, AsyncWebSocketClient* client,
AwsEventType type, void* arg, uint8_t* data, size_t len);
void onWebSocketConnect(AsyncWebSocketClient* client);
void onWebSocketDisconnect(AsyncWebSocketClient* client);
void onWebSocketReceived(AsyncWebSocketClient* client, void* arg, uint8_t* data, size_t len);
void handleClientIdentification(AsyncWebSocketClient* client, JsonDocument& command);
// Command processing - unified for both MQTT and WebSocket with grouped commands
JsonDocument parsePayload(char* payload);
void handleCommand(JsonDocument& command, const MessageContext& context);
// ═════════════════════════════════════════════════════════════════════════════════
// GROUPED COMMAND HANDLERS
// ═════════════════════════════════════════════════════════════════════════════════
// System commands
void handleSystemCommand(JsonVariant contents, const MessageContext& context);
void handleSystemInfoCommand(JsonVariant contents, const MessageContext& context);
void handlePlaybackCommand(JsonVariant contents, const MessageContext& context);
void handleFileManagerCommand(JsonVariant contents, const MessageContext& context);
void handleRelaySetupCommand(JsonVariant contents, const MessageContext& context);
void handleClockSetupCommand(JsonVariant contents, const MessageContext& context);
// System sub-commands
void handlePingCommand(const MessageContext& context);
void handleStatusCommand(const MessageContext& context);
void handleIdentifyCommand(JsonVariant contents, const MessageContext& context);
void handleGetDeviceTimeCommand(const MessageContext& context);
void handleGetClockTimeCommand(const MessageContext& context);
// Firmware management commands
void handleCommitFirmwareCommand(const MessageContext& context);
void handleRollbackFirmwareCommand(const MessageContext& context);
void handleGetFirmwareStatusCommand(const MessageContext& context);
// Network configuration command
void handleSetNetworkConfigCommand(JsonVariant contents, const MessageContext& context);
// File Manager sub-commands
void handleListMelodiesCommand(const MessageContext& context);
void handleDownloadMelodyCommand(JsonVariant contents, const MessageContext& context);
void handleDeleteMelodyCommand(JsonVariant contents, const MessageContext& context);
// Relay Setup sub-commands
void handleSetRelayTimersCommand(JsonVariant contents, const MessageContext& context);
void handleSetRelayOutputsCommand(JsonVariant contents, const MessageContext& context);
// Clock Setup sub-commands
void handleSetClockOutputsCommand(JsonVariant contents, const MessageContext& context);
void handleSetClockTimingsCommand(JsonVariant contents, const MessageContext& context);
void handleSetClockAlertsCommand(JsonVariant contents, const MessageContext& context);
void handleSetClockBacklightCommand(JsonVariant contents, const MessageContext& context);
void handleSetClockSilenceCommand(JsonVariant contents, const MessageContext& context);
void handleSetRtcTimeCommand(JsonVariant contents, const MessageContext& context);
void handleSetPhysicalClockTimeCommand(JsonVariant contents, const MessageContext& context);
void handlePauseClockUpdatesCommand(JsonVariant contents, const MessageContext& context);
void handleSetClockEnabledCommand(JsonVariant contents, const MessageContext& context);
// Utility methods
String getPayloadContent(char* data, size_t len);
int extractBellNumber(const String& key); // Extract bell number from "b1", "c1", etc.
};