-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
16 changed files
with
458 additions
and
158 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
name: CI | ||
|
||
on: | ||
push: | ||
pull_request: | ||
|
||
jobs: | ||
test: | ||
name: Test | ||
runs-on: ubuntu-latest | ||
steps: | ||
# step 1: checkout repository code | ||
- name: Checkout code into workspace directory | ||
uses: actions/checkout@v4 | ||
|
||
# step 2: set up go | ||
- name: Set up Go 1.21 | ||
uses: actions/setup-go@v4 | ||
with: | ||
go-version: ">=1.21" | ||
|
||
# step 3: install dependencies | ||
- name: Install all Go dependencies | ||
run: go mod download | ||
|
||
# step 4: run test | ||
- name: Run coverage | ||
run: go test -race -coverprofile=coverage.out -covermode=atomic ./... |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,143 +1,16 @@ | ||
package config | ||
|
||
import ( | ||
"fmt" | ||
"math/rand" | ||
"strings" | ||
) | ||
|
||
type Config struct { | ||
Telegram Telegram `yaml:"telegram"` | ||
Services []Service `yaml:"services"` | ||
Telegram Telegram `yaml:"telegram"` | ||
// Services []Service `yaml:"services"` | ||
} | ||
|
||
type Telegram struct { | ||
Token string `yaml:"token" envconfig:"TELEGRAM__TOKEN" validate:"required"` | ||
ChatID int64 `yaml:"chatId" envconfig:"TELEGRAM__CHAT_ID"` | ||
WebhookURL string `yaml:"webhookUrl" envconfig:"TELEGRAM__WEBHOOK_URL" validate:"required"` | ||
Debug bool `yaml:"debug" envconfig:"TELEGRAM__DEBUG"` | ||
Messages TelegramMessages `yaml:"messages"` | ||
} | ||
type TelegramMessages map[string]string | ||
type HTTPHeader struct { | ||
Name string `yaml:"name"` | ||
Value string `yaml:"value"` | ||
} | ||
|
||
type HTTPHeaders []HTTPHeader | ||
|
||
func (h HTTPHeaders) ToMap() map[string][]string { | ||
m := make(map[string][]string, len(h)) | ||
|
||
for _, v := range h { | ||
m[v.Name] = append(m[v.Name], v.Value) | ||
} | ||
|
||
return m | ||
} | ||
|
||
type HTTPGet struct { | ||
TCPSocket `yaml:",inline"` | ||
Scheme string `yaml:"scheme"` | ||
Path string `yaml:"path"` | ||
HTTPHeaders HTTPHeaders `yaml:"httpHeaders"` | ||
} | ||
|
||
func (s HTTPGet) IsEmpty() bool { | ||
return s.Host == "" | ||
} | ||
|
||
func (h HTTPGet) ApplyDefaultsAndValidate() (HTTPGet, error) { | ||
if h.IsEmpty() { | ||
return h, nil | ||
} | ||
|
||
if h.Scheme == "" { | ||
if h.Port == 80 { | ||
h.Scheme = "http" | ||
} | ||
if h.Port == 443 { | ||
h.Scheme = "https" | ||
} | ||
} | ||
|
||
if h.Port == 0 { | ||
if h.Scheme == "http" { | ||
h.Port = 80 | ||
} | ||
if h.Scheme == "https" { | ||
h.Port = 443 | ||
} | ||
} | ||
|
||
if h.Scheme != "http" && h.Scheme != "https" { | ||
return h, fmt.Errorf("invalid scheme %s", h.Scheme) | ||
} | ||
|
||
if !strings.HasPrefix(h.Path, "/") { | ||
h.Path = "/" + h.Path | ||
} | ||
|
||
return h, nil | ||
} | ||
|
||
type TCPSocket struct { | ||
Host string `yaml:"host" validate:"required,hostname"` | ||
Port uint16 `yaml:"port"` | ||
} | ||
|
||
func (s TCPSocket) IsEmpty() bool { | ||
return s.Host == "" | ||
} | ||
|
||
type Service struct { | ||
Id string `yaml:"id"` | ||
Name string `yaml:"name"` | ||
InitialDelaySeconds int `yaml:"initialDelaySeconds"` // пауза перед первым опросом в секундах, по умолчанию: 0; если меньше 0, то используется случайное значение между 0 и `periodSeconds` | ||
PeriodSeconds int `yaml:"periodSeconds"` // период опроса в секундах, по умолчанию: 10 | ||
TimeoutSeconds int `yaml:"timeoutSeconds"` // время ожидания ответа в секундах, по кмолчанию: 1 | ||
SuccessThreshold int `yaml:"successThreshold"` // количество последовательных успешных соединений для перехода в состояние "в сети", по умолчанию: 1 | ||
FailureThreshold int `yaml:"failureThreshold"` // количество последовательных ошибок соединения для перехода в состояние "не в сети", по умолчанию: 3 | ||
HTTPGet HTTPGet `yaml:"httpGet,omitempty"` | ||
TCPSocket TCPSocket `yaml:"tcpSocket,omitempty"` | ||
} | ||
|
||
func (s Service) ApplyDefaultsAndValidate() (svc Service, err error) { | ||
if s.PeriodSeconds < 0 { | ||
return s, fmt.Errorf("periodSeconds must be gte 0") | ||
} | ||
if s.SuccessThreshold < 0 { | ||
return s, fmt.Errorf("successThreshold must be gte 0") | ||
} | ||
if s.FailureThreshold < 0 { | ||
return s, fmt.Errorf("failureThreshold must be gte 0") | ||
} | ||
if s.HTTPGet.IsEmpty() && s.TCPSocket.IsEmpty() { | ||
return s, fmt.Errorf("one of httpGet or tcpSocket must be filled") | ||
} | ||
|
||
if s.HTTPGet, err = s.HTTPGet.ApplyDefaultsAndValidate(); err != nil { | ||
return s, err | ||
} | ||
|
||
if s.PeriodSeconds == 0 { | ||
s.PeriodSeconds = 10 | ||
} | ||
|
||
if s.InitialDelaySeconds < 0 { | ||
s.InitialDelaySeconds = rand.Intn(s.PeriodSeconds + 1) | ||
} | ||
|
||
if s.SuccessThreshold == 0 { | ||
s.SuccessThreshold = 1 | ||
} | ||
|
||
if s.FailureThreshold == 0 { | ||
s.FailureThreshold = 3 | ||
} | ||
|
||
return s, nil | ||
} | ||
|
||
type Monitor struct { | ||
Services []Service `yaml:"services"` | ||
} | ||
type TelegramMessages map[string]string |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -14,6 +14,6 @@ var ( | |
Debug: false, | ||
Messages: defaultTelegramMessages, | ||
}, | ||
Services: []Service{}, | ||
// Services: []Service{}, | ||
} | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,6 +1,8 @@ | ||
package monitor | ||
|
||
import "context" | ||
import ( | ||
"context" | ||
) | ||
|
||
const ( | ||
ServiceOnline ServiceState = "online" | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,18 @@ | ||
package storage | ||
|
||
import ( | ||
"os" | ||
|
||
"go.uber.org/fx" | ||
) | ||
|
||
var Module = fx.Module( | ||
"storage", | ||
fx.Provide(func() Storage { | ||
return NewStorageService( | ||
&yamlStorage{ | ||
Path: os.Getenv("CONFIG_PATH"), | ||
}, | ||
) | ||
}), | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
package storage | ||
|
||
type Storage interface { | ||
Load() ([]Service, error) | ||
} | ||
|
||
type StorageService struct { | ||
storage Storage | ||
} | ||
|
||
func NewStorageService(storage Storage) *StorageService { | ||
return &StorageService{ | ||
storage: storage, | ||
} | ||
} | ||
|
||
func (s *StorageService) Load() ([]Service, error) { | ||
services, err := s.storage.Load() | ||
if err != nil { | ||
return nil, err | ||
} | ||
|
||
for i := range services { | ||
if err := services[i].Validate(); err != nil { | ||
return nil, err | ||
} | ||
} | ||
|
||
return services, nil | ||
} |
Oops, something went wrong.