From cc1ea321d7570ca8e8883381103c616b24e6717d Mon Sep 17 00:00:00 2001 From: lixiumei123 Date: Mon, 10 Oct 2022 08:07:13 +0000 Subject: [PATCH] add(api):added api for modifying log level --- include/neuron/define.h | 1 + include/neuron/errcodes.h | 1 + plugins/restful/handle.c | 6 ++ plugins/restful/http.c | 1 + plugins/restful/log_handle.c | 173 +++++++++++++++++++++++++---------- plugins/restful/log_handle.h | 1 + src/parser/neu_json_log.c | 53 +++++++++++ src/parser/neu_json_log.h | 10 ++ zlog.conf | 1 - 9 files changed, 200 insertions(+), 47 deletions(-) diff --git a/include/neuron/define.h b/include/neuron/define.h index 60a01a1d..977d9b50 100644 --- a/include/neuron/define.h +++ b/include/neuron/define.h @@ -34,6 +34,7 @@ #define NEU_TAG_FLOAG_PRECISION_MAX 17 #define NEU_USER_PASSWORD_MIN_LEN 4 #define NEU_USER_PASSWORD_MAX_LEN 16 +#define NEU_LOG_LEVEL_LEN 9 typedef enum neu_plugin_kind { NEU_PLUGIN_KIND_STATIC = 0, diff --git a/include/neuron/errcodes.h b/include/neuron/errcodes.h index 35e21c14..c9e8f173 100644 --- a/include/neuron/errcodes.h +++ b/include/neuron/errcodes.h @@ -44,6 +44,7 @@ typedef enum { NEU_ERR_FILE_NOT_EXIST = 1011, NEU_ERR_INVALID_PASSWORD_LEN = 1012, NEU_ERR_DUPLICATE_PASSWORD = 1013, + NEU_ERR_LOG_LEVEL_NOT_EXIST = 1014, NEU_ERR_NODE_EXIST = 2002, NEU_ERR_NODE_NOT_EXIST = 2003, diff --git a/plugins/restful/handle.c b/plugins/restful/handle.c index 3afdabac..bb90f303 100644 --- a/plugins/restful/handle.c +++ b/plugins/restful/handle.c @@ -293,6 +293,12 @@ struct neu_rest_handler api_handlers[] = { .url = "/api/v2/log", .value.handler = handle_download_log, }, + { + .method = NEU_REST_METHOD_PUT, + .type = NEU_REST_HANDLER_FUNCTION, + .url = "/api/v2/level", + .value.handler = handle_log_level, + }, { .method = NEU_REST_METHOD_POST, .type = NEU_REST_HANDLER_FUNCTION, diff --git a/plugins/restful/http.c b/plugins/restful/http.c index ec913b5e..f0ac7d63 100644 --- a/plugins/restful/http.c +++ b/plugins/restful/http.c @@ -307,6 +307,7 @@ int http_response(nng_aio *aio, neu_err_code_e code, char *content) break; case NEU_ERR_BODY_IS_WRONG: case NEU_ERR_PARAM_IS_WRONG: + case NEU_ERR_LOG_LEVEL_NOT_EXIST: case NEU_ERR_NODE_SETTING_INVALID: case NEU_ERR_LIBRARY_INFO_INVALID: case NEU_ERR_LICENSE_INVALID: diff --git a/plugins/restful/log_handle.c b/plugins/restful/log_handle.c index 9b3484a6..a150414d 100644 --- a/plugins/restful/log_handle.c +++ b/plugins/restful/log_handle.c @@ -34,6 +34,7 @@ #include "errcodes.h" #include "handle.h" #include "http.h" +#include "parser/neu_json_log.h" #include "utils/log.h" #include "utils/neu_jwt.h" #include "json/neu_json_fn.h" @@ -42,8 +43,10 @@ #include "utils/utarray.h" UT_array *collect_log_files(); -void handle_get_log_files(nng_aio *aio); -int read_log_file(const char *log_file, void **datap, size_t *lenp); +// void handle_get_log_files(nng_aio *aio); +// int read_log_file(const char *log_file, void **datap, size_t *lenp); +int read_file(const char *file_name, void **datap, size_t *lenp); +// int update_log_level(const char *file_name, const char *zlog_level); void handle_download_log(nng_aio *aio) { @@ -57,18 +60,24 @@ void handle_download_log(nng_aio *aio) nlog_error("parse query param `node_name` fail"); NEU_JSON_RESPONSE_ERROR(NEU_ERR_PARAM_IS_WRONG, { http_response(aio, error_code.error, result_error); - }); + }) + return; } else if ((size_t) rv >= sizeof(log_file)) { nlog_error("query param overflow, `log_file`:%s", log_file); NEU_JSON_RESPONSE_ERROR(NEU_ERR_EINTERNAL, { http_response(aio, error_code.error, result_error); - }); + }) + return; } - void * data = NULL; - size_t len = 0; - nng_http_res *res = NULL; - rv = read_log_file(log_file, &data, &len); + void * data = NULL; + size_t len = 0; + nng_http_res *res = NULL; + char path[128] = { 0 }; + + snprintf(path, sizeof(path), "./logs/%s.log", log_file); + + rv = read_file(path, &data, &len); if (0 != rv) { NEU_JSON_RESPONSE_ERROR( rv, { http_response(aio, error_code.error, result_error); }); @@ -99,6 +108,86 @@ void handle_download_log(nng_aio *aio) nng_aio_finish(aio, 0); } +void handle_log_level(nng_aio *aio) +{ + REST_PROCESS_HTTP_REQUEST_VALIDATE_JWT( + aio, neu_json_update_log_level_req_t, + neu_json_decode_update_log_level_req, { + int rv = 0; + int lev = 0; + + char level[NEU_LOG_LEVEL_LEN] = { 0 }; + char node_name[NEU_NODE_NAME_LEN] = { 0 }; + + strcpy(level, req->level); + if (strcmp(level, "DEBUG") == 0) { + lev = ZLOG_LEVEL_DEBUG; + } else if (strcmp(level, "INFO") == 0) { + lev = ZLOG_LEVEL_INFO; + } else if (strcmp(level, "WARN") == 0) { + lev = ZLOG_LEVEL_WARN; + } else if (strcmp(level, "ERROR") == 0) { + lev = ZLOG_LEVEL_ERROR; + } else if (strcmp(level, "NOTICE") == 0) { + lev = ZLOG_LEVEL_NOTICE; + } else if (strcmp(level, "FATAL") == 0) { + lev = ZLOG_LEVEL_FATAL; + } else { + free(req); + + NEU_JSON_RESPONSE_ERROR(NEU_ERR_LOG_LEVEL_NOT_EXIST, { + http_response(aio, error_code.error, result_error); + }); + + return; + } + + UT_array *log_files = collect_log_files(); + utarray_foreach(log_files, char **, log_file) + { + if (strncmp(*log_file, req->node_name, strlen(*log_file) - 4) == + 0) { + strcpy(node_name, req->node_name); + } + } + + if (strlen(node_name) == 0) { + utarray_free(log_files); + free(req); + + NEU_JSON_RESPONSE_ERROR(NEU_ERR_NODE_NOT_EXIST, { + http_response(aio, error_code.error, result_error); + }); + + return; + } + + zlog_category_t *ct = zlog_get_category(node_name); + + rv = zlog_level_switch(ct, lev); + if (rv != 0) { + utarray_free(log_files); + free(req); + + nlog_error("Modify log level fail"); + NEU_JSON_RESPONSE_ERROR(NEU_ERR_EINTERNAL, { + http_response(aio, error_code.error, result_error); + }); + + return; + } + + utarray_free(log_files); + free(req); + + NEU_JSON_RESPONSE_ERROR(NEU_ERR_SUCCESS, { + http_response(aio, NEU_ERR_SUCCESS, result_error); + }); + + return; + }) +} + // void handle_get_log(nng_aio *aio) // { // int rv = 0; @@ -199,60 +288,51 @@ void handle_download_log(nng_aio *aio) // utarray_free(log_files); // } -// static inline bool ends_with(const char *str, const char *suffix) -// { -// size_t m = strlen(str); -// size_t n = strlen(suffix); -// return m >= n && !strcmp(str + m - n, suffix); -// } +static inline bool ends_with(const char *str, const char *suffix) +{ + size_t m = strlen(str); + size_t n = strlen(suffix); + return m >= n && !strcmp(str + m - n, suffix); +} -// UT_array *collect_log_files() -// { -// DIR *dp = opendir("./logs"); -// if (NULL == dp) { -// nlog_error("open logs directory fail"); -// return NULL; -// } +UT_array *collect_log_files() +{ + DIR *dp = opendir("./logs"); + if (NULL == dp) { + nlog_error("open logs directory fail"); + return NULL; + } -// UT_array *log_files = NULL; -// utarray_new(log_files, &ut_str_icd); + UT_array *log_files = NULL; + utarray_new(log_files, &ut_str_icd); -// struct dirent *de = NULL; -// while (NULL != (de = readdir(dp))) { -// char *name = de->d_name; -// if (ends_with(de->d_name, ".log")) { -// utarray_push_back(log_files, &name); -// } -// } + struct dirent *de = NULL; + while (NULL != (de = readdir(dp))) { + char *name = de->d_name; + if (ends_with(de->d_name, ".log")) { + utarray_push_back(log_files, &name); + } + } -// closedir(dp); + closedir(dp); -// return log_files; -// } + return log_files; +} -// reads the entire named file, allocating storage to receive the data and -// returning the data and the size in the reference arguments. -int read_log_file(const char *log_file, void **datap, size_t *lenp) +int read_file(const char *file_name, void **datap, size_t *lenp) { int rv = 0; FILE * f; struct stat st; size_t len; void * data; - char name[128] = { 0 }; - if ((size_t) snprintf(name, sizeof(name), "./logs/%s.log", log_file) >= - sizeof(name)) { - nlog_error("log_file path overflow:%s", name); - return NEU_ERR_EINTERNAL; - } - - if (stat(name, &st) != 0) { + if (stat(file_name, &st) != 0) { return NEU_ERR_FILE_NOT_EXIST; } - if ((f = fopen(name, "rb")) == NULL) { - nlog_error("open fail: %s", name); + if ((f = fopen(file_name, "rb")) == NULL) { + nlog_error("open fail: %s", file_name); return NEU_ERR_EINTERNAL; } @@ -264,6 +344,7 @@ int read_log_file(const char *log_file, void **datap, size_t *lenp) } if (fread(data, 1, len, f) != len) { rv = errno; + nlog_info("rv = %d", rv); free(data); goto done; } diff --git a/plugins/restful/log_handle.h b/plugins/restful/log_handle.h index fbd14b7e..f81706ff 100644 --- a/plugins/restful/log_handle.h +++ b/plugins/restful/log_handle.h @@ -24,5 +24,6 @@ void handle_get_log(nng_aio *aio); void handle_download_log(nng_aio *aio); +void handle_log_level(nng_aio *aio); #endif diff --git a/src/parser/neu_json_log.c b/src/parser/neu_json_log.c index 70d3a268..d35897f2 100644 --- a/src/parser/neu_json_log.c +++ b/src/parser/neu_json_log.c @@ -28,6 +28,59 @@ #include "json/json.h" #include "neu_json_log.h" +#include "utils/log.h" + +int neu_json_decode_update_log_level_req( + char *buf, neu_json_update_log_level_req_t **result) +{ + int ret = 0; + void *json_obj = neu_json_decode_new(buf); + + neu_json_update_log_level_req_t *req = + calloc(1, sizeof(neu_json_update_log_level_req_t)); + if (req == NULL) { + return -1; + } + + neu_json_elem_t req_elems[] = { { + .name = "level", + .t = NEU_JSON_STR, + }, + { + .name = "node_name", + .t = NEU_JSON_STR, + } }; + + ret = neu_json_decode_by_json(json_obj, NEU_JSON_ELEM_SIZE(req_elems), + req_elems); + if (ret != 0) { + goto decode_fail; + } + + req->level = req_elems[0].v.val_str; + req->node_name = req_elems[1].v.val_str; + + *result = req; + goto decode_exit; + +decode_fail: + free(req); + ret = -1; +decode_exit: + if (json_obj != NULL) { + neu_json_decode_free(json_obj); + } + return ret; +} + +void neu_json_decode_update_log_level_req_free( + neu_json_update_log_level_req_t *req) +{ + free(req->level); + free(req->node_name); + + free(req); +} int neu_json_encode_get_log_resp(void *json_object, void *param) { diff --git a/src/parser/neu_json_log.h b/src/parser/neu_json_log.h index 85a4e192..3ba6caf5 100644 --- a/src/parser/neu_json_log.h +++ b/src/parser/neu_json_log.h @@ -33,6 +33,11 @@ extern "C" { typedef char *neu_json_get_log_resp_row_t; +typedef struct { + char *level; + char *node_name; +} neu_json_update_log_level_req_t; + typedef struct { int64_t page_count; int n_row; @@ -40,6 +45,11 @@ typedef struct { int64_t error; } neu_json_get_log_resp_t; +void neu_json_decode_update_log_level_req_free( + neu_json_update_log_level_req_t *req); +int neu_json_decode_update_log_level_req( + char *buf, neu_json_update_log_level_req_t **result); + int neu_json_encode_get_log_resp(void *json_object, void *param); #ifdef __cplusplus diff --git a/zlog.conf b/zlog.conf index 8af6bab4..66e7dd48 100644 --- a/zlog.conf +++ b/zlog.conf @@ -1,6 +1,5 @@ [global] -reload conf period = 60 file perms = 666 [formats]