Problem with Mapping Templates

I created a field mapping for keyword only field and ingested the data to ES,but I could still see field.keyword in my index.
In my case field name is AB.Field1
Is it due to .(dot) in my field Name or any other issue?

   PUT _template/test1
{
    "order": 9,
    "version": 1,
    "index_patterns": [
      "test1*",
      "test2*"
    ],
    "settings": {
      "index": {
        "number_of_shards": "2",
        "number_of_replicas": "1",
        "refresh_interval": "5s"
      }
    },
    "mappings": {
        "dynamic_templates": [
          {
            "keyword_only_field": {
              "match_pattern": "regex",
              "match": "^(AB.Field1|BC.Field1|AB.Field2|BC.Field2)$",
              "match_mapping_type": "string",
              "mapping": {
                "type": "keyword",
                "ignore_above": 256
              }
            }
          }
        ]
    },
    "aliases": {}
}

Yes, it is due to the dot. You need to expand the field definition in the mapping.

You could define a regular (not dynamic) mapping for {"AB": {"Field1": <keyword only definition>}}. Your regex is currently just a convenient list of field names, but it's not doing any wider matching like using wildcards *.

If you're sure Field1 will always need to be keyword-only across all AB, BC etc. parent objects, you could use a simple "match": "Field1"dynamic template without regex. E.g.:

PUT _template/test1
{
    "order": 9,
    "version": 1,
    "index_patterns": [
      "test1*",
      "test2*"
    ],
    "settings": {
      "index": {
        "number_of_shards": "2",
        "number_of_replicas": "1",
        "refresh_interval": "5s"
      }
    },
    "mappings": {
        "dynamic_templates": [
          {
            "keyword_only_field": {
              "match": "Field1",
              "match_mapping_type": "string",
              "mapping": {
                "type": "keyword",
                "ignore_above": 256
              }
            }
          }
        ]
    },
    "aliases": {}
}

I tested that in Kibana Dev Console on Elasticsearch 7.9.1. After saving that dynamic template:

PUT test1index

PUT test1index/_doc/testdoc1
{
  "AB": {"Field1": "value1"},
  "regular_field": "regular value"
}

GET test1index/_doc/testdoc1

GET test1index/_mapping

The last query results in

"properties" : {
        "AB" : {
          "properties" : {
            "Field1" : {
              "type" : "keyword",
              "ignore_above" : 256
            }
          }
        },
        "regular_field" : {
          "type" : "text",
          "fields" : {
            "keyword" : {
              "type" : "keyword",
              "ignore_above" : 256
            }
          }
        }
      }

which seems to be what you want.

1 Like

Great Thanks a lot!

1 Like

This topic was automatically closed 28 days after the last reply. New replies are no longer allowed.