在调用grafana http api之前有必要学习下json数据结构。

官方grafana HTTP api链接: http://docs.grafana.org/reference/http_api/#basic-auth

Python json模块使用:http://python3-cookbook.readthedocs.org/zh_CN/latest/c06/p02_read-write_json_data.html

sqlachemy使用:http://iceyao.blog.51cto.com/9426658/1694401


[root@xxxxxxxxcom grafana_http_api]# cat grafana_http_api.py  
#!/usr/bin/env python
#coding=utf-8

import json    # json库方便json数据结构和dict数据结构相互转化
import urllib2  
import sys
from urllib2 import Request, urlopen, URLError, HTTPError   # http库
from pprint import pprint     #  专门打印json数据格式 
from sqlalchemy import create_engine      # 
from sqlalchemy.orm import sessionmaker

#grafana_url="http://localhost:3000/api/dashboards/db/test"
#grafana_url="
 
grafana_server = "localhost"    # grafana主机地址
grafana_port = 3000             # grafana api默认端口
api_keys_name = 'salt-grafana'  # 调用grafana api需要事先在界面上创建一个API_KEYS

# http的报头
grafana_header = {
        "Content-Type":"application/json",
        "Accept": "application/json",
        "Authorization": "Bearer eyJrIjoiUWp5MGlrNk9nNEdGM0hpZ1BkMTdZSFJZODBiVmRPem8iLCJuIjoic2FsdC1ncmFmYW5hIiwiaWQiOjF9"  # 这个是必须的api_keys,格式"Authorization": "Bearer “
}

# 因为没有api可以导入API_KEY,而API_KEY默认是存储在sqlite数据库里面这里直接往数据库里面注入一条记录
def create_api_keys(path):
    engine = create_engine('sqlite:///' + path, echo=True)
    Session = sessionmaker(bind=engine)
    session = Session()
    # 事先查询下如果有就不导入了
    res = session.query("name").from_statement("SELECT name FROM api_key where name=:name").params(name=api_keys_name).all()
    if len(res) > 0:
        print "API Keys already exists"
    
    else:
        api_keys_sql = """insert into api_key (id, org_id, name, key, role, created, updated)
                        values(99,1, '%s',
                        '308730ed17b47e97ebd96a071791ba291e0848347195a6050c28662add04f50a74efd328540ecb15e5a3b294c0cd1feaa91c',
                        'Admin', '2015-12-10 09:19:40', '2015-12-10 09:19:40')""" % (api_keys_name)
        try:
            session.execute(api_keys_sql)
            session.commit()
            print  "API Keys import successfully"
        except:
            print "API Keys import failed"
            sys.exit(1)
        finally:
            session.close()
            
# 从外部文件读入json数据            
def get_auth_data(file):
    with open(file, 'r') as f:
        data = json.load(f)  # load方法把json数据结构转化为dict数据结构
        auth_data = json.dumps(data)  # dumps方法把dict数据结构转化为json数据结构因为官方api提供的http数据部分就是json结构
        return auth_data

# post请求    
def post_request(url, auth_data):
    request = urllib2.Request(url,auth_data)
    for key in grafana_header:
        request.add_header(key,grafana_header[key])
    try:
        result = urllib2.urlopen(request)
    except HTTPError, e:
        print 'The server couldn\'t fulfill the request, Error code: ', e.code
    except URLError, e:
        print 'We failed to reach a server.Reason: ', e.reason
    response=json.loads(result.read().decode('utf-8'))
    result.close()
    return response

# 创建grafana dashboard
def create_dashboard(grafana_server, grafana_port, file):
    grafana_url = 'http://{0}:{1}/api/dashboards/db'.format(grafana_server,
                                                            grafana_port)
    auth_data = get_auth_data(file)
    return post_request(grafana_url, auth_data)
    
# 创建数据源
def create_datasource(grafana_server, grafana_port, datasource_type, file):
    datasources = get_datasource(grafana_server, grafana_port)
    for datasource in datasources:
        if datasource_type + '-test' in datasource['name']:
            return "Datasource {0} already exists".format(datasource['name'])
    grafana_url = 'http://{0}:{1}/api/datasources'.format(grafana_server,
                                                          grafana_port)
    auth_data = get_auth_data(file)
    return post_request(grafana_url, auth_data)
    
# 列出所有的数据源
def get_datasource(grafana_server, grafana_port):
    grafana_url = 'http://{0}:{1}/api/datasources'.format(grafana_server,
                                                          grafana_port)
    return post_request(grafana_url, None)
    

if __name__ == '__main__':
    create_api_keys("/var/lib/grafana/grafana.db")
    # 创建zabbix数据源
    pprint(create_datasource(grafana_server, grafana_port, 'zabbix', 'zabbix_datasource.json'))
    # 创建elasticsearch数据源,这里有个bug,api无法指定Index的Pattern.
    pprint(create_datasource(grafana_server, grafana_port, 'elasticsearch', 'elasticsearch_datasource.json'))
    # 创建grafana dashboard
    pprint(create_dashboard(grafana_server, grafana_port, 'data.json'))
    pprint(get_datasource(grafana_server, grafana_port))


# 下面来看json文件
[root@xxxxxx0807com grafana_http_api]# ll
total 16
-rw-r--r-- 1 root root  722 Dec 10 16:50 data.json
-rw-r--r-- 1 root root  219 Dec 10 16:59 elasticsearch_datasource.json
-rw-r--r-- 1 root root 4013 Dec 11 12:56 grafana_http_api.py
-rw-r--r-- 1 root root  205 Dec 10 15:24 zabbix_datasource.json


[root@xxxxxxxxxx grafana_http_api]# cat data.json
{
  "dashboard": {
    "id": null,
    "title": "Animbus Overview",
    "tags": [ "templated" ],
    "timezone": "browser",
    "rows": [
      {
        "collapse": false,
        "editable": true,
        "height": "150px",
        "panels": [
        {
          "content": "Just for test!",
          "editable": true,
          "error": false,
          "id": 1,
          "mode": "markdown",
          "span": 12,
          "style": {},
          "title": "no title (click here)",
          "type": "text"
        }
      ],
        "title": "Row"
      }
    ],
    "templating": {
    "list": []
  },
    "annotations": {
    "list": []
  },
    "schemaVersion": 7,
    "version": 0
  },
  "overwrite": true
}


[root@SHBAK0807com grafana_http_api]# cat zabbix_datasource.json
{
  "name":"zabbix-test",
  "type":"zabbix",
  "url":"  # 这里需要写上api path 
  "access":"direct",
  "basicAuth":false,
  "user":"Admin",      # zabbix用户
  "password":"zabbix",  # zabbix密码
  "isDefault":false
}
[root@SHBAK0807com grafana_http_api]# cat elasticsearch_datasource.json
{
  "name":"elasticsearch-test",
  "type":"elasticsearch",
  "url":"  # api地址端口 
  "access":"direct",
  "database":"[logstash-]YYYY.MM.DD",  
  "pattern":"Daily",      # 这里无法指定pattern
  "basicAuth":false,  
  "isDefault":false
}