|
17 | 17 |
|
18 | 18 | import java.util.HashMap; |
19 | 19 | import java.util.HashSet; |
| 20 | +import java.util.Iterator; |
20 | 21 | import java.util.Map; |
21 | 22 | import java.util.Set; |
22 | 23 |
|
|
30 | 31 | * <p>More specifically, this processor performs the following operations: |
31 | 32 | * <ul> |
32 | 33 | * <li>Renames specific ECS fields to their corresponding OpenTelemetry-compatible counterparts.</li> |
33 | | - * <li>Moves fields to the "attributes" and "resource.attributes" namespaces.</li> |
34 | | - * <li>Flattens the "attributes" and "resource.attributes" maps.</li> |
| 34 | + * <li>Moves all other fields to the "attributes" namespace.</li> |
| 35 | + * <li>Flattens all attributes in the "attributes" namespace.</li> |
| 36 | + * <li>Moves resource fields from the "attributes" namespace to the "resource.attributes" namespace.</li> |
35 | 37 | * </ul> |
36 | 38 | * |
37 | 39 | * <p>If a document is identified as OpenTelemetry-compatible, no transformation is performed. |
@@ -74,10 +76,6 @@ public class NormalizeToOTelProcessor extends AbstractProcessor { |
74 | 76 | KEEP_KEYS = Set.copyOf(keepKeys); |
75 | 77 | } |
76 | 78 |
|
77 | | - private static final String AGENT_PREFIX = "agent"; |
78 | | - private static final String CLOUD_PREFIX = "cloud"; |
79 | | - private static final String HOST_PREFIX = "host"; |
80 | | - |
81 | 79 | private static final String ATTRIBUTES_KEY = "attributes"; |
82 | 80 | private static final String RESOURCE_KEY = "resource"; |
83 | 81 | private static final String SCOPE_KEY = "scope"; |
@@ -119,35 +117,29 @@ public IngestDocument execute(IngestDocument document) { |
119 | 117 | } |
120 | 118 | } |
121 | 119 |
|
122 | | - Map<String, Object> newResource = new HashMap<>(); |
123 | | - Map<String, Object> newResourceAttributes = new HashMap<>(); |
124 | | - newResource.put(ATTRIBUTES_KEY, newResourceAttributes); |
125 | | - |
126 | 120 | source.put(ATTRIBUTES_KEY, newAttributes); |
127 | | - source.put(RESOURCE_KEY, newResource); |
128 | 121 |
|
129 | 122 | renameSpecialKeys(document); |
130 | 123 |
|
131 | | - // Iterate through all top level keys and move them to the appropriate namespace |
| 124 | + // move all top level keys except from specific ones to the "attributes" namespace |
132 | 125 | final var sourceItr = source.entrySet().iterator(); |
133 | 126 | while (sourceItr.hasNext()) { |
134 | 127 | final var entry = sourceItr.next(); |
135 | | - final var key = entry.getKey(); |
136 | | - final var value = entry.getValue(); |
137 | | - if (KEEP_KEYS.contains(key)) { |
138 | | - continue; |
139 | | - } |
140 | | - if (shouldMoveToResourceAttributes(key)) { |
141 | | - newResourceAttributes.put(key, value); |
142 | | - } else { |
143 | | - newAttributes.put(key, value); |
| 128 | + if (KEEP_KEYS.contains(entry.getKey()) == false) { |
| 129 | + newAttributes.put(entry.getKey(), entry.getValue()); |
| 130 | + sourceItr.remove(); |
144 | 131 | } |
145 | | - sourceItr.remove(); |
146 | 132 | } |
147 | 133 |
|
148 | 134 | // Flatten attributes |
149 | | - source.put(ATTRIBUTES_KEY, Maps.flatten(newAttributes, false, false)); |
150 | | - newResource.put(ATTRIBUTES_KEY, Maps.flatten(newResourceAttributes, false, false)); |
| 135 | + Map<String, Object> flattenAttributes = Maps.flatten(newAttributes, false, false); |
| 136 | + source.put(ATTRIBUTES_KEY, flattenAttributes); |
| 137 | + |
| 138 | + Map<String, Object> newResource = new HashMap<>(); |
| 139 | + Map<String, Object> newResourceAttributes = new HashMap<>(); |
| 140 | + newResource.put(ATTRIBUTES_KEY, newResourceAttributes); |
| 141 | + source.put(RESOURCE_KEY, newResource); |
| 142 | + moveResourceAttributes(flattenAttributes, newResourceAttributes); |
151 | 143 |
|
152 | 144 | return document; |
153 | 145 | } |
@@ -257,13 +249,16 @@ static void renameSpecialKeys(IngestDocument document) { |
257 | 249 | }); |
258 | 250 | } |
259 | 251 |
|
260 | | - private static boolean shouldMoveToResourceAttributes(String key) { |
261 | | - return key.startsWith(AGENT_PREFIX + ".") |
262 | | - || key.equals(AGENT_PREFIX) |
263 | | - || key.startsWith(CLOUD_PREFIX + ".") |
264 | | - || key.equals(CLOUD_PREFIX) |
265 | | - || key.startsWith(HOST_PREFIX + ".") |
266 | | - || key.equals(HOST_PREFIX); |
| 252 | + private static void moveResourceAttributes(Map<String, Object> attributes, Map<String, Object> resourceAttributes) { |
| 253 | + Set<String> ecsResourceFields = EcsOTelResourceAttributes.LATEST; |
| 254 | + Iterator<Map.Entry<String, Object>> attributeIterator = attributes.entrySet().iterator(); |
| 255 | + while (attributeIterator.hasNext()) { |
| 256 | + Map.Entry<String, Object> entry = attributeIterator.next(); |
| 257 | + if (ecsResourceFields.contains(entry.getKey())) { |
| 258 | + resourceAttributes.put(entry.getKey(), entry.getValue()); |
| 259 | + attributeIterator.remove(); |
| 260 | + } |
| 261 | + } |
267 | 262 | } |
268 | 263 |
|
269 | 264 | public static final class Factory implements Processor.Factory { |
|
0 commit comments