Начало работы с Elasticsearch в Python. Часть 1

NOP
NOP::Nuances of Programming
5 min readJun 12, 2018

Перевод статьи Adnan Siddiqi: Getting started with Elasticsearch in Python

В этой статье мы обсудим, что такое Elasticsearch и каким образом она взаимодействует с различными Python приложениями.

Что такое Elasticsearch?

Elasticsearch(ES) — это распространенная поисковая система с открытым исходным кодом, основанная на индексе Lucene. Написана она на языке Java и доступна для многих платформ. Все неструктурированные данные хранятся в формате JSON, что автоматически делает ES базой данных NoSQL. Но в отличие от других баз данных NoSQL, ES предоставляет возможности поиска и другие, не менее интересные функции.

Варианты использования Elasticsearch

ES- многозадачная система. Некоторые из ее возможностей мы приведем ниже:

  • Например, вы владеете сайтом, на котором предоставлено множество динамического контента: будь то интернет-магазин или ваш личный блог. Внедрив ES, вы сможете обеспечить не только многопоточную и надежную поисковую систему для вашего веб-сайта, но и предоставите пользователям функции автозаполнения в вашем приложении.
  • У вас появится возможность просматривать данные журнала события, чтобы в дальнейшем составлять графики тенденций и статистики.

Настройка и запуск

Самый простой способ установить Elasticsearch — просто скачать его и запустить исполняемый файл. Единственное, перед запуском вы должны убедиться, что используете Java 7 или более позднюю версию.

После загрузки файла, распакуйте его и запустите бинарный файл:

elasticsearch-6.2.4 bin/elasticsearch

В окне прокрутки будет тонна текста и вам вряд ли удастся проследить весь процесс. Но если вы увидите что-то похожее на то, что на картинке снизу, значит все идет по плану.

[2018-05-27T17:36:11,744][INFO ][o.e.h.n.Netty4HttpServerTransport] [c6hEGv4] publish_address {127.0.0.1:9200}, bound_addresses {[::1]:9200}, {127.0.0.1:9200}

После установки и запуска, проверьте сервер. Добавьте URL http://localhost:9200 в ваш браузер или через cURL. Если все пройдет гладко, вам должен прийти вот такой ответ:

{
"name" : "c6hEGv4",
"cluster_name" : "elasticsearch",
"cluster_uuid" : "HkRyTYXvSkGvkvHX2Q1-oQ",
"version" : {
"number" : "6.2.4",
"build_hash" : "ccec39f",
"build_date" : "2018-04-12T20:37:28.497551Z",
"build_snapshot" : false,
"lucene_version" : "7.2.1",
"minimum_wire_compatibility_version" : "5.6.0",
"minimum_index_compatibility_version" : "5.0.0"
},
"tagline" : "You Know, for Search"
}

Итак, прежде чем перейти на следующий уровень, а именно взаимодействие Elasticsearch с Python, я расскажу о REST API, который мы будем использовать для различных задач.

Простые примеры

Неважно что вам скажут другие, первым делом нужно создать индекс. Все хранится в индексе. Эквивалент RDBMS в индексе является базой данных, поэтому не путайте его с типичной концепцией индексирования, которую вы когда-то выучили в RDBMS. Я использую PostMan для запуска REST API.

Если он успешно заработает, вы увидите что-то вроде этого:

{
"acknowledged": true,
"shards_acknowledged": true,
"index": "company"
}

Мы создали базу данных с названием company. Другими словами, мы создали индекс под названием company. Если вы перейдете по адресу http://localhost:9200/company из вашего браузера, тогда вы увидите что-то вроде этого:

{
"company": {
"aliases": {

},
"mappings": {

},
"settings": {
"index": {
"creation_date": "1527638692850",
"number_of_shards": "5",
"number_of_replicas": "1",
"uuid": "RnT-gXISSxKchyowgjZOkQ",
"version": {
"created": "6020499"
},
"provided_name": "company"
}
}
}
}

Игнорируйте mappings на данный момент, обсудим это позже. Скажу только, что на деле ничего не произойдет, кроме создания микроразметки вашего документа. creation_date говорит сам за себя, то есть он создает даты. number_of_shards сообщает о количестве разделов, которые будут хранить данные этого индекса. Хранить все данные на одном диске не имеет смысла, поэтому если вы используете кластер из нескольких узлов Elastic, все данные разобьются на них. Говоря простым языком, если существует пять сегментов, то все данные разобьются между пятью сегментами и кластер Elasticsearch сможет обслуживать запросы от любого из своих узлов.

