mirror of https://git.48k.eu/ogserver
rest: add POST oglive/default
Remove 'is_default' column from 'lives' database table and add column 'priority' of type INT. This new value can store a priority value but the actual design only stores 1 or 0. Update GET oglive/list to use the new 'priority' database value. Add POST oglive/default. Set the database column 'priority' to 1 if the new default exists in the database. Set the others to priority 0. Modify legacy ogliveinfo.json if the new default coresponds to a live not found in the database. Edit the field 'default' of the file's json.master
parent
e3188191d9
commit
6a63218f85
264
src/rest.c
264
src/rest.c
|
@ -4769,11 +4769,13 @@ static int og_cmd_oglive_list(struct og_rest_ctx *ctx)
|
|||
.data = ctx->buf_reply
|
||||
};
|
||||
|
||||
const char *msglog, *live_name, *live_datetime;
|
||||
json_t *root, *live_entry, *oglive_array;
|
||||
json_t *root, *live_entry, *oglive_array, *default_entry;
|
||||
const char *msglog, *live_name;
|
||||
uint64_t live_timestamp;
|
||||
json_error_t json_err;
|
||||
struct og_dbi *dbi;
|
||||
dbi_result result;
|
||||
int priority;
|
||||
|
||||
root = json_load_file(OG_LIVE_JSON_FILE_PATH, 0, &json_err);
|
||||
if (!root) {
|
||||
|
@ -4784,7 +4786,12 @@ static int og_cmd_oglive_list(struct og_rest_ctx *ctx)
|
|||
|
||||
oglive_array = json_object_get(root, "oglive");
|
||||
if (!oglive_array || !json_is_array(oglive_array)) {
|
||||
syslog(LOG_ERR, "Expected 'oglive' to be a JSON array\n");
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
||||
default_entry = json_object_get(root, "default");
|
||||
if (!default_entry || json_typeof(default_entry) != JSON_INTEGER) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
@ -4799,8 +4806,8 @@ static int og_cmd_oglive_list(struct og_rest_ctx *ctx)
|
|||
}
|
||||
|
||||
result = dbi_conn_queryf(dbi->conn,
|
||||
"SELECT name, "
|
||||
"DATE_FORMAT(creation_date, '%%a %%b %%d %%H:%%i:%%s %%Y') AS formatted_date "
|
||||
"SELECT name, priority, "
|
||||
"UNIX_TIMESTAMP(creation_date) AS creation_timestamp "
|
||||
"FROM oglive");
|
||||
|
||||
if (!result) {
|
||||
|
@ -4815,7 +4822,19 @@ static int og_cmd_oglive_list(struct og_rest_ctx *ctx)
|
|||
|
||||
while (dbi_result_next_row(result) > 0) {
|
||||
live_name = dbi_result_get_string(result, "name");
|
||||
live_datetime = dbi_result_get_string(result, "formatted_date");
|
||||
live_timestamp = dbi_result_get_longlong(result, "creation_timestamp");
|
||||
priority = dbi_result_get_int(result, "priority");
|
||||
|
||||
if (priority > 0) {
|
||||
if (json_integer_set(default_entry, json_array_size(oglive_array)) < 0) {
|
||||
syslog(LOG_ERR, "Failed to modify 'default' entry value\n");
|
||||
dbi_result_free(result);
|
||||
og_dbi_close(dbi);
|
||||
json_decref(root);
|
||||
ctx->http_error = OG_HTTP_500_INTERNAL_SERVER_ERROR;
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
live_entry = json_object();
|
||||
if (!live_entry) {
|
||||
|
@ -4829,7 +4848,7 @@ static int og_cmd_oglive_list(struct og_rest_ctx *ctx)
|
|||
}
|
||||
|
||||
json_object_set_new(live_entry, "directory", json_string(live_name));
|
||||
json_object_set_new(live_entry, "date", json_string(live_datetime));
|
||||
json_object_set_new(live_entry, "date", json_integer(live_timestamp));
|
||||
|
||||
json_array_append_new(oglive_array, live_entry);
|
||||
}
|
||||
|
@ -5855,7 +5874,6 @@ static int og_cmd_oglive_add(struct og_rest_ctx *ctx)
|
|||
{
|
||||
const char *oglive_str;
|
||||
bool is_update = false;
|
||||
int is_default_value;
|
||||
const char *msglog;
|
||||
struct og_dbi *dbi;
|
||||
uint64_t flags = 0;
|
||||
|
@ -5906,20 +5924,16 @@ static int og_cmd_oglive_add(struct og_rest_ctx *ctx)
|
|||
|
||||
dbi_result_free(result);
|
||||
|
||||
is_default_value = 0;
|
||||
|
||||
if (is_update)
|
||||
result = dbi_conn_queryf(dbi->conn,
|
||||
"UPDATE oglive SET creation_date = NOW(), is_default = %d "
|
||||
"UPDATE oglive SET creation_date = NOW() "
|
||||
"WHERE name = '%s'",
|
||||
is_default_value,
|
||||
oglive_str);
|
||||
else
|
||||
result = dbi_conn_queryf(dbi->conn,
|
||||
"INSERT INTO oglive (name, creation_date, is_default) "
|
||||
"VALUES ('%s', NOW(), %d)",
|
||||
oglive_str,
|
||||
is_default_value);
|
||||
"INSERT INTO oglive (name, creation_date) "
|
||||
"VALUES ('%s', NOW())",
|
||||
oglive_str);
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_ERR, "failed to query database (%s:%d) %s\n",
|
||||
|
@ -6012,6 +6026,210 @@ static int og_cmd_oglive_delete(struct og_rest_ctx *ctx)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int update_ogliveinfo_default(const char *oglive_str)
|
||||
{
|
||||
char buf_data[OG_MSG_RESPONSE_MAXLEN];
|
||||
struct og_buffer og_buffer = {
|
||||
.data = buf_data
|
||||
};
|
||||
|
||||
json_t *root, *oglive_array, *default_entry, *live_entry, *dir_entry;
|
||||
char tmp_filename[] = "/tmp/ogliveinfo_XXXXXX";
|
||||
int default_idx, i, fd, ret;
|
||||
const char *live_name;
|
||||
json_error_t json_err;
|
||||
|
||||
root = json_load_file(OG_LIVE_JSON_FILE_PATH, 0, &json_err);
|
||||
if (!root) {
|
||||
syslog(LOG_ERR, "malformed json line %d: %s\n",
|
||||
json_err.line, json_err.text);
|
||||
return -1;
|
||||
}
|
||||
|
||||
oglive_array = json_object_get(root, "oglive");
|
||||
if (!oglive_array || !json_is_array(oglive_array)) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
||||
default_entry = json_object_get(root, "default");
|
||||
if (!default_entry || json_typeof(default_entry) != JSON_INTEGER) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
||||
default_idx = -1;
|
||||
|
||||
for (i = 0; i < json_array_size(oglive_array); i++) {
|
||||
live_entry = json_array_get(oglive_array, i);
|
||||
if (json_typeof(live_entry) != JSON_OBJECT) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
||||
dir_entry = json_object_get(live_entry, "directory");
|
||||
if (!dir_entry || json_typeof(dir_entry) != JSON_STRING) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
live_name = json_string_value(dir_entry);
|
||||
|
||||
if (!strncmp(oglive_str, live_name, strlen(live_name))) {
|
||||
default_idx = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (default_idx < 0) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (json_integer_set(default_entry, default_idx) < 0) {
|
||||
syslog(LOG_ERR, "Failed to modify 'default' entry value\n");
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (json_dump_callback(root, og_json_dump_clients, &og_buffer,
|
||||
JSON_INDENT(2) | JSON_PRESERVE_ORDER)) {
|
||||
json_decref(root);
|
||||
return -1;
|
||||
}
|
||||
json_decref(root);
|
||||
|
||||
fd = mkstemp(tmp_filename);
|
||||
if (fd < 0) {
|
||||
syslog(LOG_ERR, "cannot generate temp file %s: %s (%s:%d)\n",
|
||||
tmp_filename, strerror(errno), __func__, __LINE__);
|
||||
return -1;
|
||||
}
|
||||
|
||||
ret = write(fd, og_buffer.data, og_buffer.len);
|
||||
if (ret < 0) {
|
||||
syslog(LOG_ERR, "cannot write to temporary file %s: %s (%s:%d)\n",
|
||||
tmp_filename, strerror(errno), __func__, __LINE__);
|
||||
return -1;
|
||||
}
|
||||
|
||||
ret = write(fd, "\n", 1);
|
||||
if (ret < 0) {
|
||||
syslog(LOG_ERR, "cannot write to temporary file %s: %s (%s:%d)\n",
|
||||
tmp_filename, strerror(errno), __func__, __LINE__);
|
||||
return -1;
|
||||
}
|
||||
close(fd);
|
||||
|
||||
if (ret < 0) {
|
||||
syslog(LOG_ERR, "cannot write file %s: %s (%s:%d)\n",
|
||||
tmp_filename, strerror(errno), __func__, __LINE__);
|
||||
unlink(tmp_filename);
|
||||
return -1;
|
||||
}
|
||||
|
||||
if (rename(tmp_filename, OG_LIVE_JSON_FILE_PATH) < 0) {
|
||||
syslog(LOG_ERR, "cannot rename file %s to %s: %s (%s:%d)\n",
|
||||
tmp_filename, OG_LIVE_JSON_FILE_PATH, strerror(errno), __func__, __LINE__);
|
||||
unlink(tmp_filename);
|
||||
return -1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int og_cmd_oglive_set_default(struct og_rest_ctx *ctx)
|
||||
{
|
||||
const char *oglive_str;
|
||||
uint64_t flags = 0;
|
||||
const char *msglog;
|
||||
struct og_dbi *dbi;
|
||||
dbi_result result;
|
||||
bool db_has_live;
|
||||
const char *key;
|
||||
json_t *value;
|
||||
int priority;
|
||||
int err = 0;
|
||||
|
||||
json_object_foreach(ctx->json, key, value) {
|
||||
if (!strcmp(key, "name")) {
|
||||
err = og_json_parse_string(value, &oglive_str);
|
||||
flags |= OG_REST_PARAM_NAME;
|
||||
} else {
|
||||
err = -1;
|
||||
}
|
||||
|
||||
if (err < 0)
|
||||
return err;
|
||||
}
|
||||
|
||||
if (!og_flags_validate(flags, OG_REST_PARAM_NAME))
|
||||
return -1;
|
||||
|
||||
dbi = og_dbi_open(&ogconfig.db);
|
||||
if (!dbi) {
|
||||
syslog(LOG_ERR, "cannot open connection database (%s:%d)\n",
|
||||
__func__, __LINE__);
|
||||
ctx->http_error = OG_HTTP_501_SERVICE_UNAVAILABLE;
|
||||
return -1;
|
||||
}
|
||||
|
||||
result = dbi_conn_queryf(dbi->conn,
|
||||
"SELECT name FROM oglive WHERE name = '%s'",
|
||||
oglive_str);
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_ERR, "Failed to query database (%s:%d) %s\n", __func__, __LINE__, msglog);
|
||||
ctx->http_error = OG_HTTP_500_INTERNAL_SERVER_ERROR;
|
||||
og_dbi_close(dbi);
|
||||
return -1;
|
||||
}
|
||||
|
||||
db_has_live = dbi_result_next_row(result) > 0;
|
||||
dbi_result_free(result);
|
||||
|
||||
priority = 1;
|
||||
if (db_has_live) {
|
||||
result = dbi_conn_queryf(dbi->conn,
|
||||
"UPDATE oglive SET priority = %d "
|
||||
"WHERE name = '%s'",
|
||||
priority, oglive_str);
|
||||
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_ERR, "failed to query database (%s:%d) %s\n",
|
||||
__func__, __LINE__, msglog);
|
||||
ctx->http_error = OG_HTTP_500_INTERNAL_SERVER_ERROR;
|
||||
og_dbi_close(dbi);
|
||||
return -1;
|
||||
}
|
||||
|
||||
dbi_result_free(result);
|
||||
} else if (update_ogliveinfo_default(oglive_str) < 0) {
|
||||
syslog(LOG_ERR, "No live entries found with name %s", oglive_str);
|
||||
ctx->http_error = OG_HTTP_404_NOT_FOUND;
|
||||
og_dbi_close(dbi);
|
||||
return -1;
|
||||
}
|
||||
|
||||
result = dbi_conn_queryf(dbi->conn,
|
||||
"UPDATE oglive SET priority = 0 "
|
||||
"WHERE priority != 0 AND name != '%s'",
|
||||
oglive_str);
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_ERR, "failed to query database (%s:%d) %s\n",
|
||||
__func__, __LINE__, msglog);
|
||||
ctx->http_error = OG_HTTP_500_INTERNAL_SERVER_ERROR;
|
||||
og_dbi_close(dbi);
|
||||
return -1;
|
||||
}
|
||||
|
||||
dbi_result_free(result);
|
||||
og_dbi_close(dbi);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int og_cmd_get_server_stats(struct og_rest_ctx *ctx)
|
||||
{
|
||||
json_t *root, *time_obj, *memory, *swap;
|
||||
|
@ -6242,6 +6460,7 @@ struct {
|
|||
[OG_URI_OGLIVE_ADD] = { "oglive/add", },
|
||||
[OG_URI_OGLIVE_DELETE] = { "oglive/delete", },
|
||||
[OG_URI_OGLIVE_SET] = { "oglive/set", },
|
||||
[OG_URI_OGLIVE_DEFAULT] = { "oglive/default", },
|
||||
[OG_URI_CENTER_ADD] = { "center/add", },
|
||||
[OG_URI_CENTER_UPDATE] = { "center/update", },
|
||||
[OG_URI_CENTER_DELETE] = { "center/delete", },
|
||||
|
@ -6953,6 +7172,19 @@ int og_client_state_process_payload_rest(struct og_client *cli)
|
|||
goto err_process_rest_payload;
|
||||
}
|
||||
err = og_cmd_oglive_set(&ctx);
|
||||
} else if (!strncmp(cmd, "oglive/default", strlen("oglive/default"))) {
|
||||
if (method != OG_METHOD_POST) {
|
||||
ctx.http_error = OG_HTTP_405_METHOD_NOT_ALLOWED;
|
||||
goto err_process_rest_payload;
|
||||
}
|
||||
|
||||
if (!root) {
|
||||
syslog(LOG_ERR,
|
||||
"command oglive default with no payload\n");
|
||||
ctx.http_error = OG_HTTP_400_BAD_REQUEST;
|
||||
goto err_process_rest_payload;
|
||||
}
|
||||
err = og_cmd_oglive_set_default(&ctx);
|
||||
} else if (!strncmp(cmd, "center/add",
|
||||
strlen("center/add"))) {
|
||||
if (method != OG_METHOD_POST) {
|
||||
|
|
|
@ -145,6 +145,7 @@ enum og_rest_uri {
|
|||
OG_URI_OGLIVE_ADD,
|
||||
OG_URI_OGLIVE_DELETE,
|
||||
OG_URI_OGLIVE_SET,
|
||||
OG_URI_OGLIVE_DEFAULT,
|
||||
OG_URI_CENTER_ADD,
|
||||
OG_URI_CENTER_UPDATE,
|
||||
OG_URI_CENTER_DELETE,
|
||||
|
|
37
src/schema.c
37
src/schema.c
|
@ -497,6 +497,42 @@ static int og_dbi_schema_v12(struct og_dbi *dbi)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int og_dbi_schema_v13(struct og_dbi *dbi)
|
||||
{
|
||||
const char *msglog;
|
||||
dbi_result result;
|
||||
|
||||
syslog(LOG_DEBUG, "Updating table oglive\n");
|
||||
result = dbi_conn_query(dbi->conn, "ALTER TABLE `oglive` DROP COLUMN `is_default`");
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_INFO, "Error deleting column is_default in oglive table (%s:%d) %s\n",
|
||||
__func__, __LINE__, msglog);
|
||||
return -1;
|
||||
}
|
||||
dbi_result_free(result);
|
||||
|
||||
result = dbi_conn_query(dbi->conn, "ALTER TABLE `oglive` ADD COLUMN `priority` INT NOT NULL DEFAULT 0");
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_INFO, "Error adding column priority to oglive table (%s:%d) %s\n",
|
||||
__func__, __LINE__, msglog);
|
||||
return -1;
|
||||
}
|
||||
dbi_result_free(result);
|
||||
|
||||
result = dbi_conn_query(dbi->conn, "UPDATE version SET version = 13");
|
||||
if (!result) {
|
||||
dbi_conn_error(dbi->conn, &msglog);
|
||||
syslog(LOG_INFO, "Could not update version row (%s:%d) %s\n",
|
||||
__func__, __LINE__, msglog);
|
||||
return -1;
|
||||
}
|
||||
dbi_result_free(result);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct og_schema_version {
|
||||
int version;
|
||||
int (*update)(struct og_dbi *dbi);
|
||||
|
@ -513,6 +549,7 @@ static struct og_schema_version {
|
|||
{ .version = 10, .update = og_dbi_schema_v10,},
|
||||
{ .version = 11, .update = og_dbi_schema_v11,},
|
||||
{ .version = 12, .update = og_dbi_schema_v12,},
|
||||
{ .version = 13, .update = og_dbi_schema_v13,},
|
||||
{ 0, NULL },
|
||||
};
|
||||
|
||||
|
|
Loading…
Reference in New Issue