github.com/Prakhar-Agarwal-byte/moby@v0.0.0-20231027092010-a14e3e8ab87e/daemon/logger/logentries/logentries.go (about)

     1  // Package logentries provides the log driver for forwarding server logs
     2  // to logentries endpoints.
     3  package logentries // import "github.com/Prakhar-Agarwal-byte/moby/daemon/logger/logentries"
     4  
     5  import (
     6  	"context"
     7  	"fmt"
     8  	"strconv"
     9  
    10  	"github.com/bsphere/le_go"
    11  	"github.com/containerd/log"
    12  	"github.com/Prakhar-Agarwal-byte/moby/daemon/logger"
    13  	"github.com/pkg/errors"
    14  )
    15  
    16  type logentries struct {
    17  	tag           string
    18  	containerID   string
    19  	containerName string
    20  	writer        *le_go.Logger
    21  	extra         map[string]string
    22  	lineOnly      bool
    23  }
    24  
    25  const (
    26  	name     = "logentries"
    27  	token    = "logentries-token"
    28  	lineonly = "line-only"
    29  )
    30  
    31  func init() {
    32  	if err := logger.RegisterLogDriver(name, New); err != nil {
    33  		panic(err)
    34  	}
    35  	if err := logger.RegisterLogOptValidator(name, ValidateLogOpt); err != nil {
    36  		panic(err)
    37  	}
    38  }
    39  
    40  // New creates a logentries logger using the configuration passed in on
    41  // the context. The supported context configuration variable is
    42  // logentries-token.
    43  func New(info logger.Info) (logger.Logger, error) {
    44  	log.G(context.TODO()).WithField("container", info.ContainerID).
    45  		WithField("token", info.Config[token]).
    46  		WithField("line-only", info.Config[lineonly]).
    47  		Debug("logging driver logentries configured")
    48  
    49  	log, err := le_go.Connect(info.Config[token])
    50  	if err != nil {
    51  		return nil, errors.Wrap(err, "error connecting to logentries")
    52  	}
    53  	var lineOnly bool
    54  	if info.Config[lineonly] != "" {
    55  		if lineOnly, err = strconv.ParseBool(info.Config[lineonly]); err != nil {
    56  			return nil, errors.Wrap(err, "error parsing lineonly option")
    57  		}
    58  	}
    59  	return &logentries{
    60  		containerID:   info.ContainerID,
    61  		containerName: info.ContainerName,
    62  		writer:        log,
    63  		lineOnly:      lineOnly,
    64  	}, nil
    65  }
    66  
    67  func (f *logentries) Log(msg *logger.Message) error {
    68  	if !f.lineOnly {
    69  		data := map[string]string{
    70  			"container_id":   f.containerID,
    71  			"container_name": f.containerName,
    72  			"source":         msg.Source,
    73  			"log":            string(msg.Line),
    74  		}
    75  		for k, v := range f.extra {
    76  			data[k] = v
    77  		}
    78  		ts := msg.Timestamp
    79  		logger.PutMessage(msg)
    80  		f.writer.Println(f.tag, ts, data)
    81  	} else {
    82  		line := string(msg.Line)
    83  		logger.PutMessage(msg)
    84  		f.writer.Println(line)
    85  	}
    86  	return nil
    87  }
    88  
    89  func (f *logentries) Close() error {
    90  	return f.writer.Close()
    91  }
    92  
    93  func (f *logentries) Name() string {
    94  	return name
    95  }
    96  
    97  // ValidateLogOpt looks for logentries specific log option logentries-address.
    98  func ValidateLogOpt(cfg map[string]string) error {
    99  	for key := range cfg {
   100  		switch key {
   101  		case "env":
   102  		case "env-regex":
   103  		case "labels":
   104  		case "labels-regex":
   105  		case "tag":
   106  		case key:
   107  		default:
   108  			return fmt.Errorf("unknown log opt '%s' for logentries log driver", key)
   109  		}
   110  	}
   111  
   112  	if cfg[token] == "" {
   113  		return fmt.Errorf("Missing logentries token")
   114  	}
   115  
   116  	return nil
   117  }