number_of_replicas — это зеркальное отображение ваших данных. Если вы знакомы с концепцией master-slave, то это не должно быть для вас в новинку. Узнать больше об основных концепциях ES вы сможете перейдя по ссылке.

сURL версия создания индекса является однострочной.

➜  elasticsearch-6.2.4 curl -X PUT localhost:9200/company
{"acknowledged":true,"shards_acknowledged":true,"index":"company"}%

Вы также можете выполнить за один раз, как создание индекса, так и внесение отчета. Все, что вам нужно сделать, это передать свою запись в формате JSON. В PostMan для этого нужно будет проделать нехитрые действия:

Убедитесь, что вы задали для Content-Type значение application/json

Это создаст индекс, названный, company (если его еще не существует), а затем создаст новый тип под названием employees. Тип (type) в ES — это тоже самое, что и таблица в RDBMS.

Вышеуказанные запросы выведут следующую структуру JSON:

{
"_index": "company",
"_type": "employees",
"_id": "1",
"_version": 1,
"result": "created",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 0,
"_primary_term": 1
}

Вы передаете /1 как ID (идентификатор) вашей записи. Однако это необязательно. Все, что сделает запрос — установит в поле _id значение 1. Затем вам необходимо передать свои данные в формате JSON, который в конечном счете будет вставлен в новую запись или документ. Если вы перейдете по http://localhost:9200/company/employees/1 в вашем браузере, то увидите нечто похожее на это:

{"_index":"company","_type":"employees","_id":"1","_version":1,"found":true,"_source":{
"name": "Adnan Siddiqi",
"occupation": "Consultant"
}}

Вы можете посмотреть фактическую запись вместе с метаданными. Если хотите, то можете изменить свой запрос на http://localhost:9200/company/employees/1_source и вы увидите только структуру JSON.

Версия cURL будет следующая:

➜  elasticsearch-6.2.4 curl -X POST \
> http://localhost:9200/company/employees/1 \
> -H 'content-type: application/json' \
> -d '{
quote> "name": "Adnan Siddiqi",
quote> "occupation": "Consultant"
quote> }'
{"_index":"company","_type":"employees","_id":"1","_version":1,"result":"created","_shards":{"total":2,"successful":1,"failed":0},"_seq_no":0,"_primary_term":1}%

Но что если вы захотите обновить эту запись? Что ж, это довольно просто! Все что нужно для этого сделать — изменить запись JSON. Что-то по типу этого:

И результат будет следующим:

{
"_index": "company",
"_type": "employees",
"_id": "1",
"_version": 2,
"result": "updated",
"_shards": {
"total": 2,
"successful": 1,
"failed": 0
},
"_seq_no": 1,
"_primary_term": 1
}

Обратите ваше внимание на поле __result, которое теперь настроено на обновление. И конечно же, если нужно — вы также можете удалять выбранную вами запись.

Если вы сойдете с ума или ваша девушка решит вас бросить, то вы сможете быстро все уничтожить, просто запустив curl -XDELETE localhost:9200/_all из командной строки.

Теперь давайте проведем базовый поиск. Если вы запросите http://localhost:9200/company/employees/_search?q=adnan , то запрос будет искать все поля с employees и выдаст соответствующий результат.

{
"took": 7,
"timed_out": false,
"_shards": {
"total": 5,
"successful": 5,
"skipped": 0,
"failed": 0
},
"hits": {
"total": 1,
"max_score": 0.2876821,
"hits": [
{
"_index": "company",
"_type": "employees",
"_id": "1",
"_score": 0.2876821,
"_source": {
"name": "Adnan Siddiqi",
"occupation": "Software Consultant"
}
}
]
}
}

Поле max_score указывает максимальный балл в записи. Если вы будете искать в нескольких записях, то и результатов запроса будет выдано несколько.

Вы также можете ограничить критерии поиска определенным полем, указав конкретное имя поля. Поэтому http://localhost:9200/company/employees/_search?q=name:Adnan будет искать только в поле name. Фактически, это эквивалент в SQL SELECT * from table where name='Adnan'.

Таким образом, сегодня я рассмотрел самое основное по работе с ES. Система многое умеет, вы можете продолжить ее изучение, прочитав документацию и включив в Python доступ к ES.

Также читайте вторую часть нашей статьи, где мы продолжим знакомство ES на практике!

--

--