This chapter describes how to add statistics to your plugins. The Traffic Server statistics API functions add your plugin’s statistics so you can view your plugin statistics as you would any other Traffic Server statistic, using traffic_ctl or the TSRecordDump() API.

A statistic is an opaque object referred to by an integral handle returned by TSStatCreate(). Only integer statistics are supported, so the type argument to TSStatCreate() must be TS_RECORDDATATYPE_INT.

The following example shows how to add custom statistics to your plugin. Typically, you would attempt to find the statistic by name before creating is. This technique is useful if you want to increment a statistic from multiple plugins. Once you have a handle to the statistic, set the value with TSStatIntSet(), and increment it with TSStatIntIncrement() or TSStatIntDecrement().

#include <ts/ts.h>
#include <cinttypes>
#include <ctime>

#define PLUGIN_NAME "statistics"

void
TSPluginInit(int /* argc */, const char * /* argv */ [])
{
TSPluginRegistrationInfo info;

info.plugin_name   = PLUGIN_NAME;
info.vendor_name   = "Apache Software Foundation";
info.support_email = "dev@trafficserver.apache.org";

int id;
const char name[] = "plugin." PLUGIN_NAME ".now";

if (TSStatFindName(name, &id) == TS_ERROR) {
id = TSStatCreate(name, TS_RECORDDATATYPE_INT, TS_STAT_NON_PERSISTENT, TS_STAT_SYNC_SUM);
if (id == TS_ERROR) {
TSError("[%s] failed to register '%s'", PLUGIN_NAME, name);
return;
}
}

TSError("[%s] %s registered with id %d", PLUGIN_NAME, name, id);

#if DEBUG
TSReleaseAssert(id != TS_ERROR);
#endif

// Set an initial value for our statistic.
TSStatIntSet(id, time(nullptr));

// Increment the statistic as time passes.
TSStatIntIncrement(id, 1);

TSDebug(PLUGIN_NAME, "%s is set to %" PRId64, name, TSStatIntGet(id));
TSReleaseAssert(TSPluginRegister(&info) == TS_SUCCESS);
}


If this plugin is loaded, then the statistic can be accessed with

traffic_ctl metric show plugin.statistics.now


The name of the statistic can be any string but it is best to use the convention of starting it with the literal tag “plugin” followed the plugin name followed by statistic specific tags. This avoids any name collisions and also makes finding all statistics for a plugin simple. For instance, the “redirect_1” example plugin creates a number of statistics. These can be listed with the command

traffic_ctl metric match plugin.redirect_1..*


The “redirect_1” example plugin has a more realistic handling of statistics with regard to updating and is worth examining.

TSStatFindName() can be used to check if the statistic already exists or to provide a generic interface to statistics. In the example above you can see the code first verifies the statistic does not already exist before creating it. In general, though, this should be handled by not executing the registration code twice. If done only from plugin initialization then this will be the case. It can be the case however that statistics are based on configuration data which may be reloaded and the check must be done. This is more likely with remap plugins.