feat(api): Settings-Typ standalone und wifi.standalone in system/info
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
#include "fake_api_ctx.h"
|
||||
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
|
||||
#include "light/nl_boot_state.h"
|
||||
@@ -12,6 +13,10 @@ nl_ctrl_err_t fake_apply_result;
|
||||
int fake_apply_calls, fake_save_calls, fake_save_result;
|
||||
int fake_wifi_calls, fake_wifi_result;
|
||||
char fake_wifi_ssid[NL_SSID_LEN], fake_wifi_pass[NL_PASS_LEN];
|
||||
int fake_standalone_calls, fake_standalone_result;
|
||||
bool fake_standalone_enabled, fake_standalone_pulse;
|
||||
char fake_standalone_ssid[NL_SSID_LEN], fake_standalone_pass[NL_PASS_LEN];
|
||||
uint8_t fake_standalone_channel;
|
||||
int fake_factory_calls, fake_ping_calls, fake_fw_result;
|
||||
char fake_fw_url[256];
|
||||
bool fake_open;
|
||||
@@ -49,6 +54,18 @@ static int wifi_configure(const char *ssid, const char *pass)
|
||||
return fake_wifi_result;
|
||||
}
|
||||
|
||||
static int fake_standalone_configure(bool enabled, const char *ssid, const char *pass,
|
||||
uint8_t channel, bool pulse)
|
||||
{
|
||||
fake_standalone_calls++;
|
||||
fake_standalone_enabled = enabled;
|
||||
fake_standalone_pulse = pulse;
|
||||
fake_standalone_channel = channel;
|
||||
snprintf(fake_standalone_ssid, sizeof fake_standalone_ssid, "%s", ssid ? ssid : "");
|
||||
snprintf(fake_standalone_pass, sizeof fake_standalone_pass, "%s", pass ? pass : "");
|
||||
return fake_standalone_result;
|
||||
}
|
||||
|
||||
static bool open_access(void) { return fake_open; }
|
||||
static void get_info(nl_sys_info_t *out) { *out = fake_info; }
|
||||
static void factory_reset(void) { fake_factory_calls++; }
|
||||
@@ -83,6 +100,10 @@ void fake_api_reset(const char *board_id)
|
||||
fake_apply_calls = fake_save_calls = fake_save_result = 0;
|
||||
fake_wifi_calls = fake_wifi_result = 0;
|
||||
fake_wifi_ssid[0] = fake_wifi_pass[0] = '\0';
|
||||
fake_standalone_calls = fake_standalone_result = 0;
|
||||
fake_standalone_enabled = fake_standalone_pulse = false;
|
||||
fake_standalone_ssid[0] = fake_standalone_pass[0] = '\0';
|
||||
fake_standalone_channel = 0;
|
||||
fake_factory_calls = fake_ping_calls = 0;
|
||||
fake_fw_result = -1;
|
||||
fake_fw_url[0] = '\0';
|
||||
@@ -96,6 +117,8 @@ void fake_api_reset(const char *board_id)
|
||||
fake_ctx.get_settings = get_settings;
|
||||
fake_ctx.save_settings = save_settings;
|
||||
fake_ctx.wifi_configure = wifi_configure;
|
||||
fake_ctx.standalone_configure = fake_standalone_configure;
|
||||
fake_ctx.hostname = "ninlight-681f";
|
||||
fake_ctx.open_access = open_access;
|
||||
fake_ctx.get_info = get_info;
|
||||
fake_ctx.factory_reset = factory_reset;
|
||||
|
||||
@@ -12,6 +12,10 @@ extern nl_ctrl_err_t fake_apply_result;
|
||||
extern int fake_apply_calls, fake_save_calls, fake_save_result;
|
||||
extern int fake_wifi_calls, fake_wifi_result;
|
||||
extern char fake_wifi_ssid[NL_SSID_LEN], fake_wifi_pass[NL_PASS_LEN];
|
||||
extern int fake_standalone_calls, fake_standalone_result;
|
||||
extern bool fake_standalone_enabled, fake_standalone_pulse;
|
||||
extern char fake_standalone_ssid[NL_SSID_LEN], fake_standalone_pass[NL_PASS_LEN];
|
||||
extern uint8_t fake_standalone_channel;
|
||||
extern int fake_factory_calls, fake_ping_calls, fake_fw_result;
|
||||
extern char fake_fw_url[256];
|
||||
extern bool fake_open;
|
||||
|
||||
+174
@@ -589,6 +589,169 @@ static void test_put_sacn_layout_and_start_slot_together(void)
|
||||
TEST_ASSERT_EQUAL_UINT16(510, fake_settings.sacn_start_slot);
|
||||
}
|
||||
|
||||
/* --- standalone --- */
|
||||
|
||||
static void test_standalone_requires_a_password(void)
|
||||
{
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":true}");
|
||||
TEST_ASSERT_EQUAL_INT(400, resp.status);
|
||||
TEST_ASSERT_EQUAL_STRING("password required", error_text());
|
||||
TEST_ASSERT_EQUAL_INT(0, fake_standalone_calls);
|
||||
TEST_ASSERT_EQUAL_INT(0, fake_save_calls);
|
||||
}
|
||||
|
||||
/* Ein gespeichertes Passwort genuegt - man soll den Kanal aendern koennen, ohne das
|
||||
* Passwort erneut zu schicken. */
|
||||
static void test_standalone_keeps_a_stored_password(void)
|
||||
{
|
||||
strcpy(fake_settings.ap_pass, "geheim123");
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN,
|
||||
"{\"type\":\"standalone\",\"enabled\":true,\"channel\":11}");
|
||||
TEST_ASSERT_EQUAL_INT(202, resp.status);
|
||||
TEST_ASSERT_EQUAL_INT(11, fake_standalone_channel);
|
||||
TEST_ASSERT_EQUAL_STRING("geheim123", fake_standalone_pass);
|
||||
}
|
||||
|
||||
static void test_standalone_rejects_a_short_password(void)
|
||||
{
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN,
|
||||
"{\"type\":\"standalone\",\"enabled\":true,\"password\":\"1234567\"}");
|
||||
TEST_ASSERT_EQUAL_INT(400, resp.status);
|
||||
TEST_ASSERT_EQUAL_STRING("invalid password", error_text());
|
||||
/* Die Fehlermeldung nennt das Feld, nie den Wert. */
|
||||
TEST_ASSERT_NULL(strstr(resp.body, "1234567"));
|
||||
TEST_ASSERT_EQUAL_INT(0, fake_standalone_calls);
|
||||
}
|
||||
|
||||
static void test_standalone_rejects_a_channel_outside_the_band(void)
|
||||
{
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN,
|
||||
"{\"type\":\"standalone\",\"enabled\":true,\"password\":\"geheim123\",\"channel\":14}");
|
||||
TEST_ASSERT_EQUAL_INT(400, resp.status);
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN,
|
||||
"{\"type\":\"standalone\",\"enabled\":true,\"password\":\"geheim123\",\"channel\":0}");
|
||||
TEST_ASSERT_EQUAL_INT(400, resp.status);
|
||||
TEST_ASSERT_EQUAL_INT(0, fake_standalone_calls);
|
||||
}
|
||||
|
||||
static void test_standalone_accepts_a_full_request(void)
|
||||
{
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN,
|
||||
"{\"type\":\"standalone\",\"enabled\":true,\"password\":\"geheim123\","
|
||||
"\"ssid\":\"Wohnzimmerlampe\",\"channel\":6,\"pulse\":false}");
|
||||
TEST_ASSERT_EQUAL_INT(202, resp.status);
|
||||
TEST_ASSERT_EQUAL_STRING("standalone", cJSON_GetStringValue(field("status")));
|
||||
TEST_ASSERT_EQUAL_INT(1, fake_standalone_calls);
|
||||
TEST_ASSERT_TRUE(fake_standalone_enabled);
|
||||
TEST_ASSERT_EQUAL_STRING("Wohnzimmerlampe", fake_standalone_ssid);
|
||||
TEST_ASSERT_EQUAL_STRING("geheim123", fake_standalone_pass);
|
||||
TEST_ASSERT_EQUAL_INT(6, fake_standalone_channel);
|
||||
TEST_ASSERT_FALSE(fake_standalone_pulse);
|
||||
/* Gespeichert wird auch: sonst ist der Modus nach dem Neustart weg. */
|
||||
TEST_ASSERT_EQUAL_INT(1, fake_save_calls);
|
||||
TEST_ASSERT_EQUAL_UINT8(1, fake_settings.standalone);
|
||||
TEST_ASSERT_EQUAL_STRING("geheim123", fake_settings.ap_pass);
|
||||
}
|
||||
|
||||
/* Abschalten braucht kein Passwort. */
|
||||
static void test_standalone_can_be_switched_off(void)
|
||||
{
|
||||
fake_settings.standalone = 1;
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":false}");
|
||||
TEST_ASSERT_EQUAL_INT(202, resp.status);
|
||||
TEST_ASSERT_EQUAL_INT(1, fake_standalone_calls);
|
||||
TEST_ASSERT_FALSE(fake_standalone_enabled);
|
||||
TEST_ASSERT_EQUAL_UINT8(0, fake_settings.standalone);
|
||||
}
|
||||
|
||||
static void test_standalone_reports_a_busy_radio_and_a_failed_save(void)
|
||||
{
|
||||
strcpy(fake_settings.ap_pass, "geheim123");
|
||||
fake_standalone_result = -1;
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":true}");
|
||||
TEST_ASSERT_EQUAL_INT(503, resp.status);
|
||||
TEST_ASSERT_EQUAL_STRING("wifi busy", error_text());
|
||||
|
||||
fake_standalone_result = 0;
|
||||
fake_standalone_calls = 0;
|
||||
fake_save_result = -1;
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":true}");
|
||||
TEST_ASSERT_EQUAL_INT(500, resp.status);
|
||||
/* Ohne gespeicherten Datensatz darf der Wechsel nicht angestossen werden. */
|
||||
TEST_ASSERT_EQUAL_INT(0, fake_standalone_calls);
|
||||
}
|
||||
|
||||
static void test_standalone_rejects_bad_types_of_the_other_fields(void)
|
||||
{
|
||||
strcpy(fake_settings.ap_pass, "geheim123");
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":\"yes\"}");
|
||||
TEST_ASSERT_EQUAL_STRING("invalid enabled", error_text());
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":true,\"pulse\":1}");
|
||||
TEST_ASSERT_EQUAL_STRING("invalid pulse", error_text());
|
||||
call(NL_HTTP_PUT, "/api/v1/system/settings", TOKEN, "{\"type\":\"standalone\",\"enabled\":true,\"ssid\":\"\"}");
|
||||
TEST_ASSERT_EQUAL_STRING("invalid ssid", error_text());
|
||||
TEST_ASSERT_EQUAL_INT(0, fake_standalone_calls);
|
||||
}
|
||||
|
||||
/* Das AP-Passwort darf nirgends in der Antwort auftauchen. */
|
||||
static void test_settings_show_standalone_without_the_password(void)
|
||||
{
|
||||
cJSON *o, *sa;
|
||||
fake_settings.standalone = 1;
|
||||
fake_settings.ap_channel = 11;
|
||||
fake_settings.standalone_pulse = 0;
|
||||
strcpy(fake_settings.ap_ssid, "Wohnzimmerlampe");
|
||||
strcpy(fake_settings.ap_pass, "geheim123");
|
||||
call(NL_HTTP_GET, "/api/v1/system/settings", TOKEN, NULL);
|
||||
TEST_ASSERT_EQUAL_INT(200, resp.status);
|
||||
TEST_ASSERT_NULL(strstr(resp.body, "geheim123"));
|
||||
o = cJSON_Parse(resp.body);
|
||||
sa = cJSON_GetObjectItemCaseSensitive(o, "standalone");
|
||||
TEST_ASSERT_TRUE(cJSON_IsTrue(cJSON_GetObjectItemCaseSensitive(sa, "enabled")));
|
||||
TEST_ASSERT_EQUAL_STRING("Wohnzimmerlampe",
|
||||
cJSON_GetStringValue(cJSON_GetObjectItemCaseSensitive(sa, "ssid")));
|
||||
TEST_ASSERT_EQUAL_INT(11, (int)cJSON_GetNumberValue(cJSON_GetObjectItemCaseSensitive(sa, "channel")));
|
||||
TEST_ASSERT_FALSE(cJSON_IsTrue(cJSON_GetObjectItemCaseSensitive(sa, "pulse")));
|
||||
cJSON_Delete(o);
|
||||
}
|
||||
|
||||
/* Ohne eigenen Namen zeigt die Antwort den WIRKSAMEN, nicht einen leeren String -
|
||||
* sonst muesste jeder Aufrufer die Vorgabe selbst nachbilden. */
|
||||
static void test_settings_show_the_effective_ap_name(void)
|
||||
{
|
||||
cJSON *o, *sa;
|
||||
fake_settings.ap_ssid[0] = '\0';
|
||||
call(NL_HTTP_GET, "/api/v1/system/settings", TOKEN, NULL);
|
||||
o = cJSON_Parse(resp.body);
|
||||
sa = cJSON_GetObjectItemCaseSensitive(o, "standalone");
|
||||
TEST_ASSERT_EQUAL_STRING("ninlight-681f",
|
||||
cJSON_GetStringValue(cJSON_GetObjectItemCaseSensitive(sa, "ssid")));
|
||||
/* Kanal 0 im Datensatz heisst 6. */
|
||||
TEST_ASSERT_EQUAL_INT(6, (int)cJSON_GetNumberValue(cJSON_GetObjectItemCaseSensitive(sa, "channel")));
|
||||
cJSON_Delete(o);
|
||||
}
|
||||
|
||||
/* "ap" allein reicht nicht: denselben Wert meldet der Onboarding-AP. Ohne dieses Feld
|
||||
* boete die App einer fertig eingerichteten Lampe ein Onboarding an. */
|
||||
static void test_info_tells_standalone_from_onboarding(void)
|
||||
{
|
||||
cJSON *o, *w;
|
||||
fake_info.wifi_mode = "ap";
|
||||
fake_info.wifi_standalone = true;
|
||||
call(NL_HTTP_GET, "/api/v1/system/info", NULL, NULL);
|
||||
o = cJSON_Parse(resp.body);
|
||||
w = cJSON_GetObjectItemCaseSensitive(o, "wifi");
|
||||
TEST_ASSERT_TRUE(cJSON_IsTrue(cJSON_GetObjectItemCaseSensitive(w, "standalone")));
|
||||
cJSON_Delete(o);
|
||||
|
||||
fake_info.wifi_standalone = false;
|
||||
call(NL_HTTP_GET, "/api/v1/system/info", NULL, NULL);
|
||||
o = cJSON_Parse(resp.body);
|
||||
w = cJSON_GetObjectItemCaseSensitive(o, "wifi");
|
||||
TEST_ASSERT_TRUE(cJSON_IsFalse(cJSON_GetObjectItemCaseSensitive(w, "standalone")));
|
||||
cJSON_Delete(o);
|
||||
}
|
||||
|
||||
int main(void)
|
||||
{
|
||||
UNITY_BEGIN();
|
||||
@@ -627,5 +790,16 @@ int main(void)
|
||||
RUN_TEST(test_info_exposes_sacn_state);
|
||||
RUN_TEST(test_info_reports_a_dead_sacn_task);
|
||||
RUN_TEST(test_commands);
|
||||
RUN_TEST(test_standalone_requires_a_password);
|
||||
RUN_TEST(test_standalone_keeps_a_stored_password);
|
||||
RUN_TEST(test_standalone_rejects_a_short_password);
|
||||
RUN_TEST(test_standalone_rejects_a_channel_outside_the_band);
|
||||
RUN_TEST(test_standalone_accepts_a_full_request);
|
||||
RUN_TEST(test_standalone_can_be_switched_off);
|
||||
RUN_TEST(test_standalone_reports_a_busy_radio_and_a_failed_save);
|
||||
RUN_TEST(test_standalone_rejects_bad_types_of_the_other_fields);
|
||||
RUN_TEST(test_settings_show_standalone_without_the_password);
|
||||
RUN_TEST(test_settings_show_the_effective_ap_name);
|
||||
RUN_TEST(test_info_tells_standalone_from_onboarding);
|
||||
return UNITY_END();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user