做的一个项目,数据是从es获取的,所以最近研究了下yii2.0和es.
yii2.0有自身带有一个扩展 yii-elasticsearch.php,在配置的时候
config->web.php中配置
'elasticsearch' => [
'class' => 'yii\elasticsearch\Connection',
'is_conversion_net_ip' => true,
'conversion_ips' => [
'127.0.0.1' => '127.0.0.3',
'127.0.0.2' => '127.0.0.4',
],
//这两个配置是修改yii2.0扩展中的connection.php,有内网ip的节点的时候yii会返回内网的节点报错,添加这一步是为了转换。 研究好久不知道哪里的问题最后请大神来帮忙解决的。。。。
'nodes' => [
['http_address' => 'inet[/127.0.0.3:9202]'],
['http_address' => '127.0.0.1:9201'],
['http_address' => '127.0.0.2:9202'],
],
],
配置完成之后,在浏览器可以追踪bug,配置文件里这样配置就好
if (YII_ENV_DEV) {
// configuration adjustments for 'dev' environment
$config['bootstrap'][] = 'debug';
$config['modules']['debug'] = [
'class' => 'yii\debug\Module',
'panels' => [
'elasticsearch' => [
'class' => 'yii\elasticsearch\DebugPanel',
],
],
// uncomment the following to add your IP if you are not connecting from localhost.
//'allowedIPs' => ['127.0.0.1', '::1'],
];
}
这样在查询es的时候,可以看到最后生成的es查询语句。这样配置文件就完成了。下面是用es查询
在models新建了一个类 index_type_relation.php
<?php
namespace app\models;
use Yii;
use yii\elasticsearch\ActiveRecord;//使用activerecord类
use yii\helpers\ArrayHelper;
class Index_type_relation extends ActiveRecord
{
// # db
public static function index()
{
return "bi_cq"; //类似连接的库
}
//# table
public static function type()
{
return "index_type_relation";//类似表
}
public function attributes()
{
return ['index_name_s','index_create_type_s','type_name_s'];//返回表的那些字段
}
}
上面是查询一个index,一个type的设置。在controller中的
use app\models\Index_type_relation;
/**
* 获取index_type_relation
*/
public function get_mapping(){
$relation = new Index_type_relation();
$relation = $relation->find()->limit(10000)->all();
$data = ArrayHelper::toArray($relation);
$map_arr = array();
foreach ($data as $k=>$val){
$map_arr[$val['type_name_s']] = $val;
}
return $map_arr;
}
上面是一个index,一个type的查询实例,es支持多个index,多个type的查询,感觉这个很强大,mysql几次查库es一个查询语句搞定
这个没有用activeRecord(没有研究出来怎么用),用的是Query类,写了一个index_query_data类,继承query,使用自带的from()、where()、limit()等
use yii\elasticsearch\Query;
class Index_data_query extends Query
{
/*
* 日基础信息查询
*/
public function get_index_data(&$index_arr, &$table_arr, &$conditons)
{
//$this->from($index_arr,$table_arr)->where($conditons)->addOrderBy('data_date asc')->limit(10000);
$data_key = array(
"date_histogram"=>array(
"field" =>"data_date",
"interval" => "1d",
),
"aggregations" =>array(
"_type" => array(
"terms" => array(
"field" => "_type",
"size" =>10000
),
"aggregations" => array(
"total_l" =>array(
"sum" => array(
"field" => "total_l"
),
),
),
)
)
);
$this->from($index_arr,$table_arr)->where($conditons)->addAggregate('data_date',$data_key)->addOrderBy('data_date asc')->limit(0);
$command = $this->createCommand();
$rows = $command->search([],'post');
$data_arr = $rows['aggregations']['data_date']['buckets'];
return $data_arr;
}
}
中间出现一个问题,yii框架是默认使用的get查询方式,带有聚合的查询出来是源数据形式,所以修改了yii组件的search()方法。默认是get,传post就用post的方式。
目前为止,需要的数据都可以从es获取,其中感觉很有意思是聚合,类似mysql的groupby等。
注:查询源数据不设置limit()的时候es默认是10条,最大是10000,所以查询源数据设置limit(10000),带有聚合的可以设置limit(0),这样既提高查询速度,符合条件的也都可以查出来。
以上是边学习yii边实践,所以有学习不到位的地方,希望大家指正修改。