github.com/rudderlabs/rudder-go-kit@v0.30.0/logger/logger_test.go (about)

     1  package logger_test
     2  
     3  import (
     4  	"bufio"
     5  	"bytes"
     6  	"errors"
     7  	"net/http"
     8  	"os"
     9  	"testing"
    10  	"time"
    11  
    12  	"github.com/stretchr/testify/require"
    13  	"github.com/zenizh/go-capturer"
    14  
    15  	"github.com/rudderlabs/rudder-go-kit/config"
    16  	"github.com/rudderlabs/rudder-go-kit/logger"
    17  )
    18  
    19  func Test_Print_All_Levels(t *testing.T) {
    20  	fileName := t.TempDir() + "out.log"
    21  	f, err := os.Create(fileName)
    22  	require.NoError(t, err)
    23  	defer func() { _ = f.Close() }()
    24  
    25  	c := config.New()
    26  	c.Set("LOG_LEVEL", "EVENT")
    27  	c.Set("Logger.enableConsole", false)
    28  	c.Set("Logger.enableFile", true)
    29  	c.Set("Logger.enableFileNameInLog", false)
    30  	c.Set("Logger.logFileLocation", fileName)
    31  	loggerFactory := logger.NewFactory(c, constantClockOpt)
    32  
    33  	rootLogger := loggerFactory.NewLogger()
    34  	require.True(t, rootLogger.IsDebugLevel())
    35  
    36  	scanner := bufio.NewScanner(f)
    37  
    38  	rootLogger.Debug("hello ", "world")
    39  	require.True(t, scanner.Scan(), "it should print a log statement")
    40  	require.Equal(t, "2077-01-23T10:15:13.000Z	DEBUG	hello world", scanner.Text())
    41  
    42  	rootLogger.Info("hello ", "world")
    43  	require.True(t, scanner.Scan(), "it should print a log statement")
    44  	require.Equal(t, "2077-01-23T10:15:13.000Z	INFO	hello world", scanner.Text())
    45  
    46  	rootLogger.Warn("hello ", "world")
    47  	require.True(t, scanner.Scan(), "it should print a log statement")
    48  	require.Equal(t, "2077-01-23T10:15:13.000Z	WARN	hello world", scanner.Text())
    49  
    50  	rootLogger.Error("hello ", "world")
    51  	require.True(t, scanner.Scan(), "it should print a log statement")
    52  	require.Equal(t, "2077-01-23T10:15:13.000Z	ERROR	hello world", scanner.Text())
    53  
    54  	rootLogger.Fatal("hello ", "world")
    55  	require.True(t, scanner.Scan(), "it should print a log statement")
    56  	require.Equal(t, "2077-01-23T10:15:13.000Z	ERROR	hello world", scanner.Text())
    57  }
    58  
    59  func Test_Printf_All_Levels(t *testing.T) {
    60  	fileName := t.TempDir() + "out.log"
    61  	f, err := os.Create(fileName)
    62  	require.NoError(t, err)
    63  	defer func() { _ = f.Close() }()
    64  
    65  	c := config.New()
    66  	c.Set("LOG_LEVEL", "EVENT")
    67  	c.Set("Logger.enableConsole", false)
    68  	c.Set("Logger.enableFile", true)
    69  	c.Set("Logger.enableFileNameInLog", false)
    70  	c.Set("Logger.logFileLocation", fileName)
    71  	loggerFactory := logger.NewFactory(c, constantClockOpt)
    72  
    73  	rootLogger := loggerFactory.NewLogger()
    74  	require.True(t, rootLogger.IsDebugLevel())
    75  
    76  	scanner := bufio.NewScanner(f)
    77  
    78  	rootLogger.Debugf("hello %s", "world")
    79  	require.True(t, scanner.Scan(), "it should print a log statement")
    80  	require.Equal(t, "2077-01-23T10:15:13.000Z	DEBUG	hello world", scanner.Text())
    81  
    82  	rootLogger.Infof("hello %s", "world")
    83  	require.True(t, scanner.Scan(), "it should print a log statement")
    84  	require.Equal(t, "2077-01-23T10:15:13.000Z	INFO	hello world", scanner.Text())
    85  
    86  	rootLogger.Warnf("hello %s", "world")
    87  	require.True(t, scanner.Scan(), "it should print a log statement")
    88  	require.Equal(t, "2077-01-23T10:15:13.000Z	WARN	hello world", scanner.Text())
    89  
    90  	rootLogger.Errorf("hello %s", "world")
    91  	require.True(t, scanner.Scan(), "it should print a log statement")
    92  	require.Equal(t, "2077-01-23T10:15:13.000Z	ERROR	hello world", scanner.Text())
    93  
    94  	rootLogger.Fatalf("hello %s", "world")
    95  	require.True(t, scanner.Scan(), "it should print a log statement")
    96  	require.Equal(t, "2077-01-23T10:15:13.000Z	ERROR	hello world", scanner.Text())
    97  }
    98  
    99  func Test_Printw_All_Levels(t *testing.T) {
   100  	fileName := t.TempDir() + "out.log"
   101  	f, err := os.Create(fileName)
   102  	require.NoError(t, err)
   103  	defer func() { _ = f.Close() }()
   104  
   105  	c := config.New()
   106  	c.Set("LOG_LEVEL", "EVENT")
   107  	c.Set("Logger.enableConsole", false)
   108  	c.Set("Logger.enableFile", true)
   109  	c.Set("Logger.enableFileNameInLog", false)
   110  	c.Set("Logger.enableLoggerNameInLog", false)
   111  	c.Set("Logger.logFileLocation", fileName)
   112  	loggerFactory := logger.NewFactory(c, constantClockOpt)
   113  
   114  	rootLogger := loggerFactory.NewLogger()
   115  	require.True(t, rootLogger.IsDebugLevel())
   116  
   117  	scanner := bufio.NewScanner(f)
   118  
   119  	rootLogger.Debugw("hello world", "key", "value")
   120  	require.True(t, scanner.Scan(), "it should print a log statement")
   121  	require.Equal(t, `2077-01-23T10:15:13.000Z	DEBUG	hello world	{"key": "value"}`, scanner.Text())
   122  
   123  	rootLogger.Infow("hello world", "key", "value")
   124  	require.True(t, scanner.Scan(), "it should print a log statement")
   125  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world	{"key": "value"}`, scanner.Text())
   126  
   127  	rootLogger.Warnw("hello world", "key", "value")
   128  	require.True(t, scanner.Scan(), "it should print a log statement")
   129  	require.Equal(t, `2077-01-23T10:15:13.000Z	WARN	hello world	{"key": "value"}`, scanner.Text())
   130  
   131  	rootLogger.Errorw("hello world", "key", "value")
   132  	require.True(t, scanner.Scan(), "it should print a log statement")
   133  	require.Equal(t, `2077-01-23T10:15:13.000Z	ERROR	hello world	{"key": "value"}`, scanner.Text())
   134  
   135  	rootLogger.Fatalw("hello world", "key", "value")
   136  	require.True(t, scanner.Scan(), "it should print a log statement")
   137  	require.Equal(t, `2077-01-23T10:15:13.000Z	ERROR	hello world	{"key": "value"}`, scanner.Text())
   138  }
   139  
   140  func Test_Logger_With_Context(t *testing.T) {
   141  	fileName := t.TempDir() + "out.log"
   142  	f, err := os.Create(fileName)
   143  	require.NoError(t, err)
   144  	defer func() { _ = f.Close() }()
   145  
   146  	c := config.New()
   147  	c.Set("LOG_LEVEL", "INFO")
   148  	c.Set("Logger.enableConsole", false)
   149  	c.Set("Logger.enableFile", true)
   150  	c.Set("Logger.enableFileNameInLog", false)
   151  	c.Set("Logger.enableLoggerNameInLog", false)
   152  	c.Set("Logger.logFileLocation", fileName)
   153  	loggerFactory := logger.NewFactory(c, constantClockOpt)
   154  	rootLogger := loggerFactory.NewLogger()
   155  	ctxLogger := rootLogger.With("key", "value")
   156  
   157  	scanner := bufio.NewScanner(f)
   158  
   159  	rootLogger.Info("hello world")
   160  	require.True(t, scanner.Scan(), "it should print a log statement")
   161  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world`, scanner.Text())
   162  	ctxLogger.Info("hello world")
   163  	require.True(t, scanner.Scan(), "it should print a log statement")
   164  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world	{"key": "value"}`, scanner.Text())
   165  
   166  	rootLogger.Infof("hello %s", "world")
   167  	require.True(t, scanner.Scan(), "it should print a log statement")
   168  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world`, scanner.Text())
   169  	ctxLogger.Infof("hello %s", "world")
   170  	require.True(t, scanner.Scan(), "it should print a log statement")
   171  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world	{"key": "value"}`, scanner.Text())
   172  
   173  	rootLogger.Infow("hello world", "key1", "value1")
   174  	require.True(t, scanner.Scan(), "it should print a log statement")
   175  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world	{"key1": "value1"}`, scanner.Text())
   176  	ctxLogger.Infow("hello world", "key1", "value1")
   177  	require.True(t, scanner.Scan(), "it should print a log statement")
   178  	require.Equal(t, `2077-01-23T10:15:13.000Z	INFO	hello world	{"key": "value", "key1": "value1"}`, scanner.Text())
   179  }
   180  
   181  func Test_Logger_Deep_Hierarchy(t *testing.T) {
   182  	fileName := t.TempDir() + "out.log"
   183  	f, err := os.Create(fileName)
   184  	require.NoError(t, err)
   185  	defer func() { _ = f.Close() }()
   186  
   187  	c := config.New()
   188  	c.Set("LOG_LEVEL", "INFO")
   189  	c.Set("Logger.enableConsole", false)
   190  	c.Set("Logger.enableFile", true)
   191  	c.Set("Logger.enableFileNameInLog", false)
   192  	c.Set("Logger.logFileLocation", fileName)
   193  	loggerFactory := logger.NewFactory(c, constantClockOpt)
   194  	rootLogger := loggerFactory.NewLogger()
   195  	lvl1Logger := rootLogger.Child("logger1")
   196  	lvl2Logger := lvl1Logger.Child("logger2")
   197  	lvl3Logger := lvl2Logger.Child("logger3")
   198  
   199  	rootLogger.Info("hello world 0")
   200  	scanner := bufio.NewScanner(f)
   201  	require.True(t, scanner.Scan(), "it should print a log statement")
   202  	require.Equal(t, "2077-01-23T10:15:13.000Z	INFO	hello world 0", scanner.Text())
   203  
   204  	lvl1Logger.Info("hello world 1")
   205  	require.True(t, scanner.Scan(), "it should print a log statement")
   206  	require.Equal(t, "2077-01-23T10:15:13.000Z	INFO	logger1	hello world 1", scanner.Text())
   207  
   208  	lvl2Logger.Info("hello world 2")
   209  	require.True(t, scanner.Scan(), "it should print a log statement")
   210  	require.Equal(t, "2077-01-23T10:15:13.000Z	INFO	logger1.logger2	hello world 2", scanner.Text())
   211  
   212  	lvl3Logger.Info("hello world 3")
   213  	require.True(t, scanner.Scan(), "it should print a log statement")
   214  	require.Equal(t, "2077-01-23T10:15:13.000Z	INFO	logger1.logger2.logger3	hello world 3", scanner.Text())
   215  }
   216  
   217  func Test_Logger_Json_Output(t *testing.T) {
   218  	fileName := t.TempDir() + "out.log"
   219  	f, err := os.Create(fileName)
   220  	require.NoError(t, err)
   221  	defer func() { _ = f.Close() }()
   222  
   223  	c := config.New()
   224  	c.Set("LOG_LEVEL", "INFO")
   225  	c.Set("Logger.enableConsole", false)
   226  	c.Set("Logger.enableFile", true)
   227  	c.Set("Logger.enableFileNameInLog", false)
   228  	c.Set("Logger.logFileLocation", fileName)
   229  	c.Set("Logger.fileJsonFormat", true)
   230  	loggerFactory := logger.NewFactory(c, constantClockOpt)
   231  	rootLogger := loggerFactory.NewLogger().Child("mylogger")
   232  	ctxLogger := rootLogger.With("key", "value")
   233  
   234  	scanner := bufio.NewScanner(f)
   235  
   236  	rootLogger.Info("hello world")
   237  	require.True(t, scanner.Scan(), "it should print a log statement")
   238  	require.Equal(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world"}`, scanner.Text())
   239  	ctxLogger.Info("hello world")
   240  	require.True(t, scanner.Scan(), "it should print a log statement")
   241  	require.Equal(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key":"value"}`, scanner.Text())
   242  
   243  	rootLogger.Infof("hello %s", "world")
   244  	require.True(t, scanner.Scan(), "it should print a log statement")
   245  	require.Equal(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world"}`, scanner.Text())
   246  	ctxLogger.Infof("hello %s", "world")
   247  	require.True(t, scanner.Scan(), "it should print a log statement")
   248  	require.Equal(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key":"value"}`, scanner.Text())
   249  
   250  	rootLogger.Infow("hello world", "key1", "value1")
   251  	require.True(t, scanner.Scan(), "it should print a log statement")
   252  	require.Equal(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key1":"value1"}`, scanner.Text())
   253  	ctxLogger.Infow("hello world", "key1", "value1")
   254  	require.True(t, scanner.Scan(), "it should print a log statement")
   255  	require.Equal(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key":"value","key1":"value1"}`, scanner.Text())
   256  }
   257  
   258  func Test_Logger_NonSugared(t *testing.T) {
   259  	fileName := t.TempDir() + "out.log"
   260  	f, err := os.Create(fileName)
   261  	require.NoError(t, err)
   262  	defer func() { _ = f.Close() }()
   263  
   264  	c := config.New()
   265  	c.Set("LOG_LEVEL", "EVENT")
   266  	c.Set("Logger.enableConsole", false)
   267  	c.Set("Logger.enableFile", true)
   268  	c.Set("Logger.enableFileNameInLog", false)
   269  	c.Set("Logger.enableStackTrace", false)
   270  	c.Set("Logger.logFileLocation", fileName)
   271  	c.Set("Logger.fileJsonFormat", true)
   272  	loggerFactory := logger.NewFactory(c, constantClockOpt)
   273  	rootLogger := loggerFactory.NewLogger().Child("mylogger")
   274  	ctxLogger := rootLogger.Withn(logger.NewBoolField("foo", true))
   275  
   276  	scanner := bufio.NewScanner(f)
   277  
   278  	rootLogger.Debugn("hello world", logger.NewStringField("key1", "value1"))
   279  	require.True(t, scanner.Scan(), "it should print a log statement")
   280  	require.JSONEq(t, `{"level":"DEBUG","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key1":"value1"}`, scanner.Text())
   281  	ctxLogger.Debugn("hello world", logger.NewIntField("key2", 2))
   282  	require.True(t, scanner.Scan(), "it should print a log statement")
   283  	require.JSONEq(t, `{"level":"DEBUG","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key2":2,"foo":true}`, scanner.Text())
   284  
   285  	rootLogger.Infon("hello world", logger.NewStringField("key1", "value1"))
   286  	require.True(t, scanner.Scan(), "it should print a log statement")
   287  	require.JSONEq(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key1":"value1"}`, scanner.Text())
   288  	ctxLogger.Infon("hello world", logger.NewIntField("key2", 2))
   289  	require.True(t, scanner.Scan(), "it should print a log statement")
   290  	require.JSONEq(t, `{"level":"INFO","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key2":2,"foo":true}`, scanner.Text())
   291  
   292  	rootLogger.Warnn("hello world", logger.NewStringField("key1", "value1"))
   293  	require.True(t, scanner.Scan(), "it should print a log statement")
   294  	require.JSONEq(t, `{"level":"WARN","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key1":"value1"}`, scanner.Text())
   295  	ctxLogger.Warnn("hello world", logger.NewIntField("key2", 2))
   296  	require.True(t, scanner.Scan(), "it should print a log statement")
   297  	require.JSONEq(t, `{"level":"WARN","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key2":2,"foo":true}`, scanner.Text())
   298  
   299  	rootLogger.Errorn("hello world", logger.NewStringField("key1", "value1"))
   300  	require.True(t, scanner.Scan(), "it should print a log statement")
   301  	require.JSONEq(t, `{"level":"ERROR","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key1":"value1"}`, scanner.Text())
   302  	ctxLogger.Errorn("hello world", logger.NewIntField("key2", 2))
   303  	require.True(t, scanner.Scan(), "it should print a log statement")
   304  	require.JSONEq(t, `{"level":"ERROR","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key2":2,"foo":true}`, scanner.Text())
   305  
   306  	rootLogger.Fataln("hello world", logger.NewStringField("key1", "value1"))
   307  	require.True(t, scanner.Scan(), "it should print a log statement")
   308  	require.JSONEq(t, `{"level":"ERROR","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key1":"value1"}`, scanner.Text())
   309  	require.True(t, scanner.Scan(), "it should print a stacktrace statement")
   310  	require.Contains(t, scanner.Text(), `"level":"ERROR"`)
   311  	require.Contains(t, scanner.Text(), `"ts":"2077-01-23T10:15:13.000Z"`)
   312  	require.Contains(t, scanner.Text(), `"logger":"mylogger"`)
   313  	require.Contains(t, scanner.Text(), `"key1":"value1"`)
   314  	require.Contains(t, scanner.Text(), `"msg":"goroutine`)
   315  
   316  	ctxLogger.Fataln("hello world", logger.NewIntField("key2", 2))
   317  	require.True(t, scanner.Scan(), "it should print a log statement")
   318  	require.JSONEq(t, `{"level":"ERROR","ts":"2077-01-23T10:15:13.000Z","logger":"mylogger","msg":"hello world","key2":2,"foo":true}`, scanner.Text())
   319  	require.True(t, scanner.Scan(), "it should print a stacktrace statement")
   320  	require.Contains(t, scanner.Text(), `"level":"ERROR"`)
   321  	require.Contains(t, scanner.Text(), `"ts":"2077-01-23T10:15:13.000Z"`)
   322  	require.Contains(t, scanner.Text(), `"logger":"mylogger"`)
   323  	require.Contains(t, scanner.Text(), `"key2":2`)
   324  	require.Contains(t, scanner.Text(), `"foo":true`)
   325  	require.Contains(t, scanner.Text(), `"msg":"goroutine`)
   326  
   327  	rootLogger.Debugn("using all fields",
   328  		logger.NewField("foo", "any value"),
   329  		logger.NewStringField("myString", "hello"),
   330  		logger.NewIntField("myInt", 666),
   331  		logger.NewBoolField("myBool", true),
   332  		logger.NewFloatField("myFloat", 1.1),
   333  		logger.NewTimeField("myTime", time.Date(2077, 1, 23, 10, 15, 13, 0, time.UTC)),
   334  		logger.NewDurationField("myDuration", time.Second*2+time.Millisecond*321),
   335  		logger.NewErrorField(errors.New("a bad error")),
   336  	)
   337  	require.True(t, scanner.Scan(), "it should print a log statement")
   338  	require.JSONEq(t, `{
   339  		"level":"DEBUG",
   340  		"ts":"2077-01-23T10:15:13.000Z",
   341  		"logger":"mylogger",
   342  		"msg":"using all fields",
   343  		"foo":"any value",
   344  		"myString":"hello",
   345  		"myInt":666,
   346  		"myBool":true,
   347  		"myFloat":1.1,
   348  		"myTime":"2077-01-23T10:15:13.000Z",
   349  		"myDuration":2.321,
   350  		"error":"a bad error"
   351  	}`, scanner.Text())
   352  }
   353  
   354  func Test_Logger_Expand(t *testing.T) {
   355  	fileName := t.TempDir() + "out.log"
   356  	f, err := os.Create(fileName)
   357  	require.NoError(t, err)
   358  	defer func() { _ = f.Close() }()
   359  
   360  	c := config.New()
   361  	c.Set("LOG_LEVEL", "EVENT")
   362  	c.Set("Logger.enableConsole", false)
   363  	c.Set("Logger.enableFile", true)
   364  	c.Set("Logger.enableFileNameInLog", false)
   365  	c.Set("Logger.enableStackTrace", false)
   366  	c.Set("Logger.logFileLocation", fileName)
   367  	c.Set("Logger.fileJsonFormat", true)
   368  	loggerFactory := logger.NewFactory(c, constantClockOpt)
   369  	rootLogger := loggerFactory.NewLogger().Child("mylogger")
   370  
   371  	scanner := bufio.NewScanner(f)
   372  
   373  	rootLogger.Debugw("using expand",
   374  		logger.Expand(
   375  			logger.NewField("foo", "any value"),
   376  			logger.NewStringField("myString", "hello"),
   377  			logger.NewIntField("myInt", 666),
   378  			logger.NewBoolField("myBool", true),
   379  			logger.NewFloatField("myFloat", 1.1),
   380  			logger.NewTimeField("myTime", time.Date(2077, 1, 23, 10, 15, 13, 0, time.UTC)),
   381  			logger.NewDurationField("myDuration", time.Second*2+time.Millisecond*321),
   382  			logger.NewErrorField(errors.New("a bad error")),
   383  		)...,
   384  	)
   385  	require.True(t, scanner.Scan(), "it should print a log statement")
   386  	require.JSONEq(t, `{
   387  		"level":"DEBUG",
   388  		"ts":"2077-01-23T10:15:13.000Z",
   389  		"logger":"mylogger",
   390  		"msg":"using expand",
   391  		"foo":"any value",
   392  		"myString":"hello",
   393  		"myInt":666,
   394  		"myBool":true,
   395  		"myFloat":1.1,
   396  		"myTime":"2077-01-23T10:15:13.000Z",
   397  		"myDuration":2.321,
   398  		"error":"a bad error"
   399  	}`, scanner.Text())
   400  }
   401  
   402  func Test_LogRequest(t *testing.T) {
   403  	json := `{"key":"value"}`
   404  	request, err := http.NewRequest(http.MethodPost, "https://example.com", bytes.NewReader([]byte(json)))
   405  	require.NoError(t, err)
   406  	c := config.New()
   407  	c.Set("LOG_LEVEL", "EVENT")
   408  	c.Set("Logger.enableTimestamp", false)
   409  	c.Set("Logger.enableFileNameInLog", false)
   410  	c.Set("Logger.enableLoggerNameInLog", false)
   411  	stdout := capturer.CaptureStdout(func() {
   412  		loggerFactory := logger.NewFactory(c, constantClockOpt)
   413  		l := loggerFactory.NewLogger()
   414  		l.LogRequest(request)
   415  		loggerFactory.Sync()
   416  	})
   417  	require.Equal(t, "DEBUG\tRequest Body\t{\"body\": \"{\\\"key\\\":\\\"value\\\"}\"}\n", stdout)
   418  }
   419  
   420  type constantClock time.Time
   421  
   422  func (c constantClock) Now() time.Time { return time.Time(c) }
   423  func (constantClock) NewTicker(_ time.Duration) *time.Ticker {
   424  	return &time.Ticker{}
   425  }
   426  
   427  var (
   428  	date             = time.Date(2077, 1, 23, 10, 15, 13, 0o00, time.UTC)
   429  	constantClockOpt = logger.WithClock(constantClock(date))
   430  )