app/history/history.go

104 lines
1.6 KiB
Go

package history
import (
"encoding/json"
"fmt"
"time"
"github.com/rs/zerolog/log"
"gorm.io/gorm"
"kumoly.io/kumoly/app/errors"
"kumoly.io/kumoly/app/store"
)
var PROD = false
const (
ERROR = "ERROR"
INFO = "INFO"
)
type History struct {
ID uint `gorm:"primaryKey"`
CreatedAt time.Time
Module string
Type string
Caller string
Trace string
Message string
Body interface{} `gorm:"-"`
Issuer string
Group string
BodyJson string
}
func (h *History) BeforeCreate(tx *gorm.DB) (err error) {
if h.Body != nil {
body, err := json.Marshal(h.Body)
if err != nil {
h.BodyJson = string(body)
}
}
return
}
var Tunnel chan *History
var quit chan struct{}
var started chan struct{}
func init() {
Tunnel = make(chan *History)
quit = make(chan struct{}, 1)
started = make(chan struct{}, 1)
}
func Start(r Receiver) {
select {
case started <- struct{}{}:
default:
panic(errors.New(500, "history reporter has already started!"))
}
go func() {
for {
select {
case h := <-Tunnel:
if Interceptor != nil {
go Interceptor(h)
}
r(h)
case <-quit:
<-started
return
}
}
}()
}
func Stop() {
quit <- struct{}{}
}
func Send(h *History) {
if h.Type == "" {
h.Type = INFO
}
Tunnel <- h
}
type Receiver func(*History)
var Interceptor func(*History) = nil
var DBReceiver Receiver = func(h *History) {
err := store.DB.Create(h).Error
if err != nil {
log.Error().Str("mod", "history").Err(err).Msg("DBReceiver error")
}
}
var ConsoleReceiver Receiver = func(h *History) {
fmt.Printf("%+v\n", h)
}