933e70a3f6
- Add robust notification system supporting 7+ communication channels with intelligent message templating, resource monitoring, and SSL certificate alerts. Notification Channels: (Telegram, Discord, Slack, Signal, Email, Google Chat, Webhooks). - This notification system provides enterprise-grade alerting capabilities with extensive customization options and multi-channel redundancy for critical service monitoring.
113 lines
3.4 KiB
Go
113 lines
3.4 KiB
Go
|
|
package uptimemonitoring
|
|
|
|
import (
|
|
"encoding/json"
|
|
"fmt"
|
|
"net/http"
|
|
"time"
|
|
|
|
"service-operation/pocketbase"
|
|
)
|
|
|
|
// UptimeClient handles uptime service operations
|
|
type UptimeClient struct {
|
|
pbClient *pocketbase.PocketBaseClient
|
|
}
|
|
|
|
// MetricRecord represents a metric record from any collection
|
|
type MetricRecord struct {
|
|
ID string `json:"id"`
|
|
ServiceID string `json:"service_id"`
|
|
Status string `json:"status"`
|
|
ResponseTime int `json:"response_time"`
|
|
ErrorMessage string `json:"error_message"` // Added missing ErrorMessage field
|
|
Timestamp time.Time `json:"timestamp"`
|
|
Created time.Time `json:"created"`
|
|
}
|
|
|
|
// NewUptimeClient creates a new uptime client
|
|
func NewUptimeClient(pbClient *pocketbase.PocketBaseClient) *UptimeClient {
|
|
return &UptimeClient{
|
|
pbClient: pbClient,
|
|
}
|
|
}
|
|
|
|
// GetServices retrieves all services for monitoring
|
|
func (uc *UptimeClient) GetServices() ([]UptimeService, error) {
|
|
url := fmt.Sprintf("%s/api/collections/services/records", uc.pbClient.GetBaseURL())
|
|
|
|
resp, err := http.Get(url)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("failed to fetch services: %v", err)
|
|
}
|
|
defer resp.Body.Close()
|
|
|
|
if resp.StatusCode != http.StatusOK {
|
|
return nil, fmt.Errorf("failed to fetch services, status: %d", resp.StatusCode)
|
|
}
|
|
|
|
var response struct {
|
|
Items []UptimeService `json:"items"`
|
|
}
|
|
|
|
if err := json.NewDecoder(resp.Body).Decode(&response); err != nil {
|
|
return nil, fmt.Errorf("failed to decode services: %v", err)
|
|
}
|
|
|
|
// log.Printf("✅ Fetched %d services for monitoring", len(response.Items))
|
|
return response.Items, nil
|
|
}
|
|
|
|
// GetLatestMetricRecord gets the latest metric record for a service from specified collection
|
|
func (uc *UptimeClient) GetLatestMetricRecord(serviceID, collection string) ([]MetricRecord, error) {
|
|
url := fmt.Sprintf("%s/api/collections/%s/records?filter=service_id='%s'&sort=-timestamp&perPage=1",
|
|
uc.pbClient.GetBaseURL(), collection, serviceID)
|
|
|
|
// log.Printf("🔍 [METRICS-QUERY] Getting latest record for service %s from %s", serviceID, collection)
|
|
|
|
resp, err := http.Get(url)
|
|
if err != nil {
|
|
return nil, fmt.Errorf("failed to fetch metric record: %v", err)
|
|
}
|
|
defer resp.Body.Close()
|
|
|
|
if resp.StatusCode != http.StatusOK {
|
|
return nil, fmt.Errorf("failed to fetch metric record, status: %d", resp.StatusCode)
|
|
}
|
|
|
|
var response struct {
|
|
Items []struct {
|
|
ID string `json:"id"`
|
|
ServiceID string `json:"service_id"`
|
|
Status string `json:"status"`
|
|
ResponseTime int `json:"response_time"`
|
|
ErrorMessage string `json:"error_message"` // Added missing ErrorMessage field
|
|
Timestamp string `json:"timestamp"`
|
|
Created string `json:"created"`
|
|
} `json:"items"`
|
|
}
|
|
|
|
if err := json.NewDecoder(resp.Body).Decode(&response); err != nil {
|
|
return nil, fmt.Errorf("failed to decode metric record: %v", err)
|
|
}
|
|
|
|
var records []MetricRecord
|
|
for _, item := range response.Items {
|
|
timestamp, _ := time.Parse(time.RFC3339, item.Timestamp)
|
|
created, _ := time.Parse(time.RFC3339, item.Created)
|
|
|
|
records = append(records, MetricRecord{
|
|
ID: item.ID,
|
|
ServiceID: item.ServiceID,
|
|
Status: item.Status,
|
|
ResponseTime: item.ResponseTime,
|
|
ErrorMessage: item.ErrorMessage, // Include ErrorMessage in the record
|
|
Timestamp: timestamp,
|
|
Created: created,
|
|
})
|
|
}
|
|
|
|
// log.Printf("📊 [METRICS-RESULT] Found %d records for service %s in %s", len(records), serviceID, collection)
|
|
return records, nil
|
|
} |