Skip to content

Commit 3959519

Browse files
author
Ignacio Bonafonte
authored
Merge branch 'main' into main
2 parents b35d05c + 7fb8509 commit 3959519

File tree

3 files changed

+66
-2
lines changed

3 files changed

+66
-2
lines changed

Examples/Prometheus Sample/main.swift

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -37,6 +37,9 @@ var meter = meterProvider.get(instrumentationName: "MyMeter")
3737
var testCounter = meter.createIntCounter(name: "MyCounter")
3838
var testMeasure = meter.createIntMeasure(name: "MyMeasure")
3939

40+
let boundaries: Array<Int> = [5, 10, 25]
41+
var testHistogram = meter.createIntHistogram(name: "MyHistogram", explicitBoundaries: boundaries, absolute: true)
42+
4043
var testObserver = meter.createIntObserver(name: "MyObservation") { observer in
4144
var taskInfo = mach_task_basic_info()
4245
var count = mach_msg_type_number_t(MemoryLayout<mach_task_basic_info>.size) / 4
@@ -60,6 +63,11 @@ while counter < 3000 {
6063
testMeasure.record(value: 500, labelset: meter.getLabelSet(labels: labels1))
6164
testMeasure.record(value: 5, labelset: meter.getLabelSet(labels: labels1))
6265
testMeasure.record(value: 750, labelset: meter.getLabelSet(labels: labels1))
66+
67+
testHistogram.record(value: 8, labelset: meter.getLabelSet(labels: labels1))
68+
testHistogram.record(value: 20, labelset: meter.getLabelSet(labels: labels1))
69+
testHistogram.record(value: 30, labelset: meter.getLabelSet(labels: labels1))
70+
6371
counter += 1
6472
sleep(1)
6573
}

Sources/Exporters/Prometheus/PrometheusExporterExtensions.swift

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,11 @@ public enum PrometheusExporterExtensions {
1414
static let prometheusSummaryQuantileLabelName = "quantile"
1515
static let prometheusSummaryQuantileLabelValueForMin = "0"
1616
static let prometheusSummaryQuantileLabelValueForMax = "1"
17+
static let prometheusHistogramType = "histogram"
18+
static let prometheusHistogramSumPostFix = "_sum"
19+
static let prometheusHistogramCountPostFix = "_count"
20+
static let prometheusHistogramBucketPostFix = "_bucket"
21+
static let prometheusHistogramLeLabelName = "le"
1722

1823
static func writeMetricsCollection(exporter: PrometheusExporter) -> String {
1924
var output = ""
@@ -45,8 +50,20 @@ public enum PrometheusExporterExtensions {
4550
let min = summary.min
4651
let max = summary.max
4752
output += PrometheusExporterExtensions.writeSummary(prometheusMetric: prometheusMetric, timeStamp: now, labels: labels, metricName: metric.name, sum: Double(sum), count: count, min: Double(min), max: Double(max))
48-
case .intHistogram, .doubleHistogram:
49-
break
53+
case .intHistogram:
54+
let histogram = metricData as! HistogramData<Int>
55+
let count = histogram.count
56+
let sum = histogram.sum
57+
let bucketsBoundaries = histogram.buckets.boundaries.map{Double($0)}
58+
let bucketsCounts = histogram.buckets.counts
59+
output += PrometheusExporterExtensions.writeHistogram(prometheusMetric: prometheusMetric, timeStamp: now, labels: labels, metricName: metric.name, sum: Double(sum), count: count, bucketsBoundaries: bucketsBoundaries, bucketsCounts: bucketsCounts)
60+
case .doubleHistogram:
61+
let histogram = metricData as! HistogramData<Double>
62+
let count = histogram.count
63+
let sum = histogram.sum
64+
let bucketsBoundaries = histogram.buckets.boundaries
65+
let bucketsCounts = histogram.buckets.counts
66+
output += PrometheusExporterExtensions.writeHistogram(prometheusMetric: prometheusMetric, timeStamp: now, labels: labels, metricName: metric.name, sum: Double(sum), count: count, bucketsBoundaries: bucketsBoundaries, bucketsCounts: bucketsCounts)
5067
}
5168
}
5269
}
@@ -79,4 +96,24 @@ public enum PrometheusExporterExtensions {
7996
}
8097
return prometheusMetric.write(timeStamp: timeStamp)
8198
}
99+
100+
private static func writeHistogram(prometheusMetric: PrometheusMetric, timeStamp: String, labels: [String: String], metricName: String, sum: Double, count: Int, bucketsBoundaries: Array<Double>, bucketsCounts: Array<Int>) -> String {
101+
var prometheusMetric = prometheusMetric
102+
prometheusMetric.type = prometheusHistogramType
103+
labels.forEach {
104+
prometheusMetric.values.append(PrometheusValue(name: metricName + prometheusHistogramSumPostFix, labels: [$0.key: $0.value], value: sum))
105+
prometheusMetric.values.append(PrometheusValue(name: metricName + prometheusHistogramCountPostFix, labels: [$0.key: $0.value], value: Double(count)))
106+
for i in 0..<bucketsBoundaries.count {
107+
prometheusMetric.values.append(PrometheusValue(name: metricName,
108+
labels: [$0.key: $0.value,
109+
prometheusHistogramLeLabelName: String(format:"%f", bucketsBoundaries[i])],
110+
value: Double(bucketsCounts[i])))
111+
}
112+
prometheusMetric.values.append(PrometheusValue(name: metricName,
113+
labels: [$0.key: $0.value,
114+
prometheusHistogramLeLabelName: "+Inf"],
115+
value: Double(bucketsCounts[bucketsBoundaries.count])))
116+
}
117+
return prometheusMetric.write(timeStamp: timeStamp)
118+
}
82119
}

