使用命令
在本地运行Web应用程序时go run MainPackageFile.go
我们可以映射记录器,例如马提尼
m := martini.Classic()
m.Get("/m", func() string {
return "Hello world!"
})
m.Map(log.New(f, "[martini]", log.LstdFlags))
然而,如果代码外面有什么问题,例如Go无法下载软件包等,那么有什么方法可以获得那些运行时日志?
当本地运行时,错误将打印到控制台上。有没有办法在服务器上运行时,我们可以将所有这些日志写入文本文件?
答案 0 :(得分:2)
假设您的代码使用日志库在任何地方报告错误,您可以更改默认记录器写入的文件,而不是定义您自己的日志对象并传递它。这是通过日志库的SetOutput()函数完成的。
这样,以下代码只会写入您的日志文件而不是标准错误:
// Call this when your program starts and pass it the file handle for your
// log file.
func SetupErrorLog(logFile io.Writer) {
log.SetOutput(logFile)
}
...
func DoSomething() {
...
if err != nil {
// prints to your log file and exits
log.Fatalln("A fatal error has occurred:", err)
}
}
如果您没有统一使用日志库并且想要捕获所有输出(如恐慌),则接受的答案有效。但是,当您调用程序时,我更喜欢使用像logger这样的工具来简化代码的更简单的方法:
go run MainPackageFile.go 2>&1 | logger
这会将您的所有程序输出发送到syslog,而不必弄乱您的代码。 logger命令有许多选项可用于自定义日志记录行为,包括选择自己的日志文件的功能。有关详细信息,请阅读logger man page。
logger命令在Unix系统(包括Mac)上可用。 Windows解决方案可能会有所不同。
答案 1 :(得分:1)
您可以使用此功能将标准错误重定向到文件。这将收到追溯。
// redirectStderr to the file passed in
func redirectStderr(f *os.File) {
err := syscall.Dup2(int(f.Fd()), int(os.Stderr.Fd()))
if err != nil {
log.Fatalf("Failed to redirect stderr to file: %v", err)
}
}
它仅适用于linux / mac / unix。
以下是如何为Windows做同样的事情
var (
kernel32 = syscall.MustLoadDLL("kernel32.dll")
procSetStdHandle = kernel32.MustFindProc("SetStdHandle")
)
func setStdHandle(stdhandle int32, handle syscall.Handle) error {
r0, _, e1 := syscall.Syscall(procSetStdHandle.Addr(), 2, uintptr(stdhandle), uintptr(handle), 0)
if r0 == 0 {
if e1 != 0 {
return error(e1)
}
return syscall.EINVAL
}
return nil
}
// redirectStderr to the file passed in
func redirectStderr(f *os.File) {
err := setStdHandle(syscall.STD_ERROR_HANDLE, syscall.Handle(f.Fd()))
if err != nil {
log.Fatalf("Failed to redirect stderr to file: %v", err)
}
}