DataDog / datadog-go

go dogstatsd client library for datadog
MIT License
353 stars 133 forks source link

`WithTags` option does not merge tags across multiple applications of the option #277

Open LINKIWI opened 1 year ago

LINKIWI commented 1 year ago

This is not necessarily a bug, but rather a nonintuitive behavior.

statsd.WithTags(...) is used to specify a set of default tags on the statsd client. When the same option is applied multiple times on a *statsd.Client, only tags from the latest application are captured, overwriting tags from all previous applications of WithTags.

I believe the more intuitive behavior is to merge tags across multiple applications. Here is a motivating example:

package main

import (
    "github.com/DataDog/datadog-go/v5/statsd"
)

func main() {
    client, err := statsd.New("localhost:8125", statsd.WithTags([]string{"foo:foo"}))
    if err != nil {
        panic(err)
    }

    cloned, err := statsd.CloneWithExtraOptions(client, statsd.WithTags([]string{"bar:bar"}))
    if err != nil {
        panic(err)
    }

    defer cloned.Flush()

    cloned.Incr("metric", nil, 1)
}

The following example demonstrates the same semantics more obviously:

func main() {
    client, err := statsd.New("localhost:8125", statsd.WithTags([]string{"foo:foo"}), statsd.WithTags([]string{"bar:bar"}))
    if err != nil {
        panic(err)
    }

    defer client.Flush()

    cloned.Incr("metric", nil, 1)
}

Expected behavior: A metric of the following form is emitted, with both tags foo:foo and bar:bar.

metric:1|c|#foo:foo,bar:bar|c:78f691d9-39f6-4206-9e52-bb22719a4b82

Actual behavior: A metric of the following form is emitted, with only tag bar:bar.

metric:1|c|#bar:bar|c:78f691d9-39f6-4206-9e52-bb22719a4b82