Skip to content

Commit a5718ec

Browse files
Adding initial extractor
1 parent a813949 commit a5718ec

File tree

1 file changed

+92
-0
lines changed

1 file changed

+92
-0
lines changed
Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
/*
2+
* Copyright Elasticsearch B.V. and/or licensed to Elasticsearch B.V. under one
3+
* or more contributor license agreements. Licensed under the Elastic License
4+
* 2.0; you may not use this file except in compliance with the Elastic License
5+
* 2.0.
6+
*/
7+
8+
package org.elasticsearch.xpack.inference.common;
9+
10+
import java.util.ArrayList;
11+
import java.util.List;
12+
import java.util.Map;
13+
import java.util.regex.Matcher;
14+
import java.util.regex.Pattern;
15+
16+
public class MapPathExtractor {
17+
18+
private static final String DOLLAR_DOT = "$.";
19+
private static final String DOLLAR = "$";
20+
21+
public static Object extract(Map<String, Object> data, String path) {
22+
if (data == null || data.isEmpty() || path == null || path.trim().isEmpty()) {
23+
return null;
24+
}
25+
26+
var cleanedPath = path.trim();
27+
28+
// Remove the prefix if it exists
29+
if (cleanedPath.startsWith(DOLLAR_DOT)) {
30+
cleanedPath = cleanedPath.substring(DOLLAR_DOT.length());
31+
} else if (cleanedPath.startsWith(DOLLAR)) {
32+
cleanedPath = cleanedPath.substring(DOLLAR.length());
33+
}
34+
35+
return navigate(data, cleanedPath);
36+
}
37+
38+
private static Object navigate(Object current, String remainingPath) {
39+
if (remainingPath == null || remainingPath.isEmpty()) {
40+
return current;
41+
}
42+
43+
var dotFieldPattern = Pattern.compile("^\\.([^.\\[]+)(.*)");
44+
// var arrayIndexPattern = Pattern.compile("^\\[(\\d+)\\](.*)");
45+
var arrayWildcardPattern = Pattern.compile("^\\[\\*\\](.*)");
46+
47+
Matcher dotFieldMatcher = dotFieldPattern.matcher(remainingPath);
48+
// Matcher arrayIndexMatcher = arrayIndexPattern.matcher(remainingPath);
49+
Matcher arrayWildcardMatcher = arrayWildcardPattern.matcher(remainingPath);
50+
51+
if (dotFieldMatcher.matches()) {
52+
String field = dotFieldMatcher.group(1);
53+
String nextPath = dotFieldMatcher.group(2);
54+
if (current instanceof Map) {
55+
return navigate(((Map<?, ?>) current).get(field), nextPath);
56+
}
57+
} else if (arrayIndexMatcher.matches()) {
58+
String indexStr = arrayIndexMatcher.group(1);
59+
String nextPath = arrayIndexMatcher.group(2);
60+
try {
61+
int index = Integer.parseInt(indexStr);
62+
if (current instanceof List) {
63+
List<?> list = (List<?>) current;
64+
if (index >= 0 && index < list.size()) {
65+
return navigate(list.get(index), nextPath);
66+
}
67+
}
68+
} catch (NumberFormatException e) {
69+
// Ignore invalid index
70+
}
71+
} else if (arrayWildcardMatcher.matches()) {
72+
String nextPath = arrayWildcardMatcher.group(1);
73+
if (current instanceof List) {
74+
List<?> list = (List<?>) current;
75+
List<Object> results = new ArrayList<>();
76+
for (Object item : list) {
77+
Object result = navigate(item, nextPath);
78+
if (result != null) {
79+
if (result instanceof List) {
80+
results.addAll((List<?>) result);
81+
} else {
82+
results.add(result);
83+
}
84+
}
85+
}
86+
return results.isEmpty() ? null : results;
87+
}
88+
}
89+
90+
return null; // Path not found or invalid
91+
}
92+
}

0 commit comments

Comments
 (0)