php使用curl获取elasticsearch中数据

薄洪涛5年前PHP1394

我最近在做一个电动车的项目,其中,有一个功能是这样的,我需要获取指定车辆的最新的五条位置信息,位置信息是保存到es库中的,我使用的是Yii2.0框架,本来想使用Yii封装的组件去获取数据的,然后觉得麻烦,就使用了curl调接口的形式

开始的时候,我是这么写的

function httpPost($server_url, $param) {
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, $server_url); //地址
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_HEADER, 0);
    curl_setopt($ch, CURLOPT_POST, 1); //post数据提交
    curl_setopt($ch, CURLOPT_POSTFIELDS, $param); //数据
    $body = curl_exec($ch);
    curl_close($ch);
    return $body;
}
//$post_data是我查询的语句
httpPost($es_search_url,json_encode($post_data));

然后会报这个错误

{"error":"Content-Type header [application/x-www-form-urlencoded] is not supported","status":406}

对了,我想起了来我应该设置下header头,修改如下

function httpPost($header, $server_url, $param) {
    $ch = curl_init();
    if($header){
        curl_setopt($ch, CURLOPT_HTTPHEADER, $header);
    }
    curl_setopt($ch, CURLOPT_URL, $server_url); //地址
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_HEADER, 0);
    curl_setopt($ch, CURLOPT_POST, 1); //post数据提交
    curl_setopt($ch, CURLOPT_POSTFIELDS, $param); //数据
    $body = curl_exec($ch);
    curl_close($ch);
    return $body;
}
$rs_array = httpPost(["content-Type"=>"application/json"],$es_search_url,json_encode($post_data));

同时指定header为content-Type:application/json

没想到的是,没卵用,还是报上面的错误,然后我改成了这样

function http_post_json($url, $jsonStr)
{
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_POST, 1);
    curl_setopt($ch, CURLOPT_URL, $url);
    curl_setopt($ch, CURLOPT_POSTFIELDS, $jsonStr);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($ch, CURLOPT_HTTPHEADER, array(
            'Content-Type: application/json; charset=utf-8',
            'Content-Length: ' . strlen($jsonStr)
        )
    );
    $response = curl_exec($ch);
    $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
    curl_close($ch);
    return array($httpCode, $response);
}

看到没,需要加一个conent-length,原因是就是,es库对header头有严格的限制,官方解释如下

We know that the content-type sniffing has been quite convenient when using basic HTTP tools such as curl. Many of us are quite accustomed to searching a cluster by running something like this:

curl 'http://localhost:9200/_search' -d'
{
    "query" : {
        "match_all" : {}
    }
}'

But, we need to make that sort of operation slightly more verbose, and include the content-type, in the interests of clarity and security.

As Elasticsearch has evolved we’ve made a conscious decision to favour reliability and predictability over leniency. And while being lenient with content-types has been convenient, it also produced some surprising results.

For example, if you tried to send plain text content to an API that didn’t support it, then you would usually receive a clear error like this:

Content-Type header [text/plain] is not supported

But under the covers Elasticsearch was doing its best to try and guess what you might have meant. So, if your body started with “{” then it would guess that your content was actually JSON, but when it tried to parse that, it would fail and the error message would look more like:

Unexpected character ('a' (code 97)): was expecting double-quote to start field name

And, while most of our APIs support YAML formatted requests, the content-type sniffing required that the body start with a start-of-document marker (“---”), which is not what users expected.

When it comes to content-type, we’ve come to the conclusion that “Say what you mean” provides a more reliable and predictable outcome, than guessing. Being explicit is the safer, clearer and more consistent approach.



标签: Elasticsearch

相关文章

Elasticsearch第三篇之全文搜索及在Yii2.0中的使用

Elasticsearch第三篇之全文搜索及在Yii2.0中的使用

前几天做了一个模块,大数据的搜索,其实也不是特别大,组合起来差不多800万左右,用的是mysql数据库,需求有这么变态的两点;需要按照地址去搜索按照起止时间去搜索别的不说,就这两条,mysql也就只能...

Elasticsearch按照日期聚合

Elasticsearch按照日期聚合

我们现在做的是医疗的业务,有个需求是这样的,查询出某位医生前七天的坐诊记录,并且,医生的坐诊记录是不连续的,这样就需要写一个dsl语句来实现es库的搜索首先我使用了es库中的聚合功能,按照日期去聚合,...

Elasticsearch为什么搜索那么快?

Elasticsearch为什么搜索那么快?

介绍Elasticsearch 是一个分布式可扩展的实时搜索和分析引擎,一个建立在全文搜索引擎 Apache Lucene(TM) 基础上的搜索引擎.当然 Elasticsearch 并不仅仅是 Lu...

Elasticsearch集群第一篇之安装

Elasticsearch集群第一篇之安装

    全文搜索属于最常见的需求,开源的 Elasticsearch (以下简称 Elastic)是目前全文搜索引擎的首选。它可以快速地储存...

Elasticsearch第二篇之数据操作

    上一篇向大家讲解了Elasticsearch的部署安装和基本设置,这篇文章就和大家一起熟悉下Elastic的数据库操作,和普通数据库不同,es库需要公告...

发表评论    

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。