1
0
Fork 0

Merge pull request #11 from thouveng/use-json-dashboards

Add support for JSON dashboards
This commit is contained in:
thouveng 2016-11-15 09:27:28 +01:00 committed by GitHub
commit 13574258bc
5 changed files with 92 additions and 65 deletions

View File

@ -44,7 +44,9 @@ Server installed with PostgreSQL database
user: grafana user: grafana
password: passwd password: passwd
Server installed with default StackLight JSON dashboards Server installed with default StackLight JSON dashboards. This will
be replaced by the possibility for a service to provide its own dashboard
using salt-mine.
.. code-block:: yaml .. code-block:: yaml

View File

@ -65,6 +65,7 @@ def present(name,
base_panels_from_pillar=None, base_panels_from_pillar=None,
base_rows_from_pillar=None, base_rows_from_pillar=None,
dashboard=None, dashboard=None,
dashboard_format='yaml',
profile='grafana'): profile='grafana'):
''' '''
Ensure the grafana dashboard exists and is managed. Ensure the grafana dashboard exists and is managed.
@ -84,19 +85,39 @@ def present(name,
dashboard dashboard
A dict that defines a dashboard that should be managed. A dict that defines a dashboard that should be managed.
dashboard_format
You can use two formats for dashboards. You can use the JSON format
if you provide a complete dashboard in raw JSON or you can use the YAML
format (this is the default) and provide a description of the
dashboard in YAML.
profile profile
A pillar key or dict that contains grafana information A pillar key or dict that contains grafana information
''' '''
ret = {'name': name, 'result': True, 'comment': '', 'changes': {}} ret = {'name': name, 'result': True, 'comment': '', 'changes': {}}
base_dashboards_from_pillar = base_dashboards_from_pillar or []
base_panels_from_pillar = base_panels_from_pillar or []
base_rows_from_pillar = base_rows_from_pillar or []
dashboard = dashboard or {} dashboard = dashboard or {}
if isinstance(profile, six.string_types): if isinstance(profile, six.string_types):
profile = __salt__['config.option'](profile) profile = __salt__['config.option'](profile)
if dashboard_format == 'json':
# In this case, a raw JSON of the full dashboard is provided.
response = _update(dashboard, profile)
if response.get('status') == 'success':
ret['comment'] = 'Dashboard {0} created.'.format(name)
ret['changes']['new'] = 'Dashboard {0} created.'.format(name)
else:
ret['result'] = False
ret['comment'] = ("Failed to create dashboard {0}, "
"response={1}").format(name, response)
return ret
base_dashboards_from_pillar = base_dashboards_from_pillar or []
base_panels_from_pillar = base_panels_from_pillar or []
base_rows_from_pillar = base_rows_from_pillar or []
# Add pillar keys for default configuration # Add pillar keys for default configuration
base_dashboards_from_pillar = ([_DEFAULT_DASHBOARD_PILLAR] + base_dashboards_from_pillar = ([_DEFAULT_DASHBOARD_PILLAR] +
base_dashboards_from_pillar) base_dashboards_from_pillar)
@ -439,16 +460,10 @@ def _delete(url, profile):
'''Delete a specific dashboard.''' '''Delete a specific dashboard.'''
request_url = "{0}/api/dashboards/{1}".format(profile.get('grafana_url'), request_url = "{0}/api/dashboards/{1}".format(profile.get('grafana_url'),
url) url)
if profile.get('grafana_token', False):
response = requests.delete(
request_url,
headers=_get_headers(profile),
timeout=profile.get('grafana_timeout'),
)
else:
response = requests.delete( response = requests.delete(
request_url, request_url,
auth=_get_auth(profile), auth=_get_auth(profile),
headers=_get_headers(profile),
timeout=profile.get('grafana_timeout'), timeout=profile.get('grafana_timeout'),
) )
data = response.json() data = response.json()
@ -461,30 +476,28 @@ def _update(dashboard, profile):
'dashboard': dashboard, 'dashboard': dashboard,
'overwrite': True 'overwrite': True
} }
request_url = "{0}/api/dashboards/db".format(profile.get('grafana_url'))
if profile.get('grafana_token', False):
response = requests.post( response = requests.post(
request_url, "{0}/api/dashboards/db".format(profile.get('grafana_url')),
headers=_get_headers(profile),
json=payload
)
else:
response = requests.post(
request_url,
auth=_get_auth(profile), auth=_get_auth(profile),
headers=_get_headers(profile),
json=payload json=payload
) )
return response.json() return response.json()
def _get_headers(profile): def _get_headers(profile):
return { headers = {'Content-type': 'application/json'}
'Accept': 'application/json',
'Authorization': 'Bearer {0}'.format(profile['grafana_token']) if profile.get('grafana_token', False):
} headers['Authorization'] = 'Bearer {0}'.format(profile['grafana_token'])
return headers
def _get_auth(profile): def _get_auth(profile):
if profile.get('grafana_token', False):
return None
return requests.auth.HTTPBasicAuth( return requests.auth.HTTPBasicAuth(
profile['grafana_user'], profile['grafana_user'],
profile['grafana_password'] profile['grafana_password']

View File

@ -47,6 +47,8 @@ grafana_client_datasource_{{ datasource_name }}:
{%- endif %} {%- endif %}
{%- for dashboard_name, dashboard in raw_dict.iteritems() %} {%- for dashboard_name, dashboard in raw_dict.iteritems() %}
{%- if dashboard.get('format', 'yaml')|lower == 'yaml' %}
# Dashboards in JSON format are considered as blob
{%- set rows = [] %} {%- set rows = [] %}
{%- for row_name, row in dashboard.get('row', {}).iteritems() %} {%- for row_name, row in dashboard.get('row', {}).iteritems() %}
{%- set panels = [] %} {%- set panels = [] %}
@ -62,26 +64,28 @@ grafana_client_datasource_{{ datasource_name }}:
{%- do rows.extend([row]) %} {%- do rows.extend([row]) %}
{%- endfor %} {%- endfor %}
{%- do dashboard.update({'rows': rows}) %} {%- do dashboard.update({'rows': rows}) %}
{%- endif %}
{%- do final_dict.update({dashboard_name: dashboard}) %} {%- do final_dict.update({dashboard_name: dashboard}) %}
{%- endfor %} {%- endfor %}
{%- for dashboard_name, dashboard in final_dict.iteritems() %} {%- for dashboard_name, dashboard in final_dict.iteritems() %}
{%- if dashboard.get('enabled', True) %} {%- if dashboard.get('enabled', True) %}
grafana_client_dashboard_{{ dashboard_name }}: grafana_client_dashboard_{{ dashboard_name }}:
grafana3_dashboard.present: grafana3_dashboard.present:
- name: {{ dashboard_name }} - name: {{ dashboard_name }}
- dashboard: {{ dashboard }} {%- if dashboard.get('format', 'yaml')|lower == 'json' %}
{%- import_json dashboard.template as dash %}
- dashboard: {{ dash|json }}
- dashboard_format: json
{%- else %}
- dashboard: {{ dashboard }}
{%- endif %}
{%- else %} {%- else %}
grafana_client_dashboard_{{ dashboard_name }}: grafana_client_dashboard_{{ dashboard_name }}:
grafana3_dashboard.absent: grafana3_dashboard.absent:
- name: {{ dashboard_name }} - name: {{ dashboard_name }}
{%- endif %} {%- endif %}
{%- endfor %} {%- endfor %}
{%- endif %} {%- endif %}

View File

@ -13,6 +13,7 @@ grafana_grains_dir:
{# Loading the other service support metadata for localhost #} {# Loading the other service support metadata for localhost #}
{%- for service_name, service in pillar.iteritems() %} {%- for service_name, service in pillar.iteritems() %}
{%- if service.get('_support', {}).get('grafana', {}).get('enabled', False) %}
{%- macro load_grains_file(grains_fragment_file) %}{% include grains_fragment_file ignore missing %}{% endmacro %} {%- macro load_grains_file(grains_fragment_file) %}{% include grains_fragment_file ignore missing %}{% endmacro %}
@ -20,6 +21,7 @@ grafana_grains_dir:
{%- set grains_yaml = load_grains_file(grains_fragment_file)|load_yaml %} {%- set grains_yaml = load_grains_file(grains_fragment_file)|load_yaml %}
{%- set service_grains = salt['grains.filter_by']({'default': service_grains}, merge=grains_yaml) %} {%- set service_grains = salt['grains.filter_by']({'default': service_grains}, merge=grains_yaml) %}
{%- endif %}
{%- endfor %} {%- endfor %}
grafana_grain: grafana_grain:

View File

@ -0,0 +1,6 @@
applications:
- grafana
parameters:
grafana:
collector:
enabled: true