// POST /api/devices/register — Register a new device by MAC // Body: {"mac": "AA:BB:CC:DD:EE:FF"} #include "cJSON.h" #include "esp_http_server.h" #include "esp_log.h" #include "types.hpp" #include "device.hpp" internal const char *kTagDeviceRegister = "API_DEV_REG"; internal esp_err_t api_devices_register_handler(httpd_req_t *req) { httpd_resp_set_type(req, "application/json"); httpd_resp_set_hdr(req, "Access-Control-Allow-Origin", "*"); char buf[128]; int received = httpd_req_recv(req, buf, sizeof(buf) - 1); if (received <= 0) { httpd_resp_send_err(req, HTTPD_400_BAD_REQUEST, "Empty body"); return ESP_FAIL; } buf[received] = '\0'; cJSON *body = cJSON_Parse(buf); if (!body) { httpd_resp_send_err(req, HTTPD_400_BAD_REQUEST, "Invalid JSON"); return ESP_FAIL; } cJSON *mac_item = cJSON_GetObjectItem(body, "mac"); if (!cJSON_IsString(mac_item) || !mac_item->valuestring || strlen(mac_item->valuestring) == 0) { cJSON_Delete(body); httpd_resp_send_err(req, HTTPD_400_BAD_REQUEST, "Missing 'mac'"); return ESP_FAIL; } bool was_new = false; device_t *dev = register_device(mac_item->valuestring, &was_new); if (!dev) { cJSON_Delete(body); httpd_resp_send_err(req, HTTPD_500_INTERNAL_SERVER_ERROR, "Device limit reached"); return ESP_FAIL; } cJSON *resp = cJSON_CreateObject(); if (was_new) { cJSON_AddStringToObject(resp, "status", "ok"); ESP_LOGI(kTagDeviceRegister, "Registered new device: %s", dev->mac); } else { cJSON_AddStringToObject(resp, "status", "already_registered"); } cJSON_AddStringToObject(resp, "mac", dev->mac); cJSON_Delete(body); const char *json = cJSON_PrintUnformatted(resp); httpd_resp_sendstr(req, json); free((void *)json); cJSON_Delete(resp); return ESP_OK; } internal const httpd_uri_t api_devices_register_uri = { .uri = "/api/devices/register", .method = HTTP_POST, .handler = api_devices_register_handler, .user_ctx = NULL};