Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 0 additions & 1 deletion .golangci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,6 @@ linters:
- nakedret
- nlreturn
- nolintlint
- nonamedreturns
- tagliatelle
- varnamelen
- wrapcheck
Expand Down
2 changes: 1 addition & 1 deletion exit.go
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,7 @@ func BaseExit(rc Status) {
_, _ = os.Stdout.WriteString(o)
}

// ExitError exists with an Unknown state while reporting the error
// ExitError exits with an Unknown state while reporting the error
// The Unknown state is used, since the plugin likely could not determine
// the actual status of whatever was meant to be checked.
func ExitError(err error) {
Expand Down
9 changes: 3 additions & 6 deletions perfdata/perfdata.go
Original file line number Diff line number Diff line change
Expand Up @@ -78,14 +78,11 @@ func formatNumeric(value any) (string, error) {
// Perfdata represents all properties of performance data for Icinga
//
// Implements fmt.Stringer to return the plaintext format for a plugin output.
// See also: https://www.monitoring-plugins.org/doc/guidelines.html#AEN201
//
// For examples of Uom see:
//
// https://www.monitoring-plugins.org/doc/guidelines.html#AEN201
//
// https://github.com/Icinga/icinga2/blob/master/lib/base/perfdatavalue.cpp
//
// https://icinga.com/docs/icinga-2/latest/doc/05-service-monitoring/#unit-of-measurement-uom
// - https://github.com/Icinga/icinga2/blob/master/lib/base/perfdatavalue.cpp
// - https://icinga.com/docs/icinga-2/latest/doc/05-service-monitoring/#unit-of-measurement-uom
type Perfdata struct {
Label string
Value any
Expand Down
8 changes: 5 additions & 3 deletions status.go
Original file line number Diff line number Diff line change
Expand Up @@ -83,10 +83,12 @@ func (s Status) String() string {

// WorstState determines the worst state from a list of states
//
// Helps combining an overall states, only based on a
// few numbers for various checks.
//
// This can be used to combine multiple states into a one state.
// Order of preference: Critical, Unknown, Warning, Ok
//
// Note that, this precedence was decided for this package since
// there is no specification for the preference.
// See also: https://www.monitoring-plugins.org/doc/guidelines.html#AEN74
func WorstState(states ...Status) Status {
if len(states) < 1 {
return Unknown
Expand Down
57 changes: 29 additions & 28 deletions threshold.go
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ import (
// 10:20 < 10 or > 20, (outside the range of {10 .. 20})
// @10:20 ≥ 10 and ≤ 20, (inside the range of {10 .. 20})
//
// Reference: https://www.monitoring-plugins.org/doc/guidelines.html#THRESHOLDFORMAT
// See also: https://www.monitoring-plugins.org/doc/guidelines.html#THRESHOLDFORMAT
type Threshold struct {
Inside bool
Lower float64
Expand All @@ -34,72 +34,73 @@ var (
NegInf = math.Inf(-1)
)

const (
NegativeInfinitySymbol = "~"
RangeSeparatorSymbol = ":"
RangeStartSymbol = "@"
)

// ParseThreshold parses a Threshold from a string.
//
// See the Threshold type for details.
func ParseThreshold(spec string) (t *Threshold, err error) {
t = &Threshold{}
func ParseThreshold(spec string) (*Threshold, error) {
t := &Threshold{}

parts := thresholdRe.FindStringSubmatch(spec)
if spec == "" || len(parts) == 0 {
err = fmt.Errorf("could not parse threshold: %s", spec)
return
return t, fmt.Errorf("could not parse threshold: %s", spec)
}

// @ at the beginning
if parts[1] != "" {
t.Inside = true
}

var v float64

// Lower bound
if parts[2] == "~" {
if parts[2] == NegativeInfinitySymbol {
t.Lower = NegInf
} else if parts[2] != "" {
v, err = strconv.ParseFloat(parts[2], 64)
if err != nil {
err = fmt.Errorf("can not parse lower bound '%s': %w", parts[2], err)
return
v, errParseLow := strconv.ParseFloat(parts[2], 64)
if errParseLow != nil {
return t, fmt.Errorf("can not parse lower bound '%s': %w", parts[2], errParseLow)
}

t.Lower = v
}

// Upper bound
if parts[3] == "~" || (parts[3] == "" && parts[2] != "") {
if parts[3] == NegativeInfinitySymbol || (parts[3] == "" && parts[2] != "") {
t.Upper = PosInf
} else if parts[3] != "" {
v, err = strconv.ParseFloat(parts[3], 64)
if err != nil {
err = fmt.Errorf("can not parse upper bound '%s': %w", parts[3], err)
return
v, errParseUp := strconv.ParseFloat(parts[3], 64)
if errParseUp != nil {
return t, fmt.Errorf("can not parse upper bound '%s': %w", parts[3], errParseUp)
}

t.Upper = v
}

return
return t, nil
}

// String returns the plain representation of the Threshold
func (t Threshold) String() (s string) {
s = BoundaryToString(t.Upper)
func (t Threshold) String() string {
s := BoundaryToString(t.Upper)

// remove upper ~, which is the default
if s == "~" {
if s == NegativeInfinitySymbol {
s = ""
}

if t.Lower != 0 {
s = BoundaryToString(t.Lower) + ":" + s
s = BoundaryToString(t.Lower) + RangeSeparatorSymbol + s
}

if t.Inside {
s = "@" + s
s = RangeStartSymbol + s
}

return
return s
}

// DoesViolate compares a value against the threshold, and returns true if the value violates the threshold.
Expand All @@ -112,15 +113,15 @@ func (t Threshold) DoesViolate(value float64) bool {
}

// BoundaryToString returns the string representation of a Threshold boundary.
func BoundaryToString(value float64) (s string) {
s = FormatFloat(value)
func BoundaryToString(value float64) string {
s := FormatFloat(value)

// In the threshold context, the sign derives from lower and upper bound, we only need the ~ notation
if s == "+Inf" || s == "-Inf" {
s = "~"
s = NegativeInfinitySymbol
}

return
return s
}

// FormatFloat returns a string representation of floats, avoiding scientific notation and removes trailing zeros.
Expand Down
Loading