前言
Elasticsearch 是一个基于 Apache Lucene (TM) 的开源搜索引擎,无论在开源还是专有领域,Lucene 可 以被认为是迄今为止最先进、性能最好的、功能最全的搜索引擎库。
Elasticsearch 也是使用 Java 编写并使用 Lucene 来建立索引并实现搜索功能,但是它的目的是通过简单连贯的 RESTful API 让全文搜索变得简单并隐藏 Lucene 的复杂性。
这里不在讲解es的基础,下面直接与laravel进行融合使用,走着!!
安装类库包文件
使用composer安装elasticsearch类库包
composer require elasticsearch/elasticsearch -vvv
创建index索引(mysql中的数据表)
这里推荐用 Laravel 自带的 Artisan 命令行功能。
php artisan make:command ESOpenCommand
会在 app\Console\Commands\ 目录下创建 ESOpenCommand.php
/**
* The name and signature of the console command.
* 这是命令的名字
* @var string
*/
//运行命令的名称
protected $signature = 'command:esInit';
/**
* The console command description.
* 命令的描述
* @var string
*/
protected $description = 'Command description';
/**
* Create a new command instance.
* @return void
*/
public function __construct()
{
parent::__construct();
}
/**
* 在这里写要写的东西
* Execute the console command.
* @return mixed
*/
public function handle()
{
//coding,待会儿我们要在这里写代码
}
在 ESOpenCommand.php 里的 handle () 方法里写
//主机地址 如:[127.0.0.1:9200]
$config = config('elasticSearch.host');
//要生成的索引 如:test
$index = config('elasticSearch.index');
// 得到es客户端对象
$client = ClientBuilder::create()->setHosts($config)->build();
//检查要创建的index类型是否存在,存在删除
if ($client->indices()->exists(['index' => $index])) {
$this->warn("Index {$index} exists, deleting...");
$client->indices()->delete(['index' => $index]);
}
$this->info("Creating index: {$index}");
// 创建索引
$params = [
// 生成索引的名称
'index' => $index,
// 类型 body
'body' => [
'settings' => [
// 分区数
'number_of_shards' => 5,
// 副本数
'number_of_replicas' => 1
],
'mappings' => [
'_doc' => [
'_source' => [
'enabled' => true
],
// 字段 类似表字段,设置类型
'properties' => [
'fang_name' => [
// 相当于数据查询是的 = 张三你好,必须找到张三你好
'type' => 'keyword'
],
'fang_desn' => [
'type' => 'text',
//中文分词 张三你好 张三 你好 张三你好
'analyzer' => 'ik_max_word',
'search_analyzer' => 'ik_max_word'
]
]
]
]
]
];
return $client->indices()->create($params);
执行运行命令
php artisan command:esInit
效果图如下:
打开kibana检查test是否创建成功
//查看索引状态
GET /_cat/indices
单例封装es类库
<?php
namespace App\Business;
use Elasticsearch\ClientBuilder;
class ElasticSearchBusiness
{
/**
* 定义单例es
* @var \Elasticsearch\Client
*/
private $Esclient;
/**
* 定义单例变量
* @var
*/
private static $_instance;
/**
* 私有构造方法
*/
private function __construct()
{
$hosts = config('elasticSearch.host');
$this->Esclient = ClientBuilder::create()->setHosts($hosts)->build();
}
/**
* 入口文件
* @return ElasticSearchBusiness
*/
public static function getInstance()
{
if (self::$_instance == false) {
self::$_instance = new self();
}
return self::$_instance;
}
/**
* 同步es文档 (新增/修改)
* @param $params
* @return array|callable
*/
public function syncFangEsInfo($params)
{
return $this->Esclient->index($params);
}
/**
* 搜索es文档信息 (搜索数据)
* @param $params
* @return array|callable
*/
public function getEsFangData($params)
{
return $this->Esclient->search($params);
}
}
使用单例模式实现es数据更新(新增/修改)
$params = [
'index' => 'fang',
'type' => '_doc',
//id不存在,为新增;存在则修改
'id' => $result->id,
'body' => [
//字段根据自己业务来做...
'fang_name' => $result->fang_name,
'fang_desn' => $result->fang_desn,
'fang_xiaoqu' => $result->fang_xiaoqu,
'fang_owner_name' => $fangOwner->name,
'fang_addr' => $result->fang_addr,
'fang_using_area' => $result->fang_using_area,
'fang_year' => $result->fang_year,
'fang_rent' => $result->fang_rent,
'fang_status' => $result->fang_status == 0 ? '未出租' : '已出租',
'created_at' => $result->created_at,
],
];
// 添加数据到索引文档中
ElasticSearchBusiness::getInstance()->syncFangEsInfo($params);
使用单例模式实现es数据搜索(高亮加分页)
// 拼写es搜索样式
$params = [
'index' => 'fang',//数据库
'type' => '_doc',//数据表
'body' => [
'query' => [//查询字段
'match' => [
'fang_name' => [
'query' => $fang_name
]
]
],
"highlight" => [//搜索高亮显示
"fields" => [
"fang_name" => [
"pre_tags" => [
"<span style='color: red'>"
],
"post_tags" => [
"</span>"
]
]
]
],
],
'size' => 10, //每页显示条数 $request->get('size',10)
'from' => 0, //偏移量 $request->get('from',0)
];
//es搜索显示
$results = ElasticSearchBusiness::getInstance()->getEsFangData($params);
//处理es搜索后数据
foreach ($results['hits']['hits'] as $key => $item) {
$results['hits']['hits'][$key]['_source']['id'] = $results['hits']['hits'][$key]['_id'];
$results['hits']['hits'][$key]['_source']['fang_name'] = $item['highlight']['fang_name'][0];
}
$data = array_column($results['hits']['hits'], '_source');
return $data;