当前位置:   article > 正文

Elasticsearch:从 ES|QL 到 Python 数据帧

Elasticsearch:从 ES|QL 到 Python 数据帧

在我之前的文章 “Elasticsearch:ES|QL 查询展示”,我展示了如何在 Kibana 中使用 ES|QL 对索引来进行查询及统计。在很多的情况下,我们需要在客户端中来对数据进行查询,那么我们该怎么办呢?我们需要使用到 Elasticsearch 的客户端。在今天的文章中,我们来展示如何使用 Python 来对数据进行查询。

注意:为了使用 ES|QL,我们的 Elastic Stack 版本至少在 8.12 及以上。

安装

如果你还没有安装好自己的 Elasticsearch 及 Kibana,请参考如下的链接来进行安装:

在安装的时候,我们选择 Elastic Stack 8.x 来进行安装。特别值得指出的是:ES|QL 只在 Elastic Stack 8.11 及以后得版本中才有。你需要下载 Elastic Stack 8.11 及以后得版本来进行安装。

在首次启动 Elasticsearch 的时候,我们可以看到如下的输出:

我们需要记下 Elasticsearch 超级用户 elastic 的密码。

我们还需要安装 Elasticsearch 的 python 依赖包:

pip3 install elasticsearch==8.12.1
  1. $ pip3 list | grep elasticsearch
  2. elasticsearch 8.12.1

准备数据

我们参考之前的文章 “Elasticsearch:ES|QL 查询展示” 来创建索引:

  1. PUT sample_data
  2. {
  3. "mappings": {
  4. "properties": {
  5. "client.ip": {
  6. "type": "ip"
  7. },
  8. "message": {
  9. "type": "keyword"
  10. }
  11. }
  12. }
  13. }
  1. PUT sample_data/_bulk
  2. {"index": {}}
  3. {"@timestamp": "2023-10-23T12:15:03.360Z", "client.ip": "172.21.2.162", "message": "Connected to 10.1.0.3", "event.duration": 3450233}
  4. {"index": {}}
  5. {"@timestamp": "2023-10-23T12:27:28.948Z", "client.ip": "172.21.2.113", "message": "Connected to 10.1.0.2", "event.duration": 2764889}
  6. {"index": {}}
  7. {"@timestamp": "2023-10-23T13:33:34.937Z", "client.ip": "172.21.0.5", "message": "Disconnected", "event.duration": 1232382}
  8. {"index": {}}
  9. {"@timestamp": "2023-10-23T13:51:54.732Z", "client.ip": "172.21.3.15", "message": "Connection error", "event.duration": 725448}
  10. {"index": {}}
  11. {"@timestamp": "2023-10-23T13:52:55.015Z", "client.ip": "172.21.3.15", "message": "Connection error", "event.duration": 8268153}
  12. {"index": {}}
  13. {"@timestamp": "2023-10-23T13:53:55.832Z", "client.ip": "172.21.3.15", "message": "Connection error", "event.duration": 5033755}
  14. {"index": {}}
  15. {"@timestamp": "2023-10-23T13:55:01.543Z", "client.ip": "172.21.3.15", "message": "Connected to 10.1.0.1", "event.duration": 1756467}

使用 Elasticsearch 客户端来进行查询

Elasticsearch 查询语言 (ES|QL) 提供了一种强大的方法来过滤、转换和分析 Elasticsearch 中存储的数据。 它旨在易于最终用户、SRE 团队、应用程序开发人员和管理员学习和使用。 但它也非常适合熟悉 Pandas 和其他基于数据框的框架的数据科学家。

事实上,ES|QL 查询会生成带有命名列的表,即数据帧。 但是如何使用 Python 处理这些数据呢? ES|QL 目前没有 Apache Arrow 输出,但 CSV 输出是一个很好的开始。

我们使用如下的测试程序:

