Prometheus远程写Metric

2020-10-05  本文已影响0人  jyhnp
一路坑坑洼洼走过来真不简单!

prometheus学习网址:https://my.oschina.net/u/4400455/blog/3442099

大致思路先写下,prometheus.yml加个配置项,远程写是调用http请求来写的,数据格式是protobuf(一种自定义的编码格式),编码格式是snappy(一种压缩格式);远程写通过snappy先压缩,然后protobuf编码的字节数组请求的;接收到远程写数据时是乱码,先用snappy进行解压缩,prometheus官网文档远程写提供remote.proto(包含编码和解码),remote.proto文件中依赖了types.proto和gogo.proto两个文件,我是在prometheus源码的包里边找到的,所以需要把这三个protobuf文件生成java文件,调用Remote.WriteRequest.parseFrom来解码

一、protobuf转java

1. 下载Protocol Buffers

地址:https://github.com/protocolbuffers/protobuf/releases
Mac解压,如图:

image.png
2. 把remote.proto、types.proto、gogo.proto三个文件copy的bin下面 如图:
image.png

3. protoc生成java文件

// src_dir: .proto 所在的源目录
// --java_out: 生成 java 代码
// dst_dir: 生成代码的目标目录
// xxx.proto: 要针对哪个 proto 文件生成接口代码
protoc -I=src_dir --java_out=dst_dir src_dir/xxx.proto

如图三个protobuf文件生成三个java文件:


image.png image.png

二、prometheus.yml配置

# 远程写地址
remote_write:
 - url: "http://172.16.128.209:8081/receive"
   # 基本认证 这是每个远程写请求的授权头属性
   basic_auth:
     username: prometheus 
     password: prometheus

image.png

三、java代码(三个java文件copy到项目中)

package com.jyh.prome;
import com.jyh.prome.protobuf.Remote;
import com.jyh.prome.protobuf.Types;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.xerial.snappy.Snappy;
import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

@RestController
public class RemoteWrite {

    @RequestMapping(value = "/receive")
    public void write(@RequestBody byte[] body, HttpServletRequest request) throws IOException, InterruptedException {
        byte[] a = Snappy.uncompress(body);
        List<Types.TimeSeries> timeSeriesList = Remote.WriteRequest.parseFrom(a).getTimeseriesList();
        for (Types.TimeSeries timeSeries : timeSeriesList) {
            List<Types.Sample> samples = timeSeries.getSamplesList();
            List<Types.Label> labels = timeSeries.getLabelsList();
            Map<String, Object> map = new LinkedHashMap<>();
            for (Types.Label label : labels) {
                    map.put(label.getName(), label.getValue());
            }
            for (Types.Sample sample : samples) {
                map.put("timestamp", sample.getTimestamp());
                map.put("value", sample.getValue());
            }
            System.out.println(map);
        }
    }

}

控制台打印:
labels {
  name: "__name__"
  value: "mysql_global_variables_query_cache_min_res_unit"
}
labels {
  name: "instance"
  value: "192.168.31.40:9101"
}
labels {
  name: "job"
  value: "ser4"
}
samples {
  value: 4096.0
  timestamp: 1601196751516
}



不懂就问

上一篇 下一篇

猜你喜欢

热点阅读