Refactors event socket

This commit is contained in:
Rune Harlyk
2024-11-07 16:58:19 +01:00
committed by Rune Harlyk
parent fd652bd967
commit 89611b5e3e
20 changed files with 98 additions and 127 deletions
+1 -1
View File
@@ -27,7 +27,7 @@
onMount(async () => { onMount(async () => {
const ws = $location ? $location : window.location.host; const ws = $location ? $location : window.location.host;
socket.init(`ws://${ws}/ws/events`); socket.init(`ws://${ws}/api/ws/events`);
addEventListeners(); addEventListeners();
+1 -1
View File
@@ -7,7 +7,7 @@
const update = () => { const update = () => {
const ws = $location ? $location : window.location.host; const ws = $location ? $location : window.location.host;
socket.init(`ws://${ws}/ws/events`); socket.init(`ws://${ws}/api/ws/events`);
}; };
</script> </script>
+20 -25
View File
@@ -5,29 +5,24 @@ import viteLittleFS from './vite-plugin-littlefs';
import EnvCaster from '@niku/vite-env-caster'; import EnvCaster from '@niku/vite-env-caster';
export default defineConfig({ export default defineConfig({
plugins: [ plugins: [
sveltekit(), sveltekit(),
Icons({ Icons({
compiler: 'svelte' compiler: 'svelte'
}), }),
viteLittleFS(), viteLittleFS(),
EnvCaster() EnvCaster()
], ],
test: { test: {
include: ['src/**/*.{test,spec}.{js,ts}'] include: ['src/**/*.{test,spec}.{js,ts}']
}, },
server: { server: {
proxy: { proxy: {
'/api': { '/api': {
target: 'http://spot-micro.local/', target: 'http://spot-micro.local/',
changeOrigin: true, changeOrigin: true,
ws: true ws: true
}, }
'/ws': { }
target: 'ws://spot-micro.local/', }
changeOrigin: true,
ws: true
}
}
}
}); });
+1 -6
View File
@@ -1,6 +1,6 @@
# Developing # Developing
> *Prerequsition*: You have successfully build, flashed and configured your robot. > _Prerequsition_: You have successfully build, flashed and configured your robot.
## Setting up SvelteKit ## Setting up SvelteKit
@@ -15,11 +15,6 @@ server: {
target: 'http://spot-micro.local', // Here target: 'http://spot-micro.local', // Here
changeOrigin: true, changeOrigin: true,
ws: true ws: true
},
'/ws': {
target: 'ws://spot-micro.local', // Here
changeOrigin: true,
ws: true
} }
} }
}, },
+4 -5
View File
@@ -15,7 +15,7 @@
#include <ArduinoJson.h> #include <ArduinoJson.h>
#include <filesystem.h> #include <filesystem.h>
#include <EventSocket.h> #include <event_socket.h>
#include <TaskManager.h> #include <TaskManager.h>
#include <WiFi.h> #include <WiFi.h>
#include <Timing.h> #include <Timing.h>
@@ -26,7 +26,7 @@
class AnalyticsService { class AnalyticsService {
public: public:
AnalyticsService(EventSocket *socket, TaskManager *taskManager) : _socket(socket), _taskManager(taskManager) {}; AnalyticsService(TaskManager *taskManager) : _taskManager(taskManager) {};
void begin() {}; void begin() {};
@@ -35,11 +35,10 @@ class AnalyticsService {
char message[MAX_ESP_ANALYTICS_SIZE]; char message[MAX_ESP_ANALYTICS_SIZE];
private: private:
EventSocket *_socket;
TaskManager *_taskManager; TaskManager *_taskManager;
void updateAnalytics() { void updateAnalytics() {
if (!_socket->hasSubscribers(EVENT_ANALYTICS)) return; if (!socket.hasSubscribers(EVENT_ANALYTICS)) return;
doc.clear(); doc.clear();
doc["uptime"] = millis() / 1000; doc["uptime"] = millis() / 1000;
doc["free_heap"] = ESP.getFreeHeap(); doc["free_heap"] = ESP.getFreeHeap();
@@ -62,6 +61,6 @@ class AnalyticsService {
} }
serializeJson(doc, message); serializeJson(doc, message);
_socket->emit(EVENT_ANALYTICS, message); socket.emit(EVENT_ANALYTICS, message);
} }
}; };
+2 -3
View File
@@ -14,8 +14,7 @@
#include <BatteryService.h> #include <BatteryService.h>
BatteryService::BatteryService(Peripherals *peripherals, EventSocket *socket) BatteryService::BatteryService(Peripherals *peripherals) : _peripherals(peripherals) {}
: _peripherals(peripherals), _socket(socket) {}
void BatteryService::begin() {} void BatteryService::begin() {}
@@ -25,5 +24,5 @@ void BatteryService::batteryEvent() {
doc["voltage"] = _voltage; doc["voltage"] = _voltage;
doc["current"] = _current; doc["current"] = _current;
serializeJson(doc, message); serializeJson(doc, message);
_socket->emit(EVENT_BATTERY, message); socket.emit(EVENT_BATTERY, message);
} }
+2 -3
View File
@@ -14,7 +14,7 @@
* the terms of the LGPL v3 license. See the LICENSE file for details. * the terms of the LGPL v3 license. See the LICENSE file for details.
**/ **/
#include <EventSocket.h> #include <event_socket.h>
#include <JsonUtils.h> #include <JsonUtils.h>
#include <Peripherals.h> #include <Peripherals.h>
#include <Timing.h> #include <Timing.h>
@@ -36,7 +36,7 @@
class BatteryService { class BatteryService {
public: public:
BatteryService(Peripherals *peripherals, EventSocket *socket); BatteryService(Peripherals *peripherals);
void begin(); void begin();
@@ -57,7 +57,6 @@ class BatteryService {
private: private:
void batteryEvent(); void batteryEvent();
EventSocket *_socket;
Peripherals *_peripherals; Peripherals *_peripherals;
float _voltage = 0; float _voltage = 0;
@@ -120,10 +120,10 @@ class CameraSettings {
class CameraSettingsService : public StatefulService<CameraSettings> { class CameraSettingsService : public StatefulService<CameraSettings> {
public: public:
CameraSettingsService(PsychicHttpServer *server, FS *fs, EventSocket *socket) CameraSettingsService(PsychicHttpServer *server, FS *fs)
: _server(server), : _server(server),
_httpEndpoint(CameraSettings::read, CameraSettings::update, this, server, CAMERA_SETTINGS_PATH), _httpEndpoint(CameraSettings::read, CameraSettings::update, this, server, CAMERA_SETTINGS_PATH),
_eventEndpoint(CameraSettings::read, CameraSettings::update, this, socket, EVENT_CAMERA_SETTINGS), _eventEndpoint(CameraSettings::read, CameraSettings::update, this, EVENT_CAMERA_SETTINGS),
_fsPersistence(CameraSettings::read, CameraSettings::update, this, fs, CAMERA_SETTINGS_FILE) { _fsPersistence(CameraSettings::read, CameraSettings::update, this, fs, CAMERA_SETTINGS_FILE) {
addUpdateHandler([&](const String &originId) { updateCamera(); }, false); addUpdateHandler([&](const String &originId) { updateCamera(); }, false);
} }
@@ -131,6 +131,7 @@ class CameraSettingsService : public StatefulService<CameraSettings> {
void begin() { void begin() {
_httpEndpoint.begin(); _httpEndpoint.begin();
_eventEndpoint.begin(); _eventEndpoint.begin();
_fsPersistence.readFromFS();
sensor_t *s = safe_sensor_get(); sensor_t *s = safe_sensor_get();
_state.pixformat = s->pixformat; _state.pixformat = s->pixformat;
_state.framesize = s->status.framesize; _state.framesize = s->status.framesize;
@@ -15,7 +15,6 @@
extern const uint8_t rootca_crt_bundle_start[] asm("_binary_src_certs_x509_crt_bundle_bin_start"); extern const uint8_t rootca_crt_bundle_start[] asm("_binary_src_certs_x509_crt_bundle_bin_start");
static EventSocket *_socket = nullptr;
static int previousProgress = 0; static int previousProgress = 0;
JsonDocument doc; JsonDocument doc;
@@ -23,7 +22,7 @@ void update_started() {
String output; String output;
doc["status"] = "preparing"; doc["status"] = "preparing";
serializeJson(doc, output); serializeJson(doc, output);
_socket->emit(EVENT_DOWNLOAD_OTA, output.c_str()); socket.emit(EVENT_DOWNLOAD_OTA, output.c_str());
} }
void update_progress(int currentBytes, int totalBytes) { void update_progress(int currentBytes, int totalBytes) {
@@ -32,7 +31,7 @@ void update_progress(int currentBytes, int totalBytes) {
int progress = ((currentBytes * 100) / totalBytes); int progress = ((currentBytes * 100) / totalBytes);
if (progress > previousProgress) { if (progress > previousProgress) {
doc["progress"] = progress; doc["progress"] = progress;
_socket->emit(EVENT_DOWNLOAD_OTA, output.c_str()); socket.emit(EVENT_DOWNLOAD_OTA, output.c_str());
ESP_LOGV("Download OTA", "HTTP update process at %d of %d bytes... (%d %%)", currentBytes, totalBytes, ESP_LOGV("Download OTA", "HTTP update process at %d of %d bytes... (%d %%)", currentBytes, totalBytes,
progress); progress);
} }
@@ -43,7 +42,7 @@ void update_finished() {
String output; String output;
doc["status"] = "finished"; doc["status"] = "finished";
serializeJson(doc, output); serializeJson(doc, output);
_socket->emit(EVENT_DOWNLOAD_OTA, output.c_str()); socket.emit(EVENT_DOWNLOAD_OTA, output.c_str());
// delay to allow the event to be sent out // delay to allow the event to be sent out
vTaskDelay(100 / portTICK_PERIOD_MS); vTaskDelay(100 / portTICK_PERIOD_MS);
@@ -71,7 +70,7 @@ void updateTask(void *param) {
doc["status"] = "error"; doc["status"] = "error";
doc["error"] = httpUpdate.getLastErrorString().c_str(); doc["error"] = httpUpdate.getLastErrorString().c_str();
serializeJson(doc, output); serializeJson(doc, output);
_socket->emit(EVENT_DOWNLOAD_OTA, output.c_str()); socket.emit(EVENT_DOWNLOAD_OTA, output.c_str());
ESP_LOGE("Download OTA", "HTTP Update failed with error (%d): %s", httpUpdate.getLastError(), ESP_LOGE("Download OTA", "HTTP Update failed with error (%d): %s", httpUpdate.getLastError(),
httpUpdate.getLastErrorString().c_str()); httpUpdate.getLastErrorString().c_str());
@@ -81,7 +80,7 @@ void updateTask(void *param) {
doc["status"] = "error"; doc["status"] = "error";
doc["error"] = "Update failed, has same firmware version"; doc["error"] = "Update failed, has same firmware version";
serializeJson(doc, output); serializeJson(doc, output);
_socket->emit(EVENT_DOWNLOAD_OTA, output.c_str()); socket.emit(EVENT_DOWNLOAD_OTA, output.c_str());
ESP_LOGE("Download OTA", "HTTP Update failed, has same firmware version"); ESP_LOGE("Download OTA", "HTTP Update failed, has same firmware version");
break; break;
@@ -90,9 +89,8 @@ void updateTask(void *param) {
vTaskDelete(NULL); vTaskDelete(NULL);
} }
DownloadFirmwareService::DownloadFirmwareService(PsychicHttpServer *server, EventSocket *socket, DownloadFirmwareService::DownloadFirmwareService(PsychicHttpServer *server, TaskManager *taskManager)
TaskManager *taskManager) : _server(server), _taskManager(taskManager) {}
: _server(server), _socket(socket), _taskManager(taskManager) {}
void DownloadFirmwareService::begin() { void DownloadFirmwareService::begin() {
_server->on(GITHUB_FIRMWARE_PATH, HTTP_POST, _server->on(GITHUB_FIRMWARE_PATH, HTTP_POST,
@@ -116,7 +114,7 @@ esp_err_t DownloadFirmwareService::downloadUpdate(PsychicRequest *request, JsonV
String output; String output;
serializeJson(doc, output); serializeJson(doc, output);
_socket->emit(EVENT_DOWNLOAD_OTA, output.c_str()); socket.emit(EVENT_DOWNLOAD_OTA, output.c_str());
if (_taskManager->createTask(&updateTask, // Function that should be called if (_taskManager->createTask(&updateTask, // Function that should be called
"Firmware download", // Name of the task (for debugging) "Firmware download", // Name of the task (for debugging)
@@ -18,7 +18,7 @@
#include <WiFi.h> #include <WiFi.h>
#include <ArduinoJson.h> #include <ArduinoJson.h>
#include <EventSocket.h> #include <event_socket.h>
#include <PsychicHttp.h> #include <PsychicHttp.h>
#include <HTTPClient.h> #include <HTTPClient.h>
@@ -32,13 +32,12 @@
class DownloadFirmwareService { class DownloadFirmwareService {
public: public:
DownloadFirmwareService(PsychicHttpServer *server, EventSocket *socket, TaskManager *taskManager); DownloadFirmwareService(PsychicHttpServer *server, TaskManager *taskManager);
void begin(); void begin();
private: private:
PsychicHttpServer *_server; PsychicHttpServer *_server;
EventSocket *_socket;
TaskManager *_taskManager; TaskManager *_taskManager;
esp_err_t downloadUpdate(PsychicRequest *request, JsonVariant &json); esp_err_t downloadUpdate(PsychicRequest *request, JsonVariant &json);
}; };
+10 -9
View File
@@ -20,34 +20,33 @@ ESP32SvelteKit::ESP32SvelteKit(PsychicHttpServer *server, unsigned int numberEnd
_numberEndpoints(numberEndpoints), _numberEndpoints(numberEndpoints),
_taskManager(), _taskManager(),
_featureService(server), _featureService(server),
_socket(server),
#if FT_ENABLED(USE_UPLOAD_FIRMWARE) #if FT_ENABLED(USE_UPLOAD_FIRMWARE)
_uploadFirmwareService(server), _uploadFirmwareService(server),
#endif #endif
#if FT_ENABLED(USE_DOWNLOAD_FIRMWARE) #if FT_ENABLED(USE_DOWNLOAD_FIRMWARE)
_downloadFirmwareService(server, &_socket, &_taskManager), _downloadFirmwareService(server, &_taskManager),
#endif #endif
#if FT_ENABLED(USE_SLEEP) #if FT_ENABLED(USE_SLEEP)
_sleepService(server), _sleepService(server),
#endif #endif
#if FT_ENABLED(USE_BATTERY) #if FT_ENABLED(USE_BATTERY)
_batteryService(&_peripherals, &_socket), _batteryService(&_peripherals),
#endif #endif
#if FT_ENABLED(USE_ANALYTICS) #if FT_ENABLED(USE_ANALYTICS)
_analyticsService(&_socket, &_taskManager), _analyticsService(&_taskManager),
#endif #endif
#if FT_ENABLED(USE_CAMERA) #if FT_ENABLED(USE_CAMERA)
_cameraService(server, &_taskManager), _cameraService(server, &_taskManager),
_cameraSettingsService(server, &ESPFS, &_socket), _cameraSettingsService(server, &ESPFS),
#endif #endif
_servoController(server, &ESPFS, &_peripherals, &_socket), _servoController(server, &ESPFS, &_peripherals),
#if FT_ENABLED(USE_MOTION) #if FT_ENABLED(USE_MOTION)
_motionService(_server, &_socket, &_servoController, &_taskManager), _motionService(_server, &_servoController, &_taskManager),
#endif #endif
#if FT_ENABLED(USE_WS2812) #if FT_ENABLED(USE_WS2812)
_ledService(&_taskManager), _ledService(&_taskManager),
#endif #endif
_peripherals(server, &ESPFS, &_socket) { _peripherals(server, &ESPFS) {
} }
void ESP32SvelteKit::begin() { void ESP32SvelteKit::begin() {
@@ -124,6 +123,9 @@ void ESP32SvelteKit::setupServer() {
return _servoController.endpoint.handleStateUpdate(request, json); return _servoController.endpoint.handleStateUpdate(request, json);
}); });
// MISC
_server->on("/api/ws/events", socket.getHandler());
#ifdef EMBED_WWW #ifdef EMBED_WWW
ESP_LOGV("ESP32SvelteKit", "Registering routes from PROGMEM static resources"); ESP_LOGV("ESP32SvelteKit", "Registering routes from PROGMEM static resources");
WWWData::registerRoutes([&](const String &uri, const String &contentType, const uint8_t *content, size_t len) { WWWData::registerRoutes([&](const String &uri, const String &contentType, const uint8_t *content, size_t len) {
@@ -185,7 +187,6 @@ void ESP32SvelteKit::setupMDNS() {
void ESP32SvelteKit::startServices() { void ESP32SvelteKit::startServices() {
_apService.begin(); _apService.begin();
_socket.begin();
_featureService.begin(); _featureService.begin();
#if FT_ENABLED(USE_UPLOAD_FIRMWARE) #if FT_ENABLED(USE_UPLOAD_FIRMWARE)
+1 -1
View File
@@ -26,7 +26,7 @@
#include <ServoController.h> #include <ServoController.h>
#include <ESPmDNS.h> #include <ESPmDNS.h>
#include <LEDService.h> #include <LEDService.h>
#include <EventSocket.h> #include <event_socket.h>
#include <FeaturesService.h> #include <FeaturesService.h>
#include <MotionService.h> #include <MotionService.h>
#include <ntp_service.h> #include <ntp_service.h>
+8 -13
View File
@@ -15,7 +15,7 @@
* the terms of the LGPL v3 license. See the LICENSE file for details. * the terms of the LGPL v3 license. See the LICENSE file for details.
**/ **/
#include <EventSocket.h> #include <event_socket.h>
#include <PsychicHttp.h> #include <PsychicHttp.h>
#include <StatefulService.h> #include <StatefulService.h>
@@ -23,27 +23,22 @@ template <class T>
class EventEndpoint { class EventEndpoint {
public: public:
EventEndpoint(JsonStateReader<T> stateReader, JsonStateUpdater<T> stateUpdater, StatefulService<T> *statefulService, EventEndpoint(JsonStateReader<T> stateReader, JsonStateUpdater<T> stateUpdater, StatefulService<T> *statefulService,
EventSocket *socket, const char *event) const char *event)
: _stateReader(stateReader), : _stateReader(stateReader), _stateUpdater(stateUpdater), _statefulService(statefulService), _event(event) {
_stateUpdater(stateUpdater),
_statefulService(statefulService),
_socket(socket),
_event(event) {
_statefulService->addUpdateHandler([&](const String &originId) { syncState(originId); }, false); _statefulService->addUpdateHandler([&](const String &originId) { syncState(originId); }, false);
} }
void begin() { void begin() {
_socket->onEvent(_event, socket.onEvent(_event,
std::bind(&EventEndpoint::updateState, this, std::placeholders::_1, std::placeholders::_2)); std::bind(&EventEndpoint::updateState, this, std::placeholders::_1, std::placeholders::_2));
_socket->onSubscribe(_event, socket.onSubscribe(_event,
std::bind(&EventEndpoint::syncState, this, std::placeholders::_1, std::placeholders::_2)); std::bind(&EventEndpoint::syncState, this, std::placeholders::_1, std::placeholders::_2));
} }
private: private:
JsonStateReader<T> _stateReader; JsonStateReader<T> _stateReader;
JsonStateUpdater<T> _stateUpdater; JsonStateUpdater<T> _stateUpdater;
StatefulService<T> *_statefulService; StatefulService<T> *_statefulService;
EventSocket *_socket;
const char *_event; const char *_event;
void updateState(JsonObject &root, int originId) { void updateState(JsonObject &root, int originId) {
@@ -57,7 +52,7 @@ class EventEndpoint {
_statefulService->read(root, _stateReader); _statefulService->read(root, _stateReader);
serializeJson(root, output); serializeJson(root, output);
ESP_LOGV("EventEndpoint", "Syncing state: %s", output.c_str()); ESP_LOGV("EventEndpoint", "Syncing state: %s", output.c_str());
_socket->emit(_event, output.c_str(), originId.c_str(), sync); socket.emit(_event, output.c_str(), originId.c_str(), sync);
} }
}; };
@@ -32,7 +32,6 @@ class FSPersistence {
_filePath(filePath), _filePath(filePath),
_updateHandlerId(0) { _updateHandlerId(0) {
enableUpdateHandler(); enableUpdateHandler();
readFromFS();
} }
void readFromFS() { void readFromFS() {
+11 -13
View File
@@ -1,7 +1,7 @@
#ifndef MotionService_h #ifndef MotionService_h
#define MotionService_h #define MotionService_h
#include <EventSocket.h> #include <event_socket.h>
#include <TaskManager.h> #include <TaskManager.h>
#include <Kinematics.h> #include <Kinematics.h>
#include <ServoController.h> #include <ServoController.h>
@@ -20,21 +20,20 @@ enum class MOTION_STATE { DEACTIVATED, IDLE, CALIBRATION, REST, STAND, CRAWL, WA
class MotionService { class MotionService {
public: public:
MotionService(PsychicHttpServer *server, EventSocket *socket, ServoController *servoController, MotionService(PsychicHttpServer *server, ServoController *servoController, TaskManager *taskManager)
TaskManager *taskManager) : _server(server), _servoController(servoController), _taskManager(taskManager) {}
: _server(server), _socket(socket), _servoController(servoController), _taskManager(taskManager) {}
void begin() { void begin() {
_socket->onEvent(INPUT_EVENT, [&](JsonObject &root, int originId) { handleInput(root, originId); }); socket.onEvent(INPUT_EVENT, [&](JsonObject &root, int originId) { handleInput(root, originId); });
_socket->onEvent(MODE_EVENT, [&](JsonObject &root, int originId) { handleMode(root, originId); }); socket.onEvent(MODE_EVENT, [&](JsonObject &root, int originId) { handleMode(root, originId); });
_socket->onEvent(ANGLES_EVENT, [&](JsonObject &root, int originId) { anglesEvent(root, originId); }); socket.onEvent(ANGLES_EVENT, [&](JsonObject &root, int originId) { anglesEvent(root, originId); });
_socket->onEvent(POSITION_EVENT, [&](JsonObject &root, int originId) { positionEvent(root, originId); }); socket.onEvent(POSITION_EVENT, [&](JsonObject &root, int originId) { positionEvent(root, originId); });
_socket->onSubscribe(ANGLES_EVENT, socket.onSubscribe(ANGLES_EVENT,
std::bind(&MotionService::syncAngles, this, std::placeholders::_1, std::placeholders::_2)); std::bind(&MotionService::syncAngles, this, std::placeholders::_1, std::placeholders::_2));
body_state.updateFeet(default_feet_positions); body_state.updateFeet(default_feet_positions);
@@ -90,7 +89,7 @@ class MotionService {
char output[2]; char output[2];
itoa((int)motionState, output, 10); itoa((int)motionState, output, 10);
motionState == MOTION_STATE::DEACTIVATED ? _servoController->deactivate() : _servoController->activate(); motionState == MOTION_STATE::DEACTIVATED ? _servoController->deactivate() : _servoController->activate();
_socket->emit(MODE_EVENT, output, String(originId).c_str()); socket.emit(MODE_EVENT, output, String(originId).c_str());
} }
void syncAngles(const String &originId = "", bool sync = false) { void syncAngles(const String &originId = "", bool sync = false) {
@@ -98,7 +97,7 @@ class MotionService {
snprintf(output, sizeof(output), "[%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f]", angles[0], snprintf(output, sizeof(output), "[%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f]", angles[0],
angles[1], angles[2], angles[3], angles[4], angles[5], angles[6], angles[7], angles[8], angles[9], angles[1], angles[2], angles[3], angles[4], angles[5], angles[6], angles[7], angles[8], angles[9],
angles[10], angles[11]); angles[10], angles[11]);
_socket->emit(ANGLES_EVENT, output, originId.c_str()); socket.emit(ANGLES_EVENT, output, originId.c_str());
_servoController->setAngles(angles); _servoController->setAngles(angles);
} }
@@ -146,7 +145,6 @@ class MotionService {
private: private:
PsychicHttpServer *_server; PsychicHttpServer *_server;
EventSocket *_socket;
TaskManager *_taskManager; TaskManager *_taskManager;
ServoController *_servoController; ServoController *_servoController;
Kinematics kinematics; Kinematics kinematics;
+8 -10
View File
@@ -101,12 +101,11 @@ class PeripheralsConfiguration {
class Peripherals : public StatefulService<PeripheralsConfiguration> { class Peripherals : public StatefulService<PeripheralsConfiguration> {
public: public:
Peripherals(PsychicHttpServer *server, FS *fs, EventSocket *socket) Peripherals(PsychicHttpServer *server, FS *fs)
: _server(server), : _server(server),
_socket(socket),
_httpEndpoint(PeripheralsConfiguration::read, PeripheralsConfiguration::update, this, server, _httpEndpoint(PeripheralsConfiguration::read, PeripheralsConfiguration::update, this, server,
CONFIGURATION_SETTINGS_PATH), CONFIGURATION_SETTINGS_PATH),
_eventEndpoint(PeripheralsConfiguration::read, PeripheralsConfiguration::update, this, socket, _eventEndpoint(PeripheralsConfiguration::read, PeripheralsConfiguration::update, this,
EVENT_CONFIGURATION_SETTINGS), EVENT_CONFIGURATION_SETTINGS),
#if FT_ENABLED(USE_MAG) #if FT_ENABLED(USE_MAG)
_mag(12345), _mag(12345),
@@ -125,12 +124,12 @@ class Peripherals : public StatefulService<PeripheralsConfiguration> {
_eventEndpoint.begin(); _eventEndpoint.begin();
_fsPersistence.readFromFS(); _fsPersistence.readFromFS();
_socket->onEvent(EVENT_I2C_SCAN, [&](JsonObject &root, int originId) { socket.onEvent(EVENT_I2C_SCAN, [&](JsonObject &root, int originId) {
scanI2C(); scanI2C();
emitI2C(); emitI2C();
}); });
_socket->onSubscribe(EVENT_I2C_SCAN, [&](const String &originId, bool sync) { socket.onSubscribe(EVENT_I2C_SCAN, [&](const String &originId, bool sync) {
scanI2C(); scanI2C();
emitI2C(originId, sync); emitI2C(originId, sync);
}); });
@@ -142,7 +141,7 @@ class Peripherals : public StatefulService<PeripheralsConfiguration> {
_pca.setPWMFreq(FACTORY_SERVO_PWM_FREQUENCY); _pca.setPWMFreq(FACTORY_SERVO_PWM_FREQUENCY);
_pca.setOscillatorFrequency(FACTORY_SERVO_OSCILLATOR_FREQUENCY); _pca.setOscillatorFrequency(FACTORY_SERVO_OSCILLATOR_FREQUENCY);
_pca.sleep(); _pca.sleep();
_socket->onEvent(EVENT_SERVO_STATE, [&](JsonObject &root, int originId) { socket.onEvent(EVENT_SERVO_STATE, [&](JsonObject &root, int originId) {
_pca_active = root["active"] | false; _pca_active = root["active"] | false;
_pca_active ? pcaActivate() : pcaDeactivate(); _pca_active ? pcaActivate() : pcaDeactivate();
}); });
@@ -219,7 +218,7 @@ class Peripherals : public StatefulService<PeripheralsConfiguration> {
} }
serializeJson(root, output); serializeJson(root, output);
ESP_LOGI("Peripherals", "Emitting I2C scan results, %s %d", originId.c_str(), sync); ESP_LOGI("Peripherals", "Emitting I2C scan results, %s %d", originId.c_str(), sync);
_socket->emit(EVENT_I2C_SCAN, output, originId.c_str(), sync); socket.emit(EVENT_I2C_SCAN, output, originId.c_str(), sync);
} }
void scanI2C(uint8_t lower = 1, uint8_t higher = 127) { void scanI2C(uint8_t lower = 1, uint8_t higher = 127) {
@@ -418,7 +417,7 @@ class Peripherals : public StatefulService<PeripheralsConfiguration> {
#endif #endif
if (newData) { if (newData) {
serializeJson(doc, message); serializeJson(doc, message);
_socket->emit(EVENT_IMU, message); socket.emit(EVENT_IMU, message);
} }
} }
@@ -435,7 +434,7 @@ class Peripherals : public StatefulService<PeripheralsConfiguration> {
char output[16]; char output[16];
snprintf(output, sizeof(output), "[%.1f,%.1f]", _left_distance, _right_distance); snprintf(output, sizeof(output), "[%.1f,%.1f]", _left_distance, _right_distance);
_socket->emit("sonar", output); socket.emit("sonar", output);
#endif #endif
} }
@@ -444,7 +443,6 @@ class Peripherals : public StatefulService<PeripheralsConfiguration> {
private: private:
PsychicHttpServer *_server; PsychicHttpServer *_server;
EventSocket *_socket;
HttpEndpoint<PeripheralsConfiguration> _httpEndpoint; HttpEndpoint<PeripheralsConfiguration> _httpEndpoint;
EventEndpoint<PeripheralsConfiguration> _eventEndpoint; EventEndpoint<PeripheralsConfiguration> _eventEndpoint;
FSPersistence<PeripheralsConfiguration> _fsPersistence; FSPersistence<PeripheralsConfiguration> _fsPersistence;
+6 -7
View File
@@ -3,6 +3,7 @@
#include <Adafruit_PWMServoDriver.h> #include <Adafruit_PWMServoDriver.h>
#include <EventEndpoint.h> #include <EventEndpoint.h>
#include <event_socket.h>
#include <FSPersistence.h> #include <FSPersistence.h>
#include <HttpEndpoint.h> #include <HttpEndpoint.h>
#include <StatefulService.h> #include <StatefulService.h>
@@ -68,17 +69,16 @@ class ServoSettings {
class ServoController : public StatefulService<ServoSettings> { class ServoController : public StatefulService<ServoSettings> {
public: public:
ServoController(PsychicHttpServer *server, FS *fs, Peripherals *peripherals, EventSocket *socket) ServoController(PsychicHttpServer *server, FS *fs, Peripherals *peripherals)
: _server(server), : _server(server),
_peripherals(peripherals), _peripherals(peripherals),
_socket(socket),
endpoint(ServoSettings::read, ServoSettings::update, this), endpoint(ServoSettings::read, ServoSettings::update, this),
_fsPersistence(ServoSettings::read, ServoSettings::update, this, &ESPFS, SERVO_SETTINGS_FILE) {} _fsPersistence(ServoSettings::read, ServoSettings::update, this, &ESPFS, SERVO_SETTINGS_FILE) {}
void begin() { void begin() {
_socket->onEvent(EVENT_SERVO_CONFIGURATION_SETTINGS, socket.onEvent(EVENT_SERVO_CONFIGURATION_SETTINGS,
[&](JsonObject &root, int originId) { servoEvent(root, originId); }); [&](JsonObject &root, int originId) { servoEvent(root, originId); });
_socket->onEvent(EVENT_SERVO_STATE, [&](JsonObject &root, int originId) { stateUpdate(root, originId); }); socket.onEvent(EVENT_SERVO_STATE, [&](JsonObject &root, int originId) { stateUpdate(root, originId); });
_fsPersistence.readFromFS(); _fsPersistence.readFromFS();
} }
@@ -99,7 +99,7 @@ class ServoController : public StatefulService<ServoSettings> {
snprintf(output, sizeof(output), "[%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f]", angles[0], snprintf(output, sizeof(output), "[%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f,%.1f]", angles[0],
angles[1], angles[2], angles[3], angles[4], angles[5], angles[6], angles[7], angles[8], angles[9], angles[1], angles[2], angles[3], angles[4], angles[5], angles[6], angles[7], angles[8], angles[9],
angles[10], angles[11]); angles[10], angles[11]);
_socket->emit("angles", output, String(originId).c_str()); socket.emit("angles", output, String(originId).c_str());
} }
void deactivate() { _peripherals->pcaDeactivate(); } void deactivate() { _peripherals->pcaDeactivate(); }
@@ -137,7 +137,6 @@ class ServoController : public StatefulService<ServoSettings> {
private: private:
PsychicHttpServer *_server; PsychicHttpServer *_server;
Peripherals *_peripherals; Peripherals *_peripherals;
EventSocket *_socket;
FSPersistence<ServoSettings> _fsPersistence; FSPersistence<ServoSettings> _fsPersistence;
bool is_active {true}; bool is_active {true};
@@ -1,4 +1,4 @@
#include <EventSocket.h> #include <event_socket.h>
SemaphoreHandle_t clientSubscriptionsMutex = xSemaphoreCreateMutex(); SemaphoreHandle_t clientSubscriptionsMutex = xSemaphoreCreateMutex();
@@ -42,15 +42,10 @@ const char *getEventPayload(const char *msg) {
return payload; return payload;
} }
EventSocket::EventSocket(PsychicHttpServer *server) : _server(server) {} EventSocket::EventSocket() {
void EventSocket::begin() {
_socket.onOpen((std::bind(&EventSocket::onWSOpen, this, std::placeholders::_1))); _socket.onOpen((std::bind(&EventSocket::onWSOpen, this, std::placeholders::_1)));
_socket.onClose(std::bind(&EventSocket::onWSClose, this, std::placeholders::_1)); _socket.onClose(std::bind(&EventSocket::onWSClose, this, std::placeholders::_1));
_socket.onFrame(std::bind(&EventSocket::onFrame, this, std::placeholders::_1, std::placeholders::_2)); _socket.onFrame(std::bind(&EventSocket::onFrame, this, std::placeholders::_1, std::placeholders::_2));
_server->on(EVENT_SERVICE_PATH, &_socket);
ESP_LOGV("EventSocket", "Registered event socket endpoint: %s", EVENT_SERVICE_PATH);
} }
void EventSocket::onWSOpen(PsychicWebSocketClient *client) { void EventSocket::onWSOpen(PsychicWebSocketClient *client) {
@@ -176,4 +171,6 @@ void EventSocket::onEvent(String event, EventCallback callback) { event_callback
void EventSocket::onSubscribe(String event, SubscribeCallback callback) { void EventSocket::onSubscribe(String event, SubscribeCallback callback) {
subscribe_callbacks[event].push_back(callback); subscribe_callbacks[event].push_back(callback);
} }
EventSocket socket;
@@ -7,8 +7,6 @@
#include <map> #include <map>
#include <vector> #include <vector>
#define EVENT_SERVICE_PATH "/ws/events"
enum message_type_t { CONNECT = 0, DISCONNECT = 1, EVENT = 2, PING = 3, PONG = 4, BINARY_EVENT = 5 }; enum message_type_t { CONNECT = 0, DISCONNECT = 1, EVENT = 2, PING = 3, PONG = 4, BINARY_EVENT = 5 };
typedef std::function<void(JsonObject &root, int originId)> EventCallback; typedef std::function<void(JsonObject &root, int originId)> EventCallback;
@@ -16,9 +14,9 @@ typedef std::function<void(const String &originId, bool sync)> SubscribeCallback
class EventSocket { class EventSocket {
public: public:
EventSocket(PsychicHttpServer *server); EventSocket();
void begin(); PsychicWebSocketHandler *getHandler() { return &_socket; }
bool hasSubscribers(const char *event); bool hasSubscribers(const char *event);
@@ -31,7 +29,6 @@ class EventSocket {
// all clients except the originId // all clients except the originId
private: private:
PsychicHttpServer *_server;
PsychicWebSocketHandler _socket; PsychicWebSocketHandler _socket;
std::map<String, std::list<int>> client_subscriptions; std::map<String, std::list<int>> client_subscriptions;
@@ -45,4 +42,6 @@ class EventSocket {
esp_err_t onFrame(PsychicWebSocketRequest *request, httpd_ws_frame *frame); esp_err_t onFrame(PsychicWebSocketRequest *request, httpd_ws_frame *frame);
}; };
extern EventSocket socket;
#endif #endif
+1 -1
View File
@@ -13,7 +13,7 @@ void NTPService::begin() {
WiFiEvent_t::ARDUINO_EVENT_WIFI_STA_DISCONNECTED); WiFiEvent_t::ARDUINO_EVENT_WIFI_STA_DISCONNECTED);
WiFi.onEvent(std::bind(&NTPService::onStationModeGotIP, this, std::placeholders::_1, std::placeholders::_2), WiFi.onEvent(std::bind(&NTPService::onStationModeGotIP, this, std::placeholders::_1, std::placeholders::_2),
WiFiEvent_t::ARDUINO_EVENT_WIFI_STA_GOT_IP); WiFiEvent_t::ARDUINO_EVENT_WIFI_STA_GOT_IP);
_persistence.readFromFS();
configureNTP(); configureNTP();
} }