MINOR: stats: hide some columns in output

Metric style stats can be automatically calculate since the introduction
of metric_generate() when using "struct stat_col" as input. This would
allow to centralize statistics generation. However, some stats are not
outputted under specific condition. For example, health check failures
on a server are only reported if checks are active.

To support this, define a new function metric_hide(). It is called by
metric_generate(). If true, it will skip metric calcuation and return an
empty field value instead. This allows to define "stat_col" metrics and
calculate them with metric_generate() but hiding them under certain
circumstances.
This commit is contained in:
Amaury Denoyelle 2024-04-17 11:12:27 +02:00
parent a7810b7be6
commit 168301411d

View File

@ -637,6 +637,38 @@ int stats_dump_one_line(const struct field *line, size_t stats_count,
return ret;
}
/* Returns true if column at <idx> should be hidden.
* This may depends on various <objt> internal status.
*/
static int stcol_hide(enum stat_idx_px idx, enum obj_type *objt)
{
struct proxy *px __maybe_unused;
struct server *srv = NULL;
struct listener *li = NULL;
switch (obj_type(objt)) {
case OBJ_TYPE_PROXY:
px = __objt_proxy(objt);
break;
case OBJ_TYPE_SERVER:
srv = __objt_server(objt);
px = srv->proxy;
break;
case OBJ_TYPE_LISTENER:
li = __objt_listener(objt);
px = li->bind_conf->frontend;
break;
default:
ABORT_NOW();
return 0;
}
switch (idx) {
default:
return 0;
}
}
/* Generate if possible a metric value from <col>. <cap> must be set to one of
* STATS_PX_CAP_* values to check if the metric is available for this object
* type. Metric value will be extracted from <counters>.
@ -644,6 +676,7 @@ int stats_dump_one_line(const struct field *line, size_t stats_count,
* Returns a field value or an empty one if cap not compatible.
*/
static struct field me_generate_field(const struct stat_col *col,
enum stat_idx_px idx, enum obj_type *objt,
const void *counters, uint8_t cap)
{
struct field value;
@ -669,6 +702,10 @@ static struct field me_generate_field(const struct stat_col *col,
if (!(col->cap & cap))
return (struct field){ .type = FF_EMPTY };
/* Check if metric should be hidden in output. */
if (stcol_hide(idx, objt))
return (struct field){ .type = FF_EMPTY };
switch (stcol_format(col)) {
case FF_U64:
value = mkf_u64(stcol_nature(col), *(uint64_t *)counter);
@ -700,7 +737,8 @@ int stats_fill_fe_line(struct proxy *px, struct field *line, int len,
struct field field = { 0 };
if (stcol_is_generic(col)) {
field = me_generate_field(col, &px->fe_counters, STATS_PX_CAP_FE);
field = me_generate_field(col, i, &px->obj_type,
&px->fe_counters, STATS_PX_CAP_FE);
}
else {
switch (i) {
@ -976,7 +1014,8 @@ int stats_fill_li_line(struct proxy *px, struct listener *l, int flags,
struct field field = { 0 };
if (stcol_is_generic(col)) {
field = me_generate_field(col, l->counters, STATS_PX_CAP_LI);
field = me_generate_field(col, i, &l->obj_type,
l->counters, STATS_PX_CAP_LI);
}
else {
switch (i) {
@ -1257,7 +1296,8 @@ int stats_fill_sv_line(struct proxy *px, struct server *sv, int flags,
struct field field = { 0 };
if (stcol_is_generic(col)) {
field = me_generate_field(col, &sv->counters, STATS_PX_CAP_SRV);
field = me_generate_field(col, i, &sv->obj_type,
&sv->counters, STATS_PX_CAP_SRV);
}
else {
switch (i) {
@ -1723,7 +1763,8 @@ int stats_fill_be_line(struct proxy *px, int flags, struct field *line, int len,
struct field field = { 0 };
if (stcol_is_generic(col)) {
field = me_generate_field(col, &px->be_counters, STATS_PX_CAP_BE);
field = me_generate_field(col, i, &px->obj_type,
&px->be_counters, STATS_PX_CAP_BE);
}
else {
switch (i) {