Skip to content

Commit

Permalink
samples: net: prometheus: Add support for network statistics
Browse files Browse the repository at this point in the history
Add separate URL handling for network statistics.

Signed-off-by: Jukka Rissanen <[email protected]>
  • Loading branch information
jukkar authored and nashif committed Nov 26, 2024
1 parent 99abfda commit 2bc7b07
Show file tree
Hide file tree
Showing 4 changed files with 111 additions and 2 deletions.
1 change: 1 addition & 0 deletions samples/net/prometheus/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ endif()


target_sources(app PRIVATE src/main.c)
target_sources_ifdef(CONFIG_NET_STATISTICS_VIA_PROMETHEUS app PRIVATE src/stats.c)

set(gen_dir ${ZEPHYR_BINARY_DIR}/include/generated/)

Expand Down
4 changes: 4 additions & 0 deletions samples/net/prometheus/prj.conf
Original file line number Diff line number Diff line change
Expand Up @@ -84,3 +84,7 @@ CONFIG_NET_SOCKETS_LOG_LEVEL_DBG=n
CONFIG_NET_HTTP_LOG_LEVEL_DBG=n
CONFIG_NET_IPV6_LOG_LEVEL_DBG=n
CONFIG_NET_IPV6_ND_LOG_LEVEL_DBG=n

# Network statistics Prometheus support
CONFIG_NET_STATISTICS_VIA_PROMETHEUS=y
CONFIG_NET_STATISTICS=y
10 changes: 8 additions & 2 deletions samples/net/prometheus/src/main.c
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,9 @@
#include <zephyr/logging/log.h>
LOG_MODULE_REGISTER(main, LOG_LEVEL_DBG);

struct {
extern int init_stats(struct prometheus_counter *counter);

struct app_context {

struct prometheus_collector *collector;

Expand Down Expand Up @@ -88,7 +90,7 @@ HTTP_RESOURCE_DEFINE(dyn_resource, test_http_service, "/metrics", &dyn_resource_
#if defined(CONFIG_NET_SAMPLE_HTTPS_SERVICE)
#include "certificate.h"

static const sec_tag_t sec_tag_list_verify_none[] = {
const sec_tag_t sec_tag_list_verify_none[] = {
HTTP_SERVER_CERTIFICATE_TAG,
#if defined(CONFIG_MBEDTLS_KEY_EXCHANGE_PSK_ENABLED)
PSK_TAG,
Expand Down Expand Up @@ -160,6 +162,10 @@ int main(void)

prometheus_collector_register_metric(prom_context.collector, &prom_context.counter->base);

#if defined(CONFIG_NET_STATISTICS_VIA_PROMETHEUS)
(void)init_stats(prom_context.counter);
#endif

setup_tls();

http_server_start();
Expand Down
98 changes: 98 additions & 0 deletions samples/net/prometheus/src/stats.c
Original file line number Diff line number Diff line change
@@ -0,0 +1,98 @@
/*
* Copyright (c) 2024 Nordic Semiconductor
*
* SPDX-License-Identifier: Apache-2.0
*/

#include <zephyr/logging/log.h>
LOG_MODULE_DECLARE(main, LOG_LEVEL_DBG);

#include <zephyr/kernel.h>
#include <zephyr/kernel.h>
#include <zephyr/net/tls_credentials.h>
#include <zephyr/net/http/server.h>
#include <zephyr/net/http/service.h>
#include <zephyr/net/net_if.h>
#include <zephyr/net/net_ip.h>

#include <zephyr/net/prometheus/formatter.h>
#include <zephyr/net/prometheus/collector.h>
#include <zephyr/net/prometheus/counter.h>
#include <zephyr/net/prometheus/gauge.h>
#include <zephyr/net/prometheus/histogram.h>
#include <zephyr/net/prometheus/summary.h>

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

extern struct http_service_desc test_http_service;

static struct prometheus_counter *http_request_counter;
static struct prometheus_collector *stats_collector;
static struct prometheus_collector_walk_context walk_ctx;

static int stats_handler(struct http_client_ctx *client, enum http_data_status status,
uint8_t *buffer, size_t len, struct http_response_ctx *response_ctx,
void *user_data)
{
int ret;
static uint8_t prom_buffer[1024];

if (status == HTTP_SERVER_DATA_FINAL) {

/* incrase counter per request */
prometheus_counter_inc(http_request_counter);

(void)memset(prom_buffer, 0, sizeof(prom_buffer));

ret = prometheus_collector_walk_metrics(user_data,
prom_buffer,
sizeof(prom_buffer));
if (ret < 0 && ret != -EAGAIN) {
LOG_ERR("Cannot format exposition data (%d)", ret);
return ret;
}

response_ctx->body = prom_buffer;
response_ctx->body_len = strlen(prom_buffer);

if (ret == 0) {
response_ctx->final_chunk = true;
ret = prometheus_collector_walk_init(&walk_ctx, stats_collector);
if (ret < 0) {
LOG_ERR("Cannot initialize walk context (%d)", ret);
}
}
}

return 0;
}

struct http_resource_detail_dynamic stats_resource_detail = {
.common = {
.type = HTTP_RESOURCE_TYPE_DYNAMIC,
.bitmask_of_supported_http_methods = BIT(HTTP_GET),
.content_type = "text/plain",
},
.cb = stats_handler,
.user_data = &walk_ctx,
};

HTTP_RESOURCE_DEFINE(stats_resource, test_http_service, "/statistics", &stats_resource_detail);

int init_stats(struct prometheus_counter *counter)
{
/* Use a collector from default network interface */
stats_collector = net_if_get_default()->collector;
if (stats_collector == NULL) {
LOG_ERR("Cannot get collector from default network interface");
return -EINVAL;
}

(void)prometheus_collector_walk_init(&walk_ctx, stats_collector);

http_request_counter = counter;

return 0;
}

0 comments on commit 2bc7b07

Please sign in to comment.