Elasticsearch Text with Path Hierarchy vs KeyWord using Prefix query performance

Viewed 17

I'm trying to achieve the best way to filter results based on folder hierarchies. We will use this to simulate a situation where we want to get all assets/documents in provided folder and all subfolders (recursive search).

So for example for such a structure

/someFolder/someSubfolder/1
/someFolder/someSubfolder/1/subFolder
/someFolder/someSubfolder/2
/someFolder/someSubfolder/2/subFolder

If we search for /someFolder/someSubfolder/1

We want to get as results

/someFolder/someSubfolder/1
/someFolder/someSubfolder/1/subFolder

Now I've found two ways to do this. Not sure which one would be better from performance perspective.

  1. Use Text property with path_hierarchy Tokenizer
  2. Use Keyword property and use Query prefix to get results

Both of the above seem to work as I want them to (unless I missed something). Not sure which one would be better. On one hand I've read that filtering should be done on Keywords. On the other hand path_hierarchy Tokenizer seems to be created exactly for these scenarios but we can only use it with Text field.

Below I prepared a sample code.

Create index and push some test data into it.

PUT test-index-2
{
  "settings": {
    "analysis": {
      "analyzer": {
        "my_analyzer": {
          "type": "custom",
          "tokenizer": "my_tokenizer"
        }
      },
      "tokenizer": {
        "my_tokenizer": {
          "type": "path_hierarchy"
        }
      }
    }
  },
    "mappings": {
    "properties": {
      "folderPath": {
            "type": "text",
            "analyzer": "my_analyzer",
            "fields": {
              "keyword": {
                "type": "keyword",
                "ignore_above": 256
              }
            }
          }
    }
  }
}

POST test-index-2/_doc/
{
  "folderPath": "8bf5ad7949a1_104d753b-0fdf-4b07-9213-534dec89112a/Folder with Spaces"
}

POST test-index-2/_doc/
{
  "folderPath": "8bf5ad7949a1_104d753b-0fdf-4b07-9213-534dec89112a/Folder with Spaces/SomeTestValue/11"
}

Now both of below queries will return two results for matching partial path hierarchy.

1.

GET test-index-2/_search
{
  "query": { 
    "bool": { 
      "filter": [ 
        { "term":  { "folderPath": "8bf5ad7949a1_104d753b-0fdf-4b07-9213-534dec89112a/Folder with Spaces" }}
      ]
    }
  }
}
  1. GET test-index-2/_search { "query": { "prefix" : { "folderPath.keyword": "8bf5ad7949a1_104d753b-0fdf-4b07-9213-534dec89112a/Folder with Spaces" } } }

Now the question would be: Which solution is better if we want to get a subset of results ?

0 Answers
Related