Implement interval + Add timestamp to Result struct

This commit is contained in:
TwinProduction 2019-09-08 21:07:08 -04:00
parent 8a7aa96b97
commit 825906145f
6 changed files with 60 additions and 33 deletions

View File

@ -3,15 +3,25 @@
A service health dashboard in Go
config should look something like
## Usage
```yaml
services:
- name: twinnation
- name: twinnation # Name of your service, can be anything
url: https://twinnation.org/actuator/health
interval: 10
interval: 15s # Duration to wait between every status check (opt. default: 10s)
failure-threshold: 3
conditions:
- "$STATUS == 200"
- "IP == 200"
- name: github
url: https://api.github.com/healthz
conditions:
- "$STATUS == 200"
```
## Running the tests
```
go test ./... -mod vendor
```

View File

@ -1,7 +1,7 @@
services:
- name: twinnation
url: https://twinnation.org/actuator/health
interval: 15
interval: 15s
failure-threshold: 3
conditions:
- "$STATUS == 200"

View File

@ -4,6 +4,7 @@ import (
"github.com/TwinProduction/gatus/core"
"gopkg.in/yaml.v2"
"io/ioutil"
"time"
)
type Config struct {
@ -37,7 +38,7 @@ func ParseConfigBytes(yamlBytes []byte) *Config {
service.FailureThreshold = 1
}
if service.Interval == 0 {
service.Interval = 10
service.Interval = 10 * time.Second
}
}
return config

View File

@ -1,18 +1,22 @@
package config
import "testing"
import (
"fmt"
"testing"
"time"
)
func TestParseConfigBytes(t *testing.T) {
config := ParseConfigBytes([]byte(`
services:
- name: twinnation
url: https://twinnation.org/actuator/health
interval: 15
interval: 15s
failure-threshold: 3
conditions:
- "$STATUS == 200"
- name: github
url: https://github.com
url: https://api.github.com/healthz
conditions:
- "$STATUS != 400"
- "$STATUS != 500"
@ -23,14 +27,15 @@ services:
if config.Services[0].Url != "https://twinnation.org/actuator/health" {
t.Errorf("URL should have been %s", "https://twinnation.org/actuator/health")
}
if config.Services[1].Url != "https://github.com" {
t.Errorf("URL should have been %s", "https://github.com")
if config.Services[1].Url != "https://api.github.com/healthz" {
t.Errorf("URL should have been %s", "https://api.github.com/healthz")
}
if config.Services[0].Interval != 15 {
t.Errorf("Interval should have been %d", 15)
fmt.Println(config.Services[0].Interval)
if config.Services[0].Interval != 15*time.Second {
t.Errorf("Interval should have been %s", 15*time.Second)
}
if config.Services[1].Interval != 10 {
t.Errorf("Interval should have been %d, because it is the default value", 10)
if config.Services[1].Interval != 10*time.Second {
t.Errorf("Interval should have been %s, because it is the default value", 10*time.Second)
}
if config.Services[0].FailureThreshold != 3 {
t.Errorf("FailureThreshold should have been %d", 3)

View File

@ -24,15 +24,16 @@ type Result struct {
HttpStatus int `json:"status"`
Hostname string `json:"hostname"`
Ip string `json:"ip"`
Duration string `json:"duration"`
Duration time.Duration `json:"duration"`
Errors []error `json:"errors"`
ConditionResult []*ConditionResult `json:"condition-results"`
Timestamp time.Time `json:"timestamp"`
}
type Service struct {
Name string `yaml:"name"`
Url string `yaml:"url"`
Interval int `yaml:"interval,omitempty"` // TODO: Implement
Interval time.Duration `yaml:"interval,omitempty"`
FailureThreshold int `yaml:"failure-threshold,omitempty"` // TODO: Implement
Conditions []*Condition `yaml:"conditions"`
}
@ -62,7 +63,7 @@ func (service *Service) getStatus(result *Result) {
result.Errors = append(result.Errors, err)
return
}
result.Duration = time.Now().Sub(startTime).String()
result.Duration = time.Now().Sub(startTime)
result.HttpStatus = response.StatusCode
}
@ -73,6 +74,7 @@ func (service *Service) EvaluateConditions() *Result {
for _, condition := range service.Conditions {
condition.Evaluate(result)
}
result.Timestamp = time.Now()
return result
}

View File

@ -3,6 +3,7 @@ package watchdog
import (
"github.com/TwinProduction/gatus/config"
"github.com/TwinProduction/gatus/core"
"log"
"sync"
"time"
)
@ -17,18 +18,26 @@ func GetServiceResults() *map[string][]*core.Result {
}
func Monitor() {
for {
for _, service := range config.Get().Services {
go func(service *core.Service) {
for {
log.Printf("[watchdog][Monitor] Waiting interval=%s before monitoring serviceName=%s", service.Interval, service.Name)
time.Sleep(service.Interval)
log.Printf("[watchdog][Monitor] Monitoring serviceName=%s", service.Name)
result := service.EvaluateConditions()
rwLock.Lock()
defer rwLock.Unlock()
serviceResults[service.Name] = append(serviceResults[service.Name], result)
if len(serviceResults[service.Name]) > 15 {
serviceResults[service.Name] = serviceResults[service.Name][15:]
if len(serviceResults[service.Name]) > 10 {
serviceResults[service.Name] = serviceResults[service.Name][1:]
}
rwLock.Unlock()
log.Printf(
"[watchdog][Monitor] Finished monitoring serviceName=%s; errors=%d; requestDuration=%s",
service.Name,
len(result.Errors),
result.Duration.Round(time.Millisecond),
)
}
}(service)
}
time.Sleep(10 * time.Second)
}
}