Skip to content

Commit 90c9985

Browse files
authored
Merge branch 'main' into eliott.bouhana/newtelemetry
2 parents a62953e + f11947f commit 90c9985

File tree

7 files changed

+167
-102
lines changed

7 files changed

+167
-102
lines changed

.github/workflows/unit-integration-tests.yml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -53,17 +53,17 @@ jobs:
5353
with:
5454
golangci_lint_flags: "--timeout 10m" # We are hitting timeout when there is no cache
5555
go_version: ${{ inputs.go-version }}
56-
golangci_lint_version: v1.59.1
57-
fail_on_error: true
56+
golangci_lint_version: v1.63.4
57+
fail_level: error
5858
reporter: github-pr-review
5959

6060
- name: golangci-lint (internal/orchestrion/_integration)
6161
uses: reviewdog/action-golangci-lint@dd3fda91790ca90e75049e5c767509dc0ec7d99b # v2.7.0
6262
with:
6363
golangci_lint_flags: "--timeout 10m" # We are hitting timeout when there is no cache
6464
go_version: ${{ inputs.go-version }}
65-
golangci_lint_version: v1.59.1
66-
fail_on_error: true
65+
golangci_lint_version: v1.63.4
66+
fail_level: error
6767
reporter: github-pr-review
6868
workdir: internal/orchestrion/_integration
6969

.gitlab-ci.yml

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,7 @@ variables:
99
INDEX_FILE: index.txt
1010
KUBERNETES_SERVICE_ACCOUNT_OVERWRITE: dd-trace-go
1111
FF_USE_LEGACY_KUBERNETES_EXECUTION_STRATEGY: "true"
12-
BENCHMARK_TARGETS: "BenchmarkStartRequestSpan|BenchmarkHttpServeTrace|BenchmarkTracerAddSpans|BenchmarkStartSpan|BenchmarkSingleSpanRetention|BenchmarkOTelApiWithCustomTags|BenchmarkInjectW3C|BenchmarkExtractW3C|BenchmarkPartialFlushing|BenchmarkGraphQL|BenchmarkSampleWAFContext|BenchmarkCaptureStackTrace|BenchmarkSetTagString|BenchmarkSetTagStringPtr|BenchmarkSetTagMetric|BenchmarkSetTagStringer|BenchmarkLogs|BenchmarkWorstCaseScenarioFloodLogging|BenchmarkMetrics|BenchmarkWorstCaseScenarioFloodMetrics"
13-
12+
BENCHMARK_TARGETS: "BenchmarkStartRequestSpan|BenchmarkHttpServeTrace|BenchmarkTracerAddSpans|BenchmarkStartSpan|BenchmarkSingleSpanRetention|BenchmarkOTelApiWithCustomTags|BenchmarkInjectW3C|BenchmarkExtractW3C|BenchmarkPartialFlushing|BenchmarkGraphQL|BenchmarkSampleWAFContext|BenchmarkCaptureStackTrace|BenchmarkSetTagString|BenchmarkSetTagStringPtr|BenchmarkSetTagMetric|BenchmarkSetTagStringer|BenchmarkSerializeSpanLinksInMeta|BenchmarkLogs|BenchmarkWorstCaseScenarioFloodLogging|BenchmarkMetrics|BenchmarkWorstCaseScenarioFloodMetrics"
1413
include:
1514
- ".gitlab/benchmarks.yml"
1615
- ".gitlab/macrobenchmarks.yml"

ddtrace/ddtrace.go

Lines changed: 0 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -103,25 +103,6 @@ type SpanContext interface {
103103
ForeachBaggageItem(handler func(k, v string) bool)
104104
}
105105

