feat: export new version metric (#12)

Add a new `f2b_version` metric that includes the version of the fail2ban
server and the exporter.
Add a new socket command to get back the fail2ban server version.
This commit is contained in:
Hector 2021-09-10 06:13:56 +00:00
parent d9f1ee33c8
commit fba9ee2809
3 changed files with 39 additions and 0 deletions

View file

@ -85,6 +85,11 @@ var (
"Total number of IPs banned by this jail (includes expired bans)",
[]string{"jail"}, nil,
)
metricVersionInfo = prometheus.NewDesc(
prometheus.BuildFQName(namespace, "", "version"),
"Version of the exporter and fail2ban server",
[]string{"exporter", "fail2ban"}, nil,
)
)
type Exporter struct {
@ -135,6 +140,9 @@ func (e *Exporter) Collect(ch chan<- prometheus.Metric) {
if err == nil && s != nil {
e.collectJailMetrics(ch, s)
}
e.collectVersionMetric(ch, s)
} else {
e.collectVersionMetric(ch, nil)
}
e.collectErrorCountMetric(ch)
}
@ -273,6 +281,22 @@ func (e *Exporter) collectJailStatsMetric(ch chan<- prometheus.Metric, s *socket
)
}
func (e *Exporter) collectVersionMetric(ch chan<- prometheus.Metric, s *socket.Fail2BanSocket) {
var err error
var fail2banVersion = ""
if s != nil {
fail2banVersion, err = s.GetServerVersion()
if err != nil {
e.socketRequestErrorCount++
log.Printf("failed to get fail2ban server version: %v", err)
}
}
ch <- prometheus.MustNewConstMetric(
metricVersionInfo, prometheus.GaugeValue, float64(1), version, fail2banVersion,
)
}
func printAppVersion() {
fmt.Println(version)
fmt.Printf(" build date: %s\r\n commit hash: %s\r\n built by: %s\r\n", date, commit, builtBy)

View file

@ -118,6 +118,20 @@ func (s *Fail2BanSocket) GetJailStats(jail string) (JailStats, error) {
return stats, newBadFormatError(statusCommand, response)
}
func (s *Fail2BanSocket) GetServerVersion() (string, error) {
response, err := s.sendCommand([]string{versionCommand})
if err != nil {
return "", err
}
if lvl1, ok := response.(*types.Tuple); ok {
if versionStr, ok := lvl1.Get(1).(string); ok {
return versionStr, nil
}
}
return "", newBadFormatError(versionCommand, response)
}
func newBadFormatError(command string, data interface{}) error {
return fmt.Errorf("(%s) unexpected response format - cannot parse: %v", command, data)
}

View file

@ -11,6 +11,7 @@ const (
commandTerminator = "<F2B_END_COMMAND>"
pingCommand = "ping"
statusCommand = "status"
versionCommand = "version"
socketReadBufferSize = 1024
)