首页 > 其他分享 >grafana agent 动态配置内部机制简单说明

grafana agent 动态配置内部机制简单说明

时间:2022-11-08 21:55:32浏览次数:64  
标签:err cfg returnErr agent grafana filter 动态 yml

grafana agent 动态配置目前属于一个体验特性,但是设计上利用了gomplate 一个强大的模版引擎工具

参考配置

  • 运行配置参考
agentv2:
  image: grafana/agent:main
  ports:
    - 12345:12345
    - 12347:12347
  entrypoint:
    - /bin/agent
    - -config.file.type=dynamic
    - -server.http.address=0.0.0.0:12345
    - -config.file=file:///etc/agent-config/agent.yaml # 动态配置默认加载地址
    - -metrics.wal-directory=/tmp/agent/wal
    - -enable-features=dynamic-config,integrations-next # 需要开启的特性
    - -config.enable-read-api
  volumes:
    - ./agentv2.yaml:/etc/agent-config/agent.yaml
    - ./agent-data:/etc/agent/data
    - ./confs:/opt/confs # 挂载的配置文件
    - ./logs:/var/log
  • 配置参考
    比如metrics ,需要移除metrics
 
global:
    scrape_interval: 10s
    remote_write:
    - url: http://victoriametrics:8428/api/v1/write
configs:
  - name: default
    scrape_configs:
    - job_name: avalanche
      static_configs:
      - targets: ['${AVALANCHE_HOST:-localhost:9001}']

log 配置

