Manganese
Manganese

Reputation: 690

Elasticsearch: cURL to Ajax request

I am using Ajax request for elasticsearch to get search results. Finally, I have found the query which I have to go for. (This is a follow up question to link)

Here is the query in cURL:

[~]$ curl -XGET 'localhost:9200/firebase/_search?pretty' -H 'Content-Type: application/json' -d'
> {"query": {"match": {"song": {"query": "i am in", "operator": "and"}}}}'

Result:

{
  "took" : 286,
  "timed_out" : false,
  "_shards" : {
    "total" : 5,
    "successful" : 5,
    "failed" : 0
  },
  "hits" : {
    "total" : 1,
    "max_score" : 0.8630463,
    "hits" : [
      {
        "_index" : "firebase",
        "_type" : "song",
        "_id" : "0001",
        "_score" : 0.8630463,
        "_source" : {
          "song" : "i am in california",
          "song_name" : "hello",
          "song_url" : "https://s3.ap-south-1.amazonaws.com/..."
        }
      }
    ]
  }
}

This query gives me result exactly what I need. When I am using the same request with AJAX, it gives me a bad request.

Ajax.js

Case 1:

$(function() {
    $('#message').keyup(function() {    
        var query = {
            "query": {
                "match": {
                    "song": {
                        "query": $("#message").val(),
                        "operator": "and"
                    }
                }
            }
        };

        console.log(JSON.stringify(query));

        $.ajax({
            type: "GET",
            url: "http://localhost:9200/firebase/_search",
            contentType: 'application/json',
            data: query,
            success: searchSuccess,
            dataType: 'json'
        });

    });

});

Result in console:

enter image description here

Case 2: If I convert the 'data' using JSON.stringify, it gives me:enter image description here

Case 3: If I change the query structure as following and use JSON.stringify on 'data':

var query = {
    query: {
        match: {
            song: {
                query: $("#message").val(),
                operator: "and"
            }
        }
    }
};

Result is:

enter image description here

I am not sure what's the issue here, the query is correct because using the same with cURL I am getting correct results in bash. Question is how to correctly create the Ajax request here. Pointers would be appreciated.

Edit: And yes I have enabled CORS in elasticsearch.yml:

http.cors.enabled : true
http.cors.allow-origin : "*"
http.cors.allow-methods : OPTIONS, HEAD, GET, POST, PUT, DELETE
http.cors.allow-headers : X-Requested-With,X-Auth-Token,Content-Type, Content-Length

Edit1: Chrome, Network data underneath so as to provide more information: enter image description here

Edit2: Full error response is below:

{"error":{"root_cause":[{"type":"illegal_argument_exception","reason":"request [/firebase/_search] contains unrecognized parameters: [query[match][song][operator]], [query[match][song][query]]"}],"type":"illegal_argument_exception","reason":"request [/firebase/_search] contains unrecognized parameters: [query[match][song][operator]], [query[match][song][query]]"},"status":400}

Upvotes: 3

Views: 1635

Answers (2)

Pedro Estevão
Pedro Estevão

Reputation: 1074

For those coming from Google, another way to solve this problem - or even if the POST solution doesn't work - is to use source parameter in the URL, as mentioned in docs[1].

$.ajax({
  type: "GET",
  url: "http://localhost:9200/firebase/_search?source_content_type=application/json&source=" + JSON.stringify(query),
  contentType: 'application/json',
  success: searchSuccess,
  dataType: 'json'
});

[1] https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#_request_body_in_query_string

Upvotes: 1

mugbi
mugbi

Reputation: 84

From my experience the behavior of GET methods with a body is sometimes hard to predict. Actually, elastic search supports GET with body but I also had some strange results depending on the configuration of the servers, proxies and so on... The documentation even highlights the problems with javascript (search with GET).

Usually, using POST instead of GET helps to resolve these problems or at least to have a further debug option.

Upvotes: 3

Related Questions