diff --git a/attribute/attribute.go b/attribute/attribute.go index 6700e6d..a6608d7 100644 --- a/attribute/attribute.go +++ b/attribute/attribute.go @@ -4,8 +4,8 @@ import ( "time" "github.com/rs/zerolog" - "github.com/rs/zerolog/log" "kumoly.io/kumoly/app/store" + "kumoly.io/kumoly/app/util" ) type Attribute struct { @@ -23,7 +23,7 @@ type Attribute struct { var l zerolog.Logger func Init() { - l = log.With().Str("mod", "attribute").Logger() + l = util.Klog.With().Str("mod", "attribute").Logger() l.Debug().Str("service", "attribute.Service"). Msg("Migrating database for attribute.Service ...") diff --git a/auth/api_auth.go b/auth/api_auth.go index 7df564f..b29b530 100644 --- a/auth/api_auth.go +++ b/auth/api_auth.go @@ -6,7 +6,6 @@ import ( "time" "github.com/gin-gonic/gin" - "github.com/rs/zerolog/log" "kumoly.io/kumoly/app/errors" "kumoly.io/kumoly/app/history" "kumoly.io/kumoly/app/server" @@ -27,7 +26,7 @@ func ApiLogin(c *gin.Context) { if err != nil { panic(err) } - // log.Trace().Str("mod", "auth"). + // l.Trace().Str("mod", "auth"). // Str("username", data.Name).Str("password", string(pwd)). // Msg("user login") usr := &User{} @@ -53,7 +52,7 @@ func ApiLogin(c *gin.Context) { } err = usr.ValidatePassword(string(pwd)) if err != nil { - log.Error().Str("mod", "auth").Err(err).Msg("wrong password") + l.Error().Str("mod", "auth").Err(err).Msg("wrong password") usr.LoginFailed += 1 DB.Model(&usr).Update("login_failed", usr.LoginFailed) panic(ErrorLoginFailed) @@ -62,7 +61,7 @@ func ApiLogin(c *gin.Context) { panic(ErrorUserIsSSO) } if !usr.Activated { - log.Error().Str("mod", "auth"). + l.Error().Str("mod", "auth"). Err(ErrorUserNotActivated). Str("user", usr.Username).Str("uid", usr.ID). Msg("not activated") diff --git a/auth/helper.go b/auth/helper.go index c0b620f..0a654e9 100644 --- a/auth/helper.go +++ b/auth/helper.go @@ -23,7 +23,7 @@ func (c *Claims) HasGroup(grps ...string) bool { } func (srv Service) SetDefaultGroups() error { - srv.Logger.Debug().Msg("Setup default groups") + l.Debug().Msg("Setup default groups") for _, g := range []string{SYSTEM, ADMIN, USER} { grp := &Group{} if err := DB.Where("name = ?", g).First(grp).Error; err != nil { @@ -31,7 +31,7 @@ func (srv Service) SetDefaultGroups() error { Name: g, }).Error if err != nil { - srv.Logger.Error().Err(err).Msg("create group error") + l.Error().Err(err).Msg("create group error") return err } } @@ -43,7 +43,7 @@ func (srv Service) SetDefaultAdmin(username, password string) error { admin := &Group{} err := DB.Where("name = ?", ADMIN).First(admin).Error if err != nil { - srv.Logger.Error().Err(err).Msg("SetDefaultAdmin") + l.Error().Err(err).Msg("SetDefaultAdmin") return err } usrgrp := struct { @@ -54,12 +54,12 @@ func (srv Service) SetDefaultAdmin(username, password string) error { Raw("select * from user_groups where group_id = ?", admin.ID). Scan(&usrgrp) if result.Error != nil { - srv.Logger.Error().Err(result.Error).Msg("SetDefaultAdmin") + l.Error().Err(result.Error).Msg("SetDefaultAdmin") return result.Error } usr := &User{} if result.RowsAffected == 0 { - srv.Logger.Debug().Msg("Setting up admin account") + l.Debug().Msg("Setting up admin account") pwd, _ := bcrypt.GenerateFromPassword([]byte(password), 14) usr.Username = username usr.Password = string(pwd) diff --git a/auth/jwt.go b/auth/jwt.go index b9ccaa4..4e6f79c 100644 --- a/auth/jwt.go +++ b/auth/jwt.go @@ -8,10 +8,11 @@ import ( "github.com/gin-gonic/gin" "github.com/golang-jwt/jwt" "github.com/rs/xid" - "github.com/rs/zerolog/log" + "github.com/rs/zerolog" "github.com/spf13/viper" "kumoly.io/kumoly/app/errors" "kumoly.io/kumoly/app/system" + "kumoly.io/kumoly/app/util" ) const GinClaimKey = "claim" @@ -37,7 +38,10 @@ type Auth struct { Secret string } +var l zerolog.Logger + func NewAuth() *Auth { + l = util.Klog.With().Str("mod", "auth").Logger() return &Auth{ CookieMode: true, CookieSecure: strings.HasPrefix(viper.GetString("server.url"), "https"), @@ -148,7 +152,7 @@ func (srv Auth) NewToken(claims Claims) (tok string, err error) { token := jwt.NewWithClaims(jwt.SigningMethodHS256, claims) tok, err = token.SignedString([]byte(srv.Secret)) if err != nil { - log.Error().Str("mod", "auth").Err(err).Msg("NewToken") + l.Error().Err(err).Msg("NewToken") } return } @@ -162,13 +166,13 @@ func (srv Auth) Middleware(c *gin.Context) { claims.ExpiresAt = time.Now().Unix() + srv.TokenExpire tok, err := srv.NewToken(*claims) if err != nil { - log.Debug().Str("mod", "auth").Err(err).Msg("Middleware") + l.Debug().Err(err).Msg("Middleware") } else { srv.SetToken(c, tok) } } } else { - log.Trace().Err(err).Msg("") + l.Trace().Err(err).Msg("") } } diff --git a/auth/service.go b/auth/service.go index bde9f4c..6446340 100644 --- a/auth/service.go +++ b/auth/service.go @@ -1,13 +1,12 @@ package auth import ( - "github.com/rs/zerolog" - "github.com/rs/zerolog/log" "github.com/spf13/viper" "gorm.io/gorm" "kumoly.io/kumoly/app/server" "kumoly.io/kumoly/app/store" "kumoly.io/kumoly/app/system" + "kumoly.io/kumoly/app/util" ) var DB *gorm.DB @@ -18,13 +17,10 @@ func SetDB(db *gorm.DB) { type Service struct { system.BaseService - Logger zerolog.Logger - - server *server.Service } -func New(s *server.Service) *Service { - return &Service{server: s} +func New() *Service { + return &Service{} } func (srv Service) GetName() string { return "auth.Service" } @@ -32,15 +28,14 @@ func (srv Service) GetDependencies() []string { return []string{"server.Service" func (srv Service) IsService() bool { return true } func (srv Service) Init() error { - srv.Logger = log.With().Str("mod", "auth").Str("service", "auth.Service").Logger() - - srv.Logger.Debug().Msg("Migrating database for auth.Service ...") + l = util.Klog.With().Str("mod", "auth").Logger() + l.Debug().Msg("Migrating database for auth.Service ...") if err := store.Migrate(&User{}, &Profile{}, &Group{}); err != nil { - srv.Logger.Error().Err(err).Msg("Migrating database") + l.Error().Err(err).Msg("Migrating database") return err } - srv.Logger.Debug().Msg("Checking db state") + l.Debug().Msg("Checking db state") // add default group if err := srv.SetDefaultGroups(); err != nil { @@ -59,10 +54,10 @@ func (srv Service) Init() error { } func (srv Service) Load() error { - srv.server.API.POST("/login", ApiLogin) - srv.server.API.POST("/logout", ApiLogout) - srv.server.API.GET("/whoami", ApiMe) - usrAPI := srv.server.API.Group("usr") + server.API.POST("/login", ApiLogin) + server.API.POST("/logout", ApiLogout) + server.API.GET("/whoami", ApiMe) + usrAPI := server.API.Group("usr") usrAPI.POST("/", ACAdmin(), ApiUserNew) usrAPI.GET("/", ACAdmin(), ApiUsers) usrAPI.DELETE("/:id", ACAdmin(), ApiUserDelete) @@ -70,7 +65,7 @@ func (srv Service) Load() error { usrAPI.PUT("/activate/:id", ACAdmin(), ApiUserActivate) usrAPI.PUT("/deactivate/:id", ACAdmin(), ApiUserDeactivate) - grpAPI := srv.server.API.Group("grp") + grpAPI := server.API.Group("grp") grpAPI.GET("/", ACAdmin(), ApiGrps) grpAPI.POST("/", ACAdmin(), ApiGrpNew) grpAPI.PUT("/", ApiGrpUpdate) diff --git a/auth/user.go b/auth/user.go index 37fed35..5a9cfda 100644 --- a/auth/user.go +++ b/auth/user.go @@ -4,7 +4,6 @@ import ( "time" "github.com/rs/xid" - "github.com/rs/zerolog/log" "golang.org/x/crypto/bcrypt" "gorm.io/gorm" ) @@ -63,7 +62,7 @@ func (usr *User) ChangePassword(db *gorm.DB, to string) (err error) { return tx.Model(usr).Update("password", string(bytes)).Error }) if err != nil { - log.Error().Str("mod", "auth").Err(err).Msg("ChangePassword") + l.Error().Err(err).Msg("ChangePassword") } return err } diff --git a/helper.go b/helper.go index 4534ba7..4b1bace 100644 --- a/helper.go +++ b/helper.go @@ -14,6 +14,7 @@ import ( ) func Default() *system.System { + system.Setup() store.Setup() sys := system.New() server := server.New(viper.GetString("name")) @@ -24,7 +25,7 @@ func Default() *system.System { auth.SetDB(store.DB) sys.Inject(auth.Injector(server.API)) - sys.Append(server, auth.New(server), + sys.Append(server, auth.New(), &task.Service{}, &history.Service{}, &email.Service{}, diff --git a/history/history.go b/history/history.go index d583992..e5faaf2 100644 --- a/history/history.go +++ b/history/history.go @@ -6,7 +6,6 @@ import ( "sync" "time" - "github.com/rs/zerolog/log" "gorm.io/gorm" "kumoly.io/kumoly/app/errors" "kumoly.io/kumoly/app/store" @@ -40,7 +39,7 @@ type History struct { func (h *History) BeforeCreate(tx *gorm.DB) (err error) { if h.Body != nil { if body, err := json.Marshal(h.Body); err != nil { - log.Error().Str("mod", "history").Err(err).Msg("history create error") + l.Error().Str("mod", "history").Err(err).Msg("history create error") } else { h.BodyJson = string(body) } @@ -87,14 +86,14 @@ func Stop() { return } quit <- struct{}{} - log.Debug().Str("mod", "history").Msg("stop received") + l.Debug().Str("mod", "history").Msg("stop received") wg.Wait() - log.Debug().Str("mod", "history").Msg("stopped") + l.Debug().Str("mod", "history").Msg("stopped") } func Send(h *History) { if len(started) == 0 { - log.Warn().Str("mod", "history"). + l.Warn().Str("mod", "history"). Interface("history", h). Msg("history reporter has not started, report will be discarded") } @@ -111,7 +110,7 @@ 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"). + l.Error().Str("mod", "history"). Interface("history", h). Err(err).Msg("DBReceiver error") } diff --git a/history/service.go b/history/service.go index 33afdf6..97997d6 100644 --- a/history/service.go +++ b/history/service.go @@ -1,21 +1,22 @@ package history import ( - "github.com/rs/zerolog/log" + "github.com/rs/zerolog" "kumoly.io/kumoly/app/store" + "kumoly.io/kumoly/app/util" ) type Service struct { } +var l zerolog.Logger + func (srv Service) GetName() string { return "history.Service" } func (srv Service) IsService() bool { return true } func (srv Service) GetDependencies() []string { return []string{"server.Service"} } func (srv Service) Init() error { - l := log.With().Str("mod", "history"). - Str("service", "history.Service"). - Logger() + l = util.Klog.With().Str("mod", "history").Logger() l.Debug().Msg("Migrating database for history.Service ...") if err := store.Migrate(&History{}); err != nil { l.Error().Err(err).Msg("Migrating database") diff --git a/server/middleware.go b/server/middleware.go index a8258bf..db89fe5 100644 --- a/server/middleware.go +++ b/server/middleware.go @@ -34,7 +34,7 @@ func (srv *Service) Default(c *gin.Context) { } if !util.PROD { cl.Caller(2) - cl.Str("trace", util.Stack()) + // cl.Str("trace", util.Stack()) } } else if c.Writer.Status() >= 400 { cl = srv.l.Error().Strs("error", c.Errors.Errors()) diff --git a/server/service.go b/server/service.go index d573fa6..5af21ae 100644 --- a/server/service.go +++ b/server/service.go @@ -6,9 +6,9 @@ import ( "github.com/gin-gonic/gin" "github.com/rs/zerolog" - "github.com/rs/zerolog/log" "github.com/spf13/viper" "kumoly.io/kumoly/app/history" + "kumoly.io/kumoly/app/util" ) type SkipLogFunc func(c *gin.Context) bool @@ -44,14 +44,14 @@ func New(name string) *Service { if ipnetstr := viper.GetString("server.allow"); ipnetstr != "" { _, ipnet, err := net.ParseCIDR(ipnetstr) if err != nil { - log.Panic().Str("service", "server.Service").Str("name", name).Err(err).Msg("ParseCIDR error") + util.Klog.Panic().Str("service", "server.Service").Str("name", name).Err(err).Msg("ParseCIDR error") } srv.Allow = ipnet } return srv } func (srv *Service) Init() error { - srv.l = log.With().Str("service", "server.Service").Str("name", srv.Name).Logger() + srv.l = util.Klog.With().Str("service", "server.Service").Str("name", srv.Name).Logger() return nil } func (srv *Service) Load() error { diff --git a/store/db.go b/store/db.go index 31cb054..65b4b5c 100644 --- a/store/db.go +++ b/store/db.go @@ -5,7 +5,7 @@ import ( "path/filepath" "time" - "github.com/rs/zerolog/log" + "github.com/rs/zerolog" "github.com/spf13/viper" "gorm.io/driver/mysql" "gorm.io/driver/postgres" @@ -57,13 +57,16 @@ func init() { viper.SetDefault("db.automigrate", true) } +var l zerolog.Logger + // Init initialize default db using New() followed by Connect() func Setup() { + l = util.Klog.With().Str("mod", "store").Logger() var err error std = New(DBTYPE(viper.GetString("db.type"))) DB, err = std.Connect() if err != nil { - log.Error().Str("mod", "store").Err(err).Msg("std connection error") + l.Error().Err(err).Msg("std connection error") panic(err) } } @@ -88,7 +91,7 @@ func New(t DBTYPE) *Store { s.Path = viper.GetString("data") } else { err := fmt.Errorf("unknown db type %s", t) - log.Error().Str("mod", "store").Err(err).Msg("unknown db type") + l.Error().Err(err).Msg("unknown db type") panic(err) } return s @@ -116,7 +119,7 @@ func (s *Store) Connect() (db *gorm.DB, err error) { } func (s *Store) postgresConnector() error { - log.Info().Str("mod", "store").Msg("Connecting to postgres...") + l.Info().Msg("Connecting to postgres...") dsn := fmt.Sprintf( "host=%v user=%v password=%v dbname=%v port=%v sslmode=disable TimeZone=Asia/Taipei", s.Host, s.User, s.Password, s.Name, s.Port, @@ -134,22 +137,22 @@ func (s *Store) postgresConnector() error { if inter <= 0 { inter = 5 } - log.Warn().Str("mod", "store").Err(err).Msg("Unable to connect to database") - log.Warn().Str("mod", "store").Msgf("Retrying in %v second.", inter) + l.Warn().Err(err).Msg("Unable to connect to database") + l.Warn().Msgf("Retrying in %v second.", inter) time.Sleep(time.Second * inter) } - log.Info().Str("mod", "store").Msg("Connection to postgres, ok.") + l.Info().Msg("Connection to postgres, ok.") return nil } //mysqlConnector connection func (s *Store) mysqlConnector() error { - log.Info().Str("mod", "store").Msg("Connecting to mysql...") + l.Info().Msg("Connecting to mysql...") dsn := fmt.Sprintf( "%v:%v@tcp(%v:%v)/%v?charset=utf8mb4&parseTime=True&loc=Local", s.User, s.Password, s.Host, s.Port, s.Name, ) - // log.Debug(dsn) + // l.Debug(dsn) for { db, err := gorm.Open(mysql.New(mysql.Config{ DSN: dsn, // data source name @@ -163,11 +166,11 @@ func (s *Store) mysqlConnector() error { if inter <= 0 { inter = 5 } - log.Warn().Str("mod", "store").Err(err).Msg("Unable to connect to database") - log.Warn().Str("mod", "store").Msgf("Retrying in %v second.", inter) + l.Warn().Err(err).Msg("Unable to connect to database") + l.Warn().Msgf("Retrying in %v second.", inter) time.Sleep(time.Second * inter) } - log.Info().Str("mod", "store").Msg("Connection to mysql, ok.") + l.Info().Msg("Connection to mysql, ok.") return nil } @@ -175,10 +178,10 @@ func (s *Store) mysqlConnector() error { func (s *Store) sqliteConnector() error { util.Mkdir(s.Path) dbPath := filepath.Join(s.Path, s.Name+".db") - log.Info().Str("mod", "store").Str("path", dbPath).Msg("Connecting to sqlite...") + l.Info().Str("path", dbPath).Msg("Connecting to sqlite...") db, err := gorm.Open(sqlite.Open(dbPath), s.config) if err != nil { - log.Error().Str("mod", "store").Err(err).Msg("failed to connect database") + l.Error().Err(err).Msg("failed to connect database") return err } s.DB = db @@ -187,7 +190,7 @@ func (s *Store) sqliteConnector() error { func (s *Store) Migrate(dst ...interface{}) error { if !s.AutoMigrate { - log.Debug().Str("mod", "store").Msg("AutoMigration is set to off, migration skipped") + l.Debug().Msg("AutoMigration is set to off, migration skipped") return nil } return s.DB.AutoMigrate(dst...) diff --git a/system/setup.go b/system/setup.go index d46de41..1111bde 100644 --- a/system/setup.go +++ b/system/setup.go @@ -10,7 +10,6 @@ import ( "github.com/fatih/color" "github.com/rs/zerolog" - "github.com/rs/zerolog/log" "github.com/spf13/viper" "kumoly.io/kumoly/app/util" ) @@ -44,19 +43,16 @@ func init() { viper.SetEnvKeyReplacer(replacer) viper.AutomaticEnv() viper.SetConfigType("json") - Setup() } -func Setup() { - zerolog.TimeFieldFormat = zerolog.TimeFormatUnix - zerolog.DurationFieldInteger = true - zerolog.SetGlobalLevel(zerolog.Level(viper.GetInt("log.level"))) - util.PROD = viper.GetBool("prod") +var setupped bool = false + +func SetupLogger(l zerolog.Logger, skip ...int) zerolog.Logger { if !util.PROD { - log.Logger = log.With().Caller().Logger() + l = l.With().Caller().Logger() } if viper.GetBool("log.pretty") { - log.Logger = log.Output(zerolog.ConsoleWriter{ + l = l.Output(zerolog.ConsoleWriter{ Out: os.Stdout, TimeFormat: "2006/01/02 15:04:05", FormatCaller: func(i interface{}) string { @@ -90,7 +86,23 @@ func Setup() { }, }) } - l = log.With().Str("mod", "system").Logger() + return l +} + +func Setup() { + if setupped { + return + } else { + setupped = true + } + zerolog.TimeFieldFormat = zerolog.TimeFormatUnix + zerolog.DurationFieldInteger = true + zerolog.SetGlobalLevel(zerolog.Level(viper.GetInt("log.level"))) + util.PROD = viper.GetBool("prod") + + util.Klog = SetupLogger(util.Klog) + + l = util.Klog.With().Str("mod", "system").Logger() tz, err := time.LoadLocation(viper.GetString("timezone")) if err == nil { diff --git a/task/task.go b/task/task.go index 9f4388c..ca4a286 100644 --- a/task/task.go +++ b/task/task.go @@ -6,7 +6,6 @@ import ( cron "github.com/robfig/cron/v3" "github.com/rs/zerolog" - "github.com/rs/zerolog/log" "kumoly.io/kumoly/app/util" ) @@ -19,7 +18,7 @@ func init() { } func Init() { - l = log.With().Str("mod", "task").Logger() + l = util.Klog.With().Str("mod", "task").Logger() c = cron.New( cron.WithLogger(&clog), cron.WithChain(func(j cron.Job) cron.Job { diff --git a/util/logging.go b/util/logging.go index 6d170f9..6bad037 100644 --- a/util/logging.go +++ b/util/logging.go @@ -5,8 +5,13 @@ import ( "fmt" "io/ioutil" "runtime" + + "github.com/rs/zerolog" + "github.com/rs/zerolog/log" ) +var Klog zerolog.Logger = log.Logger + func Stack() string { buf := make([]byte, 1024) for {