event: move the special values back to direct embedding in the event
Change-Id: I93ebd8f0749fb483a9e56051cc2b7f2a7da7d4bc
Reviewed-on: https://go-review.googlesource.com/c/exp/+/327754
Trust: Ian Cottrell <iancottrell@google.com>
Run-TryBot: Ian Cottrell <iancottrell@google.com>
TryBot-Result: Go Bot <gobot@golang.org>
Reviewed-by: Jonathan Amsterdam <jba@google.com>
diff --git a/event/adapter/gokit/gokit_test.go b/event/adapter/gokit/gokit_test.go
index d2b5390..f8d6cad 100644
--- a/event/adapter/gokit/gokit_test.go
+++ b/event/adapter/gokit/gokit_test.go
@@ -21,13 +21,14 @@
ctx, h := eventtest.NewCapture()
log.Log(ctx, "msg", "mess", "level", 1, "name", "n/m", "traceID", 17, "resource", "R")
want := []event.Event{{
- At: eventtest.InitialTime,
+ At: eventtest.InitialTime,
+ Kind: event.LogKind,
+ Message: "mess",
Labels: []event.Label{
keys.Value("level").Of(1),
keys.Value("name").Of("n/m"),
keys.Value("traceID").Of(17),
keys.Value("resource").Of("R"),
- event.Message.Of("mess"),
},
}}
if diff := cmp.Diff(want, h.Got); diff != "" {
diff --git a/event/adapter/logfmt/logfmt.go b/event/adapter/logfmt/logfmt.go
index 83102e4..e12b580 100644
--- a/event/adapter/logfmt/logfmt.go
+++ b/event/adapter/logfmt/logfmt.go
@@ -73,6 +73,23 @@
}
p.Label(w, l)
}
+
+ if ev.TraceID != 0 {
+ p.label(w, "trace", event.Uint64Of(ev.TraceID))
+ }
+
+ if ev.Message != "" {
+ p.label(w, "msg", event.StringOf(ev.Message))
+ }
+
+ if ev.Name != "" {
+ p.label(w, "name", event.StringOf(ev.Name))
+ }
+
+ if ev.Kind == event.TraceKind && ev.TraceID == 0 {
+ p.label(w, "end", event.Value{})
+ }
+
io.WriteString(w, "\n")
}
diff --git a/event/adapter/logr/logr.go b/event/adapter/logr/logr.go
index 115a4a3..2dfb62a 100644
--- a/event/adapter/logr/logr.go
+++ b/event/adapter/logr/logr.go
@@ -89,12 +89,12 @@
// while the err field should be used to attach the actual error that
// triggered this log line, if present.
func (l *logger) Error(err error, msg string, keysAndValues ...interface{}) {
- l.log(msg, l.builder.Clone().With(event.Error.Of(err)), keysAndValues)
+ l.log(msg, l.builder.Clone().Error(err), keysAndValues)
}
func (l *logger) log(msg string, b event.Builder, keysAndValues []interface{}) {
b.With(convertVerbosity(l.verbosity))
- b.With(event.Name.Of(l.name))
+ b.Name(l.name)
addLabels(b, keysAndValues)
b.Log(msg)
}
diff --git a/event/adapter/logr/logr_test.go b/event/adapter/logr/logr_test.go
index c35fe9a..8b897e4 100644
--- a/event/adapter/logr/logr_test.go
+++ b/event/adapter/logr/logr_test.go
@@ -23,13 +23,14 @@
log = log.WithName("m")
log.Info("mess", "traceID", 17, "resource", "R")
want := []event.Event{{
- At: eventtest.InitialTime,
+ At: eventtest.InitialTime,
+ Kind: event.LogKind,
+ Message: "mess",
+ Name: "n/m",
Labels: []event.Label{
severity.Debug,
- event.Name.Of("n/m"),
keys.Value("traceID").Of(17),
keys.Value("resource").Of("R"),
- event.Message.Of("mess"),
},
}}
if diff := cmp.Diff(want, th.Got); diff != "" {
diff --git a/event/adapter/logrus/logrus_test.go b/event/adapter/logrus/logrus_test.go
index b2249af..babc686 100644
--- a/event/adapter/logrus/logrus_test.go
+++ b/event/adapter/logrus/logrus_test.go
@@ -29,11 +29,12 @@
log.WithContext(ctx).WithField("traceID", 17).WithField("resource", "R").Info("mess")
want := []event.Event{{
+ Kind: event.LogKind,
+ Message: "mess",
Labels: []event.Label{
severity.Info,
keys.Value("traceID").Of(17),
keys.Value("resource").Of("R"),
- event.Message.Of("mess"),
},
}}
// logrus fields are stored in a map, so we have to sort to overcome map
diff --git a/event/adapter/zap/zap.go b/event/adapter/zap/zap.go
index de8d603..22304dd 100644
--- a/event/adapter/zap/zap.go
+++ b/event/adapter/zap/zap.go
@@ -53,7 +53,7 @@
b := c.builder.Clone().
At(e.Time).
With(convertLevel(e.Level)).
- With(event.Name.Of(e.LoggerName))
+ Name(e.LoggerName)
// TODO: add these additional labels more efficiently.
if e.Stack != "" {
b.With(keys.String("stack").Of(e.Stack))
diff --git a/event/adapter/zap/zap_test.go b/event/adapter/zap/zap_test.go
index c504434..4ae028a 100644
--- a/event/adapter/zap/zap_test.go
+++ b/event/adapter/zap/zap_test.go
@@ -25,13 +25,14 @@
log = log.Named("n/m")
log.Info("mess", zap.Float64("pi", 3.14))
want := []event.Event{{
+ Kind: event.LogKind,
+ Message: "mess",
+ Name: "n/m",
Labels: []event.Label{
keys.Int64("traceID").Of(17),
keys.String("resource").Of("R"),
severity.Info,
- event.Name.Of("n/m"),
keys.Float64("pi").Of(3.14),
- event.Message.Of("mess"),
},
}}
if diff := cmp.Diff(want, h.Got, cmpopts.IgnoreFields(event.Event{}, "At")); diff != "" {
diff --git a/event/builder.go b/event/builder.go
index a0567e3..0c39d20 100644
--- a/event/builder.go
+++ b/event/builder.go
@@ -103,6 +103,20 @@
return b
}
+func (b Builder) Name(name string) Builder {
+ if b.data != nil {
+ b.data.Event.Name = name
+ }
+ return b
+}
+
+func (b Builder) Error(err error) Builder {
+ if b.data != nil {
+ b.data.Event.Error = err
+ }
+ return b
+}
+
func (b builderCommon) addLabel(label Label) {
if b.data != nil {
b.data.Event.Labels = append(b.data.Event.Labels, label)
@@ -161,7 +175,8 @@
if b.data.exporter.loggingEnabled() {
b.data.exporter.mu.Lock()
defer b.data.exporter.mu.Unlock()
- b.data.Event.Labels = append(b.data.Event.Labels, Message.Of(message))
+ b.data.Event.Kind = LogKind
+ b.data.Event.Message = message
b.data.exporter.prepare(&b.data.Event)
b.data.exporter.handler.Log(b.ctx, &b.data.Event)
}
@@ -180,7 +195,8 @@
// Duplicate code from Log so Exporter.deliver's invocation of runtime.Callers is correct.
b.data.exporter.mu.Lock()
defer b.data.exporter.mu.Unlock()
- b.data.Event.Labels = append(b.data.Event.Labels, Message.Of(message))
+ b.data.Event.Kind = LogKind
+ b.data.Event.Message = message
b.data.exporter.prepare(&b.data.Event)
b.data.exporter.handler.Log(b.ctx, &b.data.Event)
}
@@ -199,6 +215,7 @@
b.data.Event.Namespace = mv.m.Descriptor().Namespace()
}
b.data.Event.Labels = append(b.data.Event.Labels, MetricVal.Of(mv.v), MetricKey.Of(mv.m))
+ b.data.Event.Kind = MetricKind
b.data.exporter.prepare(&b.data.Event)
b.data.exporter.handler.Metric(b.ctx, &b.data.Event)
}
@@ -235,7 +252,7 @@
}
b.data.exporter.mu.Lock()
defer b.data.exporter.mu.Unlock()
- b.data.Event.Labels = append(b.data.Event.Labels, End.Value())
+ b.data.Event.Kind = TraceKind
b.data.exporter.prepare(&b.data.Event)
b.data.exporter.handler.End(b.ctx, &b.data.Event)
}
@@ -279,10 +296,11 @@
// create the end builder
endBuilder = b.Clone()
endBuilder.data.Event.Parent = traceID
- b.data.Event.Labels = append(b.data.Event.Labels, Trace.Of(traceID))
+ b.data.Event.Kind = TraceKind
+ b.data.Event.TraceID = traceID
b.data.exporter.prepare(&b.data.Event)
// and now deliver the start event
- b.data.Event.Labels = append(b.data.Event.Labels, Name.Of(name))
+ b.data.Event.Name = name
now := time.Now()
ctx = newContext(ctx, b.data.exporter, traceID, now)
ctx = b.data.exporter.handler.Start(ctx, &b.data.Event)
diff --git a/event/builder_test.go b/event/builder_test.go
index c7d698f..c467adb 100644
--- a/event/builder_test.go
+++ b/event/builder_test.go
@@ -180,13 +180,13 @@
}
b.Run("direct", func(b *testing.B) {
for i := 0; i < b.N; i++ {
- event.To(ctx).With(event.Name.Of("foo")).Metric(c.Record(1))
+ event.To(ctx).Name("foo").Metric(c.Record(1))
}
})
b.Run("cloned", func(b *testing.B) {
bu := event.To(ctx)
for i := 0; i < b.N; i++ {
- bu.Clone().With(event.Name.Of("foo")).Metric(c.Record(1))
+ bu.Clone().Name("foo").Metric(c.Record(1))
}
})
})
diff --git a/event/common.go b/event/common.go
index b7be86c..4eb9ea0 100644
--- a/event/common.go
+++ b/event/common.go
@@ -5,71 +5,26 @@
package event
const (
- Message = stringKey("msg")
- Name = stringKey("name")
- Trace = traceKey("trace")
- End = tagKey("end")
MetricKey = interfaceKey("metric")
MetricVal = valueKey("metricValue")
DurationMetric = interfaceKey("durationMetric")
- Error = errorKey("error")
+)
+
+type Kind int
+
+const (
+ unknownKind = Kind(iota)
+
+ LogKind
+ MetricKind
+ TraceKind
)
type (
- stringKey string
- traceKey string
- tagKey string
valueKey string
interfaceKey string
- errorKey string
)
-// Of creates a new message Label.
-func (k stringKey) Of(msg string) Label {
- return Label{Name: string(k), Value: StringOf(msg)}
-}
-
-func (k stringKey) Matches(ev *Event) bool {
- _, found := k.Find(ev)
- return found
-}
-
-func (k stringKey) Find(ev *Event) (string, bool) {
- for i := len(ev.Labels) - 1; i >= 0; i-- {
- if ev.Labels[i].Name == string(k) {
- return ev.Labels[i].Value.String(), true
- }
- }
- return "", false
-}
-
-// Of creates a new start Label.
-func (k traceKey) Of(id uint64) Label {
- return Label{Name: string(k), Value: Uint64Of(id)}
-}
-
-func (k traceKey) Matches(ev *Event) bool {
- _, found := k.Find(ev)
- return found
-}
-
-func (k traceKey) Find(ev *Event) (uint64, bool) {
- if v, ok := lookupValue(string(k), ev.Labels); ok {
- return v.Uint64(), true
- }
- return 0, false
-}
-
-// Value creates a new tag Label.
-func (k tagKey) Value() Label {
- return Label{Name: string(k)}
-}
-
-func (k tagKey) Matches(ev *Event) bool {
- _, ok := lookupValue(string(k), ev.Labels)
- return ok
-}
-
func (k valueKey) Of(v Value) Label {
return Label{Name: string(k), Value: v}
}
@@ -109,22 +64,3 @@
}
return Value{}, false
}
-
-// Of creates a new error Label.
-func (k errorKey) Of(err error) Label {
- return Label{Name: string(k), Value: ValueOf(err)}
-}
-
-func (k errorKey) Matches(ev *Event) bool {
- _, found := k.Find(ev)
- return found
-}
-
-func (k errorKey) Find(ev *Event) (error, bool) {
- for i := len(ev.Labels) - 1; i >= 0; i-- {
- if ev.Labels[i].Name == string(k) {
- return ev.Labels[i].Value.Interface().(error), true
- }
- }
- return nil, false
-}
diff --git a/event/common_test.go b/event/common_test.go
index b561ae3..d104024 100644
--- a/event/common_test.go
+++ b/event/common_test.go
@@ -21,47 +21,50 @@
const trace = "a trace"
event.To(ctx).Log(simple)
- checkFind(t, h, "Log", event.Message, true, simple)
- checkFind(t, h, "Log", event.Name, false, "")
+ checkMessage(t, h, "Log", simple)
+ checkName(t, h, "Log", "")
h.Reset()
event.To(ctx).Metric(m.Record(3))
- checkFind(t, h, "Metric", event.Message, false, "")
- checkFind(t, h, "Metric", event.Name, false, "")
+ checkMessage(t, h, "Metric", "")
+ checkName(t, h, "Metric", "")
h.Reset()
event.To(ctx).Annotate()
- checkFind(t, h, "Annotate", event.Message, false, "")
- checkFind(t, h, "Annotate", event.Name, false, "")
+ checkMessage(t, h, "Annotate", "")
+ checkName(t, h, "Annotate", "")
h.Reset()
_, eb := event.To(ctx).Start(trace)
- checkFind(t, h, "Start", event.Message, false, "")
- checkFind(t, h, "Start", event.Name, true, trace)
+ checkMessage(t, h, "Start", "")
+ checkName(t, h, "Start", trace)
h.Reset()
eb.End()
- checkFind(t, h, "End", event.Message, false, "")
- checkFind(t, h, "End", event.Name, false, "")
+ checkMessage(t, h, "End", "")
+ checkName(t, h, "End", "")
}
type finder interface {
Find(*event.Event) (string, bool)
}
-func checkFind(t *testing.T, h *eventtest.CaptureHandler, method string, key finder, match bool, text string) {
+func checkMessage(t *testing.T, h *eventtest.CaptureHandler, method string, text string) {
if len(h.Got) != 1 {
t.Errorf("Got %d events, expected 1", len(h.Got))
return
}
- m, ok := key.Find(&h.Got[0])
- if ok && !match {
- t.Errorf("%s produced an event with a %v", method, key)
+ if h.Got[0].Message != text {
+ t.Errorf("Expected event with Message %q from %s got %q", text, method, h.Got[0].Message)
}
- if !ok && match {
- t.Errorf("%s did not produce an event with a %v", method, key)
+}
+
+func checkName(t *testing.T, h *eventtest.CaptureHandler, method string, text string) {
+ if len(h.Got) != 1 {
+ t.Errorf("Got %d events, expected 1", len(h.Got))
+ return
}
- if m != text {
- t.Errorf("Expected event with %v %q from %s got %q", key, text, method, m)
+ if h.Got[0].Name != text {
+ t.Errorf("Expected event with Name %q from %s got %q", text, method, h.Got[0].Name)
}
}
diff --git a/event/event.go b/event/event.go
index 18a737d..369bcc5 100644
--- a/event/event.go
+++ b/event/event.go
@@ -12,9 +12,14 @@
// Event holds the information about an event that occurred.
// It combines the event metadata with the user supplied labels.
type Event struct {
+ TraceID uint64
Parent uint64 // id of the parent event for this event
Namespace string // namespace of event; if empty, set by exporter to import path
At time.Time // time at which the event is delivered to the exporter.
+ Kind Kind
+ Message string
+ Name string
+ Error error
Labels []Label
}
diff --git a/event/otel/trace.go b/event/otel/trace.go
index 8942841..14f8533 100644
--- a/event/otel/trace.go
+++ b/event/otel/trace.go
@@ -26,8 +26,7 @@
func (t *TraceHandler) Metric(ctx context.Context, ev *event.Event) {}
func (t *TraceHandler) Start(ctx context.Context, ev *event.Event) context.Context {
opts := labelsToSpanOptions(ev.Labels)
- name, _ := event.Name.Find(ev)
- octx, span := t.tracer.Start(ctx, name, opts...)
+ octx, span := t.tracer.Start(ctx, ev.Name, opts...)
return context.WithValue(octx, spanKey{}, span)
}