Add a flag to publish metrics with high resolution (#32)

So far, this tool is only publishing metrics with high resolution when
the original prometheus metrics have the label __cw_high_res.

However, in our case we're running exporters and prom-to-cloudwatch
as sidecars of ECS tasks. This tool being directly connected to the
exporters, we can't add the high res label.
This commit is contained in:
Albin Kerouanton 2020-02-19 16:14:22 +01:00 committed by GitHub
parent 8546fedfa2
commit bcdabf4fbd
2 changed files with 15 additions and 3 deletions

View File

@ -15,6 +15,8 @@ import (
"github.com/gobwas/glob"
)
var defaultForceHighRes, _ = strconv.ParseBool(os.Getenv("FORCE_HIGH_RES"))
var (
awsAccessKeyId = flag.String("aws_access_key_id", os.Getenv("AWS_ACCESS_KEY_ID"), "AWS access key Id with permissions to publish CloudWatch metrics")
awsSecretAccessKey = flag.String("aws_secret_access_key", os.Getenv("AWS_SECRET_ACCESS_KEY"), "AWS secret access key with permissions to publish CloudWatch metrics")
@ -33,6 +35,7 @@ var (
excludeMetrics = flag.String("exclude_metrics", os.Getenv("EXCLUDE_METRICS"), "Never publish the specified metrics (comma-separated list of glob patterns, e.g. 'tomcat_*')")
includeDimensionsForMetrics = flag.String("include_dimensions_for_metrics", os.Getenv("INCLUDE_DIMENSIONS_FOR_METRICS"), "Only publish the specified dimensions for metrics (semi-colon-separated key values of comma-separated dimensions of METRIC=dim1,dim2;, e.g. 'flink_jobmanager=job_id')")
excludeDimensionsForMetrics = flag.String("exclude_dimensions_for_metrics", os.Getenv("EXCLUDE_DIMENSIONS_FOR_METRICS"), "Never publish the specified dimensions for metrics (semi-colon-separated key values of comma-separated dimensions of METRIC=dim1,dim2;, e.g. 'flink_jobmanager=job,host;zk_up=host,pod;')")
forceHighRes = flag.Bool("force_high_res", defaultForceHighRes, "Publish all metrics with high resolution, even when original metrics don't have the label "+cwHighResLabel)
)
// kevValMustParse takes a string and exits with a message if it cannot parse as KEY=VALUE
@ -180,6 +183,7 @@ func main() {
ExcludeMetrics: excludeMetricsList,
ExcludeDimensionsForMetrics: excludeDimensionsForMetricsList,
IncludeDimensionsForMetrics: includeDimensionsForMetricsList,
ForceHighRes: *forceHighRes,
}
if *prometheusScrapeInterval != "" {

View File

@ -108,6 +108,9 @@ type Config struct {
// Exclude certain dimensions from the specified metrics
ExcludeDimensionsForMetrics []MatcherWithStringSet
// ForceHighRes forces all exported metrics to be sent as custom high-resolution metrics.
ForceHighRes bool
}
// Bridge pushes metrics to AWS CloudWatch
@ -125,6 +128,7 @@ type Bridge struct {
excludeMetrics []glob.Glob
includeDimensionsForMetrics []MatcherWithStringSet
excludeDimensionsForMetrics []MatcherWithStringSet
forceHighRes bool
}
// NewBridge initializes and returns a pointer to a Bridge using the
@ -151,6 +155,7 @@ func NewBridge(c *Config) (*Bridge, error) {
b.excludeMetrics = c.ExcludeMetrics
b.includeDimensionsForMetrics = c.IncludeDimensionsForMetrics
b.excludeDimensionsForMetrics = c.ExcludeDimensionsForMetrics
b.forceHighRes = c.ForceHighRes
if c.CloudWatchPublishInterval > 0 {
b.cloudWatchPublishInterval = c.CloudWatchPublishInterval
@ -327,7 +332,7 @@ func appendDatum(data []*cloudwatch.MetricDatum, name string, s *model.Sample, b
SetValue(value).
SetTimestamp(s.Timestamp.Time()).
SetDimensions(append(kubeStateDimensions, getAdditionalDimensions(b)...)).
SetStorageResolution(getResolution(metric)).
SetStorageResolution(b.getResolution(metric)).
SetUnit(getUnit(metric))
data = append(data, datum)
@ -338,7 +343,7 @@ func appendDatum(data []*cloudwatch.MetricDatum, name string, s *model.Sample, b
SetValue(value).
SetTimestamp(s.Timestamp.Time()).
SetDimensions(append(replacedDimensions, getAdditionalDimensions(b)...)).
SetStorageResolution(getResolution(metric)).
SetStorageResolution(b.getResolution(metric)).
SetUnit(getUnit(metric))
data = append(data, replacedDimensionDatum)
}
@ -465,7 +470,10 @@ func getAdditionalDimensions(b *Bridge) []*cloudwatch.Dimension {
}
// Returns 1 if the metric contains a __cw_high_res label, otherwise returns 60
func getResolution(m model.Metric) int64 {
func (b *Bridge) getResolution(m model.Metric) int64 {
if b.forceHighRes {
return 1
}
if _, ok := m[cwHighResLabel]; ok {
return 1
}