106-
// SpanLink represents a reference to a span that exists outside of the trace.
107-
//
108-
//go:generate msgp -unexported -marshal=false -o=span_link_msgp.go -tests=false
109-
110-
type SpanLink struct {
111-
// TraceID represents the low 64 bits of the linked span's trace id. This field is required.
112-
TraceID uint64 `msg:"trace_id" json:"trace_id"`
113-
// TraceIDHigh represents the high 64 bits of the linked span's trace id. This field is only set if the linked span's trace id is 128 bits.
114-
TraceIDHigh uint64 `msg:"trace_id_high,omitempty" json:"trace_id_high"`
115-
// SpanID represents the linked span's span id.
116-
SpanID uint64 `msg:"span_id" json:"span_id"`
117-
// Attributes is a mapping of keys to string values. These values are used to add additional context to the span link.
118-
Attributes map[string]string `msg:"attributes,omitempty" json:"attributes"`
119-
// Tracestate is the tracestate of the linked span. This field is optional.
120-
Tracestate string `msg:"tracestate,omitempty" json:"tracestate"`
121-
// Flags represents the W3C trace flags of the linked span. This field is optional.
122-
Flags uint32 `msg:"flags,omitempty" json:"flags"`
123-
}
124-
125106
// StartSpanOption is a configuration option that can be used with a Tracer's StartSpan method.
126107
type StartSpanOption func(cfg *StartSpanConfig)
127108

ddtrace/span_link.go

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
// Unless explicitly stated otherwise all files in this repository are licensed
2+
// under the Apache License Version 2.0.
3+
// This product includes software developed at Datadog (https://www.datadoghq.com/).
4+
// Copyright 2016 Datadog, Inc.
5+
6+
package ddtrace
7+
8+
// SpanLink represents a reference to a span that exists outside of the trace.
9+
//
10+
//go:generate msgp -unexported -marshal=false -o=span_link_msgp.go -tests=false
11+
12+
type SpanLink struct {
13+
// TraceID represents the low 64 bits of the linked span's trace id. This field is required.
14+
TraceID uint64 `msg:"trace_id" json:"trace_id"`
15+
// TraceIDHigh represents the high 64 bits of the linked span's trace id. This field is only set if the linked span's trace id is 128 bits.
16+
TraceIDHigh uint64 `msg:"trace_id_high" json:"trace_id_high"`
17+
// SpanID represents the linked span's span id.
18+
SpanID uint64 `msg:"span_id" json:"span_id"`
19+
// Attributes is a mapping of keys to string values. These values are used to add additional context to the span link.
20+
Attributes map[string]string `msg:"attributes" json:"attributes"`
21+
// Tracestate is the tracestate of the linked span. This field is optional.
22+
Tracestate string `msg:"tracestate" json:"tracestate"`
23+
// Flags represents the W3C trace flags of the linked span. This field is optional.
24+
Flags uint32 `msg:"flags" json:"flags"`
25+
}

ddtrace/span_link_msgp.go

Lines changed: 43 additions & 77 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

ddtrace/tracer/span.go

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ package tracer
1010
import (
1111
"context"
1212
"encoding/base64"
13+
"encoding/json"
1314
"fmt"
1415
"os"
1516
"reflect"
@@ -91,6 +92,13 @@ type span struct {
9192
taskEnd func() // ends execution tracer (runtime/trace) task, if started
9293
}
9394

95+
type SpanWithLinks interface {
96+
ddtrace.Span
97+
98+
// AddSpanLink appends the given link to span's span links.
99+
AddSpanLink(link ddtrace.SpanLink)
100+
}
101+
94102
// Context yields the SpanContext for this Span. Note that the return
95103
// value of Context() is still valid after a call to Finish(). This is
96104
// called the span context and it is different from Go's context.
@@ -464,6 +472,27 @@ func (s *span) setMetric(key string, v float64) {
464472
}
465473
}
466474

475+
// AddSpanLink appends the given link to the span's span links.
476+
func (s *span) AddSpanLink(link ddtrace.SpanLink) {
477+
s.SpanLinks = append(s.SpanLinks, link)
478+
}
479+
480+
// serializeSpanLinksInMeta saves span links as a JSON string under `Span[meta][_dd.span_links]`.
481+
func (s *span) serializeSpanLinksInMeta() {
482+
if len(s.SpanLinks) == 0 {
483+
return
484+
}
485+
spanLinkBytes, err := json.Marshal(s.SpanLinks)
486+
if err != nil {
487+
log.Debug("Unable to marshal span links. Not adding span links to span meta.")
488+
return
489+
}
490+
if s.Meta == nil {
491+
s.Meta = make(map[string]string)
492+
}
493+
s.Meta["_dd.span_links"] = string(spanLinkBytes)
494+
}
495+
467496
// Finish closes this Span (but not its children) providing the duration
468497
// of its part of the tracing session.
469498
func (s *span) Finish(opts ...ddtrace.FinishOption) {
@@ -514,6 +543,8 @@ func (s *span) Finish(opts ...ddtrace.FinishOption) {
514543
}
515544
}
516545

