diff --git a/reporters/kamon-datadog/src/main/resources/reference.conf b/reporters/kamon-datadog/src/main/resources/reference.conf index 0b2f2ccff..cc1ae4661 100644 --- a/reporters/kamon-datadog/src/main/resources/reference.conf +++ b/reporters/kamon-datadog/src/main/resources/reference.conf @@ -67,6 +67,8 @@ kamon { compression = false } + # The log level in which to log failures to submit metrics. + failure-log-level = "error" # All time values are collected in nanoseconds, # to scale before sending to datadog set "time-units" to "s" or "ms" or "µs". diff --git a/reporters/kamon-datadog/src/main/scala/kamon/datadog/DatadogAPIReporter.scala b/reporters/kamon-datadog/src/main/scala/kamon/datadog/DatadogAPIReporter.scala index 4c07b0899..f2492b1d5 100644 --- a/reporters/kamon-datadog/src/main/scala/kamon/datadog/DatadogAPIReporter.scala +++ b/reporters/kamon-datadog/src/main/scala/kamon/datadog/DatadogAPIReporter.scala @@ -31,6 +31,7 @@ import kamon.{module, Kamon} import kamon.datadog.DatadogAPIReporter.Configuration import kamon.module.{MetricReporter, ModuleFactory} import org.slf4j.LoggerFactory +import org.slf4j.event.Level import scala.util.{Failure, Success} @@ -68,7 +69,7 @@ class DatadogAPIReporter( override def reportPeriodSnapshot(snapshot: PeriodSnapshot): Unit = { httpClient.doPost("application/json; charset=utf-8", buildRequestBody(snapshot)) match { case Failure(e) => - logger.error(e.getMessage) + logger.logAtLevel(configuration.failureLogLevel, e.getMessage) case Success(response) => logger.trace(response) } @@ -166,7 +167,8 @@ private object DatadogAPIReporter { timeUnit: MeasurementUnit, informationUnit: MeasurementUnit, extraTags: Seq[(String, String)], - tagFilter: Filter + tagFilter: Filter, + failureLogLevel: Level ) implicit class QuoteInterp(val sc: StringContext) extends AnyVal { @@ -175,15 +177,22 @@ private object DatadogAPIReporter { def readConfiguration(config: Config): Configuration = { val datadogConfig = config.getConfig("kamon.datadog") + + // Remove the "host" tag since it gets added to the datadog payload separately + val extraTags = EnvironmentTags + .from(Kamon.environment, datadogConfig.getConfig("environment-tags")) + .without("host") + .all() + .map(p => p.key -> Tag.unwrapValue(p).toString) + Configuration( datadogConfig.getConfig("api"), timeUnit = readTimeUnit(datadogConfig.getString("time-unit")), informationUnit = readInformationUnit(datadogConfig.getString("information-unit")), // Remove the "host" tag since it gets added to the datadog payload separately - EnvironmentTags.from(Kamon.environment, datadogConfig.getConfig("environment-tags")).without("host").all().map( - p => p.key -> Tag.unwrapValue(p).toString - ), - Kamon.filter("kamon.datadog.environment-tags.filter") + extraTags = extraTags, + tagFilter = Kamon.filter("kamon.datadog.environment-tags.filter"), + failureLogLevel = readLogLevel(datadogConfig.getString("failure-log-level")) ) } } diff --git a/reporters/kamon-datadog/src/main/scala/kamon/datadog/package.scala b/reporters/kamon-datadog/src/main/scala/kamon/datadog/package.scala index 9f1c2ca7a..1de2e2877 100644 --- a/reporters/kamon-datadog/src/main/scala/kamon/datadog/package.scala +++ b/reporters/kamon-datadog/src/main/scala/kamon/datadog/package.scala @@ -24,6 +24,8 @@ import com.typesafe.config.Config import kamon.metric.MeasurementUnit import kamon.metric.MeasurementUnit.{information, time} import okhttp3._ +import org.slf4j.Logger +import org.slf4j.event.Level import scala.util.{Failure, Success, Try} @@ -36,6 +38,23 @@ package object datadog { } } + implicit class LoggerExtras(val logger: Logger) extends AnyVal { + def logAtLevel(level: Level, msg: String): Unit = { + level match { + case Level.TRACE => + logger.trace(msg) + case Level.DEBUG => + logger.debug(msg) + case Level.INFO => + logger.info(msg) + case Level.WARN => + logger.warn(msg) + case Level.ERROR => + logger.error(msg) + } + } + } + private[datadog] case class HttpClient( apiUrl: String, apiKey: Option[String], @@ -133,4 +152,14 @@ package object datadog { case "gb" => information.gigabytes case other => sys.error(s"Invalid time unit setting [$other], the possible values are [b, kb, mb, gb]") } + + def readLogLevel(level: String): Level = level match { + case "trace" => Level.TRACE + case "debug" => Level.DEBUG + case "info" => Level.INFO + case "warn" => Level.WARN + case "error" => Level.ERROR + case other => + sys.error(s"Invalid log level setting [$other], the possible values are [trace, debug, info, warn, error]") + } }