From 3d829ddf3b118c5de318f46062a7f3649b80c9cd Mon Sep 17 00:00:00 2001 From: Grant Rodgers Date: Wed, 8 Aug 2018 15:54:43 -0700 Subject: [PATCH] Update to latest controller-runtime Revision 60bb251. Improves logging and adds option to set resync period. --- Gopkg.lock | 11 ++--- .../github.com/go-logr/logr/testing/null.go | 32 ------------- .../github.com/go-logr/logr/testing/test.go | 39 --------------- .../controller-runtime/pkg/cache/cache.go | 2 +- .../pkg/client/config/config.go | 9 ++-- .../pkg/client/fake/client.go | 10 +++- .../pkg/internal/controller/controller.go | 2 +- .../controller-runtime/pkg/manager/manager.go | 11 ++++- .../pkg/runtime/log/deleg.go | 24 +++++++++- .../controller-runtime/pkg/runtime/log/log.go | 48 +++++++++++++++---- .../pkg/runtime/log/null.go | 44 +++++++++++++++++ 11 files changed, 133 insertions(+), 99 deletions(-) delete mode 100644 vendor/github.com/go-logr/logr/testing/null.go delete mode 100644 vendor/github.com/go-logr/logr/testing/test.go create mode 100644 vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/null.go diff --git a/Gopkg.lock b/Gopkg.lock index 5677e8cc498..6d415b16152 100644 --- a/Gopkg.lock +++ b/Gopkg.lock @@ -81,12 +81,9 @@ [[projects]] branch = "master" - digest = "1:b49dd34bdf52d28b69e41181bed939bdf48e1152ef54d21db643e3c50b3b33c0" + digest = "1:53becd66889185091b58ea3fc49294996f2179fb05a89702f4de7d15e581b509" name = "github.com/go-logr/logr" - packages = [ - ".", - "testing", - ] + packages = ["."] pruneopts = "NUT" revision = "9fb12b3b21c5415d16ac18dc5cd42c1cfdd40c4e" @@ -953,7 +950,7 @@ [[projects]] branch = "master" - digest = "1:0636bd706086f089dffeb6ea9a6e6a5079da1820943367949e4e477b7f94355c" + digest = "1:6021a2650ad6880e656ea296948bff84ec1f1df778a51fe416cee1ad6cf7a444" name = "sigs.k8s.io/controller-runtime" packages = [ "pkg/cache", @@ -978,7 +975,7 @@ "pkg/source/internal", ] pruneopts = "NUT" - revision = "f5b79b93f3aa7b978117f942f3cd67a91db12207" + revision = "60bb251ad86f9b313653618aad0c2c53f41a6625" [solve-meta] analyzer-name = "dep" diff --git a/vendor/github.com/go-logr/logr/testing/null.go b/vendor/github.com/go-logr/logr/testing/null.go deleted file mode 100644 index c69c3540b15..00000000000 --- a/vendor/github.com/go-logr/logr/testing/null.go +++ /dev/null @@ -1,32 +0,0 @@ -package testing - -import "github.com/go-logr/logr" - -// NullLogger is a logr.Logger that does nothing. -type NullLogger struct{} - -var _ logr.Logger = NullLogger{} - -func (_ NullLogger) Info(_ string, _ ...interface{}) { - // Do nothing. -} - -func (_ NullLogger) Enabled() bool { - return false -} - -func (_ NullLogger) Error(_ error, _ string, _ ...interface{}) { - // Do nothing. -} - -func (log NullLogger) V(_ int) logr.InfoLogger { - return log -} - -func (log NullLogger) WithName(_ string) logr.Logger { - return log -} - -func (log NullLogger) WithValues(_ ...interface{}) logr.Logger { - return log -} diff --git a/vendor/github.com/go-logr/logr/testing/test.go b/vendor/github.com/go-logr/logr/testing/test.go deleted file mode 100644 index af761fbdb9d..00000000000 --- a/vendor/github.com/go-logr/logr/testing/test.go +++ /dev/null @@ -1,39 +0,0 @@ -package testing - -import ( - "testing" - - "github.com/go-logr/logr" -) - -// TestLogger is a logr.Logger that prints through a testing.T object. -// Only error logs will have any effect. -type TestLogger struct { - T *testing.T -} - -var _ logr.Logger = TestLogger{} - -func (_ TestLogger) Info(_ string, _ ...interface{}) { - // Do nothing. -} - -func (_ TestLogger) Enabled() bool { - return false -} - -func (log TestLogger) Error(err error, msg string, args ...interface{}) { - log.T.Logf("%s: %v -- %v", msg, err, args) -} - -func (log TestLogger) V(v int) logr.InfoLogger { - return log -} - -func (log TestLogger) WithName(_ string) logr.Logger { - return log -} - -func (log TestLogger) WithValues(_ ...interface{}) logr.Logger { - return log -} diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/cache/cache.go b/vendor/sigs.k8s.io/controller-runtime/pkg/cache/cache.go index f43c6cb3b16..5435d271510 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/cache/cache.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/cache/cache.go @@ -77,7 +77,7 @@ type Options struct { // Mapper is the RESTMapper to use for mapping GroupVersionKinds to Resources Mapper meta.RESTMapper - // Resync is the resync period + // Resync is the resync period. Defaults to defaultResyncTime. Resync *time.Duration } diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/client/config/config.go b/vendor/sigs.k8s.io/controller-runtime/pkg/client/config/config.go index 01cc50f2a5f..849ba7af958 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/client/config/config.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/client/config/config.go @@ -19,17 +19,18 @@ package config import ( "flag" "fmt" - "log" "os" "os/user" "path/filepath" "k8s.io/client-go/rest" "k8s.io/client-go/tools/clientcmd" + logf "sigs.k8s.io/controller-runtime/pkg/runtime/log" ) var ( kubeconfig, masterURL string + log = logf.KBLog.WithName("client").WithName("config") ) func init() { @@ -62,7 +63,7 @@ func GetConfig() (*rest.Config, error) { } // If an env variable is specified with the config locaiton, use that if len(os.Getenv("KUBECONFIG")) > 0 { - return clientcmd.BuildConfigFromFlags(masterURL, kubeconfig) + return clientcmd.BuildConfigFromFlags(masterURL, os.Getenv("KUBECONFIG")) } // If no explicit location, try the in-cluster config if c, err := rest.InClusterConfig(); err == nil { @@ -83,11 +84,11 @@ func GetConfig() (*rest.Config, error) { // If --kubeconfig is set, will use the kubeconfig file at that location. Otherwise will assume running // in cluster and use the cluster provided kubeconfig. // -// Will log.Fatal if there is an error creating the rest.Config. +// Will log an error and exit if there is an error creating the rest.Config. func GetConfigOrDie() *rest.Config { config, err := GetConfig() if err != nil { - log.Fatal(err) + log.Error(err, "unable to get kubeconfig") } return config } diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go b/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go index d4051369d35..08e8c14bb3d 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/client/fake/client.go @@ -19,7 +19,7 @@ package fake import ( "context" "encoding/json" - "log" + "os" "k8s.io/apimachinery/pkg/api/meta" "k8s.io/apimachinery/pkg/runtime" @@ -29,6 +29,11 @@ import ( "sigs.k8s.io/controller-runtime/pkg/client" "sigs.k8s.io/controller-runtime/pkg/client/apiutil" + logf "sigs.k8s.io/controller-runtime/pkg/runtime/log" +) + +var ( + log = logf.KBLog.WithName("fake-client") ) type fakeClient struct { @@ -44,7 +49,8 @@ func NewFakeClient(initObjs ...runtime.Object) client.Client { for _, obj := range initObjs { err := tracker.Add(obj) if err != nil { - log.Fatalf("failed to add object: %#v, error: %v", obj, err) + log.Error(err, "failed to add object", "object", obj) + os.Exit(1) return nil } } diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go b/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go index b596868565b..522f5c23c91 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/internal/controller/controller.go @@ -206,7 +206,7 @@ func (c *Controller) processNextWorkItem() bool { // resource to be synced. if result, err := c.Do.Reconcile(req); err != nil { c.Queue.AddRateLimited(req) - log.Error(nil, "Reconciler error", "Controller", c.Name, "Request", req) + log.Error(err, "Reconciler error", "Controller", c.Name, "Request", req) return false } else if result.Requeue { diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/manager/manager.go b/vendor/sigs.k8s.io/controller-runtime/pkg/manager/manager.go index ae69eaa34a7..c73041015f6 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/manager/manager.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/manager/manager.go @@ -18,6 +18,7 @@ package manager import ( "fmt" + "time" "k8s.io/apimachinery/pkg/api/meta" "k8s.io/apimachinery/pkg/runtime" @@ -75,6 +76,14 @@ type Options struct { // MapperProvider provides the rest mapper used to map go types to Kubernetes APIs MapperProvider func(c *rest.Config) (meta.RESTMapper, error) + // SyncPeriod determines the minimum frequency at which watched objects are + // reconciled. A lower period will correct entropy more quickly but reduce + // responsiveness to change. Choose a low value if reconciles are fast and/or + // there are few objects to reconcile. Choose a high value if reconciles are + // slow and/or there are many object to reconcile. Defaults to 10 hours if + // unset. + SyncPeriod *time.Duration + // Dependency injection for testing newCache func(config *rest.Config, opts cache.Options) (cache.Cache, error) newClient func(config *rest.Config, options client.Options) (client.Client, error) @@ -120,7 +129,7 @@ func New(config *rest.Config, options Options) (Manager, error) { } // Create the cache for the cached read client and registering informers - cache, err := options.newCache(config, cache.Options{Scheme: options.Scheme, Mapper: mapper}) + cache, err := options.newCache(config, cache.Options{Scheme: options.Scheme, Mapper: mapper, Resync: options.SyncPeriod}) if err != nil { return nil, err diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/deleg.go b/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/deleg.go index 60823b090e4..5df7412144b 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/deleg.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/deleg.go @@ -79,12 +79,32 @@ func (l *DelegatingLogger) WithName(name string) logr.Logger { // WithValues provides a new Logger with the tags appended func (l *DelegatingLogger) WithValues(tags ...interface{}) logr.Logger { if l.promise == nil { - return l.Logger.WithValues(tags) + return l.Logger.WithValues(tags...) } res := &DelegatingLogger{Logger: l.Logger} - promise := l.promise.WithValues(res, tags) + promise := l.promise.WithValues(res, tags...) res.promise = promise return res } + +// Fulfill switches the logger over to use the actual logger +// provided, instead of the temporary initial one, if this method +// has not been previously called. +func (l *DelegatingLogger) Fulfill(actual logr.Logger) { + if l.promise != nil { + l.promise.Fulfill(actual) + } +} + +// NewDelegatingLogger constructs a new DelegatingLogger which uses +// the given logger before it's promise is fulfilled. +func NewDelegatingLogger(initial logr.Logger) *DelegatingLogger { + l := &DelegatingLogger{ + Logger: initial, + promise: &loggerPromise{}, + } + l.promise.logger = l + return l +} diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/log.go b/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/log.go index 5407a7a449f..69464bf9813 100644 --- a/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/log.go +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/log.go @@ -3,16 +3,20 @@ package log import ( + "io" "log" + "time" "github.com/go-logr/logr" - tlogr "github.com/go-logr/logr/testing" "github.com/go-logr/zapr" "go.uber.org/zap" + "go.uber.org/zap/zapcore" ) // ZapLogger is a Logger implementation. -// if development is true stack traces will be printed for errors +// If development is true, a Zap development config will be used +// (stacktraces on warnings, no sampling), otherwise a Zap production +// config will be used (stacktraces on errors, sampling). func ZapLogger(development bool) logr.Logger { var zapLog *zap.Logger var err error @@ -28,6 +32,36 @@ func ZapLogger(development bool) logr.Logger { return zapr.NewLogger(zapLog) } +// ZapLoggerTo returns a new Logger implementation using Zap which logs +// to the given destination, instead of stderr. It otherise behaves like +// ZapLogger. +func ZapLoggerTo(destWriter io.Writer, development bool) logr.Logger { + // this basically mimics NewConfig, but with a custom sink + sink := zapcore.AddSync(destWriter) + + var enc zapcore.Encoder + var lvl zap.AtomicLevel + var opts []zap.Option + if development { + encCfg := zap.NewDevelopmentEncoderConfig() + enc = zapcore.NewConsoleEncoder(encCfg) + lvl = zap.NewAtomicLevelAt(zap.DebugLevel) + opts = append(opts, zap.Development(), zap.AddStacktrace(zap.ErrorLevel)) + } else { + encCfg := zap.NewProductionEncoderConfig() + enc = zapcore.NewJSONEncoder(encCfg) + lvl = zap.NewAtomicLevelAt(zap.InfoLevel) + opts = append(opts, zap.AddStacktrace(zap.WarnLevel), + zap.WrapCore(func(core zapcore.Core) zapcore.Core { + return zapcore.NewSampler(core, time.Second, 100, 100) + })) + } + opts = append(opts, zap.AddCallerSkip(1), zap.ErrorOutput(sink)) + log := zap.New(zapcore.NewCore(enc, sink, lvl)) + log = log.WithOptions(opts...) + return zapr.NewLogger(log) +} + func fatalIfErr(err error, f func(format string, v ...interface{})) { if err != nil { f("unable to construct the logger: %v", err) @@ -36,23 +70,17 @@ func fatalIfErr(err error, f func(format string, v ...interface{})) { // SetLogger sets a concrete logging implementation for all deferred Loggers. func SetLogger(l logr.Logger) { - if Log.promise != nil { - Log.promise.Fulfill(l) - } + Log.Fulfill(l) } // Log is the base logger used by kubebuilder. It delegates // to another logr.Logger. You *must* call SetLogger to // get any actual logging. -var Log = &DelegatingLogger{ - Logger: tlogr.NullLogger{}, - promise: &loggerPromise{}, -} +var Log = NewDelegatingLogger(NullLogger{}) // KBLog is a base parent logger. var KBLog logr.Logger func init() { - Log.promise.logger = Log KBLog = Log.WithName("kubebuilder") } diff --git a/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/null.go b/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/null.go new file mode 100644 index 00000000000..7e806e032c9 --- /dev/null +++ b/vendor/sigs.k8s.io/controller-runtime/pkg/runtime/log/null.go @@ -0,0 +1,44 @@ +package log + +import ( + "github.com/go-logr/logr" +) + +// NB: this is the same as the null logger logr/testing, +// but avoids accidentally adding the testing flags to +// all binaries. + +// NullLogger is a logr.Logger that does nothing. +type NullLogger struct{} + +var _ logr.Logger = NullLogger{} + +// Info implements logr.InfoLogger +func (NullLogger) Info(_ string, _ ...interface{}) { + // Do nothing. +} + +// Enabled implements logr.InfoLogger +func (NullLogger) Enabled() bool { + return false +} + +// Error implements logr.Logger +func (NullLogger) Error(_ error, _ string, _ ...interface{}) { + // Do nothing. +} + +// V implements logr.Logger +func (log NullLogger) V(_ int) logr.InfoLogger { + return log +} + +// WithName implements logr.Logger +func (log NullLogger) WithName(_ string) logr.Logger { + return log +} + +// WithValues implements logr.Logger +func (log NullLogger) WithValues(_ ...interface{}) logr.Logger { + return log +}