Skip to content

Commit

Permalink
Rewrite label names to be Prometheus compliant
Browse files Browse the repository at this point in the history
I am running into issues where my OpenTSDB tags with periods in their names are failing to be scraped by Prometheus. It seems like the most logical place to fix that is in this exporter. This approach takes any tag name that would fail validation in Prometheus and rewrites it to pass.
  • Loading branch information
stormybriggs1 authored and andreifecioru committed Oct 5, 2020
1 parent 021b8da commit dde951f
Show file tree
Hide file tree
Showing 6 changed files with 35 additions and 13 deletions.
2 changes: 1 addition & 1 deletion VERSION
Original file line number Diff line number Diff line change
@@ -1 +1 @@
0.3.3
0.4.0
9 changes: 8 additions & 1 deletion web/app/models/OpenTsdbQueryResult.scala
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ case class TsdbQueryResult(
mapping <- metric.query.mappings.find(_.subQuery == subQuery)
tags <- mergeTags(mapping.prometheusTags)
dp <- latestDataPoint
} yield PrometheusMetric(metric.name, metric.description, metric.metricType, tags, dp.value)
} yield PrometheusMetric(metric.name, metric.description, metric.metricType, TsdbQueryResult.sanitizeTags(tags), dp.value)
}
}

Expand Down Expand Up @@ -100,4 +100,11 @@ object TsdbQueryResult {
subQuery = query
)
)

def sanitizeTags(prometheusTags: Map[String, String]): Map[String, String] = {
def sanitizeTagName(label: String): String = label
.replaceFirst("^[^\\p{L}_:]", ":")
.replaceAll("[^\\p{L}0-9_:]+", "_")
prometheusTags.map { case (key, value) => (sanitizeTagName(key), value) }
}
}
16 changes: 8 additions & 8 deletions web/test/MetricsControllerSpec.scala
Original file line number Diff line number Diff line change
Expand Up @@ -78,10 +78,10 @@ class MetricsControllerSpec extends PlaySpec
output must contain theSameElementsInOrderAs List(
"# HELP test_app_metrics_one TestApp metrics: one",
"# TYPE test_app_metrics_one counter",
"""test_app_metrics_one{severity="critical",escalation="pagerduty",role="developer"} 15.0""",
"""test_app_metrics_one{severity="critical",escalation="pagerduty",user_role="developer"} 15.0""",
"# HELP test_app_metrics_two TestApp metrics: two",
"# TYPE test_app_metrics_two counter",
"""test_app_metrics_two{severity="critical",escalation="pagerduty",role="developer"} 10.0"""
"""test_app_metrics_two{severity="critical",escalation="pagerduty",user_role="developer"} 10.0"""
)
}
}
Expand All @@ -96,7 +96,7 @@ class SimpleOpenTsdbWSMock extends OpenTsdbWSMock {
| {
| "metric": "test.app.metrics.one",
| "tags": {
| "role": "developer"
| "user.role": "developer"
| },
| "aggregateTags": [],
| "query": {
Expand All @@ -107,15 +107,15 @@ class SimpleOpenTsdbWSMock extends OpenTsdbWSMock {
| "rate": false,
| "filters": [
| {
| "tagk": "role",
| "tagk": "user.role",
| "filter": "developer",
| "group_by": true,
| "type": "literal_or"
| }
| ],
| "rateOptions": null,
| "tags": {
| "role": "literal_or(developer)"
| "user.role": "literal_or(developer)"
| }
| },
| "dps": {
Expand All @@ -139,7 +139,7 @@ class SimpleOpenTsdbWSMock extends OpenTsdbWSMock {
| {
| "metric": "test.app.metrics.two",
| "tags": {
| "role": "developer"
| "user.role": "developer"
| },
| "aggregateTags": [],
| "query": {
Expand All @@ -150,15 +150,15 @@ class SimpleOpenTsdbWSMock extends OpenTsdbWSMock {
| "rate": false,
| "filters": [
| {
| "tagk": "role",
| "tagk": "user.role",
| "filter": "developer",
| "group_by": true,
| "type": "literal_or"
| }
| ],
| "rateOptions": null,
| "tags": {
| "role": "literal_or(developer)"
| "user.role": "literal_or(developer)"
| }
| },
| "dps": {
Expand Down
2 changes: 1 addition & 1 deletion web/test/data/test.app.metrics.one.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
"aggregator": "avg",
"rate": false,
"tags": {
"role": "developer"
"user.role": "developer"
}
},
"prometheusTags": {
Expand Down
4 changes: 2 additions & 2 deletions web/test/data/test.app.metrics.two.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@
"aggregator": "avg",
"rate": false,
"tags": {
"role": "developer"
"user.role": "developer"
}
},
"prometheusTags": {
Expand All @@ -29,7 +29,7 @@
"aggregator": "avg",
"rate": false,
"tags": {
"role": "developer"
"user.role": "developer"
}
},
"prometheusTags": {
Expand Down
15 changes: 15 additions & 0 deletions web/test/models/OpenTsdbQueryResultSpec.scala
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
package models

import org.scalatestplus.play.PlaySpec

class OpenTsdbQueryResultSpec extends PlaySpec {

"OpenTsdbQueryResult" should {
"Santize tag names" in {
val inputs = Map("abCD" -> "1", "123abc" -> "2", "@email" -> "3", "Unic\u00F6de" -> "4", "teach.me" -> "5")
val expected = Map("abCD" -> "1", ":23abc" -> "2", ":email" -> "3", "Unic\u00F6de" -> "4", "teach_me" -> "5")
TsdbQueryResult.sanitizeTags(inputs) must contain theSameElementsAs expected
}
}

}

0 comments on commit dde951f

Please sign in to comment.