github.com/pyroscope-io/pyroscope@v0.37.3-0.20230725203016-5f6947968bd0/pkg/health/disk_pressure.go (about) 1 package health 2 3 import ( 4 "errors" 5 "fmt" 6 7 "github.com/pyroscope-io/pyroscope/pkg/util/bytesize" 8 "github.com/pyroscope-io/pyroscope/pkg/util/disk" 9 ) 10 11 var ( 12 errZeroTotalSize = errors.New("total disk size is zero") 13 errTotalLessThanAvailable = errors.New("total disk size is less than available space") 14 ) 15 16 const minAvailSpace = bytesize.GB 17 18 type DiskPressure struct { 19 Threshold float64 20 Path string 21 } 22 23 func (d DiskPressure) Probe() (StatusMessage, error) { 24 if d.Threshold == 0 { 25 return StatusMessage{Status: Healthy}, nil 26 } 27 u, err := disk.Usage(d.Path) 28 if err != nil { 29 return StatusMessage{}, err 30 } 31 return d.makeProbe(u) 32 } 33 34 func (d DiskPressure) makeProbe(u disk.UsageStats) (StatusMessage, error) { 35 var m StatusMessage 36 if u.Total == 0 { 37 return m, errZeroTotalSize 38 } 39 if u.Available > u.Total { 40 return m, errTotalLessThanAvailable 41 } 42 m.Status = Healthy 43 if u.Available < d.minRequired(u) { 44 availPercent := 100 * float64(u.Available) / float64(u.Total) 45 m.Message = fmt.Sprintf("Disk space is running low: %v available (%.1f%%)", u.Available, availPercent) 46 m.Status = Critical 47 } 48 return m, nil 49 } 50 51 func (d DiskPressure) minRequired(u disk.UsageStats) bytesize.ByteSize { 52 t := bytesize.ByteSize(float64(u.Total) / 100 * d.Threshold) 53 if t > minAvailSpace { 54 return t 55 } 56 return minAvailSpace 57 }