>  기사  >  PHP 프레임워크  >  Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.

Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.

藏色散人
藏色散人앞으로
2020-09-16 09:15:423558검색

다음 튜토리얼 칼럼인 Laravel에서는 새로운 버전의 Elasticsearch7.9 중국어 검색을 Laravel7 프로젝트에 쉽게 통합하는 방법을 소개하겠습니다. 도움이 필요한 친구들에게 도움이 되길 바랍니다!


ar414 5分钟 集成新版 Elasticsearch7.9 中文搜索 到你的 Laravel7 项目

5단계:

1. ik 중국어 단어 분할 플러그인을 통합하는 Elasticsearch7.9 Docker 이미지를 시작하세요.

강좌 추천 →: "Elasticsearch 전체 텍스트 검색 실습"(실전 전투 영상)

수천만 데이터 동시성 솔루션(이론적 + 실무적)"

2, Laravel7 Scout 구성

3, 모델 모델 구성

4 과정 중에서, 데이터 가져오기

5, 검색

데모 주소

ar414 5分钟 集成新版 Elasticsearch7.9 中文搜索 到你的 Laravel7 项目

www.ar414.com/search?query=php%E5%...

검색 범위

    기사 내용
  • 제목
  • 태그
결과 가중치

    나타나는 키워드 수
  1. 나타나는 키워드 수
검색 페이지

    하이라이트
  • 단어 분할 표시
  • 결과 페이징

머리말

주로 그런데 검색만 하고 싶어서 블로그 기사로 정리

Laravel + Elasticsearch 많은 선배님들이 튜토리얼과 사례를 작성해 오셨는데, Elasticsearch와 laravel 버전이 업그레이드되면서 이전 기사 중 상당수가 새 버전에 적용되지 않게 되었습니다. . 오픈 소스 프로젝트를 사용하기 전에 문서를 읽어 보는 것이 좋습니다. 현재 사용되는 버전 문서는 튜토리얼

    Elasticsearch 7.9
  • Laravel 7
  • elasticsearch-analytic-ik v7.9
  • 으로 보완됩니다.

참조

    ik 중국어 단어 분할 플러그인
  • elasticsearch 공식 문서

ik 중국어 단어 분할 플러그인ik中文分词插件的Elasticsearch

拉取docker

$ docker pull ar414/elasticsearch-7.9-ik-plugin

创建日志和数据存储目录

本地映射到docker容器内,防止docker重启数据丢失

$ mkdir -p /data/elasticsearch/data
$ mkdir -p /data/elasticsearch/log
$ chmod -R 777 /data/elasticsearch/data
$ chmod -R 777 /data/elasticsearch/log

运行

docker run -d -p 9200:9200 -p 9300:9300 -e "discovery.type=single-node" -v /data/elasticsearch/data:/var/lib/elasticsearch -v /data/elasticsearch/log:/var/log/elasticsearch ar414/elasticsearch-7.9-ik-plugin

验证

$ curl http://localhost:9200{
  "name" : "01ac21393985",  "cluster_name" : "docker-cluster",  "cluster_uuid" : "h8L336qcRb2i1aydOv04Og",  "version" : {
    "number" : "7.9.0",    "build_flavor" : "default",    "build_type" : "docker",    "build_hash" : "a479a2a7fce0389512d6a9361301708b92dff667",    "build_date" : "2020-08-11T21:36:48.204330Z",    "build_snapshot" : false,    "lucene_version" : "8.6.0",    "minimum_wire_compatibility_version" : "6.8.0",    "minimum_index_compatibility_version" : "6.0.0-beta1"
  },  "tagline" : "You Know, for Search"}

测试中文分词

curl -X POST "http://localhost:9200/_analyze?pretty" -H 'Content-Type: application/json' -d'
{
  "analyzer": "ik_max_word",
  "text":     "laravel天下无敌"
}
'{
  "tokens" : [
    {
      "token" : "laravel",      "start_offset" : 0,      "end_offset" : 7,      "type" : "ENGLISH",      "position" : 0    },    {
      "token" : "天下无敌",      "start_offset" : 7,      "end_offset" : 11,      "type" : "CN_WORD",      "position" : 1    },    {
      "token" : "天下",      "start_offset" : 7,      "end_offset" : 9,      "type" : "CN_WORD",      "position" : 2    },    {
      "token" : "无敌",      "start_offset" : 9,      "end_offset" : 11,      "type" : "CN_WORD",      "position" : 3    }
  ]}

