Go版本
go版本 go1.21.0 darwin/arm64
go env
在你的模块/工作区中的输出:
GO111MODULE=''
GOARCH='arm64'
GOBIN=''
GOCACHE='/Users/s.hajyahya/Library/Caches/go-build'
GOENV='/Users/s.hajyahya/Library/Application Support/go/env'
GOEXE=''
GOEXPERIMENT=''
GOFLAGS=''
GOHOSTARCH='arm64'
GOHOSTOS='darwin'
GOINSECURE=''
GOMODCACHE='/Users/s.hajyahya/go/pkg/mod'
GONOPROXY=''
GONOSUMDB=''
GOOS='darwin'
GOPATH='/Users/s.hajyahya/go'
GOPRIVATE=''
GOPROXY='https://proxy.golang.org,direct'
GOROOT='/usr/local/go'
GOSUMDB='sum.golang.org'
GOTMPDIR=''
GOTOOLCHAIN='auto'
GOTOOLDIR='/usr/local/go/pkg/tool/darwin_arm64'
GOVCS=''
GOVERSION='go1.21.0'
GCCGO='gccgo'
AR='ar'
CC='clang'
CXX='clang++'
CGO_ENABLED='1'
GOMOD='/Users/s.hajyahya/dev/stuff/ssh/go.mod'
GOWORK=''
CGO_CFLAGS='-O2 -g'
CGO_CPPFLAGS=''
CGO_CXXFLAGS='-O2 -g'
CGO_FFLAGS='-O2 -g'
CGO_LDFLAGS='-O2 -g'
PKG_CONFIG='pkg-config'
GOGCCFLAGS='-fPIC -arch arm64 -pthread -fno-caret-diagnostics -Qunused-arguments -fmessage-length=0 -ffile-prefix-map=/var/folders/_w/y7hb861d42z_drrgmkk7pb440000gp/T/go-build182075280=/tmp/go-build -gno-record-gcc-switches -fno-common'
你做了什么?
func TestXxx(t *testing.T) {
t.Error("log")
h := new(remoteHandler)
lg := slog.New(h)
lg.Info("example")
}
type remoteHandler struct {
}
func (h *remoteHandler) Enabled(_ context.Context, level slog.Level) bool {
return true
}
// WithAttrs returns a new [TextHandler] whose attributes consists
// of h's attributes followed by attrs.
func (h *remoteHandler) WithAttrs(attrs []slog.Attr) slog.Handler {
return nil
}
func (h *remoteHandler) WithGroup(name string) slog.Handler {
return nil
}
func (h *remoteHandler) Handle(_ context.Context, r slog.Record) error {
err := errors.New("any remote error")
fmt.Println(err)
return err
}
你看到了什么发生?
日志记录器忽略了处理程序的错误,并且有一个方法可以显式设置错误处理机制。
参见 https://github.com/golang/go/blob/master/src/log/slog/logger.go#L257
你期望看到什么?
Slog通过采用前端和后端设计引入了一种哲学,其中日志记录器作为前端,处理程序作为后端。然而,后端/处理程序可能需要将日志写入远程日志记录器,因此处理这些错误对于用户来说至关重要,以了解为什么某些日志没有被发送或记录,而不管处理程序在做什么。尽管默认情况下前端/日志记录器可以通过忽略这些错误来接受这些错误,但用户至少应该允许自己设置错误处理程序。
当使用stdlib log时,没有办法设置错误处理程序,但这是可以接受的,因为该日志包只采用了不同的设计。如果用户打算处理错误,他们可以将自定义错误处理程序 Package 到io writer中。然而,将slog处理程序 Package 并将其传递给slog被认为是过度使用,因为它与slog的设计和哲学不兼容。
查看其他包,如flag,它提供了像continue或panic这样的错误处理选项,以及httputil,其中代理允许通过显式设置函数来处理错误,这将有助于更新文档以澄清slog日志记录器忽略处理程序的错误(如果此信息尚未出现)。此外,向用户公开一个错误处理函数以便显式设置它也是有益的。
这可能需要从错误报告转换为提案,但在此将其移动到提案板之前在这里开始讨论可能会有所帮助。
func TestXxx(t *testing.T) {
t.Error("log")
h := new(remoteHandler)
lg := slog.New(h).WithErrorHandler(func(slog.Record, error){
// handle error.
})
lg.Info("example")
}
type remoteHandler struct {
}
func (h *remoteHandler) Enabled(_ context.Context, level slog.Level) bool {
return true
}
// WithAttrs returns a new [TextHandler] whose attributes consists
// of h's attributes followed by attrs.
func (h *remoteHandler) WithAttrs(attrs []slog.Attr) slog.Handler {
return nil
}
func (h *remoteHandler) WithGroup(name string) slog.Handler {
return nil
}
func (h *remoteHandler) Handle(_ context.Context, r slog.Record) error {
err := errors.New("any remote error")
fmt.Println(err)
return err
}
2条答案
按热度按时间lhcgjxsq1#
CC @jba
s71maibg2#
然而,将slog处理器进行 Package 并传递给slog被认为是过度设计,因为它与slog的设计和哲学不兼容。相反,一个报告错误的 Package 处理器正是我们所期望的。我们应该在文档中更好地解释这一点,也许可以提供一个示例。我认为一旦我们这样做了,编写这样一个处理器就会变得足够容易,我们不需要向包中添加任何API。