转载请注明出处:https://blog.csdn.net/coididy/article/details/105436463
做毕设的时候需要使用ELK的Kibana进行数据可视化,为了实现通过python代码动态生成Kibana的可视化图表,所以接触了Kibana REST API,因为官网上给出的API文档较为简陋,所以在此记录一下。
Kibana REST API官方网址:
https://www.elastic.co/guide/en/kibana/current/api.html
一些注意点:
1、请求头(headers):
headers = {
'Content-Type': 'application/json',
'kbn-xsrf': 'true'
}
2、有效数据或者说参数(data):
通常,我们的API都是直接使用json数据,但是Kibana API使用的是字符串格式,所以我们需要先将json数据转换成字符串,然后作为API的参数。比如:
import json
import requests
headers = ''
url = ''
payload = {'data':'123'}
res = requests.request("POST", url, headers, json.dumps(payload))
另外Kibana的某些API(后面会讲,比如创建可视化)的原始json数据中嵌入了转换成字符串后的json数据!
3、当传入的参数中存在中文时:
data = json.dumps(paydata, ensure_ascii=False).encode("UTF-8")
4、当需要在API中指定Kibana空间id时:
在Kibana REST API中通常包含两种API,一种是使用默认default空间,一种需要手动指定空间id(space_id)。需要注意的是:**这个space_id参数并不是通用的,它不能包含default,所以需要对默认空间进行特殊处理。**如下:
if spaceId == 'default':
url = 'http://127.0.0.1:5601/api/saved_objects/index-pattern/' + patternId
else:
url = 'http://127.0.0.1:5601/s/' + spaceId + '/api/saved_objects/index-pattern/' + patternId
5、动态创建可视化图表的技巧
在官网中,对创建对象的API的介绍非常简单,仅仅只介绍了创建索引模式的例子,并没有涉及到创建可视化图表。所以我们并不知道在发起请求时应该设置怎样的参数。以下是我获取参数的方法:
在Kibana中创建的对象,是可以导出的。导出文件中包含这个对象的所有属性,包括其依赖。
我们动态创建图表并不需要文件中的所有数据,只需要关注两个属性::attributes和references
- attributes:包含了图表的基本属性
- references:指明该图表对象依赖的索引模式
举例如下:
spaceId ='test'
objId = 'PE_compare_ELF_pie_id'
objName = 'PE、ELF文件比较图'
objData = {
"attributes": {
"description": "",
"kibanaSavedObjectMeta": {
"searchSourceJSON": "{\"query\":{\"query\":\"\",\"language\":\"kuery\"},\"filter\":[],\"indexRefName\":\"kibanaSavedObjectMeta.searchSourceJSON.index\"}"
},
"title": objName,
"uiStateJSON": "{}",
"version": 1,
"visState": "{\"title\":\"" + objName + "\",\"type\":\"pie\",\"params\":{\"type\":\"pie\",\"addTooltip\":true,\"addLegend\":true,\"legendPosition\":\"right\",\"isDonut\":true,\"labels\":{\"show\":true,\"values\":true,\"last_level\":true,\"truncate\":20},\"dimensions\":{\"metric\":{\"accessor\":1,\"format\":{\"id\":\"number\"},\"params\":{},\"aggType\":\"count\"},\"buckets\":[{\"accessor\":0,\"format\":{\"id\":\"terms\",\"params\":{\"id\":\"string\",\"otherBucketLabel\":\"其他\",\"missingBucketLabel\":\"缺失\"}},\"params\":{},\"aggType\":\"terms\"},{\"accessor\":2,\"format\":{\"id\":\"terms\",\"params\":{\"id\":\"string\",\"otherBucketLabel\":\"其他\",\"missingBucketLabel\":\"缺失\"}},\"params\":{},\"aggType\":\"terms\"},{\"accessor\":4,\"format\":{\"id\":\"terms\",\"params\":{\"id\":\"string\",\"otherBucketLabel\":\"其他\",\"missingBucketLabel\":\"缺失\"}},\"params\":{},\"aggType\":\"terms\"}]}},\"aggs\":[{\"id\":\"1\",\"enabled\":true,\"type\":\"count\",\"schema\":\"metric\",\"params\":{}},{\"id\":\"5\",\"enabled\":false,\"type\":\"terms\",\"schema\":\"split\",\"params\":{\"field\":\"file_type.keyword\",\"orderBy\":\"1\",\"order\":\"desc\",\"size\":2,\"otherBucket\":false,\"otherBucketLabel\":\"其他\",\"missingBucket\":false,\"missingBucketLabel\":\"缺失\",\"row\":false}},{\"id\":\"2\",\"enabled\":true,\"type\":\"terms\",\"schema\":\"segment\",\"params\":{\"field\":\"file_type.keyword\",\"orderBy\":\"1\",\"order\":\"desc\",\"size\":2,\"otherBucket\":false,\"otherBucketLabel\":\"其他\",\"missingBucket\":false,\"missingBucketLabel\":\"缺失\",\"customLabel\":\"文件类型\"}},{\"id\":\"3\",\"enabled\":false,\"type\":\"terms\",\"schema\":\"segment\",\"params\":{\"field\":\"imports.keyword\",\"orderBy\":\"1\",\"order\":\"desc\",\"size\":20,\"otherBucket\":false,\"otherBucketLabel\":\"其他\",\"missingBucket\":false,\"missingBucketLabel\":\"缺失\",\"customLabel\":\"库\"}},{\"id\":\"4\",\"enabled\":true,\"type\":\"terms\",\"schema\":\"segment\",\"params\":{\"field\":\"sections.keyword\",\"orderBy\":\"1\",\"order\":\"desc\",\"size\":20,\"otherBucket\":false,\"otherBucketLabel\":\"其他\",\"missingBucket\":false,\"missingBucketLabel\":\"缺失\",\"exclude\":\"\",\"customLabel\":\"节\"}}]}"
},
"references": [
{
"id": spaceId + '-pattern',
"name": "kibanaSavedObjectMeta.searchSourceJSON.index",
"type": "index-pattern"
}
]
}
if spaceId == 'default':
url = 'http://127.0.0.1:5601/api/saved_objects/visualization/' + objId
else:
url = 'http://127.0.0.1:5601/s/' + spaceId + '/api/saved_objects/visualization/' + objId
payload = json.dumps(objData, ensure_ascii=False).encode("UTF-8")
headers = {
'Content-Type': 'application/json',
'kbn-xsrf': 'true'
}
res = requests.request("POST", url, headers=headers, data=payload)
需要注意的是在我的objData中,searchSourceJSON和visState的数据都是字符串化的json数据