src/logsmanagement/rrd_api/rrd_api.h
/** @file rrd_api.h
*/
#ifndef RRD_API_H_
#define RRD_API_H_
#include "daemon/common.h"
#include "../circular_buffer.h"
#include "../helper.h"
struct Chart_meta;
struct Chart_str {
const char *type;
const char *id;
const char *title;
const char *units;
const char *family;
const char *context;
const char *chart_type;
long priority;
int update_every;
};
#include "rrd_api_generic.h"
#include "rrd_api_web_log.h"
#include "rrd_api_kernel.h"
#include "rrd_api_systemd.h"
#include "rrd_api_docker_ev.h"
#include "rrd_api_mqtt.h"
#define CHART_TITLE_TOTAL_COLLECTED_LOGS "Total collected log records"
#define CHART_TITLE_RATE_COLLECTED_LOGS "Rate of collected log records"
#define NETDATA_CHART_PRIO_LOGS_INCR 100 /**< PRIO increment step from one log source to another **/
typedef struct Chart_data_cus {
char *id;
struct chart_data_cus_dim {
char *name;
collected_number val;
unsigned long long *p_counter;
} *dims;
int dims_size;
struct Chart_data_cus *next;
} Chart_data_cus_t ;
struct Chart_meta {
enum log_src_type_t type;
long base_prio;
union {
chart_data_generic_t *chart_data_generic;
chart_data_web_log_t *chart_data_web_log;
chart_data_kernel_t *chart_data_kernel;
chart_data_systemd_t *chart_data_systemd;
chart_data_docker_ev_t *chart_data_docker_ev;
chart_data_mqtt_t *chart_data_mqtt;
};
Chart_data_cus_t *chart_data_cus_arr;
void (*init)(struct File_info *p_file_info);
void (*update)(struct File_info *p_file_info);
};
static inline struct Chart_str lgs_mng_create_chart(const char *type,
const char *id,
const char *title,
const char *units,
const char *family,
const char *context,
const char *chart_type,
long priority,
int update_every){
struct Chart_str cs = {
.type = type,
.id = id,
.title = title,
.units = units,
.family = family ? family : "",
.context = context ? context : "",
.chart_type = chart_type ? chart_type : "",
.priority = priority,
.update_every = update_every
};
printf("CHART '%s.%s' '' '%s' '%s' '%s' '%s' '%s' %ld %d '' '" LOGS_MANAGEMENT_PLUGIN_STR "' ''\n",
cs.type,
cs.id,
cs.title,
cs.units,
cs.family,
cs.context,
cs.chart_type,
cs.priority,
cs.update_every
);
return cs;
}
static inline void lgs_mng_add_dim( const char *id,
const char *algorithm,
collected_number multiplier,
collected_number divisor){
printf("DIMENSION '%s' '' '%s' %lld %lld\n", id, algorithm, multiplier, divisor);
}
static inline void lgs_mng_add_dim_post_init( struct Chart_str *cs,
const char *dim_id,
const char *algorithm,
collected_number multiplier,
collected_number divisor){
printf("CHART '%s.%s' '' '%s' '%s' '%s' '%s' '%s' %ld %d '' '" LOGS_MANAGEMENT_PLUGIN_STR "' ''\n",
cs->type,
cs->id,
cs->title,
cs->units,
cs->family,
cs->context,
cs->chart_type,
cs->priority,
cs->update_every
);
lgs_mng_add_dim(dim_id, algorithm, multiplier, divisor);
}
static inline void lgs_mng_update_chart_begin(const char *type, const char *id){
printf("BEGIN '%s.%s'\n", type, id);
}
static inline void lgs_mng_update_chart_set(const char *id, collected_number val){
printf("SET '%s' = %lld\n", id, val);
}
static inline void lgs_mng_update_chart_end(time_t sec){
printf("END %" PRId64 " 0 1\n", sec);
}
#define lgs_mng_do_num_of_logs_charts_init(p_file_info, chart_prio) do { \
\
/* Number of collected logs total - initialise */ \
if(p_file_info->parser_config->chart_config & CHART_COLLECTED_LOGS_TOTAL){ \
lgs_mng_create_chart( \
(char *) p_file_info->chartname /* type */ \
, "collected_logs_total" /* id */ \
, CHART_TITLE_TOTAL_COLLECTED_LOGS /* title */ \
, "log records" /* units */ \
, "collected_logs" /* family */ \
, NULL /* context */ \
, RRDSET_TYPE_AREA_NAME /* chart_type */ \
, ++chart_prio /* priority */ \
, p_file_info->update_every /* update_every */ \
); \
lgs_mng_add_dim("total records", RRD_ALGORITHM_ABSOLUTE_NAME, 1, 1); \
} \
\
/* Number of collected logs rate - initialise */ \
if(p_file_info->parser_config->chart_config & CHART_COLLECTED_LOGS_RATE){ \
lgs_mng_create_chart( \
(char *) p_file_info->chartname /* type */ \
, "collected_logs_rate" /* id */ \
, CHART_TITLE_RATE_COLLECTED_LOGS /* title */ \
, "log records" /* units */ \
, "collected_logs" /* family */ \
, NULL /* context */ \
, RRDSET_TYPE_LINE_NAME /* chart_type */ \
, ++chart_prio /* priority */ \
, p_file_info->update_every /* update_every */ \
); \
lgs_mng_add_dim("records", RRD_ALGORITHM_INCREMENTAL_NAME, 1, 1); \
} \
\
} while(0)
#define lgs_mng_do_num_of_logs_charts_update(p_file_info, lag_in_sec, chart_data) do { \
\
/* Number of collected logs total - update previous values */ \
if(p_file_info->parser_config->chart_config & CHART_COLLECTED_LOGS_TOTAL){ \
for(time_t sec = p_file_info->parser_metrics->last_update - lag_in_sec; \
sec < p_file_info->parser_metrics->last_update; \
sec++){ \
lgs_mng_update_chart_begin(p_file_info->chartname, "collected_logs_total"); \
lgs_mng_update_chart_set("total records", chart_data->num_lines); \
lgs_mng_update_chart_end(sec); \
} \
} \
\
/* Number of collected logs rate - update previous values */ \
if(p_file_info->parser_config->chart_config & CHART_COLLECTED_LOGS_RATE){ \
for(time_t sec = p_file_info->parser_metrics->last_update - lag_in_sec; \
sec < p_file_info->parser_metrics->last_update; \
sec++){ \
lgs_mng_update_chart_begin(p_file_info->chartname, "collected_logs_rate"); \
lgs_mng_update_chart_set("records", chart_data->num_lines); \
lgs_mng_update_chart_end(sec); \
} \
} \
\
chart_data->num_lines = p_file_info->parser_metrics->num_lines; \
\
/* Number of collected logs total - update */ \
if(p_file_info->parser_config->chart_config & CHART_COLLECTED_LOGS_TOTAL){ \
lgs_mng_update_chart_begin( (char *) p_file_info->chartname, "collected_logs_total"); \
lgs_mng_update_chart_set("total records", chart_data->num_lines); \
lgs_mng_update_chart_end(p_file_info->parser_metrics->last_update); \
} \
\
/* Number of collected logs rate - update */ \
if(p_file_info->parser_config->chart_config & CHART_COLLECTED_LOGS_RATE){ \
lgs_mng_update_chart_begin( (char *) p_file_info->chartname, "collected_logs_rate"); \
lgs_mng_update_chart_set("records", chart_data->num_lines); \
lgs_mng_update_chart_end(p_file_info->parser_metrics->last_update); \
} \
} while(0)
#define lgs_mng_do_custom_charts_init(p_file_info) do { \
\
for(int cus_off = 0; p_file_info->parser_cus_config[cus_off]; cus_off++){ \
\
Chart_data_cus_t *cus; \
Chart_data_cus_t **p_cus = &p_file_info->chart_meta->chart_data_cus_arr; \
\
for(cus = p_file_info->chart_meta->chart_data_cus_arr; \
cus; \
cus = cus->next){ \
\
if(!strcmp(cus->id, p_file_info->parser_cus_config[cus_off]->chartname)) \
break; \
\
p_cus = &(cus->next); \
} \
\
if(!cus){ \
cus = callocz(1, sizeof(Chart_data_cus_t)); \
*p_cus = cus; \
\
cus->id = p_file_info->parser_cus_config[cus_off]->chartname; \
\
lgs_mng_create_chart( \
(char *) p_file_info->chartname /* type */ \
, cus->id /* id */ \
, cus->id /* title */ \
, "matches" /* units */ \
, "custom_charts" /* family */ \
, NULL /* context */ \
, RRDSET_TYPE_AREA_NAME /* chart_type */ \
, p_file_info->chart_meta->base_prio + 1000 + cus_off /* priority */ \
, p_file_info->update_every /* update_every */ \
); \
} \
\
cus->dims = reallocz(cus->dims, ++cus->dims_size * sizeof(struct chart_data_cus_dim)); \
cus->dims[cus->dims_size - 1].name = \
p_file_info->parser_cus_config[cus_off]->regex_name; \
cus->dims[cus->dims_size - 1].val = 0; \
cus->dims[cus->dims_size - 1].p_counter = \
&p_file_info->parser_metrics->parser_cus[cus_off]->count; \
\
lgs_mng_add_dim(cus->dims[cus->dims_size - 1].name, \
RRD_ALGORITHM_INCREMENTAL_NAME, 1, 1); \
\
} \
} while(0)
#define lgs_mng_do_custom_charts_update(p_file_info, lag_in_sec) do { \
\
for(time_t sec = p_file_info->parser_metrics->last_update - lag_in_sec; \
sec < p_file_info->parser_metrics->last_update; \
sec++){ \
\
for(Chart_data_cus_t *cus = p_file_info->chart_meta->chart_data_cus_arr; \
cus; \
cus = cus->next){ \
\
lgs_mng_update_chart_begin(p_file_info->chartname, cus->id); \
\
for(int d_idx = 0; d_idx < cus->dims_size; d_idx++) \
lgs_mng_update_chart_set(cus->dims[d_idx].name, cus->dims[d_idx].val); \
\
lgs_mng_update_chart_end(sec); \
} \
\
} \
\
for(Chart_data_cus_t *cus = p_file_info->chart_meta->chart_data_cus_arr; \
cus; \
cus = cus->next){ \
\
lgs_mng_update_chart_begin(p_file_info->chartname, cus->id); \
\
for(int d_idx = 0; d_idx < cus->dims_size; d_idx++){ \
\
cus->dims[d_idx].val += *(cus->dims[d_idx].p_counter); \
*(cus->dims[d_idx].p_counter) = 0; \
\
lgs_mng_update_chart_set(cus->dims[d_idx].name, cus->dims[d_idx].val); \
} \
\
lgs_mng_update_chart_end(p_file_info->parser_metrics->last_update); \
} \
} while(0)
#endif // RRD_API_H_