from copy import deepcopy as dc
+# Template for search source format
SEARCH_SOURCE_FORMAT = {"index": None, "filter": [],
"query": {"language": "lucene", "query": ""}}
+# Template for filter format
FILTER_FORMAT = {
"query": {
"match": {
search_source = dc(SEARCH_SOURCE_FORMAT)
+ # Search for 'match-with' and 'field' for each keys in 'filter' either
+ # in viz_config or dash_config
+ #
+ # ex:- filter:
+ # 1:
+ # field: my_field
+ # match-with: pattern
+
try:
filters = dash_config['filter']
for _, value in filters.items():
import json
+# Pretty Printer
+
def p(x):
print(json.dumps(x, indent=4, sort_keys=True))
class visState:
+ # viState template
def __init__(self):
self.content = {
'title': None,
}
self.counter = 0
+ # Category axes are named as CategoryAxis-i
def create(self):
self.counter += 1
temp = dc(self.content)
return temp
+# 'seriesParams' are the ones that actually show up in the plots.
+# They point to a data source a.k.a 'aggs' (short for aggregation)
+# to get their data.
+
class seriesParams:
def __init__(self, data_type, mode, label, agg_id, value_axis):
'mode': mode,
'data': {
'label': label,
- 'id': str(agg_id)
+ 'id': str(agg_id) # the id of the aggregation they point to
},
'valueAxis': 'ValueAxis-{}'.format(value_axis),
'drawLinesBetweenPoints': True,
def create(self):
return self.content
+# 'aggs' or aggregation refers to collection of values. They are the data
+# source which are used by seriesParams. and as expected they take 'field'
+# as the nested name of the key.
+#
+# Example, if your value is in {
+# 'perfomance': {
+# 'plots': {
+# 'rate': myval,
+# ...
+# }
+# },
+# then I would have to use, 'performance.plots.rate' as the 'field' for aggs
+# the 'schema' of an agg is 'metric' which are to be
+# plotted in the Y-axis and 'segment' for the ones in X-axis
+
class aggs:
def __init__(self):
return temp
+# 'series' actually combines and simplifies both 'seriesParams' and 'aggs'
+# Both 'seriesParams' and 'aggs' support 'default' to set default values
+
# generate takes both the template config and project specific config and
# parses and organizes as much info available from that and
# generates an intermediate format first which
except Exception:
pass
+ ####################################################################
+ # Extract 'value_axes', 'seriesParams' or 'aggs' if present in viz_config
value_axes_counter = 1
for m in viz_config['value_axes']:
if m != "default":
format['aggs'].update(temp)
except KeyError:
pass
+ ####################################################################
+ # collect 'series' from both the configs
configs = []
try:
viz_config['series']
except KeyError:
pass
+ ########################################################################
+ # Extract 'series' from either of the configs
for config in configs:
try:
value_axes_counter = 1
except KeyError as e:
print("required fields are empty!")
+ ##########################################################################
+
# to remove the default template index
for i in ['value_axes', 'seriesParams', 'aggs']:
try:
if len(missing):
raise ValueError('Missing required field values :-', *missing)
- # print(format)
p(format)
vis = visState()
generated_visState = vis.create(format)
- # checking incase there are None values \
+ # checking incase there are None values
# in the format indicating missing fields
missing = config_validator(generated_visState)
# raise e
print('Unable to push data to ElasticSearch')
-# Create and push visualizations
try:
viz_config_path = glob.glob('**/dashboard/viz_config.yaml')[0]
except IndexError:
viz_config = yaml.safe_load(f)
+# Create and push visualizations
for dashboard_id, dashboard_content in dash_config.items():
for _, i in dash_config[dashboard_id]['viz'].items():
# p(intermediate_format)
# p(visState)
+ # Template for visualization template
VIZ_BODY = {
'type': 'visualization',
'visualization': {
searchSourceJSON)
p(VIZ_BODY)
+ # Pushing visualization to Kibana
index = '.kibana'
ES_ID = 'visualization:{}'.format(i['id'])
res = es.index(index=index, doc_type='doc', id=ES_ID, body=VIZ_BODY)
# Create and push dashboards
+ # Template for dashboard body in Kibana
DASH_BODY = {
'type': 'dashboard',
'dashboard': {
dash_gen.generate(dashboard_content['viz']))
p(DASH_BODY)
-
+ # Pushing dashboard to kibana
index = '.kibana'
ES_ID = 'dashboard:{}'.format(dashboard_content['id'])
res = es.index(index=index, doc_type='doc', id=ES_ID, body=DASH_BODY)