1
0
Fork 0
telegraf/testutil/plugin_input/plugin.go
Daniel Baumann 4978089aab
Adding upstream version 1.34.4.
Signed-off-by: Daniel Baumann <daniel@debian.org>
2025-05-24 07:26:29 +02:00

177 lines
4.4 KiB
Go

package input
import (
_ "embed"
"errors"
"os"
"path/filepath"
"time"
"github.com/influxdata/telegraf"
"github.com/influxdata/telegraf/plugins/inputs"
"github.com/influxdata/telegraf/plugins/parsers/influx/influx_upstream"
"github.com/influxdata/telegraf/testutil"
)
//go:embed sample.conf
var sampleConfig string
// Example struct should be named the same as the Plugin
type Plugin struct {
Files []string `toml:"files"`
DefaultTags map[string]string `toml:"default_tag_defs"`
AdditionalParams map[string]interface{} `toml:"additional_params"`
Parser telegraf.Parser `toml:"-"`
Log telegraf.Logger `toml:"-"`
// Settings used by test-code
Path string `toml:"-"` // start path for relative files
ExpectedFilename string `toml:"-"` // filename of the expected metrics (default: expected.out)
UseTypeTag string `toml:"-"` // if specified use this tag to infer metric type
// Test-data derived from the files
Expected []telegraf.Metric `toml:"-"` // expected metrics
ExpectedErrors []string `toml:"-"` // expected errors
ShouldIgnoreTimestamp bool `toml:"-"` // flag indicating if the expected metrics do have timestamps
// Internal data
inputFilenames []string
}
func (*Plugin) SampleConfig() string {
return sampleConfig
}
func (p *Plugin) Init() error {
// Setup the filenames
p.inputFilenames = make([]string, 0, len(p.Files))
for _, fn := range p.Files {
if !filepath.IsAbs(fn) && p.Path != "" {
fn = filepath.Join(p.Path, fn)
}
p.inputFilenames = append(p.inputFilenames, fn)
}
// Setup an influx parser for reading the expected metrics
expectedParser := &influx_upstream.Parser{}
if err := expectedParser.Init(); err != nil {
return err
}
expectedParser.SetTimeFunc(func() time.Time { return time.Time{} })
// Read the expected metrics if any
expectedFn := "expected.out"
if p.ExpectedFilename != "" {
expectedFn = p.ExpectedFilename
}
if !filepath.IsAbs(expectedFn) && p.Path != "" {
expectedFn = filepath.Join(p.Path, expectedFn)
}
if _, err := os.Stat(expectedFn); err == nil {
var err error
p.Expected, err = testutil.ParseMetricsFromFile(expectedFn, expectedParser)
if err != nil {
return err
}
}
// Read the expected errors if any
expectedErrorFn := "expected.err"
if !filepath.IsAbs(expectedErrorFn) && p.Path != "" {
expectedErrorFn = filepath.Join(p.Path, expectedErrorFn)
}
if _, err := os.Stat(expectedErrorFn); err == nil {
var err error
p.ExpectedErrors, err = testutil.ParseLinesFromFile(expectedErrorFn)
if err != nil {
return err
}
if len(p.ExpectedErrors) == 0 {
return errors.New("got empty expected errors file")
}
}
// Fixup the metric type if requested
if p.UseTypeTag != "" {
for i, m := range p.Expected {
typeTag, found := m.GetTag(p.UseTypeTag)
if !found {
continue
}
var mtype telegraf.ValueType
switch typeTag {
case "counter":
mtype = telegraf.Counter
case "gauge":
mtype = telegraf.Gauge
case "untyped":
mtype = telegraf.Untyped
case "summary":
mtype = telegraf.Summary
case "histogram":
mtype = telegraf.Histogram
default:
continue
}
m.SetType(mtype)
m.RemoveTag(p.UseTypeTag)
p.Expected[i] = m
}
}
// Determine if we should check the timestamps indicated by a missing
// timestamp in the expected input
for i, m := range p.Expected {
missingTimestamp := m.Time().IsZero()
if i == 0 {
p.ShouldIgnoreTimestamp = missingTimestamp
continue
}
if missingTimestamp != p.ShouldIgnoreTimestamp {
return errors.New("mixed timestamp and non-timestamp data in expected metrics")
}
}
// Set the parser's default tags, just in case
if p.Parser != nil {
p.Parser.SetDefaultTags(p.DefaultTags)
}
return nil
}
func (p *Plugin) Gather(acc telegraf.Accumulator) error {
if p.Parser == nil {
return errors.New("no parser defined")
}
for _, fn := range p.inputFilenames {
data, err := os.ReadFile(fn)
if err != nil {
return err
}
metrics, err := p.Parser.Parse(data)
if err != nil {
return err
}
for _, m := range metrics {
acc.AddMetric(m)
}
}
return nil
}
func (p *Plugin) SetParser(parser telegraf.Parser) {
p.Parser = parser
if len(p.DefaultTags) > 0 {
p.Parser.SetDefaultTags(p.DefaultTags)
}
}
// Register the plugin
func init() {
inputs.Add("test", func() telegraf.Input {
return &Plugin{}
})
}