Check for presence of DS and special CDS 0 0 0 00 removal record
This commit is contained in:
parent
6dbc1c3155
commit
b175d73156
1 changed files with 41 additions and 10 deletions
51
main.go
51
main.go
|
@ -21,9 +21,17 @@ import (
|
||||||
|
|
||||||
const namespace = "dnssec"
|
const namespace = "dnssec"
|
||||||
|
|
||||||
|
var removalCds = DsData{
|
||||||
|
KeyTag: 0,
|
||||||
|
Algorithm: 0,
|
||||||
|
DigestType: 0,
|
||||||
|
Digest: "00",
|
||||||
|
}
|
||||||
|
|
||||||
type MetricsCollector struct {
|
type MetricsCollector struct {
|
||||||
Log log.Logger
|
Log log.Logger
|
||||||
signatureOkMetric *prom.GaugeVec
|
signatureOkMetric *prom.GaugeVec
|
||||||
|
dsPresentMetric *prom.GaugeVec
|
||||||
cdsPresentMetric *prom.GaugeVec
|
cdsPresentMetric *prom.GaugeVec
|
||||||
cdsDsMatchMetric *prom.GaugeVec
|
cdsDsMatchMetric *prom.GaugeVec
|
||||||
zones []string
|
zones []string
|
||||||
|
@ -40,6 +48,14 @@ func NewMetricsCollector(zonelist []string, resolver string, logger log.Logger)
|
||||||
},
|
},
|
||||||
[]string{"zone", "tld", "parent"},
|
[]string{"zone", "tld", "parent"},
|
||||||
)
|
)
|
||||||
|
dsPresentMetric := prom.NewGaugeVec(
|
||||||
|
prom.GaugeOpts{
|
||||||
|
Namespace: namespace,
|
||||||
|
Name: "ds_present",
|
||||||
|
Help: "1 if CDS record is present in the parent zone, 0 otherwise",
|
||||||
|
},
|
||||||
|
[]string{"zone", "tld", "parent"},
|
||||||
|
)
|
||||||
cdsPresentMetric := prom.NewGaugeVec(
|
cdsPresentMetric := prom.NewGaugeVec(
|
||||||
prom.GaugeOpts{
|
prom.GaugeOpts{
|
||||||
Namespace: namespace,
|
Namespace: namespace,
|
||||||
|
@ -58,6 +74,7 @@ func NewMetricsCollector(zonelist []string, resolver string, logger log.Logger)
|
||||||
)
|
)
|
||||||
collector := MetricsCollector{
|
collector := MetricsCollector{
|
||||||
signatureOkMetric: signatureOkMetric,
|
signatureOkMetric: signatureOkMetric,
|
||||||
|
dsPresentMetric: dsPresentMetric,
|
||||||
cdsPresentMetric: cdsPresentMetric,
|
cdsPresentMetric: cdsPresentMetric,
|
||||||
cdsDsMatchMetric: cdsDsMatchMetric,
|
cdsDsMatchMetric: cdsDsMatchMetric,
|
||||||
zones: zonelist,
|
zones: zonelist,
|
||||||
|
@ -69,6 +86,7 @@ func NewMetricsCollector(zonelist []string, resolver string, logger log.Logger)
|
||||||
|
|
||||||
func (c *MetricsCollector) Describe(ch chan<- *prom.Desc) {
|
func (c *MetricsCollector) Describe(ch chan<- *prom.Desc) {
|
||||||
c.signatureOkMetric.Describe(ch)
|
c.signatureOkMetric.Describe(ch)
|
||||||
|
c.dsPresentMetric.Describe(ch)
|
||||||
c.cdsPresentMetric.Describe(ch)
|
c.cdsPresentMetric.Describe(ch)
|
||||||
c.cdsDsMatchMetric.Describe(ch)
|
c.cdsDsMatchMetric.Describe(ch)
|
||||||
}
|
}
|
||||||
|
@ -87,7 +105,7 @@ func (c *MetricsCollector) reportMetrics(ch chan<- prom.Metric) error {
|
||||||
if err1 != nil {
|
if err1 != nil {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
cdp, cdm, err2 := c.cdsDsMatches(zone)
|
dsp, cdp, cdm, err2 := c.cdsDsMatches(zone)
|
||||||
if err2 != nil {
|
if err2 != nil {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
@ -100,6 +118,7 @@ func (c *MetricsCollector) reportMetrics(ch chan<- prom.Metric) error {
|
||||||
"parent": parent,
|
"parent": parent,
|
||||||
}
|
}
|
||||||
signatureOkMetric := c.signatureOkMetric.With(promlabels)
|
signatureOkMetric := c.signatureOkMetric.With(promlabels)
|
||||||
|
dsPresentMetric := c.dsPresentMetric.With(promlabels)
|
||||||
cdsPresentMetric := c.cdsPresentMetric.With(promlabels)
|
cdsPresentMetric := c.cdsPresentMetric.With(promlabels)
|
||||||
cdsDsMatchMetric := c.cdsDsMatchMetric.With(promlabels)
|
cdsDsMatchMetric := c.cdsDsMatchMetric.With(promlabels)
|
||||||
if sok {
|
if sok {
|
||||||
|
@ -107,6 +126,11 @@ func (c *MetricsCollector) reportMetrics(ch chan<- prom.Metric) error {
|
||||||
} else {
|
} else {
|
||||||
signatureOkMetric.Set(0)
|
signatureOkMetric.Set(0)
|
||||||
}
|
}
|
||||||
|
if dsp {
|
||||||
|
dsPresentMetric.Set(1)
|
||||||
|
} else {
|
||||||
|
dsPresentMetric.Set(0)
|
||||||
|
}
|
||||||
if cdp {
|
if cdp {
|
||||||
cdsPresentMetric.Set(1)
|
cdsPresentMetric.Set(1)
|
||||||
} else {
|
} else {
|
||||||
|
@ -120,6 +144,7 @@ func (c *MetricsCollector) reportMetrics(ch chan<- prom.Metric) error {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
c.signatureOkMetric.Collect(ch)
|
c.signatureOkMetric.Collect(ch)
|
||||||
|
c.dsPresentMetric.Collect(ch)
|
||||||
c.cdsPresentMetric.Collect(ch)
|
c.cdsPresentMetric.Collect(ch)
|
||||||
c.cdsDsMatchMetric.Collect(ch)
|
c.cdsDsMatchMetric.Collect(ch)
|
||||||
return nil
|
return nil
|
||||||
|
@ -154,20 +179,20 @@ func (c *MetricsCollector) signatureOk(zone string) (bool, error) {
|
||||||
return false, err
|
return false, err
|
||||||
}
|
}
|
||||||
level.Debug(c.Log).Log(fmt.Sprintf("SOA header: %+v\n", rsoa.MsgHdr))
|
level.Debug(c.Log).Log(fmt.Sprintf("SOA header: %+v\n", rsoa.MsgHdr))
|
||||||
return rsoa.MsgHdr.AuthenticatedData, nil
|
return rsoa.MsgHdr.AuthenticatedData && rsoa.MsgHdr.Rcode == dns.RcodeSuccess, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (c *MetricsCollector) cdsDsMatches(zone string) (bool, bool, error) {
|
func (c *MetricsCollector) cdsDsMatches(zone string) (bool, bool, bool, error) {
|
||||||
|
dsPresent := false
|
||||||
|
cdsPresent := false
|
||||||
|
|
||||||
qcds := new(dns.Msg)
|
qcds := new(dns.Msg)
|
||||||
qcds.SetQuestion(dns.Fqdn(zone), dns.TypeCDS)
|
qcds.SetQuestion(dns.Fqdn(zone), dns.TypeCDS)
|
||||||
rcds, _, err := c.DNS.Exchange(qcds, c.Resolver)
|
rcds, _, err := c.DNS.Exchange(qcds, c.Resolver)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return false, false, err
|
return dsPresent, cdsPresent, false, err
|
||||||
}
|
|
||||||
if len(rcds.Answer) == 0 {
|
|
||||||
// Zone doesn't publish CDS records
|
|
||||||
return false, false, nil
|
|
||||||
}
|
}
|
||||||
|
cdsPresent = len(rcds.Answer) > 0
|
||||||
cdsdata := make([]DsData, len(rcds.Answer))
|
cdsdata := make([]DsData, len(rcds.Answer))
|
||||||
level.Debug(c.Log).Log(fmt.Sprintf("CDS data: %+v\n", rcds.Answer))
|
level.Debug(c.Log).Log(fmt.Sprintf("CDS data: %+v\n", rcds.Answer))
|
||||||
for i, a := range rcds.Answer {
|
for i, a := range rcds.Answer {
|
||||||
|
@ -185,8 +210,9 @@ func (c *MetricsCollector) cdsDsMatches(zone string) (bool, bool, error) {
|
||||||
qds.SetQuestion(dns.Fqdn(zone), dns.TypeDS)
|
qds.SetQuestion(dns.Fqdn(zone), dns.TypeDS)
|
||||||
rds, _, err := c.DNS.Exchange(qds, c.Resolver)
|
rds, _, err := c.DNS.Exchange(qds, c.Resolver)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return true, false, err
|
return dsPresent, cdsPresent, false, err
|
||||||
}
|
}
|
||||||
|
dsPresent = len(rds.Answer) > 0
|
||||||
dsdata := make([]DsData, len(rds.Answer))
|
dsdata := make([]DsData, len(rds.Answer))
|
||||||
level.Debug(c.Log).Log(fmt.Sprintf("DS data: %+v\n", rds.Answer))
|
level.Debug(c.Log).Log(fmt.Sprintf("DS data: %+v\n", rds.Answer))
|
||||||
for i, a := range rds.Answer {
|
for i, a := range rds.Answer {
|
||||||
|
@ -200,7 +226,12 @@ func (c *MetricsCollector) cdsDsMatches(zone string) (bool, bool, error) {
|
||||||
}
|
}
|
||||||
sort.SliceStable(dsdata, func(a, b int) bool { return dsdata[a].KeyTag < dsdata[b].KeyTag })
|
sort.SliceStable(dsdata, func(a, b int) bool { return dsdata[a].KeyTag < dsdata[b].KeyTag })
|
||||||
|
|
||||||
return true, Equal(dsdata, cdsdata), nil
|
match := cdsPresent && Equal(dsdata, cdsdata)
|
||||||
|
// special case: removal requested
|
||||||
|
if len(cdsdata) == 1 && len(dsdata) == 0 && cdsdata[0] == removalCds {
|
||||||
|
match = true
|
||||||
|
}
|
||||||
|
return dsPresent, cdsPresent, match, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
|
|
Loading…
Reference in a new issue