go.mondoo.com/cnquery@v0.0.0-20231005093811-59568235f6ea/logger/stackdriver/stackdriver.go (about)

     1  // Copyright (c) Mondoo, Inc.
     2  // SPDX-License-Identifier: BUSL-1.1
     3  
     4  package stackdriver
     5  
     6  import (
     7  	"context"
     8  	"encoding/json"
     9  
    10  	"cloud.google.com/go/logging"
    11  	"github.com/rs/zerolog"
    12  )
    13  
    14  // LogLevelMap maps zerolog.Level to logging.Severity
    15  var logLevelMap = map[zerolog.Level]logging.Severity{
    16  	zerolog.DebugLevel: logging.Debug,
    17  	zerolog.InfoLevel:  logging.Info,
    18  	zerolog.WarnLevel:  logging.Warning,
    19  	zerolog.ErrorLevel: logging.Error,
    20  	zerolog.FatalLevel: logging.Critical,
    21  	zerolog.PanicLevel: logging.Critical,
    22  	zerolog.NoLevel:    logging.Info,
    23  	zerolog.TraceLevel: logging.Debug,
    24  }
    25  
    26  // https://pkg.go.dev/cloud.google.com/go/logging
    27  // by default, everything is logged async, only zerolog fatal messages are logged synchronously
    28  func NewStackdriverWriter(projectID string, logID string) (zerolog.LevelWriter, error) {
    29  	client, err := logging.NewClient(context.Background(), projectID)
    30  	if err != nil {
    31  		return nil, err
    32  	}
    33  
    34  	return &stackdriverWriter{
    35  		logger: client.Logger(logID),
    36  	}, nil
    37  }
    38  
    39  type stackdriverWriter struct {
    40  	logger *logging.Logger
    41  	zerolog.LevelWriter
    42  }
    43  
    44  func (c *stackdriverWriter) Write(p []byte) (int, error) {
    45  	c.logger.Log(logging.Entry{
    46  		Severity: logging.Info, // if no level is provided, we assume its info
    47  		Payload:  json.RawMessage(p),
    48  	})
    49  	return len(p), nil
    50  }
    51  
    52  func (c *stackdriverWriter) WriteLevel(level zerolog.Level, payload []byte) (int, error) {
    53  	entry := logging.Entry{
    54  		Severity: logLevelMap[level],
    55  		Payload:  json.RawMessage(payload),
    56  	}
    57  
    58  	if level == zerolog.FatalLevel {
    59  		// since its fatal, we want to make sure its data is transferred
    60  		err := c.logger.LogSync(context.Background(), entry)
    61  		if err != nil {
    62  			return 0, err
    63  		}
    64  		// prepare the logger to be closed
    65  		err = c.logger.Flush()
    66  		if err != nil {
    67  			return 0, err
    68  		}
    69  	} else {
    70  		c.logger.Log(entry)
    71  	}
    72  	return len(payload), nil
    73  }