func (mj *JSONLog) MarshalJSONBuf(buf *bytes.Buffer) error { var ( err error timestamp string first bool = true ) buf.WriteString(`{`) if len(mj.Log) != 0 { first = false buf.WriteString(`"log":`) ffjson_WriteJsonString(buf, mj.Log) } if len(mj.Stream) != 0 { if first == true { first = false } else { buf.WriteString(`,`) } buf.WriteString(`"stream":`) ffjson_WriteJsonString(buf, mj.Stream) } if first == true { first = false } else { buf.WriteString(`,`) } buf.WriteString(`"time":`) timestamp, err = timeutils.FastMarshalJSON(mj.Created) if err != nil { return err } buf.WriteString(timestamp) buf.WriteString(`}`) return nil }
// Log converts logger.Message to jsonlog.JSONLog and serializes it to file func (l *JSONFileLogger) Log(msg *logger.Message) error { l.mu.Lock() defer l.mu.Unlock() timestamp, err := timeutils.FastMarshalJSON(msg.Timestamp) if err != nil { return err } err = (&jsonlog.JSONLogBytes{Log: append(msg.Line, '\n'), Stream: msg.Source, Created: timestamp}).MarshalJSONBuf(l.buf) if err != nil { return err } l.buf.WriteByte('\n') _, err = writeLog(l) return err }
// Log converts logger.Message to jsonlog.JSONLog and serializes it to file func (l *JSONFileLogger) Log(msg *logger.Message) error { l.mu.Lock() defer l.mu.Unlock() timestamp, err := timeutils.FastMarshalJSON(msg.Timestamp) if err != nil { return err } err = (&jsonlog.JSONLogBytes{Log: append(msg.Line, '\n'), Stream: msg.Source, Created: timestamp}).MarshalJSONBuf(l.buf) if err != nil { return err } l.buf.WriteByte('\n') _, err = l.buf.WriteTo(l.f) if err != nil { // this buffer is screwed, replace it with another to avoid races l.buf = bytes.NewBuffer(nil) return err } return nil }
// Log converts logger.Message to jsonlog.JSONLog and serializes it to file. func (l *JSONFileLogger) Log(msg *logger.Message) error { timestamp, err := timeutils.FastMarshalJSON(msg.Timestamp) if err != nil { return err } err = (&jsonlog.JSONLogs{ Log: append(msg.Line, '\n'), Stream: msg.Source, Created: timestamp, RawAttrs: l.extra, }).MarshalJSONBuf(l.buf) if err != nil { return err } l.buf.WriteByte('\n') _, err = l.writer.Write(l.buf.Bytes()) l.buf.Reset() return err }
// Write writes bytes to all writers. Failed writers will be evicted during // this call. func (w *BroadcastWriter) Write(p []byte) (n int, err error) { w.Lock() if writers, ok := w.streams[""]; ok { for sw := range writers { if n, err := sw.Write(p); err != nil || n != len(p) { // On error, evict the writer delete(writers, sw) } } if len(w.streams) == 1 { if w.buf.Len() >= 4096 { w.buf.Reset() } else { w.buf.Write(p) } w.Unlock() return len(p), nil } } if w.jsLogBuf == nil { w.jsLogBuf = new(bytes.Buffer) w.jsLogBuf.Grow(1024) } var timestamp string created := time.Now().UTC() w.buf.Write(p) for { if n := w.buf.Len(); n == 0 { break } i := bytes.IndexByte(w.buf.Bytes(), '\n') if i < 0 { break } lineBytes := w.buf.Next(i + 1) if timestamp == "" { timestamp, err = timeutils.FastMarshalJSON(created) if err != nil { continue } } for stream, writers := range w.streams { if stream == "" { continue } jsonLog := jsonlog.JSONLogBytes{Log: lineBytes, Stream: stream, Created: timestamp} err = jsonLog.MarshalJSONBuf(w.jsLogBuf) if err != nil { logrus.Errorf("Error making JSON log line: %s", err) continue } w.jsLogBuf.WriteByte('\n') b := w.jsLogBuf.Bytes() for sw := range writers { if _, err := sw.Write(b); err != nil { delete(writers, sw) } } } w.jsLogBuf.Reset() } w.jsLogBuf.Reset() w.Unlock() return len(p), nil }