cmd/ctrld: unified logging

By using a separate console logging and use it in all places before
reading in logging config.
This commit is contained in:
Cuong Manh Le
2023-05-15 20:54:01 +07:00
committed by Cuong Manh Le
parent 270ea9f6ca
commit 440d085c6d
4 changed files with 122 additions and 85 deletions
+91 -59
View File
@@ -7,7 +7,6 @@ import (
"encoding/base64" "encoding/base64"
"errors" "errors"
"fmt" "fmt"
"log"
"net" "net"
"net/netip" "net/netip"
"os" "os"
@@ -75,6 +74,9 @@ var rootCmd = &cobra.Command{
Use: "ctrld", Use: "ctrld",
Short: strings.TrimLeft(rootShortDesc, "\n"), Short: strings.TrimLeft(rootShortDesc, "\n"),
Version: curVersion(), Version: curVersion(),
PreRun: func(cmd *cobra.Command, args []string) {
initConsoleLogging()
},
} }
func curVersion() string { func curVersion() string {
@@ -106,9 +108,12 @@ func initCLI() {
Use: "run", Use: "run",
Short: "Run the DNS proxy server", Short: "Run the DNS proxy server",
Args: cobra.NoArgs, Args: cobra.NoArgs,
PreRun: func(cmd *cobra.Command, args []string) {
initConsoleLogging()
},
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
if daemon && runtime.GOOS == "windows" { if daemon && runtime.GOOS == "windows" {
log.Fatal("Cannot run in daemon mode. Please install a Windows service.") mainLog.Fatal().Msg("Cannot run in daemon mode. Please install a Windows service.")
} }
waitCh := make(chan struct{}) waitCh := make(chan struct{})
@@ -152,7 +157,7 @@ func initCLI() {
dir, err := userHomeDir() dir, err := userHomeDir()
if err != nil { if err != nil {
log.Fatalf("failed to get config dir: %v", err) mainLog.Fatal().Msgf("failed to get config dir: %v", err)
} }
for _, config := range configs { for _, config := range configs {
ctrld.SetConfigNameWithPath(v, config.name, dir) ctrld.SetConfigNameWithPath(v, config.name, dir)
@@ -165,16 +170,16 @@ func initCLI() {
readBase64Config(configBase64) readBase64Config(configBase64)
processNoConfigFlags(noConfigStart) processNoConfigFlags(noConfigStart)
if err := v.Unmarshal(&cfg); err != nil { if err := v.Unmarshal(&cfg); err != nil {
log.Fatalf("failed to unmarshal config: %v", err) mainLog.Fatal().Msgf("failed to unmarshal config: %v", err)
} }
log.Printf("starting ctrld %s\n", curVersion()) mainLog.Info().Msgf("starting ctrld %s", curVersion())
oi := osinfo.New() oi := osinfo.New()
log.Printf("os: %s\n", oi.String()) mainLog.Info().Msgf("os: %s", oi.String())
// Wait for network up. // Wait for network up.
if !ctrldnet.Up() { if !ctrldnet.Up() {
log.Fatal("network is not up yet") mainLog.Fatal().Msg("network is not up yet")
} }
processLogAndCacheFlags() processLogAndCacheFlags()
// Log config do not have thing to validate, so it's safe to init log here, // Log config do not have thing to validate, so it's safe to init log here,
@@ -182,7 +187,7 @@ func initCLI() {
initLogging() initLogging()
processCDFlags() processCDFlags()
if err := ctrld.ValidateConfig(validator.New(), &cfg); err != nil { if err := ctrld.ValidateConfig(validator.New(), &cfg); err != nil {
log.Fatalf("invalid config: %v", err) mainLog.Fatal().Msgf("invalid config: %v", err)
} }
initCache() initCache()
@@ -250,10 +255,13 @@ func initCLI() {
rootCmd.AddCommand(runCmd) rootCmd.AddCommand(runCmd)
startCmd := &cobra.Command{ startCmd := &cobra.Command{
PreRun: checkHasElevatedPrivilege, PreRun: func(cmd *cobra.Command, args []string) {
Use: "start", initConsoleLogging()
Short: "Install and start the ctrld service", checkHasElevatedPrivilege()
Args: cobra.NoArgs, },
Use: "start",
Short: "Install and start the ctrld service",
Args: cobra.NoArgs,
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
sc := &service.Config{} sc := &service.Config{}
*sc = *svcConfig *sc = *svcConfig
@@ -264,7 +272,7 @@ func initCLI() {
setDependencies(sc) setDependencies(sc)
sc.Arguments = append([]string{"run"}, osArgs...) sc.Arguments = append([]string{"run"}, osArgs...)
if err := router.ConfigureService(sc); err != nil { if err := router.ConfigureService(sc); err != nil {
log.Fatal(err) mainLog.Fatal().Err(err).Msg("failed to configure service on router")
} }
// No config path, generating config in HOME directory. // No config path, generating config in HOME directory.
@@ -284,7 +292,7 @@ func initCLI() {
readConfigFile(writeDefaultConfig && cdUID == "") readConfigFile(writeDefaultConfig && cdUID == "")
if err := v.Unmarshal(&cfg); err != nil { if err := v.Unmarshal(&cfg); err != nil {
log.Fatalf("failed to unmarshal config: %v", err) mainLog.Fatal().Msgf("failed to unmarshal config: %v", err)
} }
logPath := cfg.Service.LogPath logPath := cfg.Service.LogPath
@@ -304,7 +312,7 @@ func initCLI() {
prog := &prog{} prog := &prog{}
s, err := service.New(prog, sc) s, err := service.New(prog, sc)
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
return return
} }
tasks := []task{ tasks := []task{
@@ -327,7 +335,7 @@ func initCLI() {
status = selfCheckStatus(status) status = selfCheckStatus(status)
switch status { switch status {
case service.StatusRunning: case service.StatusRunning:
mainLog.Info().Msg("Service started") mainLog.Warn().Msg("Service started")
default: default:
mainLog.Error().Msg("Service did not start, please check system/service log for details error") mainLog.Error().Msg("Service did not start, please check system/service log for details error")
if runtime.GOOS == "linux" { if runtime.GOOS == "linux" {
@@ -354,40 +362,46 @@ func initCLI() {
_ = startCmd.Flags().MarkHidden("router") _ = startCmd.Flags().MarkHidden("router")
stopCmd := &cobra.Command{ stopCmd := &cobra.Command{
PreRun: checkHasElevatedPrivilege, PreRun: func(cmd *cobra.Command, args []string) {
Use: "stop", initConsoleLogging()
Short: "Stop the ctrld service", checkHasElevatedPrivilege()
Args: cobra.NoArgs, },
Use: "stop",
Short: "Stop the ctrld service",
Args: cobra.NoArgs,
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
prog := &prog{} prog := &prog{}
s, err := service.New(prog, svcConfig) s, err := service.New(prog, svcConfig)
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
return return
} }
initLogging() initLogging()
if doTasks([]task{{s.Stop, true}}) { if doTasks([]task{{s.Stop, true}}) {
prog.resetDNS() prog.resetDNS()
mainLog.Info().Msg("Service stopped") mainLog.Warn().Msg("Service stopped")
} }
}, },
} }
stopCmd.Flags().StringVarP(&iface, "iface", "", "", `Reset DNS setting for iface, "auto" means the default interface gateway`) stopCmd.Flags().StringVarP(&iface, "iface", "", "", `Reset DNS setting for iface, "auto" means the default interface gateway`)
restartCmd := &cobra.Command{ restartCmd := &cobra.Command{
PreRun: checkHasElevatedPrivilege, PreRun: func(cmd *cobra.Command, args []string) {
Use: "restart", initConsoleLogging()
Short: "Restart the ctrld service", checkHasElevatedPrivilege()
Args: cobra.NoArgs, },
Use: "restart",
Short: "Restart the ctrld service",
Args: cobra.NoArgs,
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
s, err := service.New(&prog{}, svcConfig) s, err := service.New(&prog{}, svcConfig)
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
return return
} }
initLogging() initLogging()
if doTasks([]task{{s.Restart, true}}) { if doTasks([]task{{s.Restart, true}}) {
stdoutMsg("Service restarted") mainLog.Warn().Msg("Service restarted")
} }
}, },
} }
@@ -396,39 +410,48 @@ func initCLI() {
Use: "status", Use: "status",
Short: "Show status of the ctrld service", Short: "Show status of the ctrld service",
Args: cobra.NoArgs, Args: cobra.NoArgs,
PreRun: func(cmd *cobra.Command, args []string) {
initConsoleLogging()
},
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
s, err := service.New(&prog{}, svcConfig) s, err := service.New(&prog{}, svcConfig)
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
return return
} }
status, err := serviceStatus(s) status, err := serviceStatus(s)
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
os.Exit(1) os.Exit(1)
} }
switch status { switch status {
case service.StatusUnknown: case service.StatusUnknown:
stdoutMsg("Unknown status") mainLog.Warn().Msg("Unknown status")
os.Exit(2) os.Exit(2)
case service.StatusRunning: case service.StatusRunning:
stdoutMsg("Service is running") mainLog.Warn().Msg("Service is running")
os.Exit(0) os.Exit(0)
case service.StatusStopped: case service.StatusStopped:
stdoutMsg("Service is stopped") mainLog.Warn().Msg("Service is stopped")
os.Exit(1) os.Exit(1)
} }
}, },
} }
if runtime.GOOS == "darwin" { if runtime.GOOS == "darwin" {
// On darwin, running status command without privileges may return wrong information. // On darwin, running status command without privileges may return wrong information.
statusCmd.PreRun = checkHasElevatedPrivilege statusCmd.PreRun = func(cmd *cobra.Command, args []string) {
initConsoleLogging()
checkHasElevatedPrivilege()
}
} }
uninstallCmd := &cobra.Command{ uninstallCmd := &cobra.Command{
PreRun: checkHasElevatedPrivilege, PreRun: func(cmd *cobra.Command, args []string) {
Use: "uninstall", initConsoleLogging()
Short: "Stop and uninstall the ctrld service", checkHasElevatedPrivilege()
},
Use: "uninstall",
Short: "Stop and uninstall the ctrld service",
Long: `Stop and uninstall the ctrld service. Long: `Stop and uninstall the ctrld service.
NOTE: Uninstalling will set DNS to values provided by DHCP.`, NOTE: Uninstalling will set DNS to values provided by DHCP.`,
@@ -437,7 +460,7 @@ NOTE: Uninstalling will set DNS to values provided by DHCP.`,
prog := &prog{} prog := &prog{}
s, err := service.New(prog, svcConfig) s, err := service.New(prog, svcConfig)
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
return return
} }
tasks := []task{ tasks := []task{
@@ -454,7 +477,7 @@ NOTE: Uninstalling will set DNS to values provided by DHCP.`,
if err := router.Cleanup(); err != nil { if err := router.Cleanup(); err != nil {
mainLog.Warn().Err(err).Msg("could not cleanup router") mainLog.Warn().Err(err).Msg("could not cleanup router")
} }
mainLog.Info().Msg("Service uninstalled") mainLog.Warn().Msg("Service uninstalled")
return return
} }
}, },
@@ -465,6 +488,9 @@ NOTE: Uninstalling will set DNS to values provided by DHCP.`,
Use: "list", Use: "list",
Short: "List network interfaces of the host", Short: "List network interfaces of the host",
Args: cobra.NoArgs, Args: cobra.NoArgs,
PreRun: func(cmd *cobra.Command, args []string) {
initConsoleLogging()
},
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
err := interfaces.ForeachInterface(func(i interfaces.Interface, prefixes []netip.Prefix) { err := interfaces.ForeachInterface(func(i interfaces.Interface, prefixes []netip.Prefix) {
fmt.Printf("Index : %d\n", i.Index) fmt.Printf("Index : %d\n", i.Index)
@@ -487,7 +513,7 @@ NOTE: Uninstalling will set DNS to values provided by DHCP.`,
println() println()
}) })
if err != nil { if err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
} }
}, },
} }
@@ -522,9 +548,12 @@ NOTE: Uninstalling will set DNS to values provided by DHCP.`,
serviceCmd.AddCommand(interfacesCmd) serviceCmd.AddCommand(interfacesCmd)
rootCmd.AddCommand(serviceCmd) rootCmd.AddCommand(serviceCmd)
startCmdAlias := &cobra.Command{ startCmdAlias := &cobra.Command{
PreRun: checkHasElevatedPrivilege, PreRun: func(cmd *cobra.Command, args []string) {
Use: "start", initConsoleLogging()
Short: "Quick start service and configure DNS on interface", checkHasElevatedPrivilege()
},
Use: "start",
Short: "Quick start service and configure DNS on interface",
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
if !cmd.Flags().Changed("iface") { if !cmd.Flags().Changed("iface") {
os.Args = append(os.Args, "--iface="+ifaceStartStop) os.Args = append(os.Args, "--iface="+ifaceStartStop)
@@ -537,9 +566,12 @@ NOTE: Uninstalling will set DNS to values provided by DHCP.`,
startCmdAlias.Flags().AddFlagSet(startCmd.Flags()) startCmdAlias.Flags().AddFlagSet(startCmd.Flags())
rootCmd.AddCommand(startCmdAlias) rootCmd.AddCommand(startCmdAlias)
stopCmdAlias := &cobra.Command{ stopCmdAlias := &cobra.Command{
PreRun: checkHasElevatedPrivilege, PreRun: func(cmd *cobra.Command, args []string) {
Use: "stop", initConsoleLogging()
Short: "Quick stop service and remove DNS from interface", checkHasElevatedPrivilege()
},
Use: "stop",
Short: "Quick stop service and remove DNS from interface",
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
if !cmd.Flags().Changed("iface") { if !cmd.Flags().Changed("iface") {
os.Args = append(os.Args, "--iface="+ifaceStartStop) os.Args = append(os.Args, "--iface="+ifaceStartStop)
@@ -583,7 +615,7 @@ func readConfigFile(writeDefaultConfig bool) bool {
// If err == nil, there's a config supplied via `--config`, no default config written. // If err == nil, there's a config supplied via `--config`, no default config written.
err := v.ReadInConfig() err := v.ReadInConfig()
if err == nil { if err == nil {
log.Println("loading config file from:", v.ConfigFileUsed()) mainLog.Info().Msg("loading config file from: " + v.ConfigFileUsed())
defaultConfigFile = v.ConfigFileUsed() defaultConfigFile = v.ConfigFileUsed()
return true return true
} }
@@ -595,22 +627,22 @@ func readConfigFile(writeDefaultConfig bool) bool {
// If error is viper.ConfigFileNotFoundError, write default config. // If error is viper.ConfigFileNotFoundError, write default config.
if _, ok := err.(viper.ConfigFileNotFoundError); ok { if _, ok := err.(viper.ConfigFileNotFoundError); ok {
if err := v.Unmarshal(&cfg); err != nil { if err := v.Unmarshal(&cfg); err != nil {
log.Fatalf("failed to unmarshal default config: %v", err) mainLog.Fatal().Msgf("failed to unmarshal default config: %v", err)
} }
if err := writeConfigFile(); err != nil { if err := writeConfigFile(); err != nil {
log.Fatalf("failed to write default config file: %v", err) mainLog.Fatal().Msgf("failed to write default config file: %v", err)
} else { } else {
fp, err := filepath.Abs(defaultConfigFile) fp, err := filepath.Abs(defaultConfigFile)
if err != nil { if err != nil {
log.Fatalf("failed to get default config file path: %v", err) mainLog.Fatal().Msgf("failed to get default config file path: %v", err)
} }
log.Println("writing default config file to: " + fp) mainLog.Info().Msg("writing default config file to: " + fp)
} }
defaultConfigWritten = true defaultConfigWritten = true
return false return false
} }
// Otherwise, report fatal error and exit. // Otherwise, report fatal error and exit.
log.Fatalf("failed to decode config file: %v", err) mainLog.Fatal().Msgf("failed to decode config file: %v", err)
return false return false
} }
@@ -620,10 +652,10 @@ func readBase64Config(configBase64 string) {
} }
configStr, err := base64.StdEncoding.DecodeString(configBase64) configStr, err := base64.StdEncoding.DecodeString(configBase64)
if err != nil { if err != nil {
log.Fatalf("invalid base64 config: %v", err) mainLog.Fatal().Msgf("invalid base64 config: %v", err)
} }
if err := v.ReadConfig(bytes.NewReader(configStr)); err != nil { if err := v.ReadConfig(bytes.NewReader(configStr)); err != nil {
log.Fatalf("failed to read base64 config: %v", err) mainLog.Fatal().Msgf("failed to read base64 config: %v", err)
} }
} }
@@ -632,7 +664,7 @@ func processNoConfigFlags(noConfigStart bool) {
return return
} }
if listenAddress == "" || primaryUpstream == "" { if listenAddress == "" || primaryUpstream == "" {
log.Fatal(`"listen" and "primary_upstream" flags must be set in no config mode`) mainLog.Fatal().Msg(`"listen" and "primary_upstream" flags must be set in no config mode`)
} }
processListenFlag() processListenFlag()
@@ -713,7 +745,7 @@ func processCDFlags() {
logger.Info().Msg("using defined custom config of Control-D resolver") logger.Info().Msg("using defined custom config of Control-D resolver")
readBase64Config(resolverConfig.Ctrld.CustomConfig) readBase64Config(resolverConfig.Ctrld.CustomConfig)
if err := v.Unmarshal(&cfg); err != nil { if err := v.Unmarshal(&cfg); err != nil {
log.Fatalf("failed to unmarshal config: %v", err) mainLog.Fatal().Msgf("failed to unmarshal config: %v", err)
} }
} else { } else {
cfg = ctrld.Config{} cfg = ctrld.Config{}
@@ -757,11 +789,11 @@ func processListenFlag() {
} }
host, portStr, err := net.SplitHostPort(listenAddress) host, portStr, err := net.SplitHostPort(listenAddress)
if err != nil { if err != nil {
log.Fatalf("invalid listener address: %v", err) mainLog.Fatal().Msgf("invalid listener address: %v", err)
} }
port, err := strconv.Atoi(portStr) port, err := strconv.Atoi(portStr)
if err != nil { if err != nil {
log.Fatalf("invalid port number: %v", err) mainLog.Fatal().Msgf("invalid port number: %v", err)
} }
lc := &ctrld.ListenerConfig{ lc := &ctrld.ListenerConfig{
IP: host, IP: host,
@@ -828,7 +860,7 @@ func selfCheckStatus(status service.Status) service.Status {
mu.Lock() mu.Lock()
defer mu.Unlock() defer mu.Unlock()
if err := v.UnmarshalKey("listener", &lcChanged); err != nil { if err := v.UnmarshalKey("listener", &lcChanged); err != nil {
log.Printf("failed to unmarshal listener config: %v", err) mainLog.Error().Msgf("failed to unmarshal listener config: %v", err)
return return
} }
}) })
+5 -3
View File
@@ -1,7 +1,6 @@
package main package main
import ( import (
"log"
"os" "os"
"os/exec" "os/exec"
"strings" "strings"
@@ -27,6 +26,9 @@ func initRouterCLI() {
routerCmd := &cobra.Command{ routerCmd := &cobra.Command{
Use: "setup", Use: "setup",
Short: b.String(), Short: b.String(),
PreRun: func(cmd *cobra.Command, args []string) {
initConsoleLogging()
},
Run: func(cmd *cobra.Command, args []string) { Run: func(cmd *cobra.Command, args []string) {
if len(args) == 0 { if len(args) == 0 {
_ = cmd.Help() _ = cmd.Help()
@@ -47,7 +49,7 @@ func initRouterCLI() {
} }
exe, err := os.Executable() exe, err := os.Executable()
if err != nil { if err != nil {
log.Fatal(err) mainLog.Fatal().Msgf("could not find executable path: %v", err)
os.Exit(1) os.Exit(1)
} }
@@ -59,7 +61,7 @@ func initRouterCLI() {
command.Stderr = os.Stderr command.Stderr = os.Stderr
command.Stdin = os.Stdin command.Stdin = os.Stdin
if err := command.Run(); err != nil { if err := command.Run(); err != nil {
log.Fatal(err) mainLog.Fatal().Msg(err.Error())
} }
}, },
} }
+22 -9
View File
@@ -2,7 +2,6 @@ package main
import ( import (
"io" "io"
"log"
"os" "os"
"path/filepath" "path/filepath"
"time" "time"
@@ -31,7 +30,8 @@ var (
ifaceStartStop string ifaceStartStop string
setupRouter bool setupRouter bool
mainLog = zerolog.New(io.Discard) mainLog = zerolog.New(io.Discard)
consoleWriter zerolog.ConsoleWriter
) )
func main() { func main() {
@@ -39,7 +39,7 @@ func main() {
initCLI() initCLI()
initRouterCLI() initRouterCLI()
if err := rootCmd.Execute(); err != nil { if err := rootCmd.Execute(); err != nil {
stderrMsg(err.Error()) mainLog.Error().Msg(err.Error())
os.Exit(1) os.Exit(1)
} }
} }
@@ -58,28 +58,41 @@ func normalizeLogFilePath(logFilePath string) string {
return filepath.Join(dir, logFilePath) return filepath.Join(dir, logFilePath)
} }
func initConsoleLogging() {
consoleWriter = zerolog.NewConsoleWriter(func(w *zerolog.ConsoleWriter) {
w.TimeFormat = time.StampMilli
})
multi := zerolog.MultiLevelWriter(consoleWriter)
mainLog = mainLog.Output(multi).With().Timestamp().Logger()
switch {
case verbose == 1:
zerolog.SetGlobalLevel(zerolog.InfoLevel)
case verbose > 1:
zerolog.SetGlobalLevel(zerolog.DebugLevel)
default:
zerolog.SetGlobalLevel(zerolog.WarnLevel)
}
}
func initLogging() { func initLogging() {
writers := []io.Writer{io.Discard} writers := []io.Writer{io.Discard}
if logFilePath := normalizeLogFilePath(cfg.Service.LogPath); logFilePath != "" { if logFilePath := normalizeLogFilePath(cfg.Service.LogPath); logFilePath != "" {
// Create parent directory if necessary. // Create parent directory if necessary.
if err := os.MkdirAll(filepath.Dir(logFilePath), 0750); err != nil { if err := os.MkdirAll(filepath.Dir(logFilePath), 0750); err != nil {
log.Printf("failed to create log path: %v", err) mainLog.Error().Msgf("failed to create log path: %v", err)
os.Exit(1) os.Exit(1)
} }
// Backup old log file with .1 suffix. // Backup old log file with .1 suffix.
if err := os.Rename(logFilePath, logFilePath+".1"); err != nil && !os.IsNotExist(err) { if err := os.Rename(logFilePath, logFilePath+".1"); err != nil && !os.IsNotExist(err) {
log.Printf("could not backup old log file: %v", err) mainLog.Error().Msgf("could not backup old log file: %v", err)
} }
logFile, err := os.OpenFile(logFilePath, os.O_CREATE|os.O_RDWR, os.FileMode(0o600)) logFile, err := os.OpenFile(logFilePath, os.O_CREATE|os.O_RDWR, os.FileMode(0o600))
if err != nil { if err != nil {
log.Printf("failed to create log file: %v", err) mainLog.Error().Msgf("failed to create log file: %v", err)
os.Exit(1) os.Exit(1)
} }
writers = append(writers, logFile) writers = append(writers, logFile)
} }
consoleWriter := zerolog.NewConsoleWriter(func(w *zerolog.ConsoleWriter) {
w.TimeFormat = time.StampMilli
})
writers = append(writers, consoleWriter) writers = append(writers, consoleWriter)
multi := zerolog.MultiLevelWriter(writers...) multi := zerolog.MultiLevelWriter(writers...)
mainLog = mainLog.Output(multi).With().Timestamp().Logger() mainLog = mainLog.Output(multi).With().Timestamp().Logger()
+4 -14
View File
@@ -3,22 +3,12 @@ package main
import ( import (
"bytes" "bytes"
"errors" "errors"
"fmt"
"os" "os"
"os/exec" "os/exec"
"github.com/kardianos/service" "github.com/kardianos/service"
"github.com/spf13/cobra"
) )
func stderrMsg(msg string) {
_, _ = fmt.Fprintln(os.Stderr, msg)
}
func stdoutMsg(msg string) {
_, _ = fmt.Fprintln(os.Stdout, msg)
}
type task struct { type task struct {
f func() error f func() error
abortOnError bool abortOnError bool
@@ -29,7 +19,7 @@ func doTasks(tasks []task) bool {
for _, task := range tasks { for _, task := range tasks {
if err := task.f(); err != nil { if err := task.f(); err != nil {
if task.abortOnError { if task.abortOnError {
stderrMsg(errors.Join(prevErr, err).Error()) mainLog.Error().Msg(errors.Join(prevErr, err).Error())
return false return false
} }
prevErr = err prevErr = err
@@ -38,14 +28,14 @@ func doTasks(tasks []task) bool {
return true return true
} }
func checkHasElevatedPrivilege(cmd *cobra.Command, args []string) { func checkHasElevatedPrivilege() {
ok, err := hasElevatedPrivilege() ok, err := hasElevatedPrivilege()
if err != nil { if err != nil {
fmt.Printf("could not detect user privilege: %v", err) mainLog.Error().Msgf("could not detect user privilege: %v", err)
return return
} }
if !ok { if !ok {
fmt.Println("Please relaunch process with admin/root privilege.") mainLog.Error().Msg("Please relaunch process with admin/root privilege.")
os.Exit(1) os.Exit(1)
} }
} }