是否可以在运行时更新 zap 记录器的日志级别?

我创建了一个记录器kubebuilder,它基于 zap 记录器:


import (

    "flag"

    "github.com/gin-gonic/gin"

    "net/http"

    "os"

    "go.uber.org/zap/zapcore"

    uzap "go.uber.org/zap"

    // Import all Kubernetes client auth plugins (e.g. Azure, GCP, OIDC, etc.)

    // to ensure that exec-entrypoint and run can make use of them.

    _ "k8s.io/client-go/plugin/pkg/client/auth"


    "k8s.io/apimachinery/pkg/runtime"

    utilruntime "k8s.io/apimachinery/pkg/util/runtime"

    clientgoscheme "k8s.io/client-go/kubernetes/scheme"

    ctrl "sigs.k8s.io/controller-runtime"

    "sigs.k8s.io/controller-runtime/pkg/healthz"

    "sigs.k8s.io/controller-runtime/pkg/log/zap"


)


var (

    scheme   = runtime.NewScheme()

    setupLog = ctrl.Log.WithName("setup")

)


var zapOpts []uzap.Option

    zapOpts = append(zapOpts, uzap.AddCaller())

    zapOpts = append(zapOpts, uzap.AddCallerSkip(1))

    zapOpts = append(zapOpts, uzap.AddStacktrace(uzap.DebugLevel))


    opts := zap.Options{

        Development:     developmentFlag,

        StacktraceLevel: stacktraceLevel,

        Level:           level,

        Encoder:         encoder,

        ZapOpts:  zapOpts,

    }


    opts.BindFlags(flag.CommandLine)

    flag.Parse()


    ctrl.SetLogger(zap.New(zap.UseFlagOptions(&opts)))

现在我想将日志级别更改zapcore.InfoLevel为运行时。我没有找到任何SetLogLevel或类似的 API。


我是否需要创建新选项然后设置新级别?


我还需要用sigs.k8s.io/controller-runtime/pkg/log/zap库设置记录器。记录器的接口来自go-logr并实现logr.Logger接口。如果我尝试将其更改为,zapcore.NewCore我将无法再设置记录器ctrl.SetLogger。


我想保留更新所有选项zap.Options 并更改日志级别的选项,并且仍然使用来自sigs.k8s.io/controller-runtime/pkg/log/zap.


可以用 sigs.k8s.io/controller-runtime/pkg/log/zap and来做sigs.k8s.io/controller-runtime吗?


临摹微笑
浏览 132回答 2
2回答

神不在的星期二

更好的答案:正如@Oliver Dain 所建议的,使用zap.AtomicLevel. 有关详细信息,请参阅他们的答案。另一种选择是创建具有自定义LevelEnabler功能的核心。您可以使用zap.LevelEnablerFunc将闭包转换为zapcore.LevelEnabler.相关文档:LevelEnabler 决定在记录消息时是否启用给定的记录级别。LevelEnablerFunc 是使用匿名函数实现 zapcore.LevelEnabler 的便捷方式。然后该函数可能会返回true或false基于在运行时更改的其他一些变量:  // will be actually initialized and changed at run time     // based on your business logic    var infoEnabled bool     errorUnlessEnabled := zap.LevelEnablerFunc(func(level zapcore.Level) bool {        // true: log message at this level        // false: skip message at this level        return level >= zapcore.ErrorLevel || infoEnabled    })    core := zapcore.NewCore(        zapcore.NewJSONEncoder(zap.NewProductionEncoderConfig()),        os.Stdout,        errorUnlessEnabled,    )    logger := zap.New(core)    logger.Info("foo") // not logged        infoEnabled = true    logger.Info("foo again") // loggedPS:这段代码是人为的。您的程序必须在运行时实现初始化、值更改以及对infoEnabled变量进行适当的同步(如果需要)。您可以在操场上运行此示例:https: //play.golang.org/p/oT3nvnP1Bwc

Qyouu

是的,可以使用AtomicLevel. 从文档:atom := zap.NewAtomicLevel()// To keep the example deterministic, disable timestamps in the output.encoderCfg := zap.NewProductionEncoderConfig()encoderCfg.TimeKey = ""logger := zap.New(zapcore.NewCore(    zapcore.NewJSONEncoder(encoderCfg),    zapcore.Lock(os.Stdout),    atom,))defer logger.Sync()logger.Info("info logging enabled")atom.SetLevel(zap.ErrorLevel)logger.Info("info logging disabled")
打开App,查看更多内容
随时随地看视频慕课网APP

相关分类

Go