configs:
  - name: default
    positions:
      filename: /tmp/positions.yaml
    scrape_configs:
      - job_name: varlogs
        static_configs:
          - targets: [localhost]
            labels:
              job: varlogs
              __path__: /var/log/*log
    clients:
      - url: http://loki:3100/loki/api/v1/push

filter 配置 (agentv2.yaml)

template_paths:
  - file:///opt/confs # 基于文件格式
# Filters allow you to override the default naming convention
 
agent_filter:            "agent-*.yml" # defaults to agent-*.yml
server_filter:           "server-*.yml" # defaults to server-*.yml
metrics_filter:          "metrics-*.yml" # defaults to metrics-*.yml
#metrics_instance_filter: string # defaults to metrics_instances-*.yml
integrations_filter:     "integrations-*.yml" # defaults to integrations-*.yml
logs_filter:             "logs-*.yml" # defaults to logs-*.yml
traces_filter:           "traces-*.yml" # defaults to traces-*.yml

内部机制

grafana agent 动态配置实际上上利用了gomplate,但是目前来说似乎只能是第一次加载的时候,并不能实时reload
处理机制上核心是开发的一些filter,如果需要加载其他数据源推荐配置datasource,默认可以通过本地文件
filter 处理部分

 
// ProcessConfigs loads the configurations in a predetermined order to handle functioning correctly.
func (c *DynamicLoader) ProcessConfigs(cfg *Config) error {
  if c.cfg == nil {
    return fmt.Errorf("LoadConfig or LoadConfigByPath must be called")
  }
  var returnErr error
 
  err := c.processAgent(cfg)
  returnErr = errorAppend(returnErr, err)
 
  serverConfig, err := c.processServer()
  returnErr = errorAppend(returnErr, err)
  if serverConfig != nil {
    cfg.Server = *serverConfig
  }
 
  metricConfig, err := c.processMetrics()
  returnErr = errorAppend(returnErr, err)
  if metricConfig != nil {
    cfg.Metrics = *metricConfig
  }
 
  instancesConfigs, err := c.processMetricInstances()
  returnErr = errorAppend(returnErr, err)
  cfg.Metrics.Configs = append(cfg.Metrics.Configs, instancesConfigs...)
 
  logsCfg, err := c.processLogs()
  returnErr = errorAppend(returnErr, err)
  if logsCfg != nil {
    cfg.Logs = logsCfg
  }
 
  traceConfigs, err := c.processTraces()
  returnErr = errorAppend(returnErr, err)
  if traceConfigs != nil {
    cfg.Traces = *traceConfigs
  }
 
  integrations, err := c.processIntegrations()
  returnErr = errorAppend(returnErr, err)
 
  cfg.Integrations.ExtraIntegrations = append(cfg.Integrations.ExtraIntegrations, integrations...)
 
  return returnErr
}

不同filter 处理(log 参考)

func (c *DynamicLoader) processLogs() (*logs.Config, error) {
  var returnError error
  found := 0
  var cfg *logs.Config
  // 基于配置的模版进行模版数据的处理
  for _, path := range c.cfg.TemplatePaths {
    filesContents, err := c.retrieveMatchingFileContents(path, c.cfg.LogsFilter, "logs")
    returnError = errorAppend(returnError, err)
    found = len(filesContents) + found
    if len(filesContents) == 1 {
      cfg = &logs.Config{}
      err = yaml.Unmarshal([]byte(filesContents[0]), cfg)
      returnError = errorAppend(returnError, err)
    }
  }
  // 只支持一个文件,实际上官方文档也说明了log 只支持一个
  if found > 1 {
    returnError = errorAppend(returnError, fmt.Errorf("found %d logs templates; expected 0 or 1", found))
  }
  return cfg, returnError
}

datasource 的加载(基于了gomplate的能力)

// DynamicLoader is used to load configs from a variety of sources and squash them together.
// This is used by the dynamic configuration feature to load configurations from a set of templates and then run them through
// gomplate producing an end result.
type DynamicLoader struct {
  loader *loader.ConfigLoader
  mux    fsimpl.FSMux
  cfg    *LoaderConfig
}
 
// NewDynamicLoader instantiates a new DynamicLoader.
func NewDynamicLoader() (*DynamicLoader, error) {
  // 此处基于了hairyhenderson 提供的vfs 能力,目前只支持本地以及对象存储文件,实际上hairyhenderson/go-fsimpl 还提供其他费事(git,http。。。。)
  return &DynamicLoader{
    mux: newFSProvider(),
  }, nil
}
 
// LoadConfig loads an already created LoaderConfig into the DynamicLoader.
func (c *DynamicLoader) LoadConfig(cfg LoaderConfig) error {
  sources := make(map[string]*data.Source)
  for _, v := range cfg.Sources {
    sourceURL, err := url.Parse(v.URL)
    if err != nil {
      return err
    }
    sources[v.Name] = &data.Source{
      URL:   sourceURL,
      Alias: v.Name,
    }
  }
  // Set Defaults
  if cfg.IntegrationsFilter == "" {
    cfg.IntegrationsFilter = "integrations-*.yml"
  }
  if cfg.AgentFilter == "" {
    cfg.AgentFilter = "agent-*.yml"
  }
  if cfg.ServerFilter == "" {
    cfg.ServerFilter = "server-*.yml"
  }
  if cfg.MetricsFilter == "" {
    cfg.MetricsFilter = "metrics-*.yml"
  }
  if cfg.MetricsInstanceFilter == "" {
    cfg.MetricsInstanceFilter = "metrics_instances-*.yml"
  }
  if cfg.LogsFilter == "" {
    cfg.LogsFilter = "logs-*.yml"
  }
  if cfg.TracesFilter == "" {
    cfg.TracesFilter = "traces-*.yml"
  }
  cl := loader.NewConfigLoader(context.Background(), sources)
  c.loader = cl
  c.cfg = &cfg
  return nil
}

说明

以上是一个简单的说明,详细的可以多看看源码

参考资料

https://github.com/grafana/agent/blob/987c214431af8abae7e13468468b99d21d2df3e3/pkg/config
https://github.com/hairyhenderson/gomplate
https://grafana.com/docs/agent/latest/configuration/dynamic-config/

标签:err,cfg,returnErr,agent,grafana,filter,动态,yml
From: https://www.cnblogs.com/rongfengliang/p/16871359.html

相关文章

  • OpenCV:Debug和Release模式 && 静态和动态编译
    OpenCV:Debug和Release模式&&静态和动态编译 目录1.Release和Debug的区别2.Opencv在Release和Debug下配置的区别3.直接运行利用debug和release生成的exe4.静态编译和动......
  • postman动态获取token到环境变量供后续接口使用
    一:新建环境(为了方便供本项目使用,与其他项目隔离)左侧点击Environments,点击加号新建在界面内填写变量、类型、初始值、当前值变量与脚本设置的变量一致类型默......
  • 近日动态和计划
    目录近日动态和计划一、个人事务1、沉迷短视频逛B站2、每天花费大量时间双十一各种电商活动二、学校事务1、期中考试2、红帽挑战赛3、学校课程4、体育运动5、四六级考试三......
  • Flask框架:运用Ajax轮询动态绘图
    Ajax是异步JavaScript和XML可用于前后端交互,在之前《Flask框架:运用Ajax实现数据交互》简单实现了前后端交互,本章将通过Ajax轮询获取后端的数据,前台使用echart绘图库进行图......
  • mybatis-plus动态表名
    场景:当一个业务数据量比较大了,通常都会采用分表分库的方式进行数据存放,但我们通常使用的mybatis-Plus表名是通过注解写死的,当我们想查询不同表明之间的数据1老老实实......
  • Flask框架:运用Ajax轮询动态绘图
    Ajax是异步JavaScript和XML可用于前后端交互,在之前《Flask框架:运用Ajax实现数据交互》简单实现了前后端交互,本章将通过Ajax轮询获取后端的数据,前台使用echart绘图库进行图......
  • 前端制作动态爱心效果
    话不多说先看效果!希望各位小伙伴表白成功,祝你们永远幸福!  代码::<!DOCTYPEHTMLPUBLIC"-//W3C//DTDHTML4.0Transitional//EN"><HTML><HEAD><TITLE>loveYou<......
  • 【Python】Python使用Tk实现动态爱心效果
    【Python】Python使用Tk实现动态爱心效果是抄的一个UP主的(视频链接在文章结尾),自己改了点小东西,加了注释,然后最后光环的那里UP没有放出一部分代码,自己脑补了。写的时候发现......
  • leetcode 300. 最长递增子序列 js 动态规划实现
    给你一个整数数组nums,找到其中最长严格递增子序列的长度。子序列是由数组派生而来的序列,删除(或不删除)数组中的元素而不改变其余元素的顺序。例如,[3,6,2,7]是数组[0......
  • 编译型语言、解释型语言、静态类型语言、动态类型语言、强类型语言、弱类型语言
    分类代表语言区别优缺点编译型语言C、C++、Pascal、Object-C以及最近很火的苹果新语言swift把做好的源程序全部编译成二进制代码的可运行程序。然后,可直接运......