Page 49 - MSDN Magazine, May 2017
P. 49
Figure 5 Loop Processing Telemetry Output in Application Insights
Fixed-rate sampling reduces the volume of per-node telemetry. For example, you might want to collect only 20 percent of all tele- metry from each node.
Adaptive sampling automati- cally adjusts the volume of per-node telemetry. For example, you might want to decrease collection when the load is greater than 5 eps/node.
Note: There’s, also ingestion sampling that discards telemetry, which arrives from your app at the service ingestion endpoint. We aren’t going to cover this technique in this article, but documentation can be found at bit.ly/2mNiDHS.
Both sampling telemetry pro- cessors use a common algorithm that lets you mix and match those
this approach is that your business is far more dynamic and it’s not always possible to know what metrics you might need in advance. The Application Insights SDK addresses this issue by providing a balance between aggregated and raw telemetry—it aggregates key application performance indicators and sends sampled raw application telem- etry. This sampling approach lets the SDK minimize the overhead of raw data collection and increases the ROI of the collected data.
Sampling
There are two out-of-the-box sampling telemetry processors provided by the Application Insights SDK—fixed sampling and adaptive sampling (bit.ly/2mNiDHS).
Figure 6 Telemetry Processor for Item Size Calculation
processors without affecting statistical accuracy of the data. In order to decide if the telemetry item has to be sampled in or out, the SDK uses a stateless hash function and compares returned value with configuration ratio. It means that regardless of which thread,
Figure 7 Building a Telemetry Processing Chain with Items Sampling
// Initialize state for the telemetry size calculation var collectedItems = 0;
var sentItems = 0;
// Build telemetry processing pipeline configuration.TelemetryProcessorChainBuilder
// This telemetry processor will be executed
// first for all telemetry items to calculate the size and # of items .Use((next) => { return new SizeCalculatorTelemetryProcessor(next,
size => Interlocked.Add(ref collectedItems, size)); })
// This is a standard fixed sampling processor that'll let only 10% .Use((next) =>
{
return new SamplingTelemetryProcessor(next) {
IncludedTypes = "Dependency",
SamplingPercentage = 10, };
})
// This is a standard adaptive sampling telemetry processor
// that will sample in/out any telemetry item it receives .Use((next) =>
{
return new AdaptiveSamplingTelemetryProcessor(next) {
ExcludedTypes = "Event", // Exclude custom events from being sampled MaxTelemetryItemsPerSecond = 1, // Default: 5 calls/sec SamplingPercentageIncreaseTimeout =
TimeSpan.FromSeconds(1), // Default: 2 min SamplingPercentageDecreaseTimeout =
TimeSpan.FromSeconds(1), // Default: 30 sec EvaluationInterval = TimeSpan.FromSeconds(1), // Default: 15 sec InitialSamplingPercentage = 25, // Default: 100%
}; })
// This telemetry processor will be executed ONLY when telemetry is sampled in .Use((next) => { return new SizeCalculatorTelemetryProcessor(next,
size => Interlocked.Add(ref sentItems, size)); }) .Build();
internal class SizeCalculatorTelemetryProcessor : ITelemetryProcessor {
private ITelemetryProcessor next; private Action<int> onAddSize;
public SizeCalculatorTelemetryProcessor(ITelemetryProcessor next, Action<int> onAddSize)
{
this.next = next; this.onAddSize = onAddSize;
}
public void Process(ITelemetry item) {
try {
item.Sanitize();
byte[] content =
JsonSerializer.Serialize(new List<ITelemetry>() { item }, false);
int size = content.Length;
string json = Encoding.Default.GetString(content);
this.onAddSize(size); }
finally {
this.next.Process(item); }
} }
msdnmagazine.com
May 2017 43