Use booleans instead of string for controlling the blocking status. Return the GET response after a successful PATCH request.
Signed-off-by: DL6ER <dl6er@dl6er.de>
This commit is contained in:
parent
be3b4045ae
commit
fa5f6cdcdf
171
src/api/dns.c
171
src/api/dns.c
|
@ -18,88 +18,109 @@
|
|||
// set_blockingmode_timer()
|
||||
#include "../timers.h"
|
||||
|
||||
static int get_blocking(struct mg_connection *conn)
|
||||
{
|
||||
// Return current status
|
||||
cJSON *json = JSON_NEW_OBJ();
|
||||
const bool blocking = get_blockingstatus();
|
||||
JSON_OBJ_ADD_BOOL(json, "blocking", blocking);
|
||||
|
||||
// Get timer information (if applicable)
|
||||
int delay;
|
||||
bool target_status;
|
||||
get_blockingmode_timer(&delay, &target_status);
|
||||
if(delay > -1)
|
||||
{
|
||||
cJSON *timer = JSON_NEW_OBJ();
|
||||
JSON_OBJ_ADD_NUMBER(timer, "delay", delay);
|
||||
JSON_OBJ_ADD_BOOL(timer, "blocking_target", target_status);
|
||||
JSON_OBJ_ADD_ITEM(json, "timer", timer);
|
||||
}
|
||||
else
|
||||
{
|
||||
JSON_OBJ_ADD_NULL(json, "timer");
|
||||
}
|
||||
|
||||
// Send object (HTTP 200 OK)
|
||||
JSON_SEND_OBJECT(json);
|
||||
}
|
||||
|
||||
static int set_blocking(struct mg_connection *conn)
|
||||
{
|
||||
// Verify requesting client is allowed to access this ressource
|
||||
if(check_client_auth(conn) < 0)
|
||||
{
|
||||
return send_json_unauthorized(conn);
|
||||
}
|
||||
|
||||
char buffer[1024];
|
||||
const int data_len = mg_read(conn, buffer, sizeof(buffer) - 1);
|
||||
if ((data_len < 1) || (data_len >= (int)sizeof(buffer))) {
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request", "No request body data",
|
||||
NULL);
|
||||
}
|
||||
buffer[data_len] = '\0';
|
||||
|
||||
cJSON *obj = cJSON_Parse(buffer);
|
||||
if (obj == NULL) {
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request",
|
||||
"Invalid request body data",
|
||||
NULL);
|
||||
}
|
||||
|
||||
cJSON *elem = cJSON_GetObjectItemCaseSensitive(obj, "blocking");
|
||||
if (!cJSON_IsBool(elem)) {
|
||||
cJSON_Delete(obj);
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request",
|
||||
"No \"blocking\" boolean in body data",
|
||||
NULL);
|
||||
}
|
||||
const bool target_status = cJSON_IsTrue(elem);
|
||||
|
||||
// Get (optional) delay
|
||||
int delay = -1;
|
||||
elem = cJSON_GetObjectItemCaseSensitive(obj, "delay");
|
||||
if (cJSON_IsNumber(elem) && elem->valuedouble > 0.0)
|
||||
delay = elem->valueint;
|
||||
|
||||
// Free memory not needed any longer
|
||||
cJSON_Delete(obj);
|
||||
|
||||
if(target_status == get_blockingstatus())
|
||||
{
|
||||
// The blocking status does not need to be changed
|
||||
|
||||
// If delay is absent (or -1), we delete a possibly running timer
|
||||
if(delay < 0)
|
||||
set_blockingmode_timer(-1, true);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Activate requested status
|
||||
set_blockingstatus(target_status);
|
||||
|
||||
// Start timer (-1 disables all running timers)
|
||||
set_blockingmode_timer(delay, !target_status);
|
||||
}
|
||||
|
||||
// Return GET property as result of POST/PUT/PATCH action
|
||||
// if no error happened above
|
||||
return get_blocking(conn);
|
||||
}
|
||||
|
||||
int api_dns_blockingstatus(struct mg_connection *conn)
|
||||
{
|
||||
int method = http_method(conn);
|
||||
if(method == HTTP_GET)
|
||||
{
|
||||
// Return current status
|
||||
cJSON *json = JSON_NEW_OBJ();
|
||||
const char *action = get_blockingstatus() ? "active" : "inactive";
|
||||
JSON_OBJ_REF_STR(json, "status", action);
|
||||
JSON_SEND_OBJECT(json);
|
||||
return get_blocking(conn);
|
||||
}
|
||||
else if(method == HTTP_POST)
|
||||
else if(method == HTTP_PATCH)
|
||||
{
|
||||
// Verify requesting client is allowed to access this ressource
|
||||
if(check_client_auth(conn) < 0)
|
||||
{
|
||||
return send_json_unauthorized(conn);
|
||||
}
|
||||
|
||||
char buffer[1024];
|
||||
int data_len = mg_read(conn, buffer, sizeof(buffer) - 1);
|
||||
if ((data_len < 1) || (data_len >= (int)sizeof(buffer))) {
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request", "No request body data",
|
||||
NULL);
|
||||
}
|
||||
buffer[data_len] = '\0';
|
||||
|
||||
cJSON *obj = cJSON_Parse(buffer);
|
||||
if (obj == NULL) {
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request",
|
||||
"Invalid request body data",
|
||||
NULL);
|
||||
}
|
||||
|
||||
cJSON *elem1 = cJSON_GetObjectItemCaseSensitive(obj, "status");
|
||||
if (!cJSON_IsString(elem1)) {
|
||||
cJSON_Delete(obj);
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request",
|
||||
"No \"status\" string in body data",
|
||||
NULL);
|
||||
}
|
||||
char *status = strdup(elem1->valuestring);
|
||||
|
||||
unsigned int delay = -1;
|
||||
cJSON *elem2 = cJSON_GetObjectItemCaseSensitive(obj, "delay");
|
||||
if (cJSON_IsNumber(elem2) && elem2->valuedouble > 0.0)
|
||||
{
|
||||
delay = elem2->valueint;
|
||||
}
|
||||
|
||||
cJSON_Delete(obj);
|
||||
cJSON *json = JSON_NEW_OBJ();
|
||||
JSON_OBJ_COPY_STR(json, "status", status);
|
||||
|
||||
// Execute requested status
|
||||
if(strcmp(status, "active") == 0)
|
||||
{
|
||||
// If no "time" key was present, we call this subroutine with
|
||||
// delay == -1 which will disable all previously set timers
|
||||
set_blockingmode_timer(delay, false);
|
||||
set_blockingstatus(true);
|
||||
}
|
||||
else if(strcmp(status, "inactive") == 0)
|
||||
{
|
||||
// If no "time" key was present, we call this subroutine with
|
||||
// delay == -1 which will disable all previously set timers
|
||||
set_blockingmode_timer(delay, true);
|
||||
set_blockingstatus(false);
|
||||
}
|
||||
else
|
||||
{
|
||||
free(status);
|
||||
return send_json_error(conn, 400,
|
||||
"bad_request",
|
||||
"Invalid \"status\" requested",
|
||||
json);
|
||||
}
|
||||
free(status);
|
||||
JSON_SEND_OBJECT(json);
|
||||
return set_blocking(conn);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
14
src/timers.c
14
src/timers.c
|
@ -50,12 +50,18 @@ void sleepms(const int milliseconds)
|
|||
}
|
||||
|
||||
static int timer_delay = -1;
|
||||
static bool timer_targer_state;
|
||||
static bool timer_target_status;
|
||||
|
||||
void set_blockingmode_timer(int delay, bool blocked)
|
||||
void set_blockingmode_timer(int delay, bool target_status)
|
||||
{
|
||||
timer_delay = delay;
|
||||
timer_targer_state = blocked;
|
||||
timer_target_status = target_status;
|
||||
}
|
||||
|
||||
void get_blockingmode_timer(int *delay, bool *target_status)
|
||||
{
|
||||
*delay = timer_delay;
|
||||
*target_status = timer_target_status;
|
||||
}
|
||||
|
||||
void *timer(void *val)
|
||||
|
@ -74,7 +80,7 @@ void *timer(void *val)
|
|||
}
|
||||
else if(timer_delay == 0)
|
||||
{
|
||||
set_blockingstatus(timer_targer_state);
|
||||
set_blockingstatus(timer_target_status);
|
||||
timer_delay = -1;
|
||||
}
|
||||
sleepms(1000);
|
||||
|
|
|
@ -19,6 +19,7 @@ void timer_start(const int i);
|
|||
double timer_elapsed_msec(const int i);
|
||||
void sleepms(const int milliseconds);
|
||||
void set_blockingmode_timer(int delay, bool blocked);
|
||||
void get_blockingmode_timer(int *delay, bool *target_status);
|
||||
void *timer(void *val);
|
||||
|
||||
#endif //TIMERS_H
|
||||
|
|
|
@ -175,23 +175,15 @@ int http_method(struct mg_connection *conn)
|
|||
{
|
||||
const struct mg_request_info *request = mg_get_request_info(conn);
|
||||
if(strcmp(request->request_method, "GET") == 0)
|
||||
{
|
||||
return HTTP_GET;
|
||||
}
|
||||
else if(strcmp(request->request_method, "DELETE") == 0)
|
||||
{
|
||||
return HTTP_DELETE;
|
||||
}
|
||||
else if(strcmp(request->request_method, "PUT") == 0)
|
||||
{
|
||||
return HTTP_PUT;
|
||||
}
|
||||
else if(strcmp(request->request_method, "POST") == 0)
|
||||
{
|
||||
return HTTP_POST;
|
||||
}
|
||||
else if(strcmp(request->request_method, "PATCH") == 0)
|
||||
return HTTP_PATCH;
|
||||
else
|
||||
{
|
||||
return HTTP_UNKNOWN;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -45,7 +45,7 @@ int get_int_var(const char *source, const char *var);
|
|||
#define GET_VAR(variable, destination, source) mg_get_var(source, strlen(source), variable, destination, sizeof(destination))
|
||||
|
||||
// Method routines
|
||||
enum { HTTP_UNKNOWN, HTTP_GET, HTTP_POST, HTTP_PUT, HTTP_DELETE };
|
||||
enum { HTTP_UNKNOWN, HTTP_GET, HTTP_POST, HTTP_PUT, HTTP_PATCH, HTTP_DELETE };
|
||||
int http_method(struct mg_connection *conn);
|
||||
|
||||
// Utils
|
||||
|
|
|
@ -80,7 +80,7 @@
|
|||
}
|
||||
|
||||
#define JSON_OBJ_ADD_BOOL(object, key, value) {\
|
||||
cJSON *bool_item = cJSON_CreateBool(value ? cJSON_True : cJSON_False); \
|
||||
cJSON *bool_item = cJSON_CreateBool((cJSON_bool)value); \
|
||||
if(bool_item == NULL) \
|
||||
{ \
|
||||
cJSON_Delete(object); \
|
||||
|
|
|
@ -60,9 +60,9 @@ int ph7_handler(struct mg_connection *conn, void *cbdata)
|
|||
}
|
||||
|
||||
char full_path[buffer_len];
|
||||
strncpy(full_path, httpsettings.webroot, webroot_len);
|
||||
memcpy(full_path, httpsettings.webroot, webroot_len);
|
||||
full_path[webroot_len] = '/';
|
||||
strncpy(full_path + webroot_len + 1u, local_uri, local_uri_len);
|
||||
memcpy(full_path + webroot_len + 1u, local_uri, local_uri_len);
|
||||
full_path[webroot_len + local_uri_len + 1u] = '\0';
|
||||
if(append_index)
|
||||
{
|
||||
|
|
Loading…
Reference in New Issue