27

I try to index some nested documents into an Elasticsearch (v2.3.1) mapping which looks as follows (based on this example from the documentation):

PUT /my_index
{
  "mappings": {
    "blogpost": {
      "properties": {
        "title": { "type": "string" },
        "comments": {
          "type": "nested", 
          "properties": {
            "name":    { "type": "string"  },
            "comment": { "type": "string"  }
          }
        }
      }
    }
  }
}

However, I do not understand what my JSON documents have to look like in order to fit into that mapping. I tried with

PUT /my_index/some_type/1
{
  "title": "some_title",
  "comments": {
    "name": "some_name",
    "comment": "some_comment"
  }
}

as well as with

PUT /my_index_some_type/1
{
  "title": "some_title",
  "comments": [
      {
        "name": "some_name",
        "comment": "some_comment"
      }
  ]
}

which both result in

{

    "error": 

{

    "root_cause": 

[

            {
                "type": "remote_transport_exception",
                "reason": "[Caiman][172.18.0.4:9300][indices:data/write/index[p]]"
            }
        ],
        "type": "illegal_argument_exception",
        "reason": "object mapping [comments] can't be changed from nested to non-nested"
    },
    "status": ​400

}

Which is the correct format to index nested documents? Any working examples are much appreciated, most examples here at SO or on other pages concentrate on nested queries rather than how the documents have been indexed before.

Dirk
  • 9,381
  • 17
  • 70
  • 98
  • 4
    Are you using the `blogpost` mapping type in your URL or not? It's not clear from your question (i.e. `some_type` vs `blogpost`). It seems you're really creating a document of type `some_type` and `comments` will default to a normal object, which is not allowed since you already have a nested object called `comments` in the `blogpost` mapping type. – Val Apr 12 '16 at 12:17
  • Ahh no, seriously... that's what happens when you copy and paste too much from different sources. If you want to add this as an answer, I'll be happy to accept it so that we have one more complete example around. – Dirk Apr 12 '16 at 12:33

1 Answers1

22

It seems you're really creating a document of type some_type and comments will default to a normal object (i.e. not nested), which is not allowed since you already have a nested object called comments in the blogpost mapping type in the same index.

Try this instead and it should work:

PUT /my_index/blogpost/1
{
  "title": "some_title",
  "comments": {
    "name": "some_name",
    "comment": "some_comment"
  }
}
Val
  • 207,596
  • 13
  • 358
  • 360
  • 2
    How is this an answer? It's exactly as the same as the example that doesn't work (except for the change of the type). I have this problem, I am using the correct type, and I keep getting the same error. – Gullbyrd Jan 29 '17 at 15:56
  • 5
    @Gullbyrd look at the type name more carefully (hint: `blogpost` instead of `some_type`) ;-) I suggest you create a new question referencing this one but explaining your context and details and we'll be able to figure it out. – Val Jan 29 '17 at 15:59
  • @Val while it works if I remove the type, how do i still ensure that the document type is what i want it to be when i create it. I'm migrating from 2.4 to 7.6 – Vishnu Narang Mar 19 '20 at 23:43
  • @Val (answering my own question) I just figured it out. As per the documentation, mapping-types are removed. https://www.elastic.co/guide/en/elasticsearch/reference/7.6/removal-of-types.html We need to either use an explicit field or use a different index for each mapping type. – Vishnu Narang Mar 19 '20 at 23:47