Skip to content

Commit 3dbe261

Browse files
authored
loki.process: enable structured_metadata labels conversion (loki/#10752) (grafana#5481)
1 parent ca7226d commit 3dbe261

File tree

3 files changed

+56
-1
lines changed

3 files changed

+56
-1
lines changed

CHANGELOG.md

+3
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,9 @@ Main (unreleased)
4242

4343
- Update Prometheus dependency to v2.47.2. (@tpaschalis)
4444

45+
- Allow converting labels to structured metadata with Loki's structured_metadata stage. (@gonzalesraul)
46+
47+
4548
v0.37.1 (2023-10-10)
4649
-----------------
4750

component/loki/process/stages/structured_metadata.go

+21-1
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,26 @@ func (s *structuredMetadataStage) Run(in chan Entry) chan Entry {
3232
processLabelsConfigs(s.logger, e.Extracted, s.cfgs, func(labelName model.LabelName, labelValue model.LabelValue) {
3333
e.StructuredMetadata = append(e.StructuredMetadata, logproto.LabelAdapter{Name: string(labelName), Value: string(labelValue)})
3434
})
35-
return e
35+
return s.extractFromLabels(e)
3636
})
3737
}
38+
39+
func (s *structuredMetadataStage) extractFromLabels(e Entry) Entry {
40+
labels := e.Labels
41+
foundLabels := []model.LabelName{}
42+
43+
for lName, lSrc := range s.cfgs.Values {
44+
labelKey := model.LabelName(*lSrc)
45+
if lValue, ok := labels[labelKey]; ok {
46+
e.StructuredMetadata = append(e.StructuredMetadata, logproto.LabelAdapter{Name: lName, Value: string(lValue)})
47+
foundLabels = append(foundLabels, labelKey)
48+
}
49+
}
50+
51+
// Remove found labels, do this after append to structure metadata
52+
for _, fl := range foundLabels {
53+
delete(labels, fl)
54+
}
55+
e.Labels = labels
56+
return e
57+
}

component/loki/process/stages/structured_metadata_test.go

+32
Original file line numberDiff line numberDiff line change
@@ -71,6 +71,26 @@ stage.labels {
7171
}
7272
`
7373

74+
var pipelineStagesStructuredMetadataFromStaticLabels = `
75+
stage.static_labels {
76+
values = {"component" = "querier", "pod" = "loki-querier-664f97db8d-qhnwg"}
77+
}
78+
79+
stage.structured_metadata {
80+
values = {"pod" = ""}
81+
}
82+
`
83+
84+
var pipelineStagesStructuredMetadataFromStaticLabelsDifferentKey = `
85+
stage.static_labels {
86+
values = {"component" = "querier", "pod" = "loki-querier-664f97db8d-qhnwg"}
87+
}
88+
89+
stage.structured_metadata {
90+
values = {"pod_name" = "pod"}
91+
}
92+
`
93+
7494
func Test_StructuredMetadataStage(t *testing.T) {
7595
tests := map[string]struct {
7696
pipelineStagesYaml string
@@ -104,6 +124,18 @@ func Test_StructuredMetadataStage(t *testing.T) {
104124
expectedStructuredMetadata: push.LabelsAdapter{push.LabelAdapter{Name: "app", Value: "loki"}},
105125
expectedLabels: model.LabelSet{model.LabelName("component"): model.LabelValue("ingester")},
106126
},
127+
"expected structured metadata and regular labels to be extracted with static labels stage and to be added to entry": {
128+
pipelineStagesYaml: pipelineStagesStructuredMetadataFromStaticLabels,
129+
logLine: `sample log line`,
130+
expectedStructuredMetadata: push.LabelsAdapter{push.LabelAdapter{Name: "pod", Value: "loki-querier-664f97db8d-qhnwg"}},
131+
expectedLabels: model.LabelSet{model.LabelName("component"): model.LabelValue("querier")},
132+
},
133+
"expected structured metadata and regular labels to be extracted with static labels stage using different structured key": {
134+
pipelineStagesYaml: pipelineStagesStructuredMetadataFromStaticLabelsDifferentKey,
135+
logLine: `sample log line`,
136+
expectedStructuredMetadata: push.LabelsAdapter{push.LabelAdapter{Name: "pod_name", Value: "loki-querier-664f97db8d-qhnwg"}},
137+
expectedLabels: model.LabelSet{model.LabelName("component"): model.LabelValue("querier")},
138+
},
107139
}
108140
for name, test := range tests {
109141
t.Run(name, func(t *testing.T) {

0 commit comments

Comments
 (0)