Laravel 项目中使用 Elasticsearch

Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.
Elasticsearch官方有提供 SDK,在 Laravel 项目中可以更加优雅快速的接入 Elasticsearch,Laravel 本身有提供 Scout全文搜索 的解决方案,我们只需将默认的 Algolia 驱动 替换成ElasticSearch驱动

安装

  • laravel/scout
  • Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.
    $ composer require laravel/scout
    $ composer require Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.

配置

  1. 生成 Scout 配置文件(config/scout.php)

    $ php artisan vendor:publish --provider="Laravel\Scout\ScoutServiceProvider"Copied File [\vendor\laravel\scout\config\scout.php] To [\config\scout.php]Publishing complete.
  2. 指定 Scout 驱动

  • 第一种:在.env文件中指定(建议)
    SCOUT_DRIVER=Matchish\ScoutElasticSearch\Engines\ElasticSearchEngine
  • 第二种:在config/scout.php直接修改默认驱动
    'driver' => env('SCOUT_DRIVER', 'algolia')改为'driver' => env('SCOUT_DRIVER', 'Matchish\ScoutElasticSearch\Engines\ElasticSearchEngine')
  1. 指定Elasticsearch服务IP端口

    如果使用docker部署则使用docker0的IP,Linux通过ifconfig查看

    .env中配置

    ELASTICSEARCH_HOST=172.17.0.1:9200
  2. 注册服务
    config/app.php

  3. 을 통합하는 Elasticsearch를 사용하여 docker를 가져오세요
  4. 'providers' => [
     // Other Service Providers
     \Matchish\ScoutElasticSearch\ElasticSearchServiceProvider::class],

  5. 로그 및 데이터 저장 디렉터리 생성

Docker가 데이터를 다시 시작하지 못하도록 로컬로 매핑 리🎜 🎜🎜Laravel 프로젝트에서 Elasticsearch 사용🎜🎜Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요. 🎜Elasticsearch우아하게 할 수 있는 공식 SDK가 제공됩니다. Elasticsearch에 빠르게 연결됩니다. Laravel 자체는 Scout 전체 텍스트 검색 솔루션을 제공합니다. 기본 Algolia 드라이버를 ElasticSearch 드라이버로 교체하세요. 🎜🎜🎜🎜Installation🎜🎜🎜laravel/scout🎜🎜Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.
$ php artisan config:clear
🎜🎜🎜🎜🎜Configuration🎜🎜🎜🎜Scout 구성 파일 생성(config/scout.php)🎜
$ touch config/elasticsearch.php
🎜 🎜🎜스카우트 드라이버 지정🎜 🎜🎜🎜🎜첫 번째: .env 파일에서
<?phpreturn  [
 &#39;indices&#39; => [
     'mappings' => [
         'blog-articles' => [
             "properties"=>  [
                 "content"=>  [
                     "type"=>  "text",
                     "analyzer"=>  "ik_max_word",
                     "search_analyzer"=>  "ik_smart"
                 ],
                 "tags"=>  [
                     "type"=>  "text",
                     "analyzer"=>  "ik_max_word",
                     "search_analyzer"=>  "ik_smart"
                 ],
                 "title"=>  [
                     "type"=>  "text",
                     "analyzer"=>  "ik_max_word",
                     "search_analyzer"=>  "ik_smart"
                 ]
             ]
         ]
     ]
 ],];
를 지정(권장)합니다.🎜🎜두 번째: config/scout.php에서 기본 드라이버
 namespace App\Models\Blog;

 use Laravel\Scout\Searchable;

 class Article extends BlogBaseModel
 {
     use Searchable;
 }
