Skip to content

Commit

Permalink
Support custom classes for dynamic templates.
Browse files Browse the repository at this point in the history
Signed-off-by: Youssef Aouichaoui <[email protected]>
  • Loading branch information
youssef3wi committed Sep 2, 2024
1 parent d641f45 commit 88f2ed3
Show file tree
Hide file tree
Showing 3 changed files with 74 additions and 18 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -677,13 +677,18 @@ private <R> void populateFieldsUsingDynamicTemplates(ElasticsearchPersistentEnti
ElasticsearchPersistentProperty property = targetEntity
.getPersistentPropertyWithFieldName(templateEntry.getKey());
if (property != null && property.isDynamicFieldMapping()) {
targetEntity.getPropertyAccessor(result).setProperty(property,
document.entrySet().stream()
.filter(fieldKey -> templateEntry.getValue().getMatch().stream()
.anyMatch(regex -> simpleMatch(regex, fieldKey.getKey()))
&& templateEntry.getValue().getUnmatch().stream()
.noneMatch(regex -> simpleMatch(regex, fieldKey.getKey())))
.collect(Collectors.toMap(Entry::getKey, Entry::getValue)));
// prepare value
Map<String, Object> values = new HashMap<>();
// TODO: Path match and unmatched
document.entrySet().stream()
.filter(fieldKey -> templateEntry.getValue().getMatch().stream()
.anyMatch(regex -> simpleMatch(regex, fieldKey.getKey()))
&& templateEntry.getValue().getUnmatch().stream()
.noneMatch(regex -> simpleMatch(regex, fieldKey.getKey())))
.forEach(entry -> values.put(entry.getKey(), entry.getValue()));

// set property
targetEntity.getPropertyAccessor(result).setProperty(property, read(property.getType(), Document.from(values)));
}
}
}
Expand Down Expand Up @@ -1089,7 +1094,14 @@ protected void writeProperty(ElasticsearchPersistentProperty property, Object va

addCustomTypeKeyIfNecessary(value, document, TypeInformation.of(property.getRawType()));
writeInternal(value, document, entity);
sink.set(property, document);
if (property.isDynamicFieldMapping()) {
// flatten
for (Entry<String, Object> entry : document.entrySet()) {
sink.set(entry.getKey(), entry.getValue());
}
} else {
sink.set(property, document);
}
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -23,14 +23,7 @@

import java.time.Instant;
import java.time.LocalDate;
import java.util.Collection;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.*;

import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.DisplayName;
Expand Down Expand Up @@ -293,15 +286,24 @@ void shouldMapDynamicFields() {

DynamicFieldDocument document = new DynamicFieldDocument();
document.dynamicFields = Map.of("a_str", randomUUID().toString(), "b_str", randomUUID().toString());
document.value = new DynamicFieldDocument.Value(1L, new Date());
operations.save(document);

// When
SearchHits<DynamicFieldDocument> results = operations.search(new StringQuery(MATCH_ALL), DynamicFieldDocument.class);
SearchHits<DynamicFieldDocument> results = operations.search(new StringQuery(MATCH_ALL),
DynamicFieldDocument.class);

// Then
assertThat(results.getTotalHits()).isEqualTo(1);
assertThat(results.getSearchHits()).first().extracting(SearchHit::getContent).extracting(doc -> doc.dynamicFields)
assertThat(results.getSearchHits()).first()
.extracting(SearchHit::getContent)
.extracting(doc -> doc.dynamicFields)
.isEqualTo(document.dynamicFields);
assertThat(results.getSearchHits()).first()
.extracting(SearchHit::getContent)
.extracting(doc -> doc.value)
.isEqualTo(document.value);

documentOperations.delete();
}

Expand Down Expand Up @@ -966,6 +968,39 @@ private static class DynamicFieldDocument {
@Id String id;

@Field(name = "_str", dynamicTemplate = true) private Map<String, String> dynamicFields = new HashMap<>();

@Nullable
@Field(name = "obj", dynamicTemplate = true) private Value value;

static class Value {
@Nullable
@Field(name = "value_sum", type = FieldType.Long)
private Long sum;

@Nullable
@Field(name = "value_date", type = FieldType.Long)
private Date date;

public Value() {
}

public Value(Long sum, Date date) {
this.sum = sum;
this.date = date;
}

@Override
public boolean equals(Object o) {
if (this == o) return true;
if (!(o instanceof Value value)) return false;
return Objects.equals(sum, value.sum) && Objects.equals(date, value.date);
}

@Override
public int hashCode() {
return Objects.hash(sum, date);
}
}
}
// endregion
}
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,15 @@
"type": "keyword"
}
}
},
{
"obj": {
"match": "value_*",
"mapping": {
"type": "text",
"index": false
}
}
}
]
}

0 comments on commit 88f2ed3

Please sign in to comment.