1
0
Fork 0

Adding upstream version 1.34.4.

Signed-off-by: Daniel Baumann <daniel@debian.org>
This commit is contained in:
Daniel Baumann 2025-05-24 07:26:29 +02:00
parent e393c3af3f
commit 4978089aab
Signed by: daniel
GPG key ID: FBB4F0E80A80222F
4963 changed files with 677545 additions and 0 deletions

View file

@ -0,0 +1,171 @@
package bind
import (
"encoding/xml"
"fmt"
"net"
"net/http"
"net/url"
"time"
"github.com/influxdata/telegraf"
"github.com/influxdata/telegraf/metric"
)
type v2Root struct {
XMLName xml.Name
Version string `xml:"version,attr"`
Statistics v2Statistics `xml:"bind>statistics"`
}
// Omitted branches: socketmgr, taskmgr
type v2Statistics struct {
Version string `xml:"version,attr"`
Views []struct {
// Omitted branches: zones
Name string `xml:"name"`
RdTypes []v2Counter `xml:"rdtype"`
ResStats []v2Counter `xml:"resstat"`
Caches []struct {
Name string `xml:"name,attr"`
RRSets []v2Counter `xml:"rrset"`
} `xml:"cache"`
} `xml:"views>view"`
Server struct {
OpCodes []v2Counter `xml:"requests>opcode"`
RdTypes []v2Counter `xml:"queries-in>rdtype"`
NSStats []v2Counter `xml:"nsstat"`
ZoneStats []v2Counter `xml:"zonestat"`
ResStats []v2Counter `xml:"resstat"`
SockStats []v2Counter `xml:"sockstat"`
} `xml:"server"`
Memory struct {
Contexts []struct {
// Omitted nodes: references, maxinuse, blocksize, pools, hiwater, lowater
ID string `xml:"id"`
Name string `xml:"name"`
Total int64 `xml:"total"`
InUse int64 `xml:"inuse"`
} `xml:"contexts>context"`
Summary struct {
TotalUse int64
InUse int64
BlockSize int64
ContextSize int64
Lost int64
} `xml:"summary"`
} `xml:"memory"`
}
// BIND statistics v2 counter struct used throughout
type v2Counter struct {
Name string `xml:"name"`
Value int `xml:"counter"`
}
// addXMLv2Counter adds a v2Counter array to a Telegraf Accumulator, with the specified tags
func addXMLv2Counter(acc telegraf.Accumulator, commonTags map[string]string, stats []v2Counter) {
grouper := metric.NewSeriesGrouper()
ts := time.Now()
for _, c := range stats {
tags := make(map[string]string)
// Create local copy of tags since maps are reference types
for k, v := range commonTags {
tags[k] = v
}
grouper.Add("bind_counter", tags, ts, c.Name, c.Value)
}
// Add grouped metrics
for _, groupedMetric := range grouper.Metrics() {
acc.AddMetric(groupedMetric)
}
}
// readStatsXMLv2 decodes a BIND9 XML statistics version 2 document. Unlike the XML v3 statistics
// format, the v2 format does not support broken-out subsets.
func (b *Bind) readStatsXMLv2(addr *url.URL, acc telegraf.Accumulator) error {
var stats v2Root
resp, err := b.client.Get(addr.String())
if err != nil {
return err
}
defer resp.Body.Close()
if resp.StatusCode != http.StatusOK {
return fmt.Errorf("%s returned HTTP status: %s", addr, resp.Status)
}
if err := xml.NewDecoder(resp.Body).Decode(&stats); err != nil {
return fmt.Errorf("unable to decode XML document: %w", err)
}
tags := map[string]string{"url": addr.Host}
host, port, err := net.SplitHostPort(addr.Host)
if err != nil {
return fmt.Errorf("unable to parse address host %q: %w", addr.Host, err)
}
tags["source"] = host
tags["port"] = port
// Opcodes
tags["type"] = "opcode"
addXMLv2Counter(acc, tags, stats.Statistics.Server.OpCodes)
// Query RDATA types
tags["type"] = "qtype"
addXMLv2Counter(acc, tags, stats.Statistics.Server.RdTypes)
// Nameserver stats
tags["type"] = "nsstat"
addXMLv2Counter(acc, tags, stats.Statistics.Server.NSStats)
// Zone stats
tags["type"] = "zonestat"
addXMLv2Counter(acc, tags, stats.Statistics.Server.ZoneStats)
// Socket statistics
tags["type"] = "sockstat"
addXMLv2Counter(acc, tags, stats.Statistics.Server.SockStats)
// Memory stats
fields := map[string]interface{}{
"total_use": stats.Statistics.Memory.Summary.TotalUse,
"in_use": stats.Statistics.Memory.Summary.InUse,
"block_size": stats.Statistics.Memory.Summary.BlockSize,
"context_size": stats.Statistics.Memory.Summary.ContextSize,
"lost": stats.Statistics.Memory.Summary.Lost,
}
acc.AddGauge("bind_memory", fields, map[string]string{"url": addr.Host, "source": host, "port": port})
// Detailed, per-context memory stats
if b.GatherMemoryContexts {
for _, c := range stats.Statistics.Memory.Contexts {
tags := map[string]string{"url": addr.Host, "id": c.ID, "name": c.Name, "source": host, "port": port}
fields := map[string]interface{}{"total": c.Total, "in_use": c.InUse}
acc.AddGauge("bind_memory_context", fields, tags)
}
}
// Detailed, per-view stats
if b.GatherViews {
for _, v := range stats.Statistics.Views {
tags := map[string]string{"url": addr.Host, "view": v.Name}
// Query RDATA types
tags["type"] = "qtype"
addXMLv2Counter(acc, tags, v.RdTypes)
// Resolver stats
tags["type"] = "resstats"
addXMLv2Counter(acc, tags, v.ResStats)
}
}
return nil
}