Skip to content

Commit

Permalink
Add a new preserve tag (preserveWhenMissing) to copy only when the ke…
Browse files Browse the repository at this point in the history
…y wasn't in the target's doc.

That makes it a bit easier to write '"preserveWhenMissing": "*"' and not have to spend us much effort to be more specific.

Signed-off-by: Greg Schohn <[email protected]>
  • Loading branch information
gregschohn committed Dec 9, 2024
1 parent 95b71f4 commit 2b1f3e0
Show file tree
Hide file tree
Showing 5 changed files with 60 additions and 25 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -81,29 +81,6 @@ public Map<String, Object> transformJson(Map<String, Object> incomingJson) {
var resultStr = jinjava.render(templateStr, createContextWithSourceFunction.apply(incomingJson));
log.atInfo().setMessage("output from jinjava... {}").addArgument(resultStr).log();
var parsedObj = (Map<String,Object>) objectMapper.readValue(resultStr, LinkedHashMap.class);
return doFinalSubstitutions(incomingJson, parsedObj);
}

private Map<String, Object> doFinalSubstitutions(Map<String, Object> incomingJson, Map<String, Object> parsedObj) {
return Optional.ofNullable(parsedObj.get(JsonKeysForHttpMessage.PRESERVE_KEY)).filter(v->v.equals("*"))
.map(star -> incomingJson)
.orElseGet(() -> {
findAndReplacePreserves(incomingJson, parsedObj);
findAndReplacePreserves((Map<String, Object>) incomingJson.get(JsonKeysForHttpMessage.PAYLOAD_KEY),
(Map<String, Object>) parsedObj.get(JsonKeysForHttpMessage.PAYLOAD_KEY));
return parsedObj;
});
}

private void findAndReplacePreserves(Map<String, Object> incomingRoot, Map<String, Object> parsedRoot) {
if (parsedRoot == null || incomingRoot == null) {
return;
}
var preserveKeys = (List<String>) parsedRoot.get(JsonKeysForHttpMessage.PRESERVE_KEY);
if (preserveKeys != null) {
preserveKeys.forEach(preservedKey ->
Optional.ofNullable(incomingRoot.get(preservedKey)).ifPresent(v->parsedRoot.put(preservedKey, v)));
parsedRoot.remove(JsonKeysForHttpMessage.PRESERVE_KEY);
}
return PreservesProcessor.doFinalSubstitutions(incomingJson, parsedObj);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
package org.opensearch.migrations.transform;

import java.util.List;
import java.util.Map;

public class PreservesProcessor {
private static final String PRESERVE_KEY = "preserve";
private static final String PRESERVE_WHEN_MISSING_KEY = "preserveWhenMissing";

private PreservesProcessor() {}

@SuppressWarnings("unchecked")
public static Map<String, Object> doFinalSubstitutions(Map<String, Object> incomingJson, Map<String, Object> parsedObj) {
processPreserves(incomingJson, parsedObj);

processPreserves(
(Map<String, Object>) incomingJson.get(JsonKeysForHttpMessage.PAYLOAD_KEY),
(Map<String, Object>) parsedObj.get(JsonKeysForHttpMessage.PAYLOAD_KEY)
);

return parsedObj;
}

private static void processPreserves(Map<String, Object> source, Map<String, Object> target) {
if (target == null || source == null) {
return;
}

copyValues(source, target, PRESERVE_KEY, true);
copyValues(source, target, PRESERVE_WHEN_MISSING_KEY, false);
}

private static void copyValues(Map<String, Object> source, Map<String, Object> target,
String directiveKey, boolean forced) {
Object directive = target.remove(directiveKey);
if (directive == null) {
return;
}

if (directive.equals("*")) {
source.forEach((key, value) -> {
if (forced || !target.containsKey(key)) {
target.put(key, value);
}
});
} else if (directive instanceof List) {
((List<String>) directive).forEach(key -> {
if (source.containsKey(key) &&
(forced || !target.containsKey(key)))
{
target.put(key, source.get(key));
}
});
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@
{%- set source_input_types = input_map.index_mappings[source_index_name] -%}
{%- set source_type_name = source_input_types.keys() | first() -%}
{
"preserve": ["protocol", "headers"],
"preserveWhenMissing": "*",
"method": "{{ input_map.request.method }}",
"URI": "/{{ target_index_name }}",
"payload": {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,7 @@ public void testPutSingleTypeIndex() throws Exception {
var expectedString = "{\n" +
" \"URI\" : \"/a_user\",\n" +
" \"method\" : \"PUT\",\n" +
" \"protocol\" : \"HTTP/1.1\",\n" +
" \"payload\" : {\n" +
" \"inlinedJsonBody\" : {\n" +
" \"mappings\" : {\n" +
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ public static String makePutIndexRequest(String indexName, Boolean useMultiple,
var uri = formatCreateIndexUri(indexName, includeTypeName);
return "{\n" +
" \"" + JsonKeysForHttpMessage.METHOD_KEY + "\": \"PUT\",\n" +
" \"" + JsonKeysForHttpMessage.PROTOCOL_KEY + "\": \"HTTP/1.1\",\n" +
" \"" + JsonKeysForHttpMessage.URI_KEY + "\": \"" + uri + "\",\n" +
" \"" + JsonKeysForHttpMessage.PAYLOAD_KEY + "\": {\n" +
" \"" + JsonKeysForHttpMessage.INLINED_JSON_BODY_DOCUMENT_KEY + "\": " +
Expand Down

0 comments on commit 2b1f3e0

Please sign in to comment.