Skip to content

Commit 1f6d2cc

Browse files
authored
Fix Prometheus exporter writing bool label values (#4823)
1 parent 0228fb9 commit 1f6d2cc

File tree

4 files changed

+46
-1
lines changed

4 files changed

+46
-1
lines changed

src/OpenTelemetry.Exporter.Prometheus.AspNetCore/CHANGELOG.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,9 @@
22

33
## Unreleased
44

5+
* Fixed writing boolean values to use the JSON representation
6+
([#4823](https://github.com/open-telemetry/opentelemetry-dotnet/pull/4823))
7+
58
## 1.6.0-rc.1
69

710
Released 2023-Aug-21

src/OpenTelemetry.Exporter.Prometheus.HttpListener/CHANGELOG.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,9 @@
22

33
## Unreleased
44

5+
* Fixed writing boolean values to use the JSON representation
6+
([#4823](https://github.com/open-telemetry/opentelemetry-dotnet/pull/4823))
7+
58
## 1.6.0-rc.1
69

710
Released 2023-Aug-21

src/OpenTelemetry.Exporter.Prometheus.HttpListener/Internal/PrometheusSerializer.cs

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -222,10 +222,22 @@ public static int WriteLabel(byte[] buffer, int cursor, string labelKey, object
222222
buffer[cursor++] = unchecked((byte)'"');
223223

224224
// In Prometheus, a label with an empty label value is considered equivalent to a label that does not exist.
225-
cursor = WriteLabelValue(buffer, cursor, labelValue?.ToString() ?? string.Empty);
225+
cursor = WriteLabelValue(buffer, cursor, GetLabelValueString(labelValue));
226226
buffer[cursor++] = unchecked((byte)'"');
227227

228228
return cursor;
229+
230+
static string GetLabelValueString(object labelValue)
231+
{
232+
// TODO: Attribute values should be written as their JSON representation. Extra logic may need to be added here to correctly convert other .NET types.
233+
// More detail: https://github.com/open-telemetry/opentelemetry-dotnet/issues/4822#issuecomment-1707328495
234+
if (labelValue is bool b)
235+
{
236+
return b ? "true" : "false";
237+
}
238+
239+
return labelValue?.ToString() ?? string.Empty;
240+
}
229241
}
230242

231243
[MethodImpl(MethodImplOptions.AggressiveInlining)]

test/OpenTelemetry.Exporter.Prometheus.HttpListener.Tests/PrometheusSerializerTests.cs

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -155,6 +155,33 @@ public void GaugeOneDimension()
155155
Encoding.UTF8.GetString(buffer, 0, cursor));
156156
}
157157

158+
[Fact]
159+
public void GaugeBoolDimension()
160+
{
161+
var buffer = new byte[85000];
162+
var metrics = new List<Metric>();
163+
164+
using var meter = new Meter(Utils.GetCurrentMethodName());
165+
using var provider = Sdk.CreateMeterProviderBuilder()
166+
.AddMeter(meter.Name)
167+
.AddInMemoryExporter(metrics)
168+
.Build();
169+
170+
meter.CreateObservableGauge(
171+
"test_gauge",
172+
() => new Measurement<long>(123, new KeyValuePair<string, object>("tagKey", true)));
173+
174+
provider.ForceFlush();
175+
176+
var cursor = WriteMetric(buffer, 0, metrics[0]);
177+
Assert.Matches(
178+
("^"
179+
+ "# TYPE test_gauge gauge\n"
180+
+ "test_gauge{tagKey='true'} 123 \\d+\n"
181+
+ "$").Replace('\'', '"'),
182+
Encoding.UTF8.GetString(buffer, 0, cursor));
183+
}
184+
158185
[Fact]
159186
public void GaugeDoubleSubnormal()
160187
{

0 commit comments

Comments
 (0)