master
Evan Chen 2021-12-17 15:52:32 +08:00
parent 14a5cf1615
commit 977436d334
14 changed files with 117 additions and 40 deletions

View File

@ -5,4 +5,4 @@ run:
APP_LOG_PRETTY=true \
APP_DB_TYPE=sqlite \
APP_DATA=work \
go run cmd/test/main.go
go test

44
control/service.go Normal file
View File

@ -0,0 +1,44 @@
package control
import (
"encoding/json"
"github.com/gin-gonic/gin"
"kumoly.io/kumoly/app/auth"
"kumoly.io/kumoly/app/server"
"kumoly.io/kumoly/app/system"
"kumoly.io/kumoly/app/task"
)
type Service struct{}
func (srv Service) GetName() string { return "ctrl.Service" }
func (srv Service) GetDependencies() []string { return []string{"server.Service", "auth.Auth"} }
func (srv Service) IsService() bool { return true }
func (srv Service) Init() error { return nil }
func (srv Service) Main() error { return nil }
func (srv Service) Del() {}
func (srv Service) Health() error { return nil }
func (srv Service) Load() error {
ctlAPI := server.API.Group("ctrl")
ctlAPI.GET("prof", auth.ACAdmin(), func(c *gin.Context) {
server.OK(c, system.GetProfile())
})
ctlAPI.GET("config", auth.ACAdmin(), func(c *gin.Context) {
conf, err := system.ConfigShow("json")
if err != nil {
panic(err)
}
data := map[string]interface{}{}
if err := json.Unmarshal([]byte(conf), data); err != nil {
panic(err)
}
server.OK(c, data)
})
ctlAPI.GET("tasks", auth.ACAdmin(), func(c *gin.Context) {
server.OK(c, task.GetProfile())
})
return nil
}

View File

@ -1,21 +0,0 @@
package email
type App struct {
Name string
Link string
Logo string
Copyright string
}
type Body struct {
App App
Intros []string
Outros []string
Content string
Greeting string
Receiver string
Signature string
Sender string
}

View File

@ -13,6 +13,26 @@ func init() {
viper.SetDefault("email.password", "test")
}
type App struct {
Name string
Link string
Logo string
Copyright string
}
type Body struct {
App App
Intros []string
Outros []string
Content string
Greeting string
Receiver string
Signature string
Sender string
}
// host string, port int, username string, password string
var dial *gomail.Dialer

View File

@ -46,3 +46,7 @@ func (h *History) Grp(grp string) *History {
h.Group = grp
return h
}
func (h *History) Scp(sco string) *History {
h.Scope = sco
return h
}

View File