546+
s.serializeSpanLinksInMeta()
547+
517548
s.finish(t)
518549
orchestrion.GLSPopValue(sharedinternal.ActiveSpanKey)
519550
}

ddtrace/tracer/span_test.go

Lines changed: 63 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,10 @@
66
package tracer
77

88
import (
9+
"encoding/json"
910
"errors"
1011
"fmt"
12+
"gopkg.in/DataDog/dd-trace-go.v1/ddtrace"
1113
"runtime"
1214
"strings"
1315
"sync"
@@ -1051,6 +1053,27 @@ func BenchmarkSetTagField(b *testing.B) {
10511053
}
10521054
}
10531055

1056+
func BenchmarkSerializeSpanLinksInMeta(b *testing.B) {
1057+
span := newBasicSpan("bench.span")
1058+
1059+
span.AddSpanLink(ddtrace.SpanLink{SpanID: 123, TraceID: 456})
1060+
span.AddSpanLink(ddtrace.SpanLink{SpanID: 789, TraceID: 101})
1061+
1062+
// Sample span pointer
1063+
attributes := map[string]string{
1064+
"link.kind": "span-pointer",
1065+
"ptr.dir": "d",
1066+
"ptr.hash": "eb29cb7d923f904f02bd8b3d85e228ed",
1067+
"ptr.kind": "aws.s3.object",
1068+
}
1069+
span.AddSpanLink(ddtrace.SpanLink{TraceID: 0, SpanID: 0, Attributes: attributes})
1070+
1071+
b.ResetTimer()
1072+
for i := 0; i < b.N; i++ {
1073+
span.serializeSpanLinksInMeta()
1074+
}
1075+
}
1076+
10541077
type boomError struct{}
10551078

10561079
func (e *boomError) Error() string { return "boom" }
@@ -1092,3 +1115,43 @@ func testConcurrentSpanSetTag(t *testing.T) {
10921115
}
10931116
wg.Wait()
10941117
}
1118+
1119+
func TestSpanLinksInMeta(t *testing.T) {
1120+
t.Run("no_links", func(t *testing.T) {
1121+
tracer := newTracer()
1122+
defer tracer.Stop()
1123+
1124+
sp := tracer.StartSpan("test-no-links")
1125+
sp.Finish()
1126+
1127+
internalSpan := sp.(*span)
1128+
_, ok := internalSpan.Meta["_dd.span_links"]
1129+
assert.False(t, ok, "Expected no _dd.span_links in Meta.")
1130+
})
1131+
1132+
t.Run("with_links", func(t *testing.T) {
1133+
tracer := newTracer()
1134+
defer tracer.Stop()
1135+
1136+
sp, ok := tracer.StartSpan("test-with-links").(SpanWithLinks)
1137+
require.True(t, ok, "Span does not implement SpanWithLinks interface")
1138+
1139+
sp.AddSpanLink(ddtrace.SpanLink{SpanID: 123, TraceID: 456})
1140+
sp.AddSpanLink(ddtrace.SpanLink{SpanID: 789, TraceID: 012})
1141+
sp.Finish()
1142+
1143+
internalSpan := sp.(*span)
1144+
raw, ok := internalSpan.Meta["_dd.span_links"]
1145+
require.True(t, ok, "Expected _dd.span_links in Meta after adding links.")
1146+
1147+
var links []ddtrace.SpanLink
1148+
err := json.Unmarshal([]byte(raw), &links)
1149+
require.NoError(t, err, "Failed to unmarshal links JSON")
1150+
require.Len(t, links, 2, "Expected 2 links in _dd.span_links JSON")
1151+
1152+
assert.Equal(t, uint64(123), links[0].SpanID)
1153+
assert.Equal(t, uint64(456), links[0].TraceID)
1154+
assert.Equal(t, uint64(789), links[1].SpanID)
1155+
assert.Equal(t, uint64(012), links[1].TraceID)
1156+
})
1157+
}

0 commit comments

Comments
 (0)