Skip to content

Commit 90e6395

Browse files
committed
Preprocess string concatenation for enrichment
1 parent f78e474 commit 90e6395

File tree

4 files changed

+170
-115
lines changed

4 files changed

+170
-115
lines changed

pkg/api/transform_network.go

Lines changed: 64 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,12 @@ type TransformNetwork struct {
2626
DirectionInfo NetworkTransformDirectionInfo `yaml:"directionInfo,omitempty" json:"directionInfo,omitempty" doc:"information to reinterpret flow direction (optional, to use with reinterpret_direction rule)"`
2727
}
2828

29+
func (tn *TransformNetwork) Preprocess() {
30+
for i := range tn.Rules {
31+
tn.Rules[i].preprocess()
32+
}
33+
}
34+
2935
func (tn *TransformNetwork) GetServiceFiles() (string, string) {
3036
p := tn.ProtocolsFile
3137
if p == "" {
@@ -73,6 +79,12 @@ type NetworkTransformRule struct {
7379
DecodeTCPFlags *NetworkGenericRule `yaml:"decode_tcp_flags,omitempty" json:"decode_tcp_flags,omitempty" doc:"Decode bitwise TCP flags into a string"`
7480
}
7581

82+
func (r *NetworkTransformRule) preprocess() {
83+
if r.Kubernetes != nil {
84+
r.Kubernetes.preprocess()
85+
}
86+
}
87+
7688
type K8sInfraRule struct {
7789
NamespaceNameFields []K8sReference `yaml:"namespaceNameFields,omitempty" json:"namespaceNameFields,omitempty" doc:"entries for namespace and name input fields"`
7890
Output string `yaml:"output,omitempty" json:"output,omitempty" doc:"entry output field"`
@@ -86,14 +98,58 @@ type K8sReference struct {
8698
}
8799

88100
type K8sRule struct {
89-
IPField string `yaml:"ipField,omitempty" json:"ipField,omitempty" doc:"entry IP input field"`
90-
InterfacesField string `yaml:"interfacesField,omitempty" json:"interfacesField,omitempty" doc:"entry Interfaces input field"`
91-
UDNsField string `yaml:"udnsField,omitempty" json:"udnsField,omitempty" doc:"entry UDNs input field"`
92-
MACField string `yaml:"macField,omitempty" json:"macField,omitempty" doc:"entry MAC input field"`
93-
Output string `yaml:"output,omitempty" json:"output,omitempty" doc:"entry output field"`
94-
Assignee string `yaml:"assignee,omitempty" json:"assignee,omitempty" doc:"value needs to assign to output field"`
95-
LabelsPrefix string `yaml:"labels_prefix,omitempty" json:"labels_prefix,omitempty" doc:"labels prefix to use to copy input lables, if empty labels will not be copied"`
96-
AddZone bool `yaml:"add_zone,omitempty" json:"add_zone,omitempty" doc:"if true the rule will add the zone"`
101+
IPField string `yaml:"ipField,omitempty" json:"ipField,omitempty" doc:"entry IP input field"`
102+
InterfacesField string `yaml:"interfacesField,omitempty" json:"interfacesField,omitempty" doc:"entry Interfaces input field"`
103+
UDNsField string `yaml:"udnsField,omitempty" json:"udnsField,omitempty" doc:"entry UDNs input field"`
104+
MACField string `yaml:"macField,omitempty" json:"macField,omitempty" doc:"entry MAC input field"`
105+
Output string `yaml:"output,omitempty" json:"output,omitempty" doc:"entry output field"`
106+
Assignee string `yaml:"assignee,omitempty" json:"assignee,omitempty" doc:"value needs to assign to output field"`
107+
LabelsPrefix string `yaml:"labels_prefix,omitempty" json:"labels_prefix,omitempty" doc:"labels prefix to use to copy input lables, if empty labels will not be copied"`
108+
AddZone bool `yaml:"add_zone,omitempty" json:"add_zone,omitempty" doc:"if true the rule will add the zone"`
109+
OutputKeys K8SOutputKeys `yaml:"-" json:"-"`
110+
}
111+
112+
type K8SOutputKeys struct {
113+
Namespace string
114+
Name string
115+
Kind string
116+
OwnerName string
117+
OwnerKind string
118+
NetworkName string
119+
HostIP string
120+
HostName string
121+
Zone string
122+
}
123+
124+
func (r *K8sRule) preprocess() {
125+
if r.Assignee == "otel" {
126+
// NOTE: Some of these fields are taken from opentelemetry specs.
127+
// See https://opentelemetry.io/docs/specs/semconv/resource/k8s/
128+
// Other fields (not specified in the specs) are named similarly
129+
r.OutputKeys = K8SOutputKeys{
130+
Namespace: r.Output + "k8s.namespace.name",
131+
Name: r.Output + "k8s.name",
132+
Kind: r.Output + "k8s.type",
133+
OwnerName: r.Output + "k8s.owner.name",
134+
OwnerKind: r.Output + "k8s.owner.type",
135+
NetworkName: r.Output + "k8s.net.name",
136+
HostIP: r.Output + "k8s.host.ip",
137+
HostName: r.Output + "k8s.host.name",
138+
Zone: r.Output + "k8s.zone",
139+
}
140+
} else {
141+
r.OutputKeys = K8SOutputKeys{
142+
Namespace: r.Output + "_Namespace",
143+
Name: r.Output + "_Name",
144+
Kind: r.Output + "_Type",
145+
OwnerName: r.Output + "_OwnerName",
146+
OwnerKind: r.Output + "_OwnerType",
147+
NetworkName: r.Output + "_NetworkName",
148+
HostIP: r.Output + "_HostIP",
149+
HostName: r.Output + "_HostName",
150+
Zone: r.Output + "_Zone",
151+
}
152+
}
97153
}
98154

99155
type SecondaryNetwork struct {

pkg/pipeline/transform/kubernetes/enrich.go

Lines changed: 28 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -41,36 +41,33 @@ func Enrich(outputEntry config.GenericMap, rule *api.K8sRule) {
4141
logrus.Tracef("can't find kubernetes info for keys %v and IP %s", potentialKeys, ip)
4242
return
4343
}
44-
if rule.Assignee != "otel" {
45-
// NETOBSERV-666: avoid putting empty namespaces or Loki aggregation queries will
46-
// differentiate between empty and nil namespaces.
47-
if kubeInfo.Namespace != "" {
48-
outputEntry[rule.Output+"_Namespace"] = kubeInfo.Namespace
49-
}
50-
outputEntry[rule.Output+"_Name"] = kubeInfo.Name
51-
outputEntry[rule.Output+"_Type"] = kubeInfo.Kind
52-
outputEntry[rule.Output+"_OwnerName"] = kubeInfo.OwnerName
53-
outputEntry[rule.Output+"_OwnerType"] = kubeInfo.OwnerKind
54-
outputEntry[rule.Output+"_NetworkName"] = kubeInfo.NetworkName
55-
if rule.LabelsPrefix != "" {
56-
for labelKey, labelValue := range kubeInfo.Labels {
57-
outputEntry[rule.LabelsPrefix+"_"+labelKey] = labelValue
58-
}
59-
}
60-
if kubeInfo.HostIP != "" {
61-
outputEntry[rule.Output+"_HostIP"] = kubeInfo.HostIP
62-
if kubeInfo.HostName != "" {
63-
outputEntry[rule.Output+"_HostName"] = kubeInfo.HostName
64-
}
44+
45+
// NETOBSERV-666: avoid putting empty namespaces or Loki aggregation queries will
46+
// differentiate between empty and nil namespaces.
47+
if kubeInfo.Namespace != "" {
48+
outputEntry[rule.OutputKeys.Namespace] = kubeInfo.Namespace
49+
}
50+
outputEntry[rule.OutputKeys.Name] = kubeInfo.Name
51+
outputEntry[rule.OutputKeys.Kind] = kubeInfo.Kind
52+
outputEntry[rule.OutputKeys.OwnerName] = kubeInfo.OwnerName
53+
outputEntry[rule.OutputKeys.OwnerKind] = kubeInfo.OwnerKind
54+
outputEntry[rule.OutputKeys.NetworkName] = kubeInfo.NetworkName
55+
if rule.LabelsPrefix != "" {
56+
for labelKey, labelValue := range kubeInfo.Labels {
57+
outputEntry[rule.LabelsPrefix+"_"+labelKey] = labelValue
6558
}
66-
fillInK8sZone(outputEntry, rule, kubeInfo, "_Zone")
67-
} else {
68-
// NOTE: Some of these fields are taken from opentelemetry specs.
69-
// See https://opentelemetry.io/docs/specs/semconv/resource/k8s/
70-
// Other fields (not specified in the specs) are named similarly
71-
if kubeInfo.Namespace != "" {
72-
outputEntry[rule.Output+"k8s.namespace.name"] = kubeInfo.Namespace
59+
}
60+
if kubeInfo.HostIP != "" {
61+
outputEntry[rule.OutputKeys.HostIP] = kubeInfo.HostIP
62+
if kubeInfo.HostName != "" {
63+
outputEntry[rule.OutputKeys.HostName] = kubeInfo.HostName
7364
}
65+
}
66+
fillInK8sZone(outputEntry, rule, kubeInfo)
67+
68+
if rule.Assignee == "otel" {
69+
// A few otel-specific names
70+
// TODO: remove them? This is adding quite some redundant content
7471
switch kubeInfo.Kind {
7572
case model.KindNode:
7673
outputEntry[rule.Output+"k8s.node.name"] = kubeInfo.Name
@@ -82,28 +79,12 @@ func Enrich(outputEntry config.GenericMap, rule *api.K8sRule) {
8279
outputEntry[rule.Output+"k8s.service.name"] = kubeInfo.Name
8380
outputEntry[rule.Output+"k8s.service.uid"] = kubeInfo.UID
8481
}
85-
outputEntry[rule.Output+"k8s.name"] = kubeInfo.Name
86-
outputEntry[rule.Output+"k8s.type"] = kubeInfo.Kind
87-
outputEntry[rule.Output+"k8s.owner.name"] = kubeInfo.OwnerName
88-
outputEntry[rule.Output+"k8s.owner.type"] = kubeInfo.OwnerKind
89-
if rule.LabelsPrefix != "" {
90-
for labelKey, labelValue := range kubeInfo.Labels {
91-
outputEntry[rule.LabelsPrefix+"."+labelKey] = labelValue
92-
}
93-
}
94-
if kubeInfo.HostIP != "" {
95-
outputEntry[rule.Output+"k8s.host.ip"] = kubeInfo.HostIP
96-
if kubeInfo.HostName != "" {
97-
outputEntry[rule.Output+"k8s.host.name"] = kubeInfo.HostName
98-
}
99-
}
100-
fillInK8sZone(outputEntry, rule, kubeInfo, "k8s.zone")
10182
}
10283
}
10384

10485
const nodeZoneLabelName = "topology.kubernetes.io/zone"
10586

106-
func fillInK8sZone(outputEntry config.GenericMap, rule *api.K8sRule, kubeInfo *model.ResourceMetaData, zonePrefix string) {
87+
func fillInK8sZone(outputEntry config.GenericMap, rule *api.K8sRule, kubeInfo *model.ResourceMetaData) {
10788
if !rule.AddZone {
10889
// Nothing to do
10990
return
@@ -112,7 +93,7 @@ func fillInK8sZone(outputEntry config.GenericMap, rule *api.K8sRule, kubeInfo *m
11293
case model.KindNode:
11394
zone, ok := kubeInfo.Labels[nodeZoneLabelName]
11495
if ok {
115-
outputEntry[rule.Output+zonePrefix] = zone
96+
outputEntry[rule.OutputKeys.Zone] = zone
11697
}
11798
return
11899
case model.KindPod:
@@ -124,7 +105,7 @@ func fillInK8sZone(outputEntry config.GenericMap, rule *api.K8sRule, kubeInfo *m
124105
if nodeInfo != nil {
125106
zone, ok := nodeInfo.Labels[nodeZoneLabelName]
126107
if ok {
127-
outputEntry[rule.Output+zonePrefix] = zone
108+
outputEntry[rule.OutputKeys.Zone] = zone
128109
}
129110
}
130111
return

0 commit comments

Comments
 (0)