spring对接InfluxDB(一)--创建数据库和数据写入

最近做的项目涉及到InfluxDB,相对来说,这算是个稍微偏门些的了吧,毕竟时序数据库很多朋友都不会接触。这里记录下与spring的对接,以便刚入手的朋友参考。

参照官网上数据写入这块,首先是创建数据库(database),这里默认已经安装好了Influx,这个比较简单。

官网给出的Http示例都是curl的:

curl -i -XPOST http://localhost:8086/query --data-urlencode "q=CREATE DATABASE mydb"

执行及结果(我之前已经创建了几个数据库):

[root@iZ8vb8r420ejxfron03cj7Z ~]# curl -i -XPOST http://localhost:8086/query --data-urlencode "q=CREATE DATABASE mydb"
HTTP/1.1 200 OK
Connection: close
Content-Type: application/json
Request-Id: 67281cc5-6c54-11e7-81bf-000000000000
X-Influxdb-Version: 1.2.4
Date: Wed, 19 Jul 2017 07:32:22 GMT
Transfer-Encoding: chunked

{"results":[{"statement_id":0}]}
[root@iZ8vb8r420ejxfron03cj7Z ~]# influx
Connected to http://localhost:8086 version 1.2.4
InfluxDB shell version: 1.2.4
> show databases
name: databases
name
----
_internal
testdb
mydb
mydb2
mydb3
mydb4

这是官网给的curl方法,这种方式很简单,而且在influx提供的web页面就可以实现这种功能。所以,下面介绍在代码层实现。

这里我借用的是spring的Resttemplate(使用httpclient也一样):

import org.springframework.util.LinkedMultiValueMap;
import org.springframework.util.MultiValueMap;
import org.springframework.web.client.RestTemplate;

/**
 * Created by pangkunkun on 2017/7/19.
 */
public class InfluxDBTest {
    public static void main(String[] args){
        new InfluxDBTest().createDatabase();
    }

    public void createDatabase(){
        String url="http://localhost:8086/query";

        MultiValueMap postParameter=new LinkedMultiValueMap<>();

        postParameter.add("q","CREATE DATABASE mydb1");

        RestTemplate restTemplate=new RestTemplate();

        restTemplate.postForObject(url,postParameter,Object.class);

    }
}

因为已经创建了mydb数据库,所以这里我写的是mydb1。

在服务器上查询可见mydb1在最下方,已经创建Ok。

> show databases
name: databases
name
----
_internal
testdb
mydb
mydb2
mydb3
mydb4
mydb1

> 

简单说明下,因为官网的示例是使用的post方法,data-urlencode这块的值我是把q当作一个字段,后边的创建语句当作具体值来传输的。

数据库创建OK了,现在开始写入数据。
先看官网给的示例:

curl -i -XPOST 'http://localhost:8086/write?db=mydb' --data-binary 'cpu_load_short,host=server01,region=us-west value=0.64 1434055562000000000'

上面代码中cpu_load_short是measurement(下边我们称之为表),host和region为tag,value是field,后边的时间戳是表中的time的值,如果不传,默认为当前的服务器时间。

下面开始代码实现(这里以mydb1为数据库):

public void write(){
        String url="http://localhost:8086/write?db=mydb1";

        String pointValue="cpu_load_short,host=server01,region=us-west value=0.64 1434055562000000000";

        RestTemplate restTemplate=new RestTemplate();

        restTemplate.postForObject(url,pointValue,Object.class);
    }

查询结果

> use mydb1
Using database mydb1
> select * from cpu_load_short
name: cpu_load_short
time                host     region  value
----                ----     ------  -----
1434055562000000000 server01 us-west 0.64

> 

上边是单条数据插入,继续多条数据的插入。

官网示例:

curl -i -XPOST 'http://localhost:8086/write?db=mydb' --data-binary 'cpu_load_short,host=server02 value=0.67
cpu_load_short,host=server02,region=us-west value=0.55 1422568543702900257
cpu_load_short,direction=in,host=server01,region=us-west value=2.0 1422568543702900257'

示例中显示每条记录之间用换行隔开,且每条数据的字段数可以不一样。

最简单的实现方式是把每条记录用换行符(\n)隔开,作为一个字符串来处理:

public void writeMultiplePoints(){

        String url="http://localhost:8086/write?db=mydb1";

        String pointValue="cpu_load_short,host=server02  num=0.67\ncpu_load_short,host=server02,region=us-west value=0.55 1422568543702900257\ncpu_load_short,direction=in,host=server01,region=us-west value=2.0 1422568543702900257";

        RestTemplate restTemplate=new RestTemplate();

        restTemplate.postForObject(url,pointValue,Object.class);
    }

查询结果(其中有一条是上边单此插入的):

> select * from cpu_load_short
name: cpu_load_short
time                direction host     num  region  value
----                --------- ----     ---  ------  -----
1422568543702900257 in        server01      us-west 2
1422568543702900257           server02      us-west 0.55
1434055562000000000           server01      us-west 0.64
1500451813612820648           server02 0.67         

> 

下面示例中我们把表(measurement)也给写成不一样的,为了查看方便先把数据库清空了。

> delete from cpu_load_short
> select * from cpu_load_short
> 

下面在插入语句中新增了一个my_test_table表:

public void writeMultiplePoints(){

        String url="http://localhost:8086/write?db=mydb1";

        String pointValue="my_test_table,host=server02  num=0.67\nmy_test_table,host=server02  num=0.81\ncpu_load_short,host=server02,region=us-west value=0.55 1422568543702900257\ncpu_load_short,direction=in,host=server01,region=us-west value=2.0 1422568543702900257";

        RestTemplate restTemplate=new RestTemplate();

        restTemplate.postForObject(url,pointValue,Object.class);
    }

查询:

> select * from cpu_load_short
name: cpu_load_short
time                direction host     num region  value
----                --------- ----     --- ------  -----
1422568543702900257 in        server01     us-west 2
1422568543702900257           server02     us-west 0.55

> select * from my_test_table
name: my_test_table
time                host     num
----                ----     ---
1500452059044438976 server02 0.81

> 

上面显示的my_test_table中只有一条数据,我上面代码中明明有两条,所以我做了几次测试,结果说明,如果tag的值都相同,且time也一样,这两条数据只能保存一条,而且是最后一条是保存成功的。

所以我猜测,这是由于前面所有tag都相同,且时间也一样,这时只能保存一条记录,即该point的唯一一条记录。最后一条数据保存成功,应该是把前边的已经写入的数据给覆盖重写了。具体大家可以测试下。

下边给出list个json辅助处理多条数据的方法:

    public String listValue(){

        List<String> list=new ArrayList();

        list.add("cpu_load_short,host=server02 value=0.67\n");
        list.add("cpu_load_short,host=server02,region=us-west value=0.55\n");
        list.add("cpu_load_short,direction=in,host=server01,region=us-west value=2.0\n");

        String listStr=list.toString();

        listStr=listStr.replace("[","").replace("]","").replace(", ","");

        return listStr;
    }


    public String jsonArry(){
        JSONArray jsonArray=new JSONArray();

        jsonArray.put("test_table,host=server02 value=0.67");
        jsonArray.put("test_table,host=server02,region=us-west value=0.55");
        jsonArray.put("test_table,direction=in,host=server01,region=us-west value=2.0");

        String str=jsonArray.toString();

        str=str.replace("[","").replace("]","").replace("\",\"","\n").replace("\"","");

        return str;
    }

你可能感兴趣的:(InfluxDB,Spring,SpringBoot)