1

Working on a transform for elasticsearch query result

{
   'key': factoryA,
   'buckets': [
       {
          'key': 'productX'
       }
    ]

},
{
   'key': factoryB,
   'buckets': [
       {
          'key': 'productX'
       },
       {
          'key': 'productY'
       }
    ]

}

I want to have a list whose item is a combination of aggregation on factory and its nested aggregation products:

[
   {'factory': 'factoryA', 'product': 'productX'},
   {'factory': 'factoryB', 'product': 'productX'},
   {'factory': 'factoryB', 'product': 'productY'},
]

any advice on painless script ? Thank you in advance. Or any place I can find a comprehensive guide for painless. Painless without Doc is totally painful.

perigee
  • 9,438
  • 11
  • 31
  • 35

1 Answers1

1

I think below query is what you are looking for:

Query

POST <your_index_name>/_search
{  
   "size":0,
   "aggs":{  
      "myagg":{  
         "terms":{  
            "script":{  
               "source":"'factory: ' + doc['factory.keyword'].value + params.param + 'product: ' + doc['product.keyword'].value",
               "lang":"painless",
               "params":{  
                  "param":", "
               }
            },
            "order":{  
               "_term":"asc"
            }
         }
      }
   }
}

Query Response

{
  "took": 6,
  "timed_out": false,
  "_shards": {
    "total": 5,
    "successful": 5,
    "skipped": 0,
    "failed": 0
  },
  "hits": {
    "total": 2,
    "max_score": 0,
    "hits": []
  },
  "aggregations": {
    "myagg": {
      "doc_count_error_upper_bound": 0,
      "sum_other_doc_count": 0,
      "buckets": [
        {
          "key": "factory: factory A, product: product A",
          "doc_count": 1
        },
        {
          "key": "factory: factory B, product: product B",
          "doc_count": 1
        }
      ]
    }
  }
}

Note, I'm assuming that both fields factory and product are of type keyword

Let me know if it helps!

Kamal Kunjapur
  • 8,547
  • 2
  • 22
  • 32
  • thx a lot, really appreciated, I just did not recall that I can still manipulate the aggregration, thx a lot. – perigee Nov 01 '18 at 14:35
  • thx a lot, really appreciated,just one small issue, as the `factory: factoryA, production: productA` cannot convert to json as json format {'factory' : 'factoryA', 'product': 'productA'}, as your result in key is a string not a dict. – perigee Nov 01 '18 at 15:13
  • Hey @perigee I have simply formatted them in that way. Is your expectation something like `"key": { VALUE }` where `VALUE` is a json structure? I can probably format in that way. But then yes it would merely be inside double quotes/string `"{ "factor": "factory A", "product" :"product A" }"`. If that is the case I can help you, otherwise I think what you are looking for is not possible and you may need to manage that in your service/client layer. – Kamal Kunjapur Nov 01 '18 at 16:29
  • thx, actually i want a real json format, as dict, I am looking for if there is method that can access parent aggregation result key. than i can do agg first on factory, then product, and based on the result of query, i can transform them by iterating on product level and reaching parent factory name. – perigee Nov 01 '18 at 18:08
  • Hey @perigee If you are trying to access parent bucket's key in child aggregation, I'm afraid its not possible. Aggregations can only be aggregated on the documents on the same level. Check this link https://discuss.elastic.co/t/using-parent-aggregation-key-in-subaggregation/17153/2 What you are looking for has to be managed at the client's or service layer. – Kamal Kunjapur Nov 01 '18 at 21:03