Skip to content

Commit baab40e

Browse files
committed
Add some simple head metrics.
1 parent ff4e17e commit baab40e

File tree

7 files changed

+80
-47
lines changed

7 files changed

+80
-47
lines changed

pkg/fire/modules.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -152,7 +152,7 @@ func (f *Fire) initRing() (_ services.Service, err error) {
152152
func (f *Fire) initIngester() (_ services.Service, err error) {
153153
f.Cfg.Ingester.LifecyclerConfig.ListenPort = f.Cfg.Server.HTTPListenPort
154154

155-
head, err := firedb.NewHead()
155+
head, err := firedb.NewHead(f.reg)
156156
if err != nil {
157157
return nil, err
158158
}

pkg/firedb/head.go

Lines changed: 11 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import (
1515
"github.com/go-kit/log/level"
1616
"github.com/gogo/status"
1717
"github.com/google/uuid"
18+
"github.com/prometheus/client_golang/prometheus"
1819
"github.com/prometheus/common/model"
1920
"github.com/prometheus/prometheus/model/labels"
2021
"github.com/prometheus/prometheus/promql/parser"
@@ -153,7 +154,8 @@ func (s *deduplicatingSlice[M, K, H]) getIndex(key K) (int64, bool) {
153154
}
154155

155156
type Head struct {
156-
logger log.Logger
157+
logger log.Logger
158+
metrics *headMetrics
157159

158160
index *profilesIndex
159161
strings deduplicatingSlice[string, string, *stringsHelper]
@@ -164,22 +166,23 @@ type Head struct {
164166
profiles deduplicatingSlice[*schemav1.Profile, profilesKey, *profilesHelper]
165167
}
166168

167-
func NewHead() (*Head, error) {
168-
index, err := newProfileIndex(32)
169-
if err != nil {
170-
return nil, err
171-
}
172-
169+
func NewHead(reg prometheus.Registerer) (*Head, error) {
173170
h := &Head{
174171
logger: log.NewLogfmtLogger(os.Stderr),
175-
index: index,
176172
}
177173
h.strings.init()
178174
h.mappings.init()
179175
h.functions.init()
180176
h.locations.init()
181177
h.stacktraces.init()
182178
h.profiles.init()
179+
h.metrics = newHeadMetrics(h, reg)
180+
index, err := newProfileIndex(32, h.metrics)
181+
if err != nil {
182+
return nil, err
183+
}
184+
h.index = index
185+
183186
return h, nil
184187
}
185188

@@ -188,32 +191,6 @@ type LabelPairRef struct {
188191
Value int64
189192
}
190193

191-
// resolves external labels into string slice
192-
func (h *Head) internExternalLabels(ctx context.Context, lblStrs []*commonv1.LabelPair) ([]LabelPairRef, error) {
193-
var (
194-
strs = make([]string, len(lblStrs)*2)
195-
lblRefs = make([]LabelPairRef, len(lblStrs))
196-
)
197-
198-
for pos := range lblStrs {
199-
strs[(pos * 2)] = lblStrs[pos].Name
200-
strs[(pos*2)+1] = lblStrs[pos].Value
201-
}
202-
203-
// ensure labels are in string table
204-
r := &rewriter{}
205-
if err := h.strings.ingest(ctx, strs, r); err != nil {
206-
return nil, err
207-
}
208-
209-
for pos := range lblRefs {
210-
lblRefs[pos].Name = r.strings[(pos * 2)]
211-
lblRefs[pos].Value = r.strings[(pos*2)+1]
212-
}
213-
214-
return lblRefs, nil
215-
}
216-
217194
func (h *Head) convertSamples(ctx context.Context, r *rewriter, in []*profilev1.Sample) ([]*schemav1.Sample, error) {
218195
var (
219196
out = make([]*schemav1.Sample, len(in))

pkg/firedb/head_test.go

Lines changed: 9 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import (
1010
"time"
1111

1212
"github.com/bufbuild/connect-go"
13+
"github.com/prometheus/client_golang/prometheus"
1314
"github.com/prometheus/common/model"
1415
"github.com/stretchr/testify/assert"
1516
"github.com/stretchr/testify/require"
@@ -152,7 +153,7 @@ func newProfileBaz() *profilev1.Profile {
152153
}
153154

154155
func TestHeadIngestFunctions(t *testing.T) {
155-
head, err := NewHead()
156+
head, err := NewHead(prometheus.NewRegistry())
156157
require.NoError(t, err)
157158

158159
require.NoError(t, head.Ingest(context.Background(), newProfileFoo()))
@@ -168,7 +169,7 @@ func TestHeadIngestFunctions(t *testing.T) {
168169

169170
func TestHeadIngestStrings(t *testing.T) {
170171
ctx := context.Background()
171-
head, err := NewHead()
172+
head, err := NewHead(prometheus.NewRegistry())
172173
require.NoError(t, err)
173174

174175
r := &rewriter{}
@@ -189,7 +190,7 @@ func TestHeadIngestStrings(t *testing.T) {
189190

190191
func TestHeadIngestStacktraces(t *testing.T) {
191192
ctx := context.Background()
192-
head, err := NewHead()
193+
head, err := NewHead(prometheus.NewRegistry())
193194
require.NoError(t, err)
194195

195196
require.NoError(t, head.Ingest(ctx, newProfileFoo()))
@@ -218,7 +219,7 @@ func TestHeadIngestStacktraces(t *testing.T) {
218219
}
219220

220221
func TestHeadLabelValues(t *testing.T) {
221-
head, err := NewHead()
222+
head, err := NewHead(prometheus.NewRegistry())
222223
require.NoError(t, err)
223224
require.NoError(t, head.Ingest(context.Background(), newProfileFoo(), &commonv1.LabelPair{Name: "job", Value: "foo"}, &commonv1.LabelPair{Name: "namespace", Value: "fire"}))
224225
require.NoError(t, head.Ingest(context.Background(), newProfileBar(), &commonv1.LabelPair{Name: "job", Value: "bar"}, &commonv1.LabelPair{Name: "namespace", Value: "fire"}))
@@ -233,7 +234,7 @@ func TestHeadLabelValues(t *testing.T) {
233234
}
234235

235236
func TestHeadProfileTypes(t *testing.T) {
236-
head, err := NewHead()
237+
head, err := NewHead(prometheus.NewRegistry())
237238
require.NoError(t, err)
238239
require.NoError(t, head.Ingest(context.Background(), newProfileFoo(), &commonv1.LabelPair{Name: "__name__", Value: "foo"}, &commonv1.LabelPair{Name: "job", Value: "foo"}, &commonv1.LabelPair{Name: "namespace", Value: "fire"}))
239240
require.NoError(t, head.Ingest(context.Background(), newProfileBar(), &commonv1.LabelPair{Name: "__name__", Value: "bar"}, &commonv1.LabelPair{Name: "namespace", Value: "fire"}))
@@ -249,7 +250,7 @@ func TestHeadIngestRealProfiles(t *testing.T) {
249250
"testdata/profile",
250251
}
251252

252-
head, err := NewHead()
253+
head, err := NewHead(prometheus.NewRegistry())
253254
require.NoError(t, err)
254255
ctx := context.Background()
255256

@@ -263,7 +264,7 @@ func TestHeadIngestRealProfiles(t *testing.T) {
263264
}
264265

265266
func TestSelectProfiles(t *testing.T) {
266-
head, err := NewHead()
267+
head, err := NewHead(prometheus.NewRegistry())
267268
require.NoError(t, err)
268269

269270
// todo write more robust tests.
@@ -357,7 +358,7 @@ func BenchmarkHeadIngestProfiles(t *testing.B) {
357358
profileCount = 0
358359
)
359360

360-
head, err := NewHead()
361+
head, err := NewHead(prometheus.NewRegistry())
361362
require.NoError(t, err)
362363
ctx := context.Background()
363364

pkg/firedb/metrics.go

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
package firedb
2+
3+
import "github.com/prometheus/client_golang/prometheus"
4+
5+
type headMetrics struct {
6+
series prometheus.GaugeFunc
7+
seriesCreated prometheus.Counter
8+
9+
profiles prometheus.GaugeFunc
10+
profilesCreated prometheus.Counter
11+
}
12+
13+
func newHeadMetrics(head *Head, reg prometheus.Registerer) *headMetrics {
14+
m := &headMetrics{
15+
series: prometheus.NewGaugeFunc(prometheus.GaugeOpts{
16+
Name: "fire_tsdb_head_series",
17+
Help: "Total number of series in the head block.",
18+
}, func() float64 {
19+
return float64(head.index.totalSeries.Load())
20+
}),
21+
seriesCreated: prometheus.NewCounter(prometheus.CounterOpts{
22+
Name: "fire_tsdb_head_series_created_total",
23+
Help: "Total number of series created in the head",
24+
}),
25+
profiles: prometheus.NewGaugeFunc(prometheus.GaugeOpts{
26+
Name: "fire_head_profiles",
27+
Help: "Total number of profiles in the head block.",
28+
}, func() float64 {
29+
return float64(head.index.totalProfiles.Load())
30+
}),
31+
profilesCreated: prometheus.NewCounter(prometheus.CounterOpts{
32+
Name: "fire_head_profiles_created_total",
33+
Help: "Total number of profiles created in the head",
34+
}),
35+
}
36+
if reg != nil {
37+
reg.MustRegister(
38+
m.series,
39+
m.seriesCreated,
40+
m.profiles,
41+
m.profilesCreated,
42+
)
43+
}
44+
return m
45+
}

pkg/firedb/profile_test.go

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import (
88
"testing"
99

1010
"github.com/google/uuid"
11+
"github.com/prometheus/client_golang/prometheus"
1112
"github.com/prometheus/common/model"
1213
"github.com/prometheus/prometheus/model/labels"
1314
"github.com/stretchr/testify/require"
@@ -19,7 +20,7 @@ import (
1920
)
2021

2122
func TestIndex(t *testing.T) {
22-
a, err := newProfileIndex(32)
23+
a, err := newProfileIndex(32, newHeadMetrics(&Head{}, prometheus.NewRegistry()))
2324
require.NoError(t, err)
2425
var wg sync.WaitGroup
2526
for i := 0; i < 10; i++ {
@@ -79,7 +80,7 @@ func TestIndex(t *testing.T) {
7980
}
8081

8182
func TestWriteRead(t *testing.T) {
82-
a, err := newProfileIndex(32)
83+
a, err := newProfileIndex(32, newHeadMetrics(&Head{}, prometheus.NewRegistry()))
8384
require.NoError(t, err)
8485

8586
for j := 0; j < 10; j++ {

pkg/firedb/profiles.go

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,9 +29,12 @@ type profilesIndex struct {
2929
profilesPerFP map[model.Fingerprint]*profileLabels
3030
mutex sync.RWMutex
3131
totalProfiles *atomic.Int64
32+
totalSeries *atomic.Int64
33+
34+
metrics *headMetrics
3235
}
3336

34-
func newProfileIndex(totalShards uint32) (*profilesIndex, error) {
37+
func newProfileIndex(totalShards uint32, metrics *headMetrics) (*profilesIndex, error) {
3538
ix, err := tsdb.NewBitPrefixWithShards(totalShards)
3639
if err != nil {
3740
return nil, err
@@ -40,6 +43,8 @@ func newProfileIndex(totalShards uint32) (*profilesIndex, error) {
4043
ix: ix,
4144
profilesPerFP: make(map[model.Fingerprint]*profileLabels),
4245
totalProfiles: atomic.NewInt64(0),
46+
totalSeries: atomic.NewInt64(0),
47+
metrics: metrics,
4348
}, nil
4449
}
4550

@@ -58,11 +63,14 @@ func (pi *profilesIndex) Add(ps *schemav1.Profile, lbs []firemodel.Labels) {
5863
profiles: []*schemav1.Profile{ps},
5964
}
6065
pi.profilesPerFP[fp] = profiles
66+
pi.totalSeries.Inc()
67+
pi.metrics.seriesCreated.Inc()
6168
continue
6269
}
6370
profiles.profiles = append(profiles.profiles, ps)
6471
}
6572
pi.totalProfiles.Inc()
73+
pi.metrics.profilesCreated.Inc()
6674
}
6775

6876
// forMatchingProfiles iterates through all matching profiles and calls f for each profiles.

pkg/firedb/querier_test.go

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@ import (
77
"testing"
88

99
"github.com/google/uuid"
10+
"github.com/prometheus/client_golang/prometheus"
1011
"github.com/prometheus/common/model"
1112
"github.com/prometheus/prometheus/model/labels"
1213
"github.com/stretchr/testify/require"
@@ -18,7 +19,7 @@ import (
1819
)
1920

2021
func TestQueryIndex(t *testing.T) {
21-
a, err := newProfileIndex(32)
22+
a, err := newProfileIndex(32, newHeadMetrics(&Head{}, &prometheus.Registry{}))
2223
require.NoError(t, err)
2324

2425
for j := 0; j < 10; j++ {

0 commit comments

Comments
 (0)