@ -3,6 +3,7 @@ package history
import (
"encoding/json"
"fmt"
"sync"
"time"
"github.com/rs/zerolog/log"
@ -25,14 +26,16 @@ type History struct {
Type string
Caller string
Trace string
BodyJson string
Name string
Message string
Body interface{} `gorm:"-"`
Issuer string
Group string
BodyJson string
// Group to identify auth, empty for admin
Group string
// Scope for users to narrow down view point
Scope string
}
func (h *History) BeforeCreate(tx *gorm.DB) (err error) {
@ -48,6 +51,7 @@ func (h *History) BeforeCreate(tx *gorm.DB) (err error) {
var Tunnel chan *History
var quit chan struct{}
var started chan struct{}
var wg sync.WaitGroup
func init() {
Tunnel = make(chan *History)
@ -56,19 +60,20 @@ func init() {
}
func Start(r Receiver) {
select {
case started <- struct{}{}:
default:
if len(started) == 1 {
panic(errors.New(500, "history reporter has already started!"))
}
started <- struct{}{}
go func() {
for {
select {
case h := <-Tunnel:
wg.Add(1)
if Interceptor != nil {
go Interceptor(h)
Interceptor(h)
}
r(h)
wg.Done()
case <-quit:
<-started
return
@ -79,9 +84,15 @@ func Start(r Receiver) {
func Stop() {
quit <- struct{}{}
wg.Wait()
}
func Send(h *History) {
if len(started) == 0 {
log.Warn().Str("mod", "history").
Interface("history", h).
Msg("history reporter has not started, report will be discarded")
}
if h.Type == "" {
h.Type = INFO
}
@ -95,7 +106,9 @@ 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")
log.Error().Str("mod", "history").
Interface("history", h).
Err(err).Msg("DBReceiver error")
}
}

View File

@ -4,11 +4,9 @@ import (
"github.com/rs/zerolog/log"
"github.com/spf13/viper"
"kumoly.io/kumoly/app/store"
"kumoly.io/kumoly/app/system"
)
type Service struct {
system.BaseService
}
func (srv Service) GetName() string { return "history.Service" }
@ -34,3 +32,6 @@ func (srv Service) Main() error {
func (srv Service) Del() {
Stop()
}
func (srv Service) Load() error { return nil }
func (srv Service) Health() error { return nil }

View File

@ -1,7 +1,10 @@
package main
package app
import (
"testing"
"kumoly.io/kumoly/app/auth"
"kumoly.io/kumoly/app/control"
"kumoly.io/kumoly/app/email"
"kumoly.io/kumoly/app/history"
"kumoly.io/kumoly/app/server"
@ -10,7 +13,7 @@ import (
"kumoly.io/kumoly/app/task"
)
func main() {
func TestMain(t *testing.T) {
store.Setup()
sys := system.New()
server := server.New("app")
@ -20,8 +23,11 @@ func main() {
sys.Inject(auth.Injector(server.API))
sys.Append(server, auth.New(server),
&task.Service{}, &history.Service{},
&email.Service{})
&task.Service{},
&history.Service{},
&email.Service{},
&control.Service{},
)
go sys.Start()
<-sys.Done()

2
run.sh
View File

@ -6,4 +6,4 @@ export APP_PROD=false
export APP_LOG_PRETTY=true
export APP_DB_TYPE=sqlite
export APP_DATA=work
go run cmd/test/main.go
go test

View File

@ -8,6 +8,7 @@ import (
"github.com/rs/zerolog"
"github.com/rs/zerolog/log"
"github.com/spf13/viper"
"kumoly.io/kumoly/app/history"
)
type SkipLogFunc func(c *gin.Context) bool
@ -23,6 +24,9 @@ type Service struct {
l zerolog.Logger
}
var Server *gin.Engine
var API *gin.RouterGroup
func New(name string) *Service {
if viper.GetBool("prod") {
gin.SetMode(gin.ReleaseMode)
@ -34,7 +38,9 @@ func New(name string) *Service {
Addr: fmt.Sprintf("%s:%s", viper.GetString("server.host"), viper.GetString("server.port")),
}
srv.Server.Use(srv.Default)
Server = srv.Server
srv.API = srv.Server.Group("/api")
API = srv.API
if ipnetstr := viper.GetString("server.allow"); ipnetstr != "" {
_, ipnet, err := net.ParseCIDR(ipnetstr)
if err != nil {
@ -56,6 +62,7 @@ func (srv *Service) Main() error {
go func() {
err := srv.Server.Run(srv.Addr)
if err != nil {
history.Send(history.Error().Nm("ServerStartError").Msg(err.Error()))
srv.l.Panic().Err(err).Msg("Server.Run error")
}
}()

View File

@ -10,6 +10,7 @@ import (
"github.com/rs/zerolog"
"github.com/rs/zerolog/log"
"github.com/spf13/viper"
"kumoly.io/kumoly/app/history"
)
var PROD = true
@ -98,7 +99,7 @@ func New() *System {
}
func (sys *System) Start() {
// Setup()
Setup()
sys.order()
sys.status = sys_init
go func() {
@ -125,11 +126,12 @@ func (sys *System) Start() {
sys.status = sys_main
sys.main()
sys.status = sys_wait
if !sys.isService {
sys.status = sys_wait
sys.quit <- syscall.SIGTERM
}
}()
history.Send(history.Info().Nm("SysUP").Msg("system started"))
<-sys.quit
isRestart := false
if sys.status == sys_restart {
@ -137,6 +139,7 @@ func (sys *System) Start() {
}
l.Info().Msg("Terminating...")
history.Send(history.Info().Nm("SysDown").Msg("system stoped"))
sys.status = sys_term
go func() {
time.Sleep(time.Second * time.Duration(viper.GetInt("system.terminate_timeout")))

View File

@ -37,7 +37,7 @@ type Profile struct {
func GetProfile() *Profile {
p := &Profile{
Name: "core/task",
Name: "task",
}
entries := c.Entries()
for i := 0; i < len(entries); i++ {