Add support for JSON dashboards
This patch adds the support for JSON dashboards and also provides the support for remote dashboards.
This commit is contained in:
parent
c4ddb9ebda
commit
2958bda057
5 changed files with 92 additions and 65 deletions
|
@ -44,7 +44,9 @@ Server installed with PostgreSQL database
|
|||
user: grafana
|
||||
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
|
||||
|
||||
|
|
|
@ -65,6 +65,7 @@ def present(name,
|
|||
base_panels_from_pillar=None,
|
||||
base_rows_from_pillar=None,
|
||||
dashboard=None,
|
||||
dashboard_format='yaml',
|
||||
profile='grafana'):
|
||||
'''
|
||||
Ensure the grafana dashboard exists and is managed.
|
||||
|
@ -84,19 +85,39 @@ def present(name,
|
|||
dashboard
|
||||
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
|
||||
A pillar key or dict that contains grafana information
|
||||
'''
|
||||
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 {}
|
||||
|
||||
if isinstance(profile, six.string_types):
|
||||
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
|
||||
base_dashboards_from_pillar = ([_DEFAULT_DASHBOARD_PILLAR] +
|
||||
base_dashboards_from_pillar)
|
||||
|
@ -439,16 +460,10 @@ def _delete(url, profile):
|
|||
'''Delete a specific dashboard.'''
|
||||
request_url = "{0}/api/dashboards/{1}".format(profile.get('grafana_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(
|
||||
request_url,
|
||||
auth=_get_auth(profile),
|
||||
headers=_get_headers(profile),
|
||||
timeout=profile.get('grafana_timeout'),
|
||||
)
|
||||
data = response.json()
|
||||
|
@ -461,30 +476,28 @@ def _update(dashboard, profile):
|
|||
'dashboard': dashboard,
|
||||
'overwrite': True
|
||||
}
|
||||
request_url = "{0}/api/dashboards/db".format(profile.get('grafana_url'))
|
||||
if profile.get('grafana_token', False):
|
||||
response = requests.post(
|
||||
request_url,
|
||||
headers=_get_headers(profile),
|
||||
json=payload
|
||||
)
|
||||
else:
|
||||
response = requests.post(
|
||||
request_url,
|
||||
"{0}/api/dashboards/db".format(profile.get('grafana_url')),
|
||||
auth=_get_auth(profile),
|
||||
headers=_get_headers(profile),
|
||||
json=payload
|
||||
)
|
||||
return response.json()
|
||||
|
||||
|
||||
def _get_headers(profile):
|
||||
return {
|
||||
'Accept': 'application/json',
|
||||
'Authorization': 'Bearer {0}'.format(profile['grafana_token'])
|
||||
}
|
||||
headers = {'Content-type': 'application/json'}
|
||||
|
||||
if profile.get('grafana_token', False):
|
||||
headers['Authorization'] = 'Bearer {0}'.format(profile['grafana_token'])
|
||||
|
||||
return headers
|
||||
|
||||
|
||||
def _get_auth(profile):
|
||||
if profile.get('grafana_token', False):
|
||||
return None
|
||||
|
||||
return requests.auth.HTTPBasicAuth(
|
||||
profile['grafana_user'],
|
||||
profile['grafana_password']
|
||||
|
|
|
@ -47,6 +47,8 @@ grafana_client_datasource_{{ datasource_name }}:
|
|||
{%- endif %}
|
||||
|
||||
{%- 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 = [] %}
|
||||
{%- for row_name, row in dashboard.get('row', {}).iteritems() %}
|
||||
{%- set panels = [] %}
|
||||
|
@ -62,26 +64,28 @@ grafana_client_datasource_{{ datasource_name }}:
|
|||
{%- do rows.extend([row]) %}
|
||||
{%- endfor %}
|
||||
{%- do dashboard.update({'rows': rows}) %}
|
||||
{%- endif %}
|
||||
|
||||
{%- do final_dict.update({dashboard_name: dashboard}) %}
|
||||
{%- endfor %}
|
||||
|
||||
{%- for dashboard_name, dashboard in final_dict.iteritems() %}
|
||||
|
||||
{%- if dashboard.get('enabled', True) %}
|
||||
|
||||
grafana_client_dashboard_{{ dashboard_name }}:
|
||||
grafana3_dashboard.present:
|
||||
- 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 %}
|
||||
|
||||
grafana_client_dashboard_{{ dashboard_name }}:
|
||||
grafana3_dashboard.absent:
|
||||
- name: {{ dashboard_name }}
|
||||
|
||||
{%- endif %}
|
||||
|
||||
{%- endfor %}
|
||||
|
||||
{%- endif %}
|
||||
|
|
|
@ -13,6 +13,7 @@ grafana_grains_dir:
|
|||
{# Loading the other service support metadata for localhost #}
|
||||
|
||||
{%- 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 %}
|
||||
|
||||
|
@ -20,6 +21,7 @@ grafana_grains_dir:
|
|||
{%- set grains_yaml = load_grains_file(grains_fragment_file)|load_yaml %}
|
||||
{%- set service_grains = salt['grains.filter_by']({'default': service_grains}, merge=grains_yaml) %}
|
||||
|
||||
{%- endif %}
|
||||
{%- endfor %}
|
||||
|
||||
grafana_grain:
|
||||
|
|
6
metadata/service/collector.yml
Normal file
6
metadata/service/collector.yml
Normal file
|
@ -0,0 +1,6 @@
|
|||
applications:
|
||||
- grafana
|
||||
parameters:
|
||||
grafana:
|
||||
collector:
|
||||
enabled: true
|
Loading…
Reference in a new issue