Search code examples
spring-data-elasticsearch

index is being created or updated when entity is set with createIndex=false


Spring data elastic search version is 4.1.15 I have two issues.

  1. index is being created or updated when entity is set with createIndex=false
  2. JsonIgnore field is being saved.

Here is my first testing.

  1. create index mapping directly via Kibana

  2. entity class is set with createIndex = false.

  3. I added in a new field annoated with @JsonIgnore field. This new field is not in the mapping.

     @JsonInclude(value = JsonInclude.Include.NON_NULL)
     @Document(indexName = "documentIndex", createIndex = false)
     public class Document{
         @Id
         private String id;
    
         @JsonIgnore
         private String test;
     } 
    
     Document obj = new Document();
     obj.setTest("testing");
    
     ObjectMapper om = new ObjectMapper();
     String jsonString = null;
     jsonString = om.writeValueAsString(obj);
     System.out.println(jsonString);
    
     documentRepository.save(obj);
    

jsonString output doesn't included test field, which is as expected. But the object is being saved with new field in ES and the mapping is being updated for the new field.

I did the same test in old Spring data elastic search version 3.2.6 (TransportClient). JsonIgnore field is not being saved. Mappping is not being updated.

I did another testing in 4.1.15. I created an new entity. I don't create any index mapping.

@JsonInclude(value = JsonInclude.Include.NON_NULL)
@Document(indexName = "test_index", createIndex = false)
public class ZTest {
    @Id
    private String id;

    @JsonIgnore
    private String test;
}

@Repository
public interface ZTestRepository  extends ElasticsearchRepository<ZTest, String> {
}

ZTest test = new ZTest();
test.setTest("ztest_testing");

zTestRepository.save(test);

Similar to first testing, index is being automatically created. JsonIgnore field is being saved.

"hits" : [
  {
    "_index" : "test_index",
    "_type" : "_doc",
    "_id" : "xvYrc4EB2riOtG2n0GCk",
    "_score" : 1.0,
    "_source" : {
      "_class" : "com.bean.ZTest",
      "test" : "ztest_testing"
    }
  }
]

Are these valid issues?


Solution

  • index is being created or updated when entity is set with createIndex=false

    Let me clarify what the attribute createIndex does: If this attribute is set tor true (the default) and you are using Spring Data Elasticsearch repositories, then the repository instance which is created at application startup will check if the index defined in the @Document annotation exists. If it does not exist, the index will be created and the mapping for the index will be written according to the properties of the entity that are annotated with @Field (if there is a property without this annotation it will not be written to the mapping.

    If the value of createIndex is false, then this check is not done, no index and mapping are created.

    Now what happens when you call documentRepository.save(obj);? Spring Data Elasticsearch converts the object according to the annotations found on the entity and sends it to Elasticsearch to be saved in the index specified in the @Document annotation.

    If this index does not exist Elasticsearch will create the index and store the object.

    If the index was created by Elasticsearch or you provide properties in the object that were not defined in the inde mapping before - like if you created the mapping manually -, Elasticsearch will add these properties to the mapping auto-guessing their type; read the documentation about dynamic mapping for further information.

    JsonIgnore field is being saved.

    Since version 4.0 (released in May 2020), Spring Data Elasticsearch does not use the Jackson ObjectMapper anymore for writing or reading entities to Elasticsearch. So it makes no sense to convert an entity with a ObjectMapper and compare that to what Spring Data Elasticsearch does.

    If you want a property of your entity class to not be regarded during the conversion, annotate it with the Spring Data annotation @org.springframework.data.annotation.Transient

    Btw, the 4.1.x branch of Spring Data Elasticsearch is out of maintenance since November 2021, you should use an actual version.