Stuck with searching on nested documents


(Raine Nguyen) #1

Hi all, I'm brand new to ElasticSearch (1.0.0 RC1), superb software with so
many new things to learn and I have been pulling our my hair on this for
many days. I think I'm going bald.

Basically I want to search a list of products each contains many options
which in turn contain many values. I will have the mapping and sample data
posted below:

POST test/product/_mapping
{
"product":{
"properties" : {
"name" : {"type" : "string", "store":"yes"},
"manufacturer": {"type": "string"},
"options" : {
"type": "nested",
"properties": {
"name": {"type": "string"},
"values": {"type": "nested"}
}
},
"price":{"type": "integer"}
}
}
}

POST test/product/1
{
"name": "Shirt 1",
"manufacturer": "Umbro",
"options":[
{
"id": 1,
"name": "Color",
"values" : [
{
"id": 1,
"name": "red"
}
]
},
{
"id": 2,
"name": "Size",
"values" : [
{
"id": 2,
"name": "XL"
},
{
"id": 3,
"name": "S"
},
{
"id": 4,
"name": "M"
}
]
}
],
"price":200000
}

POST test/product/2
{
"name": "Shirt 2",
"manufacturer": "Nike",
"options":[
{
"id": 1,
"name": "Color",
"values" : [
{
"id": 11,
"name": "yellow"
},
{
"id": 1,
"name": "red"
}
]
},
{
"id": 2,
"name": "Size",
"values" : [
{
"id": 2,
"name": "XL"
},
{
"id": 4,
"name": "M"
}
]
}
],
"price":100000
}

And this is my current search query, I'm not even sure if it's efficient,
for now it doesn't return anything tho. I simply want to search all
products with the color red and size m:

POST test/product/_search
{

"query": {
    "filtered": {
       "query": {
        "match_all": {}
       },
       "filter": {
           "bool": {
                "must": [
                    {
                      "nested": {
                        "path": "options",
                        "filter": {
                          "bool": {
                              "must": [
                                 {
                                     "bool": {
                                        "must": [
                                          {
                                            "term": {
                                              "options.name": "color"
                                            }
                                          },
                                          {
                                              "nested": {
                                                 "path": 

"options.values",
"filter": {
"term": {

"options.values.name": "red"
}
}
}
}
]
}
},
{
"bool": {
"must": [
{
"term": {
"options.name": "size"
}
},
{
"nested": {
"path":
"options.values",
"filter": {
"term": {

"options.values.name": "m"
}
}
}
}
]
}
}
]
}
}
}
}
]
}
}
}
}
}

It seems like the issue is in the "must" key, but I'm not sure how to fix
it.

Also, I want to get the list of all the available options within the
result as well, how should I do it? (For example, if there were 1000
products, and the result returns 100 products then I want to have the list
of all available options for all these 100 products). It seems like the new
Aggregation on RC1 can help me to do that, I'm just not sure how

--
You received this message because you are subscribed to the Google Groups "elasticsearch" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elasticsearch+unsubscribe@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/elasticsearch/684b86c5-c961-49c0-b5c0-079d01da049c%40googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.


(Raine Nguyen) #2

Is there anyone with an answer at all? I'm feeling hopeless without any
clue.

--
You received this message because you are subscribed to the Google Groups "elasticsearch" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elasticsearch+unsubscribe@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/elasticsearch/6b7feafe-2345-408d-93bd-d183afd2c51f%40googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.


(Binh Ly) #3

I'd probably just simplify and eliminate all the nested stuff. So for
example, if your document is like this:

{
"name": "Shirt1",
"color": ["Red"]
"size": ["XL", "S", "M"]
}

It's easy to execute queries like this:

{
"query": {
"filtered": {
"filter": {
"bool": {
"must": [
{ "term": { "color": "red" } },
{ "term": { "size": "m" } }
]
}
}
}
}
}

The reason your query doesn't match any is because the nested:options part
will look into a single option item to satisfy both your conditions which
will never be true. If you change your query to something like this, it
should work as expected:

{
"query": {
"filtered": {
"query": {
"match_all": {}
},
"filter": {
"bool": {
"must": [
{
"bool": {
"must": [
{
"nested": {
"path": "options",
"filter": {
"bool": {
"must": [
{
"term": {
"options.name": "size"
}
},
{
"nested": {
"path": "options.values",
"filter": {
"term": {
"options.values.name": "m"
}
}
}
}
]
}
}
}
},
{
"nested": {
"path": "options",
"filter": {
"bool": {
"must": [
{
"term": {
"options.name": "color"
}
},
{
"nested": {
"path": "options.values",
"filter": {
"term": {
"options.values.name": "red"
}
}
}
}
]
}
}
}
}
]
}
}
]
}
}
}
}
}

--
You received this message because you are subscribed to the Google Groups "elasticsearch" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elasticsearch+unsubscribe@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/elasticsearch/8bfb26cd-8879-4c9b-ad2a-62be25a2a91c%40googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.


(Raine Nguyen) #4

@Binh Ly: Thank you very much, it works, I just cannot thank you enough
^_^. Thank you.

BTW, I'm trying to get the list of possible product options given a filter
rule set like this for example: Say I have a total of 4 product options:
Color, Material, Size, Price; I filter my products with price range
100-250, and Color Red or Yellow and I get back a list of 1000 products
that satisfy the conditions.
Now I want to filter down to narrow my search result, I need to get the
list of all available option values from those 1000 products (say Material
cotton, nylon and Size XXL, XL, S). Can you please suggest a possible
solution for this?

Raine Ng

On Tuesday, February 11, 2014 9:07:43 PM UTC+7, Binh Ly wrote:

I'd probably just simplify and eliminate all the nested stuff. So for
example, if your document is like this:

{
"name": "Shirt1",
"color": ["Red"]
"size": ["XL", "S", "M"]
}

It's easy to execute queries like this:

{
"query": {
"filtered": {
"filter": {
"bool": {
"must": [
{ "term": { "color": "red" } },
{ "term": { "size": "m" } }
]
}
}
}
}
}

The reason your query doesn't match any is because the nested:options part
will look into a single option item to satisfy both your conditions which
will never be true. If you change your query to something like this, it
should work as expected:

{
"query": {
"filtered": {
"query": {
"match_all": {}
},
"filter": {
"bool": {
"must": [
{
"bool": {
"must": [
{
"nested": {
"path": "options",
"filter": {
"bool": {
"must": [
{
"term": {
"options.name": "size"
}
},
{
"nested": {
"path": "options.values",
"filter": {
"term": {
"options.values.name": "m"
}
}
}
}
]
}
}
}
},
{
"nested": {
"path": "options",
"filter": {
"bool": {
"must": [
{
"term": {
"options.name": "color"
}
},
{
"nested": {
"path": "options.values",
"filter": {
"term": {
"options.values.name": "red"
}
}
}
}
]
}
}
}
}
]
}
}
]
}
}
}
}
}

--
You received this message because you are subscribed to the Google Groups "elasticsearch" group.
To unsubscribe from this group and stop receiving emails from it, send an email to elasticsearch+unsubscribe@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/elasticsearch/e649e7ca-5d25-4e83-9e49-435c7c7a5010%40googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.


(system) #5