를 직접 수정합니다. 🎜 🎜
    🎜🎜Elasticsearch 서비스 IP 포트를 지정하세요🎜🎜🎜docker 배포를 사용하는 경우에는 docker0의 IP를 사용하세요. Linux에서는 ifconfig🎜🎜🎜를 통해 확인할 수 있습니다. .env🎜<code>config/app.php🎜
     /**
      * 指定索引
      * @return string
      */
     public function searchableAs()
     {
         return 'blog-articles';
     }
    🎜🎜🎜에서 🎜
     /**
      * 设置导入索引的数据字段
      * @return array
      */
     public function toSearchableArray()
     {
         return [
             'content' => ArticleContent::query()
                 ->where('article_id',$this->id)
                 ->value('content'),
             'tags'    => implode(',',$this->tags),
             'title'   => $this->title
         ];
     }
    🎜🎜🎜등록 서비스 구성🎜
     /**
      * 指定 搜索索引中存储的唯一ID
      * @return mixed
      */
     public function getScoutKey()
     {
         return $this->id;
     }
    
     /**
      * 指定 搜索索引中存储的唯一ID的键名
      * @return string
      */
     public function getScoutKeyName()
     {
         return 'id';
     }
    🎜🎜🎜구성 캐시 지우기🎜
    $ php artisan scout:import "App\Models\Blog\Article"Importing [App\Models\Blog\Article]Switching to the new index
    5/5 [⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬] 100%[OK] All [App\Models\Blog\Article] records have been imported.
    🎜🎜🎜이제 laravel이 다음에 연결되었습니다. 엘라스틱서치🎜

    实际业务中使用

    需求

    14分钟14秒 集成 Elasticsearch中文搜索 到你的 Laravel 项目

    通过博客右上角的搜索框可以搜索到与关键词相关的文章,从以下几点匹配

    • 文章内容
    • 文章标题
    • 文章标签

    涉及到2张 Mysql表 以及字段

    • article
      • title
      • tags
    • article_content
      • content

    为文章配置 Elasticsearch 索引

    1. 创建索引配置文件(config/elasticsearch.php)

      $ touch config/elasticsearch.php
    2. elasticsearch.php 配置字段映射

      <?phpreturn  [
       &#39;indices&#39; => [
           'mappings' => [
               'blog-articles' => [
                   "properties"=>  [
                       "content"=>  [
                           "type"=>  "text",
                           "analyzer"=>  "ik_max_word",
                           "search_analyzer"=>  "ik_smart"
                       ],
                       "tags"=>  [
                           "type"=>  "text",
                           "analyzer"=>  "ik_max_word",
                           "search_analyzer"=>  "ik_smart"
                       ],
                       "title"=>  [
                           "type"=>  "text",
                           "analyzer"=>  "ik_max_word",
                           "search_analyzer"=>  "ik_smart"
                       ]
                   ]
               ]
           ]
       ],];
    • analyzer:字段文本的分词器
      • search_analyzer:搜索词的分词器
      • 根据具体业务场景选择(颗粒小占用资源多,一般场景analyzer使用ik_max_word,search_analyzer使用ik_smart):
        • ik_max_word:ik中文分词插件提供,对文本进行最大数量分词
          laravel天下无敌 -> laravel天下无敌,天下,无敌
        • ik_smart: ik中文分词插件提供,对文本进行最小数量分词
          laravel天下无敌 -> laravel天下无敌

    配置文章模型

    建议先看一遍 Laravel Scout 使用文档

    1. 引入Laravel Scout

       namespace App\Models\Blog;
      
       use Laravel\Scout\Searchable;
      
       class Article extends BlogBaseModel
       {
           use Searchable;
       }
    2. 指定索引(刚刚配置文件中的elasticsearch.indices.mappings.blog-articles)

       /**
        * 指定索引
        * @return string
        */
       public function searchableAs()
       {
           return 'blog-articles';
       }
    3. 设置导入索引的数据字段

       /**
        * 设置导入索引的数据字段
        * @return array
        */
       public function toSearchableArray()
       {
           return [
               'content' => ArticleContent::query()
                   ->where('article_id',$this->id)
                   ->value('content'),
               'tags'    => implode(',',$this->tags),
               'title'   => $this->title
           ];
       }
    4. 指定 搜索索引中存储的唯一ID

       /**
        * 指定 搜索索引中存储的唯一ID
        * @return mixed
        */
       public function getScoutKey()
       {
           return $this->id;
       }
      
       /**
        * 指定 搜索索引中存储的唯一ID的键名
        * @return string
        */
       public function getScoutKeyName()
       {
           return 'id';
       }

    数据导入

    其实是将数据表中的数据通过Elasticsearch导入到Lucene
    Elasticsearch 是 Lucene 的封装,提供了 REST API 的操作接口

    • 一键自动导入: php artisan scout:import
    • 导入指定模型: php artisan scout:import ${model}
    $ php artisan scout:import "App\Models\Blog\Article"Importing [App\Models\Blog\Article]Switching to the new index
    5/5 [⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬⚬] 100%[OK] All [App\Models\Blog\Article] records have been imported.

    导入失败,常见原因:

    • Unresolvable dependency resolving [Parameter #0 [  integer $retries ]] in class Elasticsearch\Transport
      • 解决: 修改配置后,没有清除配置缓存
    • invalid_index_name_exception
      • 解决: searchableAs配置错误,为索引创建别名后,指定别名

    检查索引是否正确

    $ curl -XGET http://localhost:9200/blog-articles/_mapping?pretty{
      "blog-articles_1598362919" : {
        "mappings" : {
          "properties" : {
            "__class_name" : {
              "type" : "text",          "fields" : {
                "keyword" : {
                  "type" : "keyword",              "ignore_above" : 256            }
              }
            },        "content" : {
              "type" : "text",          "analyzer" : "ik_max_word",          "search_analyzer" : "ik_smart"
            },        "tags" : {
              "type" : "text",          "analyzer" : "ik_max_word",          "search_analyzer" : "ik_smart"
            },        "title" : {
              "type" : "text",          "analyzer" : "ik_max_word",          "search_analyzer" : "ik_smart"
            }
          }
        }
      }}

    测试

    1. 创建一个测试命令行

      $ php artisan make:command ElasticTest
    2. 代码

    <?phpnamespace  App\Console\Commands;use App\Models\Blog\Article;use App\Models\Blog\ArticleContent;use Illuminate\Console\Command;use Illuminate\Support\Carbon;class ElasticTest extends Command{
        /**
         * The name and signature of the console command.
         *
         * @var string
         */
        protected $signature = &#39;elasticsearch {query}&#39;;
    
        /**
         * The console command description.
         *
         * @var string
         */
        protected $description = &#39;elasticsearch test&#39;;
    
        /**
         * Create a new command instance.
         *
         * @return void
         */
        public function __construct()
        {
            parent::__construct();
        }
    
        /**
         * Execute the console command.
         *
         * @return mixed
         */
        public function handle()
        {
            //
            $startTime = Carbon::now()->getPreciseTimestamp(3);
            $articles = Article::search($this->argument('query'))->get()->toArray();
            $userTime = Carbon::now()->getPreciseTimestamp(3) - $startTime;
            echo "耗时(毫秒):{$userTime} \n";
    
            //content在另外一张表中,方便观察测试 这里输出
            if(!empty($articles)) {
                foreach($articles as &$article) {
                    $article = ArticleContent::query()->where('article_id',$article['id'])->value('content');
                }
            }
    
            var_dump($articles);
    
        }}
    1. 测试
      $ php artisan elasticsearch 周杰伦

    ar414 5分钟 集成新版 Elasticsearch7.9 中文搜索 到你的 Laravel7 项目

    1. 复杂查询
      例如:自定义高亮显示
      //ONGR\ElasticsearchDSL\Highlight\Highlight ArticleModel::search($query,function($client,$body) {
               $higlight = new Highlight();
               $higlight->addField('content',['type' => 'plain']);
               $higlight->addField('title');
               $higlight->addField('tags');
               $body->addHighlight($higlight);
               $body->setSource(['title','tags']);
               return $client->search(['index' => (new ArticleModel())->searchableAs(), 'body' => $body->toArray()]);
           })->raw();

    复杂自定义查询回调中的$client和$body,可根据这两个包进行灵活操作

    $client 官方 elasticsearch/elasticsearch package(https://packagist.org/packages/elasticsearch/elasticsearch)

    $body ongr/elasticsearch-dsl package(https://packagist.org/packages/ongr/elasticsearch-dsl)

위 내용은 Elasticsearch7.9 중국어 검색의 새 버전을 Laravel7 프로젝트에 쉽게 통합하세요.의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
이 기사는 learnku.com에서 복제됩니다. 침해가 있는 경우 admin@php.cn으로 문의하시기 바랍니다. 삭제