[Asterisk-code-review] res statsd: Add functions that support variable arguments (asterisk[master])

Matt Jordan asteriskteam at digium.com
Mon Nov 23 08:43:35 CST 2015


Matt Jordan has submitted this change and it was merged.

Change subject: res_statsd: Add functions that support variable arguments
......................................................................


res_statsd: Add functions that support variable arguments

Often, the metric names of statistics we are generating for StatsD have some
dynamic component to them. This can be the name of a particular resource, or
some internal status label in Asterisk. With the current set of functions,
callers of the statsd API must first build the metric name themselves, then
pass this to the API functions. This results in a large amount of boilerplate
code and usage of either fixed length static buffers or dynamic memory
allocation, neither of which is desireable.

This patch adds two new functions to the StatsD API that support a printf
style format specifier for constructing the metric name. A dynamic string,
allocated in threadstorage, is used to build the metric name. This eases
the burden on users of the StatsD API.

Change-Id: If533c72d1afa26d807508ea48b4d8c7b32f414ea
---
M include/asterisk/statsd.h
M res/res_statsd.c
2 files changed, 94 insertions(+), 2 deletions(-)

Approvals:
  Anonymous Coward #1000019: Verified
  Matt Jordan: Looks good to me, approved
  Joshua Colp: Looks good to me, but someone else must approve



diff --git a/include/asterisk/statsd.h b/include/asterisk/statsd.h
index a04407f..c4ecce8 100644
--- a/include/asterisk/statsd.h
+++ b/include/asterisk/statsd.h
@@ -57,9 +57,31 @@
 
 /*!
  * \brief Send a stat to the configured statsd server.
+ * \since 13.7.0
  *
- * The is the most flexible function for sending a message to the statsd server,
- * but also the least easy to use. See ast_statsd_log() or
+ * This is the most flexible function for sending a message to the statsd
+ * server. In addition to allowing the string value and sample rate to be specified,
+ * the metric_name can be formed as a printf style string with variable
+ * arguments.
+ *
+ * \param metric_name Format string (UTF-8) specifying the name of the metric.
+ * \param metric_type Type of metric to send.
+ * \param value Value to send.
+ * \param sample_rate Percentage of samples to send.
+ *
+ * Example Usage:
+ * \code
+ *     ast_statsd_log_string_va(AST_STATSD_GUAGE, "+1", 1.0, "endpoints.states.%s", state_name);
+ * \endcode
+ */
+AST_OPTIONAL_API_ATTR(void, format(printf, 1, 5), ast_statsd_log_string_va,
+	(const char *metric_name, const char *metric_type, const char *value, double sample_rate, ...), {});
+
+/*!
+ * \brief Send a stat to the configured statsd server.
+ *
+ * The is nearly the most flexible function for sending a message to the statsd
+ * server, but also the least easy to use. See ast_statsd_log() or
  * ast_statsd_log_sample() for a slightly more convenient interface.
  *
  * \param metric_name String (UTF-8) name of the metric.
@@ -73,6 +95,28 @@
 
 /*!
  * \brief Send a stat to the configured statsd server.
+ * \since 13.7.0
+ *
+ * This is the most flexible function for sending a message to the statsd
+ * server. In addition to allowing the value and sample rate to be specified,
+ * the metric_name can be formed as a printf style string with variable
+ * arguments.
+ *
+ * \param metric_name Format string (UTF-8) specifying the name of the metric.
+ * \param metric_type Type of metric to send.
+ * \param value Value to send.
+ * \param sample_rate Percentage of samples to send.
+ *
+ * Example Usage:
+ * \code
+ *     ast_statsd_log_full_va(AST_STATSD_TIMER, rtt, 1.0, "endpoint.%s.rtt", endpoint_name);
+ * \endcode
+ */
+AST_OPTIONAL_API_ATTR(void, format(printf, 1, 5), ast_statsd_log_full_va,
+	(const char *metric_name, const char *metric_type, intmax_t value, double sample_rate, ...), {});
+
+/*!
+ * \brief Send a stat to the configured statsd server.
  * \param metric_name String (UTF-8) name of the metric.
  * \param metric_type Type of metric to send.
  * \param value Value to send.
diff --git a/res/res_statsd.c b/res/res_statsd.c
index 8bf74db..f3a64e0 100644
--- a/res/res_statsd.c
+++ b/res/res_statsd.c
@@ -160,6 +160,54 @@
 
 }
 
+AST_THREADSTORAGE(statsd_buf);
+
+void AST_OPTIONAL_API_NAME(ast_statsd_log_string_va)(const char *metric_name,
+	const char *metric_type, const char *value, double sample_rate, ...)
+{
+	struct ast_str *buf;
+	va_list ap;
+	int res;
+
+	buf = ast_str_thread_get(&statsd_buf, 128);
+	if (!buf) {
+		return;
+	}
+
+	va_start(ap, sample_rate);
+	res = ast_str_set_va(&buf, 0, metric_name, ap);
+	va_end(ap);
+
+	if (res == AST_DYNSTR_BUILD_FAILED) {
+		return;
+	}
+
+	ast_statsd_log_string(ast_str_buffer(buf), metric_type, value, sample_rate);
+}
+
+void AST_OPTIONAL_API_NAME(ast_statsd_log_full_va)(const char *metric_name,
+	const char *metric_type, intmax_t value, double sample_rate, ...)
+{
+	struct ast_str *buf;
+	va_list ap;
+	int res;
+
+	buf = ast_str_thread_get(&statsd_buf, 128);
+	if (!buf) {
+		return;
+	}
+
+	va_start(ap, sample_rate);
+	res = ast_str_set_va(&buf, 0, metric_name, ap);
+	va_end(ap);
+
+	if (res == AST_DYNSTR_BUILD_FAILED) {
+		return;
+	}
+
+	ast_statsd_log_full(ast_str_buffer(buf), metric_type, value, sample_rate);
+}
+
 void AST_OPTIONAL_API_NAME(ast_statsd_log)(const char *metric_name,
 	const char *metric_type, intmax_t value)
 {

-- 
To view, visit https://gerrit.asterisk.org/1689
To unsubscribe, visit https://gerrit.asterisk.org/settings

Gerrit-MessageType: merged
Gerrit-Change-Id: If533c72d1afa26d807508ea48b4d8c7b32f414ea
Gerrit-PatchSet: 1
Gerrit-Project: asterisk
Gerrit-Branch: master
Gerrit-Owner: Matt Jordan <mjordan at digium.com>
Gerrit-Reviewer: Anonymous Coward #1000019
Gerrit-Reviewer: Joshua Colp <jcolp at digium.com>
Gerrit-Reviewer: Matt Jordan <mjordan at digium.com>



More information about the asterisk-code-review mailing list