Fixes issue #8199
Benchmarks ``` benchmark old ns/op new ns/op delta BenchmarkMarshal-8 1216 1007 -17.19% benchmark old allocs new allocs delta BenchmarkMarshal-8 4 2 -50.00% benchmark old bytes new bytes delta BenchmarkMarshal-8 416 256 -38.46% ```pull/8207/head
parent
b869607dc2
commit
9e69bdbef5
|
@ -1773,40 +1773,35 @@ func (a Tags) HashKey() []byte {
|
|||
return nil
|
||||
}
|
||||
|
||||
// Type invariant: Tags are sorted
|
||||
|
||||
escaped := make(Tags, 0, len(a))
|
||||
sz := 0
|
||||
for _, t := range a {
|
||||
ek := escapeTag(t.Key)
|
||||
ev := escapeTag(t.Value)
|
||||
|
||||
if len(ev) > 0 {
|
||||
escaped = append(escaped, Tag{Key: ek, Value: ev})
|
||||
sz += len(ek) + len(ev)
|
||||
}
|
||||
}
|
||||
|
||||
// Extract keys and determine final size.
|
||||
sz := len(escaped) + (len(escaped) * 2) // separators
|
||||
keys := make([][]byte, len(escaped)+1)
|
||||
for i, t := range escaped {
|
||||
keys[i] = t.Key
|
||||
sz += len(t.Key) + len(t.Value)
|
||||
}
|
||||
keys = keys[:len(escaped)]
|
||||
sort.Sort(byteSlices(keys))
|
||||
sz += len(escaped) + (len(escaped) * 2) // separators
|
||||
|
||||
// Generate marshaled bytes.
|
||||
b := make([]byte, sz)
|
||||
buf := b
|
||||
idx := 0
|
||||
for i, k := range keys {
|
||||
for _, k := range escaped {
|
||||
buf[idx] = ','
|
||||
idx++
|
||||
copy(buf[idx:idx+len(k)], k)
|
||||
idx += len(k)
|
||||
copy(buf[idx:idx+len(k.Key)], k.Key)
|
||||
idx += len(k.Key)
|
||||
buf[idx] = '='
|
||||
idx++
|
||||
v := escaped[i].Value
|
||||
copy(buf[idx:idx+len(v)], v)
|
||||
idx += len(v)
|
||||
copy(buf[idx:idx+len(k.Value)], k.Value)
|
||||
idx += len(k.Value)
|
||||
}
|
||||
return b[:idx]
|
||||
}
|
||||
|
|
|
@ -40,6 +40,16 @@ func TestMarshal(t *testing.T) {
|
|||
}
|
||||
}
|
||||
|
||||
func TestTags_HashKey(t *testing.T) {
|
||||
tags = models.NewTags(map[string]string{"A FOO": "bar", "APPLE": "orange", "host": "serverA", "region": "uswest"})
|
||||
got := tags.HashKey()
|
||||
if exp := ",A\\ FOO=bar,APPLE=orange,host=serverA,region=uswest"; string(got) != exp {
|
||||
t.Log("got: ", string(got))
|
||||
t.Log("exp: ", exp)
|
||||
t.Error("invalid match")
|
||||
}
|
||||
}
|
||||
|
||||
func BenchmarkMarshal(b *testing.B) {
|
||||
for i := 0; i < b.N; i++ {
|
||||
tags.HashKey()
|
||||
|
|
Loading…
Reference in New Issue