Skip to content

Commit 02476a7

Browse files
authored
[Go] move tracing under core (#247)
Move internal/tracing to core/tracing, so third-party plugins can use it.
1 parent c74f843 commit 02476a7

15 files changed

+45
-43
lines changed

go/core/action.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ import (
2323
"time"
2424

2525
"github.com/firebase/genkit/go/internal"
26-
"github.com/firebase/genkit/go/internal/tracing"
26+
"github.com/firebase/genkit/go/core/tracing"
2727
"github.com/invopop/jsonschema"
2828
)
2929

go/core/flow.go

Lines changed: 15 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,9 @@ import (
2424
"sync"
2525
"time"
2626

27+
"github.com/firebase/genkit/go/core/tracing"
2728
"github.com/firebase/genkit/go/gtime"
2829
"github.com/firebase/genkit/go/internal"
29-
"github.com/firebase/genkit/go/internal/tracing"
3030
"github.com/google/uuid"
3131
otrace "go.opentelemetry.io/otel/trace"
3232
)
@@ -251,7 +251,7 @@ func (f *Flow[I, O, S]) action() *Action[*flowInstruction[I], *flowState[I, O],
251251
"outputSchema": inferJSONSchema(o),
252252
}
253253
cback := func(ctx context.Context, inst *flowInstruction[I], cb func(context.Context, S) error) (*flowState[I, O], error) {
254-
tracing.SpanMetaKey.FromContext(ctx).SetAttr("flow:wrapperAction", "true")
254+
tracing.SetCustomMetadataAttr(ctx, "flow:wrapperAction", "true")
255255
return f.runInstruction(ctx, inst, streamingCallback[S](cb))
256256
}
257257
return NewStreamingAction(f.name, ActionTypeFlow, metadata, cback)
@@ -359,12 +359,11 @@ func (f *Flow[I, O, S]) execute(ctx context.Context, state *flowState[I, O], dis
359359
// TODO(jba): retrieve the JSON-marshaled SpanContext from state.traceContext.
360360
// TODO(jba): add a span link to the context.
361361
output, err := tracing.RunInNewSpan(ctx, fctx.tracingState(), f.name, "flow", true, state.Input, func(ctx context.Context, input I) (O, error) {
362-
spanMeta := tracing.SpanMetaKey.FromContext(ctx)
363-
spanMeta.SetAttr("flow:execution", strconv.Itoa(len(state.Executions)-1))
362+
tracing.SetCustomMetadataAttr(ctx, "flow:execution", strconv.Itoa(len(state.Executions)-1))
364363
// TODO(jba): put labels into span metadata.
365-
spanMeta.SetAttr("flow:name", f.name)
366-
spanMeta.SetAttr("flow:id", state.FlowID)
367-
spanMeta.SetAttr("flow:dispatchType", dispatchType)
364+
tracing.SetCustomMetadataAttr(ctx, "flow:name", f.name)
365+
tracing.SetCustomMetadataAttr(ctx, "flow:id", state.FlowID)
366+
tracing.SetCustomMetadataAttr(ctx, "flow:dispatchType", dispatchType)
368367
rootSpanContext := otrace.SpanContextFromContext(ctx)
369368
traceID := rootSpanContext.TraceID().String()
370369
exec.TraceIDs = append(exec.TraceIDs, traceID)
@@ -376,15 +375,15 @@ func (f *Flow[I, O, S]) execute(ctx context.Context, state *flowState[I, O], dis
376375
if err != nil {
377376
// TODO(jba): handle InterruptError
378377
internal.Logger(ctx).Error("flow failed",
379-
"path", spanMeta.Path,
378+
"path", tracing.SpanPath(ctx),
380379
"err", err.Error(),
381380
)
382381
writeFlowFailure(ctx, f.name, latency, err)
383-
spanMeta.SetAttr("flow:state", "error")
382+
tracing.SetCustomMetadataAttr(ctx, "flow:state", "error")
384383
} else {
385-
internal.Logger(ctx).Info("flow succeeded", "path", spanMeta.Path)
384+
internal.Logger(ctx).Info("flow succeeded", "path", tracing.SpanPath(ctx))
386385
writeFlowSuccess(ctx, f.name, latency)
387-
spanMeta.SetAttr("flow:state", "done")
386+
tracing.SetCustomMetadataAttr(ctx, "flow:state", "done")
388387

389388
}
390389
// TODO(jba): telemetry
@@ -485,10 +484,9 @@ func Run[T any](ctx context.Context, name string, f func() (T, error)) (T, error
485484
// as in the js.
486485
return tracing.RunInNewSpan(ctx, fc.tracingState(), name, "flowStep", false, 0, func(ctx context.Context, _ int) (T, error) {
487486
uName := fc.uniqueStepName(name)
488-
spanMeta := tracing.SpanMetaKey.FromContext(ctx)
489-
spanMeta.SetAttr("flow:stepType", "run")
490-
spanMeta.SetAttr("flow:stepName", name)
491-
spanMeta.SetAttr("flow:resolvedStepName", uName)
487+
tracing.SetCustomMetadataAttr(ctx, "flow:stepType", "run")
488+
tracing.SetCustomMetadataAttr(ctx, "flow:stepName", name)
489+
tracing.SetCustomMetadataAttr(ctx, "flow:resolvedStepName", uName)
492490
// Memoize the function call, using the cache in the flowState.
493491
// The locking here prevents corruption of the cache from concurrent access, but doesn't
494492
// prevent two goroutines racing to check the cache and call f. However, that shouldn't
@@ -503,7 +501,7 @@ func Run[T any](ctx context.Context, name string, f func() (T, error)) (T, error
503501
if err := json.Unmarshal(j, &t); err != nil {
504502
return internal.Zero[T](), err
505503
}
506-
spanMeta.SetAttr("flow:state", "cached")
504+
tracing.SetCustomMetadataAttr(ctx, "flow:state", "cached")
507505
return t, nil
508506
}
509507
t, err := f()
@@ -517,7 +515,7 @@ func Run[T any](ctx context.Context, name string, f func() (T, error)) (T, error
517515
fs.lock()
518516
fs.cache()[uName] = json.RawMessage(bytes)
519517
fs.unlock()
520-
spanMeta.SetAttr("flow:state", "run")
518+
tracing.SetCustomMetadataAttr(ctx, "flow:state", "run")
521519
return t, nil
522520
})
523521
}

go/core/registry.go

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,16 @@ package core
1616

1717
import (
1818
"context"
19+
"crypto/md5"
1920
"fmt"
2021
"log"
2122
"log/slog"
23+
"os"
24+
"path/filepath"
2225
"slices"
2326
"sync"
2427

25-
"github.com/firebase/genkit/go/internal/tracing"
28+
"github.com/firebase/genkit/go/core/tracing"
2629
sdktrace "go.opentelemetry.io/otel/sdk/trace"
2730
"golang.org/x/exp/maps"
2831
)
@@ -58,7 +61,7 @@ func newRegistry() (*registry, error) {
5861
actions: map[string]action{},
5962
traceStores: map[Environment]tracing.Store{},
6063
}
61-
tstore, err := tracing.NewDevStore()
64+
tstore, err := newDevStore()
6265
if err != nil {
6366
return nil, err
6467
}
@@ -68,6 +71,17 @@ func newRegistry() (*registry, error) {
6871
return r, nil
6972
}
7073

74+
func newDevStore() (tracing.Store, error) {
75+
programName := filepath.Base(os.Args[0])
76+
rootHash := fmt.Sprintf("%02x", md5.Sum([]byte(programName)))
77+
dir := filepath.Join(os.TempDir(), ".genkit", rootHash, "traces")
78+
if err := os.MkdirAll(dir, 0o755); err != nil {
79+
return nil, err
80+
}
81+
// Don't remove the temp directory, for post-mortem debugging.
82+
return tracing.NewFileStore(dir)
83+
}
84+
7185
// An Environment is the execution context in which the program is running.
7286
type Environment string
7387

go/core/servers.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,7 @@ import (
3939
"time"
4040

4141
"github.com/firebase/genkit/go/internal"
42-
"github.com/firebase/genkit/go/internal/tracing"
42+
"github.com/firebase/genkit/go/core/tracing"
4343
"go.opentelemetry.io/otel/trace"
4444
)
4545

go/core/servers_test.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,7 +23,7 @@ import (
2323
"strings"
2424
"testing"
2525

26-
"github.com/firebase/genkit/go/internal/tracing"
26+
"github.com/firebase/genkit/go/core/tracing"
2727
"github.com/google/go-cmp/cmp"
2828
"github.com/google/go-cmp/cmp/cmpopts"
2929
"github.com/invopop/jsonschema"
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.
File renamed without changes.

0 commit comments

Comments
 (0)