From 8fe0950511ca7983096c470232bd241a1052e3e0 Mon Sep 17 00:00:00 2001 From: Aurelien DARRAGON Date: Wed, 18 Mar 2026 11:08:25 +0100 Subject: [PATCH] MINOR: promex: export "haproxy_sticktable_local_updates" metric haproxy_sticktable_local_updates corresponds to the table->localupdate counter, which is used internally by the peers protocol to identify update messages in order to send and ack them among peers. Here we decide to expose this information, as it is already the case in "show peers" output, because it turns out that this value, which is cumulative and grows in sync with the number of updates triggered on the table due to changes initiated by the current process, can be used to compute the update rate of the table. Computing the update rate of the table (from the process point of view, ie: updates sent by the process and not those received by the process), can be a great load indicator in order to properly scale the infrastructure that is intended to handle the table updates. Note that there is a pitfall, which is that the value will eventually wrap since it is stored using unsigned 32bits integer. Scripts or system making use of this value must take wrapping into account between two readings to properly compute the effective number of updates that were performed between two readings. Also, they must ensure that the "polling" rate between readings is small enough so that the value cannot wrap behind their back. --- addons/promex/README | 1 + src/stick_table.c | 16 ++++++++++++++++ 2 files changed, 17 insertions(+) diff --git a/addons/promex/README b/addons/promex/README index 61d99de15..4d52c1d1a 100644 --- a/addons/promex/README +++ b/addons/promex/README @@ -407,6 +407,7 @@ listed below. Metrics from extra counters are not listed. +----------------------------------------------------+ | haproxy_sticktable_size | | haproxy_sticktable_used | +| haproxy_sticktable_local_updates | +----------------------------------------------------+ * Resolvers metrics diff --git a/src/stick_table.c b/src/stick_table.c index ff3b552da..c36a91b9d 100644 --- a/src/stick_table.c +++ b/src/stick_table.c @@ -53,6 +53,7 @@ enum sticktable_field { STICKTABLE_SIZE = 0, STICKTABLE_USED, + STICKTABLE_LOCAL_UPDATES, /* must always be the last one */ STICKTABLE_TOTAL_FIELDS }; @@ -6310,6 +6311,10 @@ static int stk_promex_metric_info(unsigned int id, struct promex_metric *metric, *metric = (struct promex_metric){ .n = ist("used"), .type = PROMEX_MT_GAUGE, .flags = PROMEX_FL_MODULE_METRIC }; *desc = ist("Number of entries used in this stick table."); break; + case STICKTABLE_LOCAL_UPDATES: + *metric = (struct promex_metric){ .n = ist("local_updates"), .type = PROMEX_MT_GAUGE, .flags = PROMEX_FL_MODULE_METRIC }; + *desc = ist("Cumulative number of updates on the stick table initiated by the local process. Please note that this value will eventually wrap after 4294967295 since it is stored using unsigned int (uint32). As this metric is often used to compute the update rate of a given table between two queries, wrapping must be taken into account and the time between 2 queries must not exceed the theorical time needed for this value to wrap."); + break; default: return -1; } @@ -6347,6 +6352,17 @@ static int stk_promex_fill_ts(void *unused, void *metric_ctx, unsigned int id, s case STICKTABLE_USED: *field = mkf_u32(FN_GAUGE, t->current); break; + case STICKTABLE_LOCAL_UPDATES: + /* localupdate is meant to be guarded by updt_lock, but + * here we don't care about the most up-to-date value, nor + * need to read the value consistently with another table-related + * one, all we really want is a rough reading of the current + * number of local updates performed on the table, thus we hope + * the value is read as an atomic operation (which should be + * the case for uint32 on most platforms) + */ + *field = mkf_u32(FN_GAUGE, t->localupdate); + break; default: return -1; } -- 2.47.3