esql.py

  1. from io import StringIO
  2. import numpy as np
  3. import os
  4. from elasticsearch import Elasticsearch
  5. import pandas as pd
  6. endpoint = os.getenv("ES_SERVER")
  7. username = os.getenv("ES_USER")
  8. password = os.getenv("ES_PASSWORD")
  9. fingerprint = os.getenv("ES_FINGERPRINT")
  10. url = f"https://{endpoint}:9200"
  11. es = Elasticsearch( url ,
  12. basic_auth = (username, password),
  13. ssl_assert_fingerprint = fingerprint,
  14. http_compress = True )
  15. # print(es.info())
  16. response = es.esql.query(query="FROM sample_data", format="csv")
  17. df = pd.read_csv(StringIO(response.body))
  18. print(df)
  19. print("==================================================================")
  20. response = es.esql.query(
  21. query="""
  22. FROM sample_data
  23. | LIMIT 5
  24. | sort @timestamp desc
  25. | WHERE event.duration > 3000000
  26. | WHERE message LIKE "Connection *"
  27. """,
  28. format="csv"
  29. )
  30. df = pd.DataFrame = pd.read_csv(StringIO(response.body))
  31. print(df)
  32. print("==================================================================")
  33. response = es.esql.query(
  34. query="""
  35. FROM sample_data
  36. | STATS avg=AVG(event.duration), count=COUNT(*) BY client.ip
  37. | SORT count
  38. """,
  39. format="csv"
  40. )
  41. df = pd.DataFrame = pd.read_csv(
  42. StringIO(response.body),
  43. dtype={"count":"Int64", "avg":np.float64}
  44. )
  45. print(df)
  46. print("==================================================================")

在运行上面的代码之前,我们需要在 terminal 中设置相应的环境变量:

  1. export ES_SERVER="localhost"
  2. export ES_USER="elastic"
  3. export ES_PASSWORD="q2rqAIphl-fx9ndQ36CO"
  4. export ES_FINGERPRINT="bce66ed55097f255fc8e4420bdadafc8d609cc8027038c2dd09d805668f3459e"

然后,我们使用如下的命令来运行:

python3 esql.py
  1. $ python3 esql.py
  2. /Users/liuxg/python/esql/esql.py:22: ElasticsearchWarning: No limit defined, adding default limit of [500]
  3. response = es.esql.query(query="FROM sample_data", format="csv")
  4. @timestamp client.ip event.duration message
  5. 0 2023-10-23T12:15:03.360Z 172.21.2.162 3450233 Connected to 10.1.0.3
  6. 1 2023-10-23T12:27:28.948Z 172.21.2.113 2764889 Connected to 10.1.0.2
  7. 2 2023-10-23T13:33:34.937Z 172.21.0.5 1232382 Disconnected
  8. 3 2023-10-23T13:51:54.732Z 172.21.3.15 725448 Connection error
  9. 4 2023-10-23T13:52:55.015Z 172.21.3.15 8268153 Connection error
  10. 5 2023-10-23T13:53:55.832Z 172.21.3.15 5033755 Connection error
  11. 6 2023-10-23T13:55:01.543Z 172.21.3.15 1756467 Connected to 10.1.0.1
  12. ==================================================================
  13. @timestamp client.ip event.duration message
  14. 0 2023-10-23T13:52:55.015Z 172.21.3.15 8268153 Connection error
  15. ==================================================================
  16. /Users/liuxg/python/esql/esql.py:44: ElasticsearchWarning: No limit defined, adding default limit of [500]
  17. response = es.esql.query(
  18. avg count client.ip
  19. 0 1232382.00 1 172.21.0.5
  20. 1 3450233.00 1 172.21.2.162
  21. 2 2764889.00 1 172.21.2.113
  22. 3 3945955.75 4 172.21.3.15
  23. ==================================================================

很显然,我们得到了最终的结果。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/Gausst松鼠会/article/detail/205542
推荐阅读
相关标签
  

闽ICP备14008679号