Tests/ExportersTests/Prometheus/PrometheusExporterTests.swift

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,8 +68,11 @@ class PrometheusExporterTests: XCTestCase {
6868

6969
let testCounter = meter.createIntCounter(name: "testCounter")
7070
let testMeasure = meter.createIntMeasure(name: "testMeasure")
71+
let boundaries: Array<Int> = [5, 10, 25]
72+
var testHistogram = meter.createIntHistogram(name: "testHistogram", explicitBoundaries: boundaries, absolute: true)
7173
let labels1 = ["dim1": "value1", "dim2": "value1"]
7274
let labels2 = ["dim1": "value2", "dim2": "value2"]
75+
let labels3 = ["dim1": "value1"]
7376

7477
for _ in 0 ..< 10 {
7578
testCounter.add(value: 100, labelset: meter.getLabelSet(labels: labels1))
@@ -81,6 +84,10 @@ class PrometheusExporterTests: XCTestCase {
8184
testMeasure.record(value: 100, labelset: meter.getLabelSet(labels: labels1))
8285
testMeasure.record(value: 5, labelset: meter.getLabelSet(labels: labels1))
8386
testMeasure.record(value: 500, labelset: meter.getLabelSet(labels: labels1))
87+
88+
testHistogram.record(value: 8, labelset: meter.getLabelSet(labels: labels3))
89+
testHistogram.record(value: 20, labelset: meter.getLabelSet(labels: labels3))
90+
testHistogram.record(value: 30, labelset: meter.getLabelSet(labels: labels3))
8491
}
8592
return meterProvider
8693
}
@@ -101,5 +108,17 @@ class PrometheusExporterTests: XCTestCase {
101108
XCTAssert(responseText.contains("testMeasure{dim1=\"value1\",quantile=\"0\"} 5") || responseText.contains("testMeasure{quantile=\"0\",dim1=\"value1\"} 5"))
102109
// Max is 500
103110
XCTAssert(responseText.contains("testMeasure{dim1=\"value1\",quantile=\"1\"} 500") || responseText.contains("testMeasure{quantile=\"1\",dim1=\"value1\"} 500"))
111+
112+
// Validate histogram.
113+
XCTAssert(responseText.contains("# TYPE testHistogram histogram"))
114+
// sum is 58 = 8 + 20 + 30
115+
XCTAssert(responseText.contains("testHistogram_sum{dim1=\"value1\"} 58"))
116+
// count is 1 * 3
117+
XCTAssert(responseText.contains("testHistogram_count{dim1=\"value1\"} 3"))
118+
// validate le
119+
XCTAssert(responseText.contains("testHistogram{dim1=\"value1\",le=\"5.000000\"} 0") || responseText.contains("testHistogram{le=\"5.000000\",dim1=\"value1\"} 0"))
120+
XCTAssert(responseText.contains("testHistogram{dim1=\"value1\",le=\"10.000000\"} 1") || responseText.contains("testHistogram{le=\"10.000000\",dim1=\"value1\"} 1"))
121+
XCTAssert(responseText.contains("testHistogram{dim1=\"value1\",le=\"25.000000\"} 1") || responseText.contains("testHistogram{le=\"25.000000\",dim1=\"value1\"} 1"))
122+
XCTAssert(responseText.contains("testHistogram{dim1=\"value1\",le=\"+Inf\"} 1") || responseText.contains("testHistogram{le=\"+Inf\",dim1=\"value1\"} 1"))
104123
}
105124
}

0 commit comments

Comments
 (0)