From 111f077d17737ffa7367a7a4af7b32336d15e05e Mon Sep 17 00:00:00 2001 From: Alejandro Sirgo Rica Date: Thu, 23 May 2024 16:20:41 +0200 Subject: rest: add cache/delete Add POST cache/delete request to request deletion of images in the client's cache. Resquest payload structure: { 'clients': ['10.141.10.21', '10.141.10.22'] 'images': ['windows.img', 'linux.img'] } The clients listed in the 'clients' field will receive a cache/delete POST request with the 'clients' field removed and only containing 'images' from the payload received by the server. Each client will try to delete as many images as available in their cache from the list of files in 'images'. The clients will give response with the contents of the cache so the server can update the database. --- src/client.c | 56 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++ src/rest.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++++++ src/rest.h | 2 ++ 3 files changed, 109 insertions(+) diff --git a/src/client.c b/src/client.c index 8551d50..1486034 100644 --- a/src/client.c +++ b/src/client.c @@ -421,6 +421,59 @@ static int og_update_cache_info(struct og_dbi *dbi, struct list_head *cache_list return 0; } +static int og_resp_update_cache(json_t *data, struct og_client *cli) +{ + struct og_computer computer = {}; + json_t *value, *cache = NULL; + LIST_HEAD(cache_list); + struct og_dbi *dbi; + const char *key; + int err = 0; + + if (json_typeof(data) != JSON_OBJECT) { + og_cache_image_free(&cache_list); + return -1; + } + + json_object_foreach(data, key, value) { + if (!strcmp(key, "cache")) { + err = og_json_parse_cache(value, &cache_list); + cache = value; + } + } + + if (!cache) { + og_cache_image_free(&cache_list); + return 0; + } + + dbi = og_dbi_open(&ogconfig.db); + if (!dbi) { + og_cache_image_free(&cache_list); + syslog(LOG_ERR, "cannot open connection database (%s:%d)\n", + __func__, __LINE__); + return -1; + } + + err = og_dbi_get_computer_info(dbi, &computer, cli->addr.sin_addr); + if (err < 0) { + og_cache_image_free(&cache_list); + og_dbi_close(dbi); + return -1; + } + + err = og_update_cache_info(dbi, &cache_list, computer.id); + if (err < 0) { + og_cache_image_free(&cache_list); + og_dbi_close(dbi); + return -1; + } + + og_cache_image_free(&cache_list); + og_dbi_close(dbi); + return 0; +} + static int og_resp_refresh(json_t *data, struct og_client *cli) { struct og_partition partitions[OG_PARTITION_MAX] = {}; @@ -1013,6 +1066,9 @@ int og_agent_state_process_response(struct og_client *cli) case OG_CMD_IMAGE_RESTORE: err = og_resp_image_restore(root, cli); break; + case OG_CMD_CACHE_DELETE: + err = og_resp_update_cache(root, cli); + break; default: err = -1; break; diff --git a/src/rest.c b/src/rest.c index bdb2f01..4b85701 100644 --- a/src/rest.c +++ b/src/rest.c @@ -269,6 +269,7 @@ static const char *og_cmd_to_uri[OG_CMD_MAX] = { [OG_CMD_SETUP] = "setup", [OG_CMD_RUN_SCHEDULE] = "run/schedule", [OG_CMD_IMAGES] = "images", + [OG_CMD_CACHE_DELETE] = "cache/delete", }; static bool og_client_is_busy(const struct og_client *cli, @@ -3605,6 +3606,42 @@ static int og_cmd_cache_list(json_t *element, struct og_msg_params *params, return 0; } +static int og_cmd_cache_delete(json_t *element, struct og_msg_params *params, + char *buffer_reply) +{ + json_t *value, *body, *image_arr = NULL; + const char *key; + int err = 0; + + if (json_typeof(element) != JSON_OBJECT) + return -1; + + json_object_foreach(element, key, value) { + if (!strcmp(key, "clients")) { + err = og_json_parse_clients(value, params); + } else if (!strcmp(key, "images")) { + if (json_typeof(value) != JSON_ARRAY) { + err = -1; + } + image_arr = value; + } + + if (err < 0) + return err; + } + + if (!og_msg_params_validate(params, OG_REST_PARAM_ADDR)) + return -1; + + if (!image_arr) + return -1; + + body = json_copy(element); + json_object_del(body, "clients"); + + return og_send_request(OG_METHOD_POST, OG_CMD_CACHE_DELETE, params, body); +} + static int og_cmd_setup(json_t *element, struct og_msg_params *params) { json_t *value, *clients; @@ -7460,6 +7497,7 @@ struct { [OG_URI_IMAGE_RESTORE] = { "image/restore", }, [OG_URI_IMAGE_DELETE] = { "image/delete", }, [OG_URI_CACHE_LIST] = { "cache/list", }, + [OG_URI_CACHE_DELETE] = { "cache/delete", }, [OG_URI_PART_SETUP] = { "setup", }, [OG_URI_RUN_SCHEDULE] = { "run/schedule", }, [OG_URI_TASK_RUN] = { "task/run", }, @@ -8045,6 +8083,19 @@ int og_client_state_process_payload_rest(struct og_client *cli) goto err_process_rest_payload; } err = og_cmd_cache_list(root, ¶ms, buf_reply); + } else if (!strncmp(cmd, "cache/delete", strlen("cache/delete"))) { + if (method != OG_METHOD_POST) { + err = og_client_method_not_found(cli); + goto err_process_rest_payload; + } + + if (!root) { + syslog(LOG_ERR, + "command cache list with no payload\n"); + err = og_client_bad_request(cli); + goto err_process_rest_payload; + } + err = og_cmd_cache_delete(root, ¶ms, buf_reply); } else if (!strncmp(cmd, "setup", strlen("setup"))) { if (method != OG_METHOD_POST) { err = og_client_method_not_found(cli); diff --git a/src/rest.h b/src/rest.h index fbe0e43..1c5cc47 100644 --- a/src/rest.h +++ b/src/rest.h @@ -40,6 +40,7 @@ enum og_cmd_type { OG_CMD_SETUP, OG_CMD_RUN_SCHEDULE, OG_CMD_IMAGES, + OG_CMD_CACHE_DELETE, OG_CMD_MAX }; @@ -117,6 +118,7 @@ enum og_rest_uri { OG_URI_IMAGE_RESTORE, OG_URI_IMAGE_DELETE, OG_URI_CACHE_LIST, + OG_URI_CACHE_DELETE, OG_URI_PART_SETUP, OG_URI_RUN_SCHEDULE, OG_URI_TASK_RUN, -- cgit v1.2.3-18-g5258