问题
Below is mapping which i have
{
"defaultBoostValue":1.01,
"boostDetails": [
{
"Type": "Type1",
"value": 1.0001
},
{
"Type": "Type2",
"value": 1.002
},
{
"Type": "Type3",
"value": 1.0005
}
]
}
I want to apply boost type based on type , so if boostType is Type3 then boostFactor should be 1.0005, and if it does not have that boostType, it should apply "defaultBoostValue" as boost below is the query which i have tried
{
"query": {
"function_score": {
"boost_mode": "multiply",
"functions": [
{
"filter": {
"match": {
"boostDetails.Type": "Type1"
}
},
"field_value_factor": {
"field": "boostDetails.value",
"factor": 1,
"missing": 1
}
}
]
}
}
}
it is not working as expected as boostDetails is array of object, how can we apply filter on such case
回答1:
You could use a Script Score function_score query
{
"query": {
"function_score": {
"boost_mode": "multiply",
"functions": [
{
"filter": {
"match": {
"boostDetails.Type": "Type1"
}
},
"script_score": {
"script": {
"source": """
double findBoost(Map params_copy) {
for (def group : params_copy._source.boostDetails) {
if (group['Type'] == params_copy.preferredBoostType ) {
return group['value'];
}
}
return params_copy._source['defaultBoostValue'];
}
return findBoost(params)
""",
"params": {
"preferredBoostType": "Type1"
}
}
}
}
]
}
}
}
but keep in mind that if this particular boost type (Type1
) does not exist in a given document, the filter
of your function_score
query will prevent this script from activation -> the defaultBoostValue
won't be defaulted to at all.
So what I'd recommend instead is using a match_all
filter instead and of course keeping the preferredBoostType
:
{
"query": {
"function_score": {
"boost_mode": "multiply",
"functions": [
{
"filter": {
"match_all": {} <---
},
"script_score": {
"script": {
"source": """
...
""",
"params": {
"preferredBoostType": "Type1"
}
}
}
}
]
}
}
}
BTW, if your boostDetails
array is not of type nested
, you'll probably encounter unexpected and seemingly results as explained here and here.
来源:https://stackoverflow.com/questions/65688013/elastic-search-filter-based